Reland "Calculate draw bounds in drawEdgeAAImageSet"
This reverts commit a5fa56e910b23da4252eca526d1b805d4da91f5a.
Reason for revert: Fixes bound calculation to transform fDstRect by each entry's pre-view matrix
if needed.
Original change's description:
> Revert "Calculate draw bounds in drawEdgeAAImageSet"
>
> This reverts commit 977b50a7e0cb302208cc71dc67e04d29bf3609c4.
>
> Reason for revert: Likely broke skia_renderer bots, https://test-results.appspot.com/data/layout_results/linux-rel/177320/vulkan_swiftshader_blink_web_tests%20%28with%20patch%29/layout-test-results/results.html
>
> Original change's description:
> > Calculate draw bounds in drawEdgeAAImageSet
> >
> > This will allow SkiaRenderer to provide image filters on the SkPaint
> > instead of using an explicit saveLayer, where they must calculate the
> > draw bounds. Once SkiaRenderer provides filters that way, they will
> > automatically take advantage of any implicit layer optimizations we can
> > add down the road.
> >
> > Bug: skia:9283
> > Change-Id: I87adef336a08210d4d015e36c907e893a973947d
> > Reviewed-on: https://skia-review.googlesource.com/c/skia/+/237477
> > Reviewed-by: Brian Salomon <bsalomon@google.com>
> > Commit-Queue: Michael Ludwig <michaelludwig@google.com>
>
> TBR=bsalomon@google.com,robertphillips@google.com,michaelludwig@google.com
>
> Change-Id: I99d90f7beae89b509c35649dcfcdf392a47b3415
> No-Presubmit: true
> No-Tree-Checks: true
> No-Try: true
> Bug: skia:9283
> Reviewed-on: https://skia-review.googlesource.com/c/skia/+/237596
> Reviewed-by: Michael Ludwig <michaelludwig@google.com>
> Commit-Queue: Michael Ludwig <michaelludwig@google.com>
TBR=bsalomon@google.com,robertphillips@google.com,michaelludwig@google.com
Change-Id: I1cba1e70d32abe7cd2ad3cfe478960a3670e79ca
Bug: skia:9283
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/237900
Reviewed-by: Brian Salomon <bsalomon@google.com>
Commit-Queue: Brian Salomon <bsalomon@google.com>
Auto-Submit: Michael Ludwig <michaelludwig@google.com>
diff --git a/src/core/SkCanvas.cpp b/src/core/SkCanvas.cpp
index 7c05e11..3951f85 100644
--- a/src/core/SkCanvas.cpp
+++ b/src/core/SkCanvas.cpp
@@ -2695,7 +2695,7 @@
return;
}
- this->predrawNotify();
+ this->predrawNotify(&r, nullptr, false);
SkDrawIter iter(this);
while(iter.next()) {
iter.fDevice->drawEdgeAAQuad(r, clip, edgeAA, color, mode);
@@ -2705,17 +2705,59 @@
void SkCanvas::onDrawEdgeAAImageSet(const ImageSetEntry imageSet[], int count,
const SkPoint dstClips[], const SkMatrix preViewMatrices[],
const SkPaint* paint, SrcRectConstraint constraint) {
+ if (count <= 0) {
+ // Nothing to draw
+ return;
+ }
+
SkPaint realPaint;
init_image_paint(&realPaint, paint);
- // Looper is used when there are image filters, which drawEdgeAAImageSet needs to support
- // for Chromium's RenderPassDrawQuads' filters.
- DRAW_BEGIN(realPaint, nullptr)
- while (iter.next()) {
- iter.fDevice->drawEdgeAAImageSet(
- imageSet, count, dstClips, preViewMatrices, draw.paint(), constraint);
+ // We could calculate the set's dstRect union to always check quickReject(), but we can't reject
+ // individual entries and Chromium's occlusion culling already makes it likely that at least one
+ // entry will be visible. So, we only calculate the draw bounds when it's trivial (count == 1),
+ // or we need it for the autolooper (since it greatly improves image filter perf).
+ bool needsAutoLooper = needs_autodrawlooper(this, realPaint);
+ bool setBoundsValid = count == 1 || needsAutoLooper;
+ SkRect setBounds = imageSet[0].fDstRect;
+ if (imageSet[0].fMatrixIndex >= 0) {
+ // Account for the per-entry transform that is applied prior to the CTM when drawing
+ preViewMatrices[imageSet[0].fMatrixIndex].mapRect(&setBounds);
}
- DRAW_END
+ if (needsAutoLooper) {
+ for (int i = 1; i < count; ++i) {
+ SkRect entryBounds = imageSet[i].fDstRect;
+ if (imageSet[i].fMatrixIndex >= 0) {
+ preViewMatrices[imageSet[i].fMatrixIndex].mapRect(&entryBounds);
+ }
+ setBounds.joinPossiblyEmptyRect(entryBounds);
+ }
+ }
+
+ // If we happen to have the draw bounds, though, might as well check quickReject().
+ if (setBoundsValid && realPaint.canComputeFastBounds()) {
+ SkRect tmp;
+ if (this->quickReject(realPaint.computeFastBounds(setBounds, &tmp))) {
+ return;
+ }
+ }
+
+ if (needsAutoLooper) {
+ SkASSERT(setBoundsValid);
+ DRAW_BEGIN(realPaint, &setBounds)
+ while (iter.next()) {
+ iter.fDevice->drawEdgeAAImageSet(
+ imageSet, count, dstClips, preViewMatrices, draw.paint(), constraint);
+ }
+ DRAW_END
+ } else {
+ this->predrawNotify();
+ SkDrawIter iter(this);
+ while(iter.next()) {
+ iter.fDevice->drawEdgeAAImageSet(
+ imageSet, count, dstClips, preViewMatrices, realPaint, constraint);
+ }
+ }
}
//////////////////////////////////////////////////////////////////////////////