diff --git a/include/core/SkCanvas.h b/include/core/SkCanvas.h index e03b4f3daf..8ab281814e 100644 --- a/include/core/SkCanvas.h +++ b/include/core/SkCanvas.h @@ -24,6 +24,7 @@ class SkData; class SkDraw; class SkDrawable; class SkDrawFilter; +struct SkDrawShadowRec; class SkImage; class SkImageFilter; class SkLights; @@ -1237,6 +1238,8 @@ public: */ void temporary_internal_getRgnClip(SkRegion* region); + void private_draw_shadow_rec(const SkPath&, const SkDrawShadowRec&); + protected: // default impl defers to getDevice()->newSurface(info) virtual sk_sp onNewSurface(const SkImageInfo& info, const SkSurfaceProps& props); @@ -1331,6 +1334,7 @@ protected: const SkPaint* paint); virtual void onDrawBitmapLattice(const SkBitmap& bitmap, const Lattice& lattice, const SkRect& dst, const SkPaint* paint); + virtual void onDrawShadowRec(const SkPath&, const SkDrawShadowRec&); enum ClipEdgeStyle { kHard_ClipEdgeStyle, diff --git a/include/utils/SkNWayCanvas.h b/include/utils/SkNWayCanvas.h index ba0745e420..7701d50e26 100644 --- a/include/utils/SkNWayCanvas.h +++ b/include/utils/SkNWayCanvas.h @@ -71,6 +71,7 @@ protected: void onDrawBitmapNine(const SkBitmap&, const SkIRect& center, const SkRect& dst, const SkPaint*) override; void onDrawVerticesObject(const SkVertices*, SkBlendMode, const SkPaint&) override; + void onDrawShadowRec(const SkPath&, const SkDrawShadowRec&) override; void onClipRect(const SkRect&, SkClipOp, ClipEdgeStyle) override; void onClipRRect(const SkRRect&, SkClipOp, ClipEdgeStyle) override; diff --git a/src/core/SkCanvas.cpp b/src/core/SkCanvas.cpp index 10e2181aff..afc1203e6b 100644 --- a/src/core/SkCanvas.cpp +++ b/src/core/SkCanvas.cpp @@ -1909,6 +1909,21 @@ void SkCanvas::legacy_drawBitmapRect(const SkBitmap& bitmap, const SkRect* src, } } +void SkCanvas::private_draw_shadow_rec(const SkPath& path, const SkDrawShadowRec& rec) { + this->onDrawShadowRec(path, rec); +} + +void SkCanvas::onDrawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) { + SkPaint paint; + const SkRect& pathBounds = path.getBounds(); + + LOOPER_BEGIN(paint, SkDrawFilter::kPath_Type, &pathBounds) + while (iter.next()) { + iter.fDevice->drawShadow(path, rec); + } + LOOPER_END +} + ////////////////////////////////////////////////////////////////////////////// // These are the virtual drawing methods ////////////////////////////////////////////////////////////////////////////// diff --git a/src/core/SkColorSpaceXformCanvas.cpp b/src/core/SkColorSpaceXformCanvas.cpp index 65297a1801..530552862d 100644 --- a/src/core/SkColorSpaceXformCanvas.cpp +++ b/src/core/SkColorSpaceXformCanvas.cpp @@ -8,6 +8,7 @@ #include "SkColorFilter.h" #include "SkColorSpaceXformCanvas.h" #include "SkColorSpaceXformer.h" +#include "SkDrawShadowRec.h" #include "SkGradientShader.h" #include "SkImageFilter.h" #include "SkImagePriv.h" @@ -217,7 +218,11 @@ public: fTarget->drawImageLattice(fXformer->apply(bitmap).get(), lattice, dst, MaybePaint(paint, fXformer.get())); } - + void onDrawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) override { + SkDrawShadowRec newRec(rec); + newRec.fColor = fXformer->apply(rec.fColor); + fTarget->private_draw_shadow_rec(path, newRec); + } void onDrawPicture(const SkPicture* pic, const SkMatrix* matrix, const SkPaint* paint) override { diff --git a/src/core/SkDevice.h b/src/core/SkDevice.h index 17ccfdd198..17ea6f71f7 100644 --- a/src/core/SkDevice.h +++ b/src/core/SkDevice.h @@ -15,6 +15,7 @@ class SkBitmap; class SkDrawFilter; +struct SkDrawShadowRec; class SkImageFilterCache; struct SkIRect; class SkMatrix; @@ -234,6 +235,8 @@ protected: const SkScalar pos[], int scalarsPerPos, const SkPoint& offset, const SkPaint& paint) = 0; virtual void drawVertices(const SkVertices*, SkBlendMode, const SkPaint&) = 0; + virtual void drawShadow(const SkPath&, const SkDrawShadowRec&); + // default implementation unrolls the blob runs. virtual void drawTextBlob(const SkTextBlob*, SkScalar x, SkScalar y, const SkPaint& paint, SkDrawFilter* drawFilter); diff --git a/src/core/SkDrawShadowRec.h b/src/core/SkDrawShadowRec.h new file mode 100644 index 0000000000..19199c0cad --- /dev/null +++ b/src/core/SkDrawShadowRec.h @@ -0,0 +1,23 @@ +/* + * Copyright 2017 Google Inc. + * + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#ifndef SkDrawShadowRec_DEFINED +#define SkDrawShadowRec_DEFINED + +#include "SkPath.h" + +struct SkDrawShadowRec { + SkPoint3 fZPlaneParams; + SkPoint3 fLightPos; + SkScalar fLightRadius; + float fAmbientAlpha; + float fSpotAlpha; + SkColor fColor; + uint32_t fFlags; +}; + +#endif diff --git a/src/core/SkLiteDL.cpp b/src/core/SkLiteDL.cpp index b3149a7d42..f1101b1be2 100644 --- a/src/core/SkLiteDL.cpp +++ b/src/core/SkLiteDL.cpp @@ -8,6 +8,7 @@ #include "SkCanvas.h" #include "SkData.h" #include "SkDrawFilter.h" +#include "SkDrawShadowRec.h" #include "SkImage.h" #include "SkImageFilter.h" #include "SkLiteDL.h" @@ -55,7 +56,7 @@ namespace { M(DrawImage) M(DrawImageNine) M(DrawImageRect) M(DrawImageLattice) \ M(DrawText) M(DrawPosText) M(DrawPosTextH) \ M(DrawTextOnPath) M(DrawTextRSXform) M(DrawTextBlob) \ - M(DrawPatch) M(DrawPoints) M(DrawVertices) M(DrawAtlas) + M(DrawPatch) M(DrawPoints) M(DrawVertices) M(DrawAtlas) M(DrawShadowRec) #define M(T) T, enum class Type : uint8_t { TYPES(M) }; @@ -477,6 +478,17 @@ namespace { maybe_unset(cull), &paint); } }; + struct DrawShadowRec final : Op { + static const auto kType = Type::DrawShadowRec; + DrawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) + : fPath(path), fRec(rec) + {} + SkPath fPath; + SkDrawShadowRec fRec; + void draw(SkCanvas* c, const SkMatrix&) const { + c->private_draw_shadow_rec(fPath, fRec); + } + }; } template @@ -662,6 +674,9 @@ void SkLiteDL::drawAtlas(const SkImage* atlas, const SkRSXform xforms[], const S texs, count, colors, colors ? count : 0); } +void SkLiteDL::drawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) { + this->push(0, path, rec); +} typedef void(*draw_fn)(const void*, SkCanvas*, const SkMatrix&); typedef void(*void_fn)(const void*); diff --git a/src/core/SkLiteDL.h b/src/core/SkLiteDL.h index c5df350957..31ef38e6bf 100644 --- a/src/core/SkLiteDL.h +++ b/src/core/SkLiteDL.h @@ -77,6 +77,7 @@ public: void drawVertices(const SkVertices*, SkBlendMode, const SkPaint&); void drawAtlas(const SkImage*, const SkRSXform[], const SkRect[], const SkColor[], int, SkBlendMode, const SkRect*, const SkPaint*); + void drawShadowRec(const SkPath&, const SkDrawShadowRec&); private: template diff --git a/src/core/SkLiteRecorder.cpp b/src/core/SkLiteRecorder.cpp index 5affb3d4ab..dbee48e1bd 100644 --- a/src/core/SkLiteRecorder.cpp +++ b/src/core/SkLiteRecorder.cpp @@ -194,3 +194,6 @@ void SkLiteRecorder::onDrawAtlas(const SkImage* atlas, const SkPaint* paint) { fDL->drawAtlas(atlas, xforms, texs, colors, count, bmode, cull, paint); } +void SkLiteRecorder::onDrawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) { + fDL->drawShadowRec(path, rec); +} diff --git a/src/core/SkLiteRecorder.h b/src/core/SkLiteRecorder.h index 3c156af721..4d49eb5336 100644 --- a/src/core/SkLiteRecorder.h +++ b/src/core/SkLiteRecorder.h @@ -77,6 +77,7 @@ public: void onDrawVerticesObject(const SkVertices*, SkBlendMode, const SkPaint&) override; void onDrawAtlas(const SkImage*, const SkRSXform[], const SkRect[], const SkColor[], int, SkBlendMode, const SkRect*, const SkPaint*) override; + void onDrawShadowRec(const SkPath&, const SkDrawShadowRec&) override; private: typedef SkNoDrawCanvas INHERITED; diff --git a/src/core/SkRecordDraw.cpp b/src/core/SkRecordDraw.cpp index e668cc874c..953e874854 100644 --- a/src/core/SkRecordDraw.cpp +++ b/src/core/SkRecordDraw.cpp @@ -125,6 +125,7 @@ DRAW(DrawTextRSXform, drawTextRSXform(r.text, r.byteLength, r.xforms, r.cull, r. DRAW(DrawAtlas, drawAtlas(r.atlas.get(), r.xforms, r.texs, r.colors, r.count, r.mode, r.cull, r.paint)); DRAW(DrawVertices, drawVertices(r.vertices, r.bmode, r.paint)); +DRAW(DrawShadowRec, private_draw_shadow_rec(r.path, r.rec)); DRAW(DrawAnnotation, drawAnnotation(r.rect, r.key.c_str(), r.value.get())); #undef DRAW @@ -455,6 +456,10 @@ private: } } + Bounds bounds(const DrawShadowRec& op) const { + return this->adjustAndMap(op.path.getBounds(), nullptr); + } + Bounds bounds(const DrawPicture& op) const { SkRect dst = op.picture->cullRect(); op.matrix.mapRect(&dst); diff --git a/src/core/SkRecorder.cpp b/src/core/SkRecorder.cpp index 64d613df96..1eeef532e6 100644 --- a/src/core/SkRecorder.cpp +++ b/src/core/SkRecorder.cpp @@ -338,6 +338,10 @@ void SkRecorder::onDrawAtlas(const SkImage* atlas, const SkRSXform xform[], cons this->copy(cull)); } +void SkRecorder::onDrawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) { + APPEND(DrawShadowRec, path, rec); +} + void SkRecorder::onDrawAnnotation(const SkRect& rect, const char key[], SkData* value) { APPEND(DrawAnnotation, rect, SkString(key), sk_ref_sp(value)); } diff --git a/src/core/SkRecorder.h b/src/core/SkRecorder.h index 5344934665..04e75edd26 100644 --- a/src/core/SkRecorder.h +++ b/src/core/SkRecorder.h @@ -121,6 +121,7 @@ public: void onDrawVerticesObject(const SkVertices*, SkBlendMode, const SkPaint&) override; void onDrawAtlas(const SkImage*, const SkRSXform[], const SkRect[], const SkColor[], int count, SkBlendMode, const SkRect* cull, const SkPaint*) override; + void onDrawShadowRec(const SkPath&, const SkDrawShadowRec&) override; void onClipRect(const SkRect& rect, SkClipOp, ClipEdgeStyle) override; void onClipRRect(const SkRRect& rrect, SkClipOp, ClipEdgeStyle) override; diff --git a/src/core/SkRecords.h b/src/core/SkRecords.h index 6af4aad3f5..a63ef1c6a5 100644 --- a/src/core/SkRecords.h +++ b/src/core/SkRecords.h @@ -11,6 +11,7 @@ #include "SkData.h" #include "SkCanvas.h" #include "SkDrawable.h" +#include "SkDrawShadowRec.h" #include "SkImage.h" #include "SkImageFilter.h" #include "SkMatrix.h" @@ -80,6 +81,7 @@ namespace SkRecords { M(DrawTextBlob) \ M(DrawAtlas) \ M(DrawVertices) \ + M(DrawShadowRec) \ M(DrawAnnotation) // Defines SkRecords::Type, an enum of all record types. @@ -345,6 +347,9 @@ RECORD(DrawVertices, kDraw_Tag|kHasPaint_Tag, SkPaint paint; sk_sp vertices; SkBlendMode bmode); +RECORD(DrawShadowRec, kDraw_Tag, + SkPath path; + SkDrawShadowRec rec); RECORD(DrawAnnotation, 0, // TODO: kDraw_Tag, skia:5548 SkRect rect; SkString key; diff --git a/src/gpu/SkGpuDevice.h b/src/gpu/SkGpuDevice.h index 340f39a072..0b60a96516 100644 --- a/src/gpu/SkGpuDevice.h +++ b/src/gpu/SkGpuDevice.h @@ -92,6 +92,7 @@ public: void drawTextBlob(const SkTextBlob*, SkScalar x, SkScalar y, const SkPaint& paint, SkDrawFilter* drawFilter) override; void drawVertices(const SkVertices*, SkBlendMode, const SkPaint&) override; + void drawShadow(const SkPath&, const SkDrawShadowRec&) override; void drawAtlas(const SkImage* atlas, const SkRSXform[], const SkRect[], const SkColor[], int count, SkBlendMode, const SkPaint&) override; void drawDevice(SkBaseDevice*, int x, int y, const SkPaint&) override; diff --git a/src/utils/SkNWayCanvas.cpp b/src/utils/SkNWayCanvas.cpp index 4f6ad46d85..208f3b4719 100644 --- a/src/utils/SkNWayCanvas.cpp +++ b/src/utils/SkNWayCanvas.cpp @@ -299,6 +299,13 @@ void SkNWayCanvas::onDrawPatch(const SkPoint cubics[12], const SkColor colors[4] } } +void SkNWayCanvas::onDrawShadowRec(const SkPath& path, const SkDrawShadowRec& rec) { + Iter iter(fList); + while (iter.next()) { + iter->private_draw_shadow_rec(path, rec); + } +} + void SkNWayCanvas::onDrawAnnotation(const SkRect& rect, const char key[], SkData* data) { Iter iter(fList); while (iter.next()) { diff --git a/src/utils/SkShadowUtils.cpp b/src/utils/SkShadowUtils.cpp index 806c98e68b..f0ab230acc 100644 --- a/src/utils/SkShadowUtils.cpp +++ b/src/utils/SkShadowUtils.cpp @@ -9,6 +9,8 @@ #include "SkCanvas.h" #include "SkColorFilter.h" #include "SkColorPriv.h" +#include "SkDevice.h" +#include "SkDrawShadowRec.h" #include "SkPath.h" #include "SkPM4f.h" #include "SkRandom.h" @@ -20,9 +22,9 @@ #if SK_SUPPORT_GPU #include "GrShape.h" #include "effects/GrBlurredEdgeFragmentProcessor.h" -#endif #include "../../src/effects/shadows/SkAmbientShadowMaskFilter.h" #include "../../src/effects/shadows/SkSpotShadowMaskFilter.h" +#endif /** * Gaussian color filter -- produces a Gaussian ramp based on the color's B value, @@ -444,7 +446,9 @@ static void* kNamespace; * they are first found in SkResourceCache. */ template -void draw_shadow(const FACTORY& factory, SkCanvas* canvas, ShadowedPath& path, SkColor color) { + void draw_shadow(const FACTORY& factory, + std::function drawProc, ShadowedPath& path, SkColor color) { FindContext context(&path.viewMatrix(), &factory); SkResourceCache::Key* key = nullptr; @@ -496,82 +500,83 @@ void draw_shadow(const FACTORY& factory, SkCanvas* canvas, ShadowedPath& path, S paint.setColorFilter(SkColorFilter::MakeComposeFilter( SkColorFilter::MakeModeFilter(color, SkBlendMode::kModulate), SkGaussianColorFilter::Make())); - if (translate->fX || translate->fY) { - canvas->save(); - canvas->translate(translate->fX, translate->fY); - } - canvas->drawVertices(vertices, SkBlendMode::kModulate, paint); - if (translate->fX || translate->fY) { - canvas->restore(); - } + + drawProc(vertices.get(), SkBlendMode::kModulate, paint, translate->fX, translate->fY); } } -static bool draw_analytic_shadows(SkCanvas* canvas, const SkPath& path, SkScalar occluderZ, - const SkPoint3& devLightPos, SkScalar lightRadius, - SkScalar ambientAlpha, SkScalar spotAlpha, SkColor color, - uint32_t flags) { - // only supported in GPU code - if (!canvas->getGrContext()) { - return false; - } +static bool tilted(const SkPoint3& zPlaneParams) { + return !SkScalarNearlyZero(zPlaneParams.fX) || !SkScalarNearlyZero(zPlaneParams.fY); +} - SkRect rect; - SkRRect rrect; - const SkMatrix& ctm = canvas->getTotalMatrix(); - if (ctm.rectStaysRect() && ctm.isSimilarity()) { +static SkPoint3 map(const SkMatrix& m, const SkPoint3& pt) { + SkPoint3 result; + m.mapXY(pt.fX, pt.fY, (SkPoint*)&result.fX); + result.fZ = pt.fZ; + return result; +} + +#if SK_SUPPORT_GPU +#include "SkGpuDevice.h" +void SkGpuDevice::drawShadow(const SkPath& path, const SkDrawShadowRec& rec) { + // check z plane + bool tiltZPlane = tilted(rec.fZPlaneParams); + bool skipAnalytic = SkToBool(rec.fFlags & SkShadowFlags::kGeometricOnly_ShadowFlag); + + const SkMatrix& ctm = this->ctm(); + + if (!tiltZPlane && !skipAnalytic && ctm.rectStaysRect() && ctm.isSimilarity()) { + SkPoint3 devLightPos = map(ctm, rec.fLightPos); + + const SkScalar occluderZ = rec.fZPlaneParams.fZ; + SkPaint ambientPaint, spotPaint; + ambientPaint.setColor(rec.fColor); + spotPaint.setColor(rec.fColor); + if (rec.fAmbientAlpha > 0) { + ambientPaint.setMaskFilter(SkAmbientShadowMaskFilter::Make(occluderZ, rec.fAmbientAlpha, + rec.fFlags)); + } + if (rec.fSpotAlpha > 0) { + spotPaint.setMaskFilter(SkSpotShadowMaskFilter::Make(occluderZ, devLightPos, + rec.fLightRadius, rec.fSpotAlpha, + rec.fFlags)); + } + + SkRect rect; + SkRRect rrect; if (path.isRect(&rect)) { - SkPaint newPaint; - newPaint.setColor(color); - if (ambientAlpha > 0) { - newPaint.setMaskFilter(SkAmbientShadowMaskFilter::Make(occluderZ, - ambientAlpha, flags)); - canvas->drawRect(rect, newPaint); + if (rec.fAmbientAlpha > 0) { + this->drawRect(rect, ambientPaint); } - if (spotAlpha > 0) { - newPaint.setMaskFilter(SkSpotShadowMaskFilter::Make(occluderZ, devLightPos, - lightRadius, spotAlpha, - flags)); - canvas->drawRect(rect, newPaint); + if (rec.fSpotAlpha > 0) { + this->drawRect(rect, spotPaint); } - return true; + return; } else if (path.isRRect(&rrect) && rrect.isSimpleCircular() && rrect.radii(SkRRect::kUpperLeft_Corner).fX > SK_ScalarNearlyZero) { - SkPaint newPaint; - newPaint.setColor(color); - if (ambientAlpha > 0) { - newPaint.setMaskFilter(SkAmbientShadowMaskFilter::Make(occluderZ, - ambientAlpha, flags)); - canvas->drawRRect(rrect, newPaint); + if (rec.fAmbientAlpha > 0) { + this->drawRRect(rrect, ambientPaint); } - if (spotAlpha > 0) { - newPaint.setMaskFilter(SkSpotShadowMaskFilter::Make(occluderZ, devLightPos, - lightRadius, spotAlpha, - flags)); - canvas->drawRRect(rrect, newPaint); + if (rec.fSpotAlpha > 0) { + this->drawRRect(rrect, spotPaint); } - return true; + return; } else if (path.isOval(&rect) && SkScalarNearlyEqual(rect.width(), rect.height()) && rect.width() > SK_ScalarNearlyZero) { - SkPaint newPaint; - newPaint.setColor(color); - if (ambientAlpha > 0) { - newPaint.setMaskFilter(SkAmbientShadowMaskFilter::Make(occluderZ, - ambientAlpha, flags)); - canvas->drawOval(rect, newPaint); + if (rec.fAmbientAlpha > 0) { + this->drawOval(rect, ambientPaint); } - if (spotAlpha > 0) { - newPaint.setMaskFilter(SkSpotShadowMaskFilter::Make(occluderZ, devLightPos, - lightRadius, spotAlpha, - flags)); - canvas->drawOval(rect, newPaint); + if (rec.fSpotAlpha > 0) { + this->drawOval(rect, spotPaint); } - return true; + return; } } - return false; + // failed to find an accelerated case + this->INHERITED::drawShadow(path, rec); } +#endif static SkColor compute_render_color(SkColor color, float alpha) { return SkColorSetARGB(alpha*SkColorGetA(color), SkColorGetR(color), @@ -583,26 +588,47 @@ void SkShadowUtils::DrawShadow(SkCanvas* canvas, const SkPath& path, const SkPoi const SkPoint3& devLightPos, SkScalar lightRadius, SkScalar ambientAlpha, SkScalar spotAlpha, SkColor color, uint32_t flags) { - // check z plane - bool tiltZPlane = !SkScalarNearlyZero(zPlaneParams.fX) || !SkScalarNearlyZero(zPlaneParams.fY); - - // try fast paths - bool skipAnalytic = SkToBool(flags & SkShadowFlags::kGeometricOnly_ShadowFlag) || tiltZPlane; - if (!skipAnalytic && draw_analytic_shadows(canvas, path, zPlaneParams.fZ, devLightPos, - lightRadius, ambientAlpha, spotAlpha, color, - flags)) { + SkMatrix inverse; + if (!canvas->getTotalMatrix().invert(&inverse)) { return; } + SkPoint pt = inverse.mapXY(devLightPos.fX, devLightPos.fY); - SkAutoCanvasRestore acr(canvas, true); - SkMatrix viewMatrix = canvas->getTotalMatrix(); - canvas->resetMatrix(); + SkDrawShadowRec rec; + rec.fZPlaneParams = zPlaneParams; + rec.fLightPos = { pt.fX, pt.fY, devLightPos.fZ }; + rec.fLightRadius = lightRadius; + rec.fAmbientAlpha = SkScalarToFloat(ambientAlpha); + rec.fSpotAlpha = SkScalarToFloat(spotAlpha); + rec.fColor = color; + rec.fFlags = flags; + + canvas->private_draw_shadow_rec(path, rec); +} + +void SkBaseDevice::drawShadow(const SkPath& path, const SkDrawShadowRec& rec) { + auto drawVertsProc = [this](const SkVertices* vertices, SkBlendMode mode, const SkPaint& paint, + SkScalar tx, SkScalar ty) { + SkAutoDeviceCTMRestore adr(this, SkMatrix::Concat(this->ctm(), + SkMatrix::MakeTrans(tx, ty))); + this->drawVertices(vertices, mode, paint); + }; + + SkMatrix viewMatrix = this->ctm(); + SkAutoDeviceCTMRestore adr(this, SkMatrix::I()); ShadowedPath shadowedPath(&path, &viewMatrix); - bool transparent = SkToBool(flags & SkShadowFlags::kTransparentOccluder_ShadowFlag); + bool tiltZPlane = tilted(rec.fZPlaneParams); + bool transparent = SkToBool(rec.fFlags & SkShadowFlags::kTransparentOccluder_ShadowFlag); bool uncached = tiltZPlane || path.isVolatile(); + SkColor color = rec.fColor; + SkPoint3 zPlaneParams = rec.fZPlaneParams; + SkPoint3 devLightPos = map(viewMatrix, rec.fLightPos); + float lightRadius = rec.fLightRadius; + + float ambientAlpha = rec.fAmbientAlpha; if (ambientAlpha > 0) { ambientAlpha = SkTMin(ambientAlpha, 1.f); if (uncached) { @@ -614,19 +640,20 @@ void SkShadowUtils::DrawShadow(SkCanvas* canvas, const SkPath& path, const SkPoi // Run the vertex color through a GaussianColorFilter and then modulate the grayscale // result of that against our 'color' param. paint.setColorFilter(SkColorFilter::MakeComposeFilter( - SkColorFilter::MakeModeFilter(renderColor, SkBlendMode::kModulate), - SkGaussianColorFilter::Make())); - canvas->drawVertices(vertices, SkBlendMode::kModulate, paint); + SkColorFilter::MakeModeFilter(renderColor, SkBlendMode::kModulate), + SkGaussianColorFilter::Make())); + this->drawVertices(vertices.get(), SkBlendMode::kModulate, paint); } else { AmbientVerticesFactory factory; factory.fOccluderHeight = zPlaneParams.fZ; factory.fTransparent = transparent; SkColor renderColor = compute_render_color(color, ambientAlpha); - draw_shadow(factory, canvas, shadowedPath, renderColor); + draw_shadow(factory, drawVertsProc, shadowedPath, renderColor); } } + float spotAlpha = rec.fSpotAlpha; if (spotAlpha > 0) { spotAlpha = SkTMin(spotAlpha, 1.f); if (uncached) { @@ -641,7 +668,7 @@ void SkShadowUtils::DrawShadow(SkCanvas* canvas, const SkPath& path, const SkPoi paint.setColorFilter(SkColorFilter::MakeComposeFilter( SkColorFilter::MakeModeFilter(renderColor, SkBlendMode::kModulate), SkGaussianColorFilter::Make())); - canvas->drawVertices(vertices, SkBlendMode::kModulate, paint); + this->drawVertices(vertices.get(), SkBlendMode::kModulate, paint); } else { SpotVerticesFactory factory; SkScalar occluderHeight = zPlaneParams.fZ; @@ -690,7 +717,7 @@ void SkShadowUtils::DrawShadow(SkCanvas* canvas, const SkPath& path, const SkPoi } #endif SkColor renderColor = compute_render_color(color, spotAlpha); - draw_shadow(factory, canvas, shadowedPath, renderColor); + draw_shadow(factory, drawVertsProc, shadowedPath, renderColor); } } }