Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(720)

Unified Diff: src/core/SkImageFilter.cpp

Issue 1848953002: Image filters: optimize crop rect application (Closed) Base URL: https://skia.googlesource.com/skia.git@master
Patch Set: Fixes per review remarks Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « include/effects/SkPaintImageFilter.h ('k') | src/effects/SkColorFilterImageFilter.cpp » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/core/SkImageFilter.cpp
diff --git a/src/core/SkImageFilter.cpp b/src/core/SkImageFilter.cpp
index 3b4ad314563217ded15baa1756d36f63ce7aa960..11a2f74c70910e06901e6c8f6b873b9a91dbaf8f 100644
--- a/src/core/SkImageFilter.cpp
+++ b/src/core/SkImageFilter.cpp
@@ -69,25 +69,38 @@ void SkImageFilter::CropRect::toString(SkString* str) const {
void SkImageFilter::CropRect::applyTo(const SkIRect& imageBounds,
const SkMatrix& ctm,
+ bool embiggen,
SkIRect* cropped) const {
*cropped = imageBounds;
if (fFlags) {
SkRect devCropR;
ctm.mapRect(&devCropR, fRect);
- const SkIRect devICropR = devCropR.roundOut();
+ SkIRect devICropR = devCropR.roundOut();
- // Compute the left/top first, in case we have to read them to compute right/bottom
+ // Compute the left/top first, in case we need to modify the right/bottom for a missing edge
if (fFlags & kHasLeft_CropEdge) {
- cropped->fLeft = devICropR.fLeft;
+ if (embiggen || devICropR.fLeft > cropped->fLeft) {
+ cropped->fLeft = devICropR.fLeft;
+ }
+ } else {
+ devICropR.fRight = cropped->fLeft + devICropR.width();
}
if (fFlags & kHasTop_CropEdge) {
- cropped->fTop = devICropR.fTop;
+ if (embiggen || devICropR.fTop > cropped->fTop) {
+ cropped->fTop = devICropR.fTop;
+ }
+ } else {
+ devICropR.fBottom = cropped->fTop + devICropR.height();
}
if (fFlags & kHasWidth_CropEdge) {
- cropped->fRight = cropped->fLeft + devICropR.width();
+ if (embiggen || devICropR.fRight < cropped->fRight) {
+ cropped->fRight = devICropR.fRight;
+ }
}
if (fFlags & kHasHeight_CropEdge) {
- cropped->fBottom = cropped->fTop + devICropR.height();
+ if (embiggen || devICropR.fBottom < cropped->fBottom) {
+ cropped->fBottom = devICropR.fBottom;
+ }
}
}
}
@@ -306,7 +319,7 @@ SkIRect SkImageFilter::filterBounds(const SkIRect& src, const SkMatrix& ctm,
SkIRect bounds = this->onFilterBounds(src, ctm, direction);
bounds = this->onFilterNodeBounds(bounds, ctm, direction);
SkIRect dst;
- this->getCropRect().applyTo(bounds, ctm, &dst);
+ this->getCropRect().applyTo(bounds, ctm, this->affectsTransparentBlack(), &dst);
return dst;
}
}
@@ -328,6 +341,9 @@ SkRect SkImageFilter::computeFastBounds(const SkRect& src) const {
}
bool SkImageFilter::canComputeFastBounds() const {
+ if (this->affectsTransparentBlack()) {
+ return false;
+ }
for (int i = 0; i < fInputCount; i++) {
SkImageFilter* input = this->getInput(i);
if (input && !input->canComputeFastBounds()) {
@@ -437,7 +453,7 @@ bool SkImageFilter::asAColorFilter(SkColorFilter** filterPtr) const {
bool SkImageFilter::applyCropRect(const Context& ctx, const SkIRect& srcBounds,
SkIRect* dstBounds) const {
SkIRect temp = this->onFilterNodeBounds(srcBounds, ctx.ctm(), kForward_MapDirection);
- fCropRect.applyTo(temp, ctx.ctm(), dstBounds);
+ fCropRect.applyTo(temp, ctx.ctm(), this->affectsTransparentBlack(), dstBounds);
// Intersect against the clip bounds, in case the crop rect has
// grown the bounds beyond the original clip. This can happen for
// example in tiling, where the clip is much smaller than the filtered
@@ -453,7 +469,7 @@ bool SkImageFilter::applyCropRectDeprecated(const Context& ctx, Proxy* proxy, co
src.getBounds(&srcBounds);
srcBounds.offset(*srcOffset);
SkIRect dstBounds = this->onFilterNodeBounds(srcBounds, ctx.ctm(), kForward_MapDirection);
- fCropRect.applyTo(dstBounds, ctx.ctm(), bounds);
+ fCropRect.applyTo(dstBounds, ctx.ctm(), this->affectsTransparentBlack(), bounds);
if (!bounds->intersect(ctx.clipBounds())) {
return false;
}
@@ -504,7 +520,7 @@ sk_sp<SkSpecialImage> SkImageFilter::applyCropRect(const Context& ctx,
srcBounds = SkIRect::MakeXYWH(srcOffset->fX, srcOffset->fY, src->width(), src->height());
SkIRect dstBounds = this->onFilterNodeBounds(srcBounds, ctx.ctm(), kForward_MapDirection);
- fCropRect.applyTo(dstBounds, ctx.ctm(), bounds);
+ fCropRect.applyTo(dstBounds, ctx.ctm(), this->affectsTransparentBlack(), bounds);
if (!bounds->intersect(ctx.clipBounds())) {
return nullptr;
}
« no previous file with comments | « include/effects/SkPaintImageFilter.h ('k') | src/effects/SkColorFilterImageFilter.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698