Flutter Engine
The Flutter Engine
Public Types | Static Public Member Functions | List of all members
skgpu::TiledTextureUtils Class Reference

#include <TiledTextureUtils.h>

Public Types

enum class  ImageDrawMode { kOptimized , kDecal , kSkip }
 

Static Public Member Functions

static bool ShouldTileImage (SkIRect conservativeClipBounds, const SkISize &imageSize, const SkMatrix &ctm, const SkMatrix &srcToDst, const SkRect *src, int maxTileSize, size_t cacheSize, int *tileSize, SkIRect *clippedSubset)
 
static ImageDrawMode OptimizeSampleArea (const SkISize &imageSize, const SkRect &origSrcRect, const SkRect &origDstRect, const SkPoint dstClip[4], SkRect *outSrcRect, SkRect *outDstRect, SkMatrix *outSrcToDst)
 
static bool CanDisableMipmap (const SkMatrix &viewM, const SkMatrix &localM)
 
static void ClampedOutsetWithOffset (SkIRect *iRect, int outset, SkPoint *offset, const SkIRect &clamp)
 
static std::tuple< bool, size_t > DrawAsTiledImageRect (SkCanvas *, const SkImage *, const SkRect &srcRect, const SkRect &dstRect, SkCanvas::QuadAAFlags, const SkSamplingOptions &, const SkPaint *, SkCanvas::SrcRectConstraint, size_t cacheSize, size_t maxTextureSize)
 

Detailed Description

Definition at line 28 of file TiledTextureUtils.h.

Member Enumeration Documentation

◆ ImageDrawMode

Enumerator
kOptimized 
kDecal 
kSkip 

Definition at line 40 of file TiledTextureUtils.h.

40 {
41 // Src and dst have been restricted to the image content. May need to clamp, no need to
42 // decal.
43 kOptimized,
44 // Src and dst are their original sizes, requires use of a decal instead of plain clamping.
45 // This is used when a dst clip is provided and extends outside of the optimized dst rect.
46 kDecal,
47 // Src or dst are empty, or do not intersect the image content so don't draw anything.
48 kSkip
49 };

Member Function Documentation

◆ CanDisableMipmap()

bool skgpu::TiledTextureUtils::CanDisableMipmap ( const SkMatrix viewM,
const SkMatrix localM 
)
static

Definition at line 309 of file TiledTextureUtils.cpp.

309 {
311 matrix.setConcat(viewM, localM);
312 // We bias mipmap lookups by -0.5. That means our final LOD is >= 0 until
313 // the computed LOD is >= 0.5. At what scale factor does a texture get an LOD of
314 // 0.5?
315 //
316 // Want: 0 = log2(1/s) - 0.5
317 // 0.5 = log2(1/s)
318 // 2^0.5 = 1/s
319 // 1/2^0.5 = s
320 // 2^0.5/2 = s
321 return matrix.getMinScale() >= SK_ScalarRoot2Over2;
322}
#define SK_ScalarRoot2Over2
Definition: SkScalar.h:23
unsigned useCenter Optional< SkMatrix > matrix
Definition: SkRecords.h:258

◆ ClampedOutsetWithOffset()

void skgpu::TiledTextureUtils::ClampedOutsetWithOffset ( SkIRect iRect,
int  outset,
SkPoint offset,
const SkIRect clamp 
)
static

Definition at line 328 of file TiledTextureUtils.cpp.

329 {
330 iRect->outset(outset, outset);
331
332 int leftClampDelta = clamp.fLeft - iRect->fLeft;
333 if (leftClampDelta > 0) {
334 offset->fX -= outset - leftClampDelta;
335 iRect->fLeft = clamp.fLeft;
336 } else {
337 offset->fX -= outset;
338 }
339
340 int topClampDelta = clamp.fTop - iRect->fTop;
341 if (topClampDelta > 0) {
342 offset->fY -= outset - topClampDelta;
343 iRect->fTop = clamp.fTop;
344 } else {
345 offset->fY -= outset;
346 }
347
348 if (iRect->fRight > clamp.fRight) {
349 iRect->fRight = clamp.fRight;
350 }
351 if (iRect->fBottom > clamp.fBottom) {
352 iRect->fBottom = clamp.fBottom;
353 }
354}
static const int outset
Definition: BlurTest.cpp:58
static unsigned clamp(SkFixed fx, int max)
SeparatedVector2 offset
int32_t fBottom
larger y-axis bounds
Definition: SkRect.h:36
int32_t fTop
smaller y-axis bounds
Definition: SkRect.h:34
int32_t fLeft
smaller x-axis bounds
Definition: SkRect.h:33
void outset(int32_t dx, int32_t dy)
Definition: SkRect.h:428
int32_t fRight
larger x-axis bounds
Definition: SkRect.h:35

◆ DrawAsTiledImageRect()

std::tuple< bool, size_t > skgpu::TiledTextureUtils::DrawAsTiledImageRect ( SkCanvas canvas,
const SkImage image,
const SkRect srcRect,
const SkRect dstRect,
SkCanvas::QuadAAFlags  aaFlags,
const SkSamplingOptions origSampling,
const SkPaint paint,
SkCanvas::SrcRectConstraint  constraint,
size_t  cacheSize,
size_t  maxTextureSize 
)
static

Definition at line 356 of file TiledTextureUtils.cpp.

366 {
367 if (canvas->isClipEmpty()) {
368 return {true, 0};
369 }
370
371 if (!image->isTextureBacked()) {
372 SkRect src;
373 SkRect dst;
374 SkMatrix srcToDst;
376 srcRect, dstRect, /* dstClip= */ nullptr,
377 &src, &dst, &srcToDst);
378 if (mode == ImageDrawMode::kSkip) {
379 return {true, 0};
380 }
381
382 SkASSERT(mode != ImageDrawMode::kDecal); // only happens if there is a 'dstClip'
383
384 if (src.contains(image->bounds())) {
386 }
387
389 const SkMatrix& localToDevice = device->localToDevice();
390
391 SkSamplingOptions sampling = origSampling;
392 if (sampling.mipmap != SkMipmapMode::kNone && CanDisableMipmap(localToDevice, srcToDst)) {
394 }
395
396 SkIRect clipRect = device->devClipBounds();
397
398 int tileFilterPad;
399 if (sampling.useCubic) {
400 tileFilterPad = kBicubicFilterTexelPad;
402 // Aniso will fallback to linear filtering in the tiling case.
403 tileFilterPad = 1;
404 } else {
405 tileFilterPad = 0;
406 }
407
408 int maxTileSize = maxTextureSize - 2 * tileFilterPad;
409 int tileSize;
410 SkIRect clippedSubset;
412 image->dimensions(),
413 localToDevice,
414 srcToDst,
415 &src,
416 maxTileSize,
417 cacheSize,
418 &tileSize,
419 &clippedSubset)) {
420 // Extract pixels on the CPU, since we have to split into separate textures before
421 // sending to the GPU if tiling.
422 if (SkBitmap bm; as_IB(image)->getROPixels(nullptr, &bm)) {
423 size_t tiles = draw_tiled_bitmap(canvas,
424 bm,
425 tileSize,
426 srcToDst,
427 src,
428 clippedSubset,
429 paint,
430 aaFlags,
431 constraint,
432 sampling);
433 return {true, tiles};
434 }
435 }
436 }
437
438 return {false, 0};
439}
#define SkASSERT(cond)
Definition: SkAssert.h:116
static SkImage_Base * as_IB(SkImage *image)
Definition: SkImage_Base.h:201
static constexpr int kBicubicFilterTexelPad
static SkDevice * TopDevice(const SkCanvas *canvas)
Definition: SkCanvasPriv.h:65
virtual bool isClipEmpty() const
Definition: SkCanvas.cpp:1549
@ kFast_SrcRectConstraint
sample outside bounds; faster
Definition: SkCanvas.h:1543
virtual bool getROPixels(GrDirectContext *, SkBitmap *, CachingHint=kAllow_CachingHint) const =0
SkISize dimensions() const
Definition: SkImage.h:297
int width() const
Definition: SkImage.h:285
virtual bool isTextureBacked() const =0
int height() const
Definition: SkImage.h:291
SkIRect bounds() const
Definition: SkImage.h:303
static ImageDrawMode OptimizeSampleArea(const SkISize &imageSize, const SkRect &origSrcRect, const SkRect &origDstRect, const SkPoint dstClip[4], SkRect *outSrcRect, SkRect *outDstRect, SkMatrix *outSrcToDst)
static bool ShouldTileImage(SkIRect conservativeClipBounds, const SkISize &imageSize, const SkMatrix &ctm, const SkMatrix &srcToDst, const SkRect *src, int maxTileSize, size_t cacheSize, int *tileSize, SkIRect *clippedSubset)
static bool CanDisableMipmap(const SkMatrix &viewM, const SkMatrix &localM)
const Paint & paint
Definition: color_source.cc:38
VkDevice device
Definition: main.cc:53
clipRect(r.rect, r.opAA.op(), r.opAA.aa())) template<> void Draw
sk_sp< const SkImage > image
Definition: SkRecords.h:269
SkSamplingOptions sampling
Definition: SkRecords.h:337
it will be possible to load the file into Perfetto s trace viewer disable asset Prevents usage of any non test fonts unless they were explicitly Loaded via prefetched default font Indicates whether the embedding started a prefetch of the default font manager before creating the engine run In non interactive mode
Definition: switches.h:228
dst
Definition: cp.py:12
SkSamplingOptions(SkFilterMode::kLinear))
constexpr struct @263 tiles[]
Definition: SkRect.h:32
static constexpr SkISize Make(int32_t w, int32_t h)
Definition: SkSize.h:20
const SkFilterMode filter
const SkMipmapMode mipmap

◆ OptimizeSampleArea()

TiledTextureUtils::ImageDrawMode skgpu::TiledTextureUtils::OptimizeSampleArea ( const SkISize imageSize,
const SkRect origSrcRect,
const SkRect origDstRect,
const SkPoint  dstClip[4],
SkRect outSrcRect,
SkRect outDstRect,
SkMatrix outSrcToDst 
)
static

Optimize the src rect sampling area within an image (sized 'width' x 'height') such that 'outSrcRect' will be completely contained in the image's bounds. The corresponding rect to draw will be output to 'outDstRect'. The mapping between src and dst will be cached in 'outSrcToDst'. Outputs are not always updated when kSkip is returned.

'dstClip' should be null when there is no additional clipping.

Definition at line 263 of file TiledTextureUtils.cpp.

269 {
270 if (origSrcRect.isEmpty() || origDstRect.isEmpty()) {
272 }
273
274 *outSrcToDst = SkMatrix::RectToRect(origSrcRect, origDstRect);
275
276 SkRect src = origSrcRect;
277 SkRect dst = origDstRect;
278
279 const SkRect srcBounds = SkRect::Make(imageSize);
280
281 if (!srcBounds.contains(src)) {
282 if (!src.intersect(srcBounds)) {
284 }
285 outSrcToDst->mapRect(&dst, src);
286
287 // Both src and dst have gotten smaller. If dstClip is provided, confirm it is still
288 // contained in dst, otherwise cannot optimize the sample area and must use a decal instead
289 if (dstClip) {
290 for (int i = 0; i < 4; ++i) {
291 if (!dst.contains(dstClip[i].fX, dstClip[i].fY)) {
292 // Must resort to using a decal mode restricted to the clipped 'src', and
293 // use the original dst rect (filling in src bounds as needed)
294 *outSrcRect = src;
295 *outDstRect = origDstRect;
297 }
298 }
299 }
300 }
301
302 // The original src and dst were fully contained in the image, or there was no dst clip to
303 // worry about, or the clip was still contained in the restricted dst rect.
304 *outSrcRect = src;
305 *outDstRect = dst;
307}
static SkMatrix RectToRect(const SkRect &src, const SkRect &dst, ScaleToFit mode=kFill_ScaleToFit)
Definition: SkMatrix.h:157
bool mapRect(SkRect *dst, const SkRect &src, SkApplyPerspectiveClip pc=SkApplyPerspectiveClip::kYes) const
Definition: SkMatrix.cpp:1141
static SkRect Make(const SkISize &size)
Definition: SkRect.h:669
bool contains(SkScalar x, SkScalar y) const
Definition: extension.cpp:19
bool isEmpty() const
Definition: SkRect.h:693

◆ ShouldTileImage()

bool skgpu::TiledTextureUtils::ShouldTileImage ( SkIRect  conservativeClipBounds,
const SkISize imageSize,
const SkMatrix ctm,
const SkMatrix srcToDst,
const SkRect src,
int  maxTileSize,
size_t  cacheSize,
int tileSize,
SkIRect clippedSubset 
)
static

Definition at line 205 of file TiledTextureUtils.cpp.

213 {
214 // if it's larger than the max tile size, then we have no choice but tiling.
215 if (imageSize.width() > maxTileSize || imageSize.height() > maxTileSize) {
216 *clippedSubset = determine_clipped_src_rect(conservativeClipBounds, ctm,
217 srcToDst, imageSize, src);
218 *tileSize = determine_tile_size(*clippedSubset, maxTileSize);
219 return true;
220 }
221
222 // If the image would only produce 4 tiles of the smaller size, don't bother tiling it.
223 const size_t area = imageSize.width() * imageSize.height();
224 if (area < 4 * kBmpSmallTileSize * kBmpSmallTileSize) {
225 return false;
226 }
227
228 // At this point we know we could do the draw by uploading the entire bitmap as a texture.
229 // However, if the texture would be large compared to the cache size and we don't require most
230 // of it for this draw then tile to reduce the amount of upload and cache spill.
231 if (!cacheSize) {
232 // We don't have access to the cacheSize so we will just upload the entire image
233 // to be on the safe side and not tile.
234 return false;
235 }
236
237 // An assumption here is that sw bitmap size is a good proxy for its size as a texture
238 size_t bmpSize = area * sizeof(SkPMColor); // assume 32bit pixels
239 if (bmpSize < cacheSize / 2) {
240 return false;
241 }
242
243 // Figure out how much of the src we will need based on the src rect and clipping. Reject if
244 // tiling memory savings would be < 50%.
245 *clippedSubset = determine_clipped_src_rect(conservativeClipBounds, ctm,
246 srcToDst, imageSize, src);
247 *tileSize = kBmpSmallTileSize; // already know whole bitmap fits in one max sized tile.
248 size_t usedTileBytes = get_tile_count(*clippedSubset, kBmpSmallTileSize) *
249 kBmpSmallTileSize * kBmpSmallTileSize *
250 sizeof(SkPMColor); // assume 32bit pixels;
251
252 return usedTileBytes * 2 < bmpSize;
253}
uint32_t SkPMColor
Definition: SkColor.h:205
constexpr int32_t width() const
Definition: SkSize.h:36
constexpr int32_t height() const
Definition: SkSize.h:37

The documentation for this class was generated from the following files: