static void blur_path(SkCanvas* canvas, const SkPath& path, SkScalar gaussianSigma) { SkScalar midX = path.getBounds().centerX(); SkScalar midY = path.getBounds().centerY(); canvas->translate(-midX, -midY); SkPaint blurPaint; blurPaint.setColor(SK_ColorWHITE); SkMaskFilter* filter = SkBlurMaskFilter::Create(kNormal_SkBlurStyle, gaussianSigma, SkBlurMaskFilter::kHighQuality_BlurFlag); blurPaint.setMaskFilter(filter)->unref(); canvas->drawColor(SK_ColorBLACK); canvas->drawPath(path, blurPaint); }
// Create a 1-tier drawlooper sk_sp<SkDrawLooper> create1Looper(SkScalar xOff, SkScalar yOff, SkColor color) { SkLayerDrawLooper::Builder looperBuilder; SkLayerDrawLooper::LayerInfo info; info.fPaintBits = SkLayerDrawLooper::kColorFilter_Bit | SkLayerDrawLooper::kMaskFilter_Bit; info.fColorMode = SkXfermode::kSrc_Mode; info.fOffset.set(xOff, yOff); info.fPostTranslate = false; SkPaint* paint = looperBuilder.addLayer(info); paint->setMaskFilter(this->createBlur())->unref(); paint->setColorFilter(SkColorFilter::MakeModeFilter(color, SkXfermode::kSrcIn_Mode)); return looperBuilder.detach(); }
void DrawLooperBuilder::addShadow(const FloatSize& offset, float blur, const Color& color, ShadowTransformMode shadowTransformMode, ShadowAlphaMode shadowAlphaMode) { // Detect when there's no effective shadow. if (!color.alpha()) return; SkColor skColor = color.rgb(); SkLayerDrawLooper::LayerInfo info; switch (shadowAlphaMode) { case ShadowRespectsAlpha: info.fColorMode = SkBlendMode::kDst; break; case ShadowIgnoresAlpha: info.fColorMode = SkBlendMode::kSrc; break; default: ASSERT_NOT_REACHED(); } if (blur) info.fPaintBits |= SkLayerDrawLooper::kMaskFilter_Bit; // our blur info.fPaintBits |= SkLayerDrawLooper::kColorFilter_Bit; info.fOffset.set(offset.width(), offset.height()); info.fPostTranslate = (shadowTransformMode == ShadowIgnoresTransforms); SkPaint* paint = m_skDrawLooperBuilder.addLayerOnTop(info); if (blur) { const SkScalar sigma = RadiusToSigma(blur / 2); uint32_t mfFlags = SkBlurMaskFilter::kHighQuality_BlurFlag; if (shadowTransformMode == ShadowIgnoresTransforms) mfFlags |= SkBlurMaskFilter::kIgnoreTransform_BlurFlag; paint->setMaskFilter( SkBlurMaskFilter::Make(kNormal_SkBlurStyle, sigma, mfFlags)); } paint->setColorFilter( SkColorFilter::MakeModeFilter(skColor, SkBlendMode::kSrcIn)); }
void onDraw(int loops, SkCanvas* canvas) override { SkPaint paint; this->setupPaint(&paint); paint.setAntiAlias(true); SkRandom rand; for (int i = 0; i < loops; i++) { SkRect r = SkRect::MakeWH(rand.nextUScalar1() * 400, rand.nextUScalar1() * 400); r.offset(fRadius, fRadius); if (fRadius > 0) { paint.setMaskFilter(SkMaskFilter::MakeBlur(fStyle, SkBlurMask::ConvertRadiusToSigma(fRadius))); } canvas->drawOval(r, paint); } }
virtual void onDraw(SkCanvas* canvas) { SkPaint paint; this->setupPaint(&paint); paint.setAntiAlias(true); SkRandom rand; for (int i = 0; i < SkBENCHLOOP(10); i++) { SkRect r = SkRect::MakeWH(rand.nextUScalar1() * 400, rand.nextUScalar1() * 400); r.offset(fRadius, fRadius); if (fRadius > 0) { SkMaskFilter* mf = SkBlurMaskFilter::Create(fRadius, fStyle, 0); paint.setMaskFilter(mf)->unref(); } canvas->drawOval(r, paint); } }
void DrawLooper::addShadow(const FloatSize& offset, float blur, const Color& color, ShadowTransformMode shadowTransformMode, ShadowAlphaMode shadowAlphaMode) { // Detect when there's no effective shadow. if (!color.alpha()) return; SkColor skColor = color.rgb(); SkLayerDrawLooper::LayerInfo info; switch (shadowAlphaMode) { case ShadowRespectsAlpha: info.fColorMode = SkXfermode::kDst_Mode; break; case ShadowIgnoresAlpha: info.fColorMode = SkXfermode::kSrc_Mode; break; default: ASSERT_NOT_REACHED(); } if (blur) info.fPaintBits |= SkLayerDrawLooper::kMaskFilter_Bit; // our blur info.fPaintBits |= SkLayerDrawLooper::kColorFilter_Bit; info.fOffset.set(offset.width(), offset.height()); info.fPostTranslate = (shadowTransformMode == ShadowIgnoresTransforms); SkPaint* paint = m_skDrawLooper->addLayerOnTop(info); if (blur) { uint32_t mfFlags = SkBlurMaskFilter::kHighQuality_BlurFlag; if (shadowTransformMode == ShadowIgnoresTransforms) mfFlags |= SkBlurMaskFilter::kIgnoreTransform_BlurFlag; RefPtr<SkMaskFilter> mf = adoptRef(SkBlurMaskFilter::Create( (double)blur / 2.0, SkBlurMaskFilter::kNormal_BlurStyle, mfFlags)); paint->setMaskFilter(mf.get()); } RefPtr<SkColorFilter> cf = adoptRef(SkColorFilter::CreateModeFilter(skColor, SkXfermode::kSrcIn_Mode)); paint->setColorFilter(cf.get()); }
void onDraw(SkCanvas* canvas) override { static const SkScalar kBlurRadius = SkIntToScalar(20); static const SkScalar kBoxSize = SkIntToScalar(100); SkRect clipRect = SkRect::MakeXYWH(0, 0, kBoxSize, kBoxSize); SkRect blurRects[] = { { -kBoxSize - (kBlurRadius+1), 0, -(kBlurRadius+1), kBoxSize }, { 0, -kBoxSize - (kBlurRadius+1), kBoxSize, -(kBlurRadius+1) }, { kBoxSize+kBlurRadius+1, 0, 2*kBoxSize+kBlurRadius+1, kBoxSize }, { 0, kBoxSize+kBlurRadius+1, kBoxSize, 2*kBoxSize+kBlurRadius+1 } }; SkColor colors[] = { SK_ColorRED, SK_ColorGREEN, SK_ColorBLUE, SK_ColorYELLOW, }; SkASSERT(SK_ARRAY_COUNT(colors) == SK_ARRAY_COUNT(blurRects)); SkPaint hairlinePaint; hairlinePaint.setStyle(SkPaint::kStroke_Style); hairlinePaint.setColor(SK_ColorWHITE); hairlinePaint.setStrokeWidth(0); SkPaint blurPaint; blurPaint.setFilterQuality(kLow_SkFilterQuality); SkMaskFilter* mf = SkBlurMaskFilter::Create(kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(kBlurRadius)); blurPaint.setMaskFilter(mf)->unref(); canvas->clear(SK_ColorBLACK); canvas->save(); canvas->translate(kBoxSize, kBoxSize); canvas->drawRect(clipRect, hairlinePaint); canvas->clipRect(clipRect); for (size_t i = 0; i < SK_ARRAY_COUNT(blurRects); ++i) { blurPaint.setColor(colors[i]); canvas->drawRect(blurRects[i], blurPaint); canvas->drawRect(blurRects[i], hairlinePaint); } canvas->restore(); }
virtual void onDraw(SkCanvas* canvas) { this->drawBG(canvas); canvas->translate(this->width()/2, this->height()/2); Sk3DView view; view.rotateX(SkIntToScalar(fRX)); view.rotateY(SkIntToScalar(fRY)); view.applyToCanvas(canvas); SkPaint paint; SkScalar rad = SkIntToScalar(50); SkScalar dim = rad*2; if (view.dotWithNormal(0, 0, SK_Scalar1) < 0) { paint.setColor(SK_ColorRED); } paint.setAntiAlias(true); #if 0 SkEmbossMaskFilter::Light light; light.fDirection[0] = SK_Scalar1; light.fDirection[1] = SK_Scalar1; light.fDirection[2] = SK_Scalar1; light.fAmbient = 180; light.fSpecular = 16 * 2; paint.setMaskFilter(new SkEmbossMaskFilter(light, SkIntToScalar(4))); #endif canvas->drawCircle(0, 0, rad, paint); canvas->drawCircle(-dim, -dim, rad, paint); canvas->drawCircle(-dim, dim, rad, paint); canvas->drawCircle( dim, -dim, rad, paint); canvas->drawCircle( dim, dim, rad, paint); fRY += 1; if (fRY >= 360) fRY = 0; this->inval(NULL); }
static void draw_rrect(SkCanvas* canvas, const SkRRect& rr, const SkRRect& occRR) { const SkScalar kBlurSigma = 5.0f; SkRect occRect; SkColor strokeColor; { SkRect occRect1 = sk_tool_utils::compute_central_occluder(occRR); SkRect occRect2 = sk_tool_utils::compute_widest_occluder(occRR); SkRect occRect3 = sk_tool_utils::compute_tallest_occluder(occRR); SkScalar area1 = occRect1.width() * occRect1.height(); SkScalar area2 = occRect2.width() * occRect2.height(); SkScalar area3 = occRect3.width() * occRect3.height(); if (area1 >= area2 && area1 >= area3) { strokeColor = SK_ColorRED; occRect = occRect1; } else if (area2 > area3) { strokeColor = SK_ColorYELLOW; occRect = occRect2; } else { strokeColor = SK_ColorCYAN; occRect = occRect3; } } // draw the blur SkPaint paint; paint.setMaskFilter(SkBlurMaskFilter::Make(kNormal_SkBlurStyle, kBlurSigma, occRect)); canvas->drawRRect(rr, paint); // draw the stroked geometry of the full occluder SkPaint stroke; stroke.setStyle(SkPaint::kStroke_Style); stroke.setColor(SK_ColorBLUE); canvas->drawRRect(occRR, stroke); // draw the geometry of the occluding rect stroke.setColor(strokeColor); canvas->drawRect(occRect, stroke); }
void onDrawContent(SkCanvas* canvas) override { static const SkBlurStyle gStyles[] = { kNormal_SkBlurStyle, kInner_SkBlurStyle, kSolid_SkBlurStyle, kOuter_SkBlurStyle, }; SkRandom random; for (size_t i = 0; i < SK_ARRAY_COUNT(gStyles); ++i) { SkPaint paint; paint.setMaskFilter(SkBlurMaskFilter::Make(gStyles[i], fBlurSigma, SkBlurMaskFilter::kHighQuality_BlurFlag)); paint.setColor(random.nextU() | 0xff000000); canvas->drawCircle(200 * SK_Scalar1 + 400 * (i % 2) * SK_Scalar1, 200 * SK_Scalar1 + i / 2 * 400 * SK_Scalar1, fCircleRadius, paint); } }
virtual void onDraw(const int loops, SkCanvas* canvas) { SkPaint paint; this->setupPaint(&paint); paint.setAntiAlias(true); SkRandom rand; for (int i = 0; i < loops; i++) { SkRect r = SkRect::MakeWH(rand.nextUScalar1() * 400, rand.nextUScalar1() * 400); r.offset(fRadius, fRadius); if (fRadius > 0) { SkMaskFilter* mf = SkBlurMaskFilter::Create(fStyle, SkBlurMask::ConvertRadiusToSigma(fRadius), fFlags); paint.setMaskFilter(mf)->unref(); } canvas->drawOval(r, paint); } }
static SkPaint make_paint() { SkPaint paint; paint.setHinting(make_paint_hinting()); paint.setAntiAlias(make_bool()); paint.setDither(make_bool()); paint.setLinearText(make_bool()); paint.setSubpixelText(make_bool()); paint.setLCDRenderText(make_bool()); paint.setEmbeddedBitmapText(make_bool()); paint.setAutohinted(make_bool()); paint.setVerticalText(make_bool()); paint.setFakeBoldText(make_bool()); paint.setDevKernText(make_bool()); paint.setFilterQuality(make_filter_quality()); paint.setStyle(make_paint_style()); paint.setColor(make_color()); paint.setStrokeWidth(make_scalar()); paint.setStrokeMiter(make_scalar()); paint.setStrokeCap(make_paint_cap()); paint.setStrokeJoin(make_paint_join()); paint.setColorFilter(make_color_filter()); paint.setBlendMode(make_xfermode()); paint.setPathEffect(make_path_effect()); paint.setMaskFilter(make_mask_filter()); if (false) { // our validating buffer does not support typefaces yet, so skip this for now paint.setTypeface(SkTypeface::MakeFromName(make_font_name().c_str(), make_typeface_style())); } paint.setImageFilter(make_image_filter()); sk_sp<SkData> data(make_3Dlut(nullptr, make_bool(), make_bool(), make_bool())); paint.setTextAlign(make_paint_align()); paint.setTextSize(make_scalar()); paint.setTextScaleX(make_scalar()); paint.setTextSkewX(make_scalar()); paint.setTextEncoding(make_paint_text_encoding()); return paint; }
// Create a 4-tier draw looper sk_sp<SkDrawLooper> create4Looper(SkScalar xOff, SkScalar yOff) { SkLayerDrawLooper::Builder looperBuilder; SkLayerDrawLooper::LayerInfo info; info.fPaintBits = SkLayerDrawLooper::kColorFilter_Bit | SkLayerDrawLooper::kMaskFilter_Bit; info.fColorMode = (SK_XFERMODE_MODE_PARAM)SkBlendMode::kSrc; info.fPostTranslate = false; SkPaint* paint; for (int i = 3; i >= 0; --i) { info.fOffset.set(xOff+gBlurOffsets[i].fX, yOff+gBlurOffsets[i].fY); paint = looperBuilder.addLayer(info); paint->setMaskFilter(MakeBlur()); paint->setColorFilter(SkColorFilter::MakeModeFilter(gColors[i], SkBlendMode::kSrcIn)); } return looperBuilder.detach(); }
// Create a 4-tier draw looper sk_sp<SkDrawLooper> create4Looper(SkScalar xOff, SkScalar yOff) { SkLayerDrawLooper::Builder looperBuilder; SkLayerDrawLooper::LayerInfo info; info.fPaintBits = SkLayerDrawLooper::kColorFilter_Bit | SkLayerDrawLooper::kMaskFilter_Bit; info.fColorMode = SkXfermode::kSrc_Mode; info.fPostTranslate = false; SkPaint* paint; for (int i = 3; i >= 0; --i) { info.fOffset.set(xOff+gBlurOffsets[i].fX, yOff+gBlurOffsets[i].fY); paint = looperBuilder.addLayer(info); paint->setMaskFilter(this->createBlur())->unref(); SkColorFilter* cf = SkColorFilter::CreateModeFilter(gColors[i], SkXfermode::kSrcIn_Mode); paint->setColorFilter(cf)->unref(); } return looperBuilder.detach(); }
void onDraw(SkCanvas* canvas) override { canvas->translate(STROKE_WIDTH*3/2, STROKE_WIDTH*3/2); SkRect r = { 0, 0, 100, 50 }; SkScalar scales[] = { SK_Scalar1, 0.6f }; for (size_t s = 0; s < SK_ARRAY_COUNT(scales); ++s) { canvas->save(); for (size_t f = 0; f < SK_ARRAY_COUNT(fMaskFilters); ++f) { SkPaint paint; paint.setMaskFilter(fMaskFilters[f]); paint.setAlpha(fAlpha); SkPaint paintWithRadial = paint; paintWithRadial.setShader(make_radial()); constexpr Proc procs[] = { fill_rect, draw_donut, draw_donut_skewed }; canvas->save(); canvas->scale(scales[s], scales[s]); this->drawProcs(canvas, r, paint, false, procs, SK_ARRAY_COUNT(procs)); canvas->translate(r.width() * 4/3, 0); this->drawProcs(canvas, r, paintWithRadial, false, procs, SK_ARRAY_COUNT(procs)); canvas->translate(r.width() * 4/3, 0); this->drawProcs(canvas, r, paint, true, procs, SK_ARRAY_COUNT(procs)); canvas->translate(r.width() * 4/3, 0); this->drawProcs(canvas, r, paintWithRadial, true, procs, SK_ARRAY_COUNT(procs)); canvas->restore(); canvas->translate(0, SK_ARRAY_COUNT(procs) * r.height() * 4/3 * scales[s]); } canvas->restore(); canvas->translate(4 * r.width() * 4/3 * scales[s], 0); } }
void onDrawContent(SkCanvas* canvas) override { const char* str = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; SkPaint paint; SkScalar x = SkIntToScalar(10); SkScalar y = SkIntToScalar(20); paint.setFlags(0x105); paint.setARGB(fByte, 0xFF, 0xFF, 0xFF); paint.setMaskFilter(SkBlurMaskFilter::Create(kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(3)))); paint.getMaskFilter()->unref(); SkRandom rand; for (int ps = 6; ps <= 35; ps++) { paint.setColor(rand.nextU() | (0xFF << 24)); paint.setTextSize(SkIntToScalar(ps)); paint.setTextSize(SkIntToScalar(24)); canvas->drawText(str, strlen(str), x, y, paint); y += paint.getFontMetrics(nullptr); } }
void init() { if (fLooper) return; static const struct { SkColor fColor; SkPaint::Style fStyle; SkScalar fWidth; SkScalar fOffset; SkScalar fBlur; } gParams[] = { { SK_ColorWHITE, SkPaint::kStroke_Style, SkIntToScalar(1)*3/4, 0, 0 }, { SK_ColorRED, SkPaint::kStroke_Style, SkIntToScalar(4), 0, 0 }, { SK_ColorBLUE, SkPaint::kFill_Style, 0, 0, 0 }, { 0x88000000, SkPaint::kFill_Style, 0, SkIntToScalar(10), SkIntToScalar(3) } }; SkLayerDrawLooper::Builder looperBuilder; SkLayerDrawLooper::LayerInfo info; info.fPaintBits = SkLayerDrawLooper::kStyle_Bit | SkLayerDrawLooper::kMaskFilter_Bit; info.fColorMode = SkXfermode::kSrc_Mode; for (size_t i = 0; i < SK_ARRAY_COUNT(gParams); i++) { info.fOffset.set(gParams[i].fOffset, gParams[i].fOffset); SkPaint* paint = looperBuilder.addLayer(info); paint->setColor(gParams[i].fColor); paint->setStyle(gParams[i].fStyle); paint->setStrokeWidth(gParams[i].fWidth); if (gParams[i].fBlur > 0) { SkMaskFilter* mf = SkBlurMaskFilter::Create(kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(gParams[i].fBlur)); paint->setMaskFilter(mf)->unref(); } } fLooper = looperBuilder.detachLooper(); }
sk_sp<SkDrawLooper> SkBlurDrawLooper::Make(SkColor color, SkScalar sigma, SkScalar dx, SkScalar dy) { sk_sp<SkMaskFilter> blur = nullptr; if (sigma > 0.0f) { blur = SkMaskFilter::MakeBlur(kNormal_SkBlurStyle, sigma, true); } SkLayerDrawLooper::Builder builder; // First layer SkLayerDrawLooper::LayerInfo defaultLayer; builder.addLayer(defaultLayer); // Blur layer SkLayerDrawLooper::LayerInfo blurInfo; blurInfo.fColorMode = SkBlendMode::kSrc; blurInfo.fPaintBits = SkLayerDrawLooper::kMaskFilter_Bit; blurInfo.fOffset = SkVector::Make(dx, dy); SkPaint* paint = builder.addLayer(blurInfo); paint->setMaskFilter(std::move(blur)); paint->setColor(color); return builder.detach(); }
void makePaints() { { // no AA SkPaint p; fPaints.push_back(p); } { // AA SkPaint p; p.setAntiAlias(true); fPaints.push_back(p); } { // AA with mask filter SkPaint p; p.setAntiAlias(true); p.setMaskFilter(SkBlurMaskFilter::Make( kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5)), SkBlurMaskFilter::kHighQuality_BlurFlag)); fPaints.push_back(p); } { // AA with radial shader SkPaint p; p.setAntiAlias(true); SkPoint center = SkPoint::Make(SkIntToScalar(40), SkIntToScalar(40)); SkColor colors[] = { SK_ColorBLUE, SK_ColorRED, SK_ColorGREEN }; SkScalar pos[] = { 0, SK_ScalarHalf, SK_Scalar1 }; p.setShader(SkGradientShader::MakeRadial(center, 20, colors, pos, SK_ARRAY_COUNT(colors), SkShader::kClamp_TileMode)); fPaints.push_back(p); } { // AA with blur SkPaint p; p.setAntiAlias(true); p.setLooper(SkBlurDrawLooper::Make(SK_ColorBLUE, SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(10)), SkIntToScalar(5), SkIntToScalar(10), SkBlurDrawLooper::kIgnoreTransform_BlurFlag | SkBlurDrawLooper::kOverrideColor_BlurFlag | SkBlurDrawLooper::kHighQuality_BlurFlag)); fPaints.push_back(p); } { // AA with stroke style SkPaint p; p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); p.setStrokeWidth(SkIntToScalar(3)); fPaints.push_back(p); } { // AA with stroke style, width = 0 SkPaint p; p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); fPaints.push_back(p); } { // AA with stroke and fill style SkPaint p; p.setAntiAlias(true); p.setStyle(SkPaint::kStrokeAndFill_Style); p.setStrokeWidth(SkIntToScalar(2)); fPaints.push_back(p); } }
void makePaints() { { // no AA SkPaint p; p.setColor(SK_ColorWHITE); fPaints.push_back(p); } { // AA SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); fPaints.push_back(p); } { // AA with translucent SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setAlpha(0x66); fPaints.push_back(p); } { // AA with mask filter SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); SkMaskFilter* mf = SkBlurMaskFilter::Create( kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5)), SkBlurMaskFilter::kHighQuality_BlurFlag); p.setMaskFilter(mf)->unref(); fPaints.push_back(p); } { // AA with radial shader SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); SkPoint center = SkPoint::Make(SkIntToScalar(-5), SkIntToScalar(30)); SkColor colors[] = { SK_ColorBLUE, SK_ColorRED, SK_ColorGREEN }; SkScalar pos[] = { 0, SK_ScalarHalf, SK_Scalar1 }; SkShader* s = SkGradientShader::CreateRadial(center, SkIntToScalar(20), colors, pos, SK_ARRAY_COUNT(colors), SkShader::kClamp_TileMode); p.setShader(s)->unref(); fPaints.push_back(p); } { // AA with blur SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); SkDrawLooper* shadowLooper = SkBlurDrawLooper::Create(SK_ColorWHITE, SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(10)), SkIntToScalar(5), SkIntToScalar(10), SkBlurDrawLooper::kIgnoreTransform_BlurFlag | SkBlurDrawLooper::kOverrideColor_BlurFlag | SkBlurDrawLooper::kHighQuality_BlurFlag); SkAutoUnref aurL0(shadowLooper); p.setLooper(shadowLooper); fPaints.push_back(p); } { // AA with stroke style SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); p.setStrokeWidth(SkIntToScalar(3)); fPaints.push_back(p); } { // AA with bevel-stroke style SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); p.setStrokeJoin(SkPaint::kBevel_Join); p.setStrokeWidth(SkIntToScalar(3)); fPaints.push_back(p); } { // AA with round-stroke style SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); p.setStrokeJoin(SkPaint::kRound_Join); p.setStrokeWidth(SkIntToScalar(3)); fPaints.push_back(p); } { // AA with stroke style, width = 0 SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); fPaints.push_back(p); } { // AA with stroke style, width wider than rect width and/or height SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setStyle(SkPaint::kStroke_Style); p.setStrokeWidth(SkIntToScalar(40)); fPaints.push_back(p); } { // AA with stroke and fill style SkPaint p; p.setColor(SK_ColorWHITE); p.setAntiAlias(true); p.setStyle(SkPaint::kStrokeAndFill_Style); p.setStrokeWidth(SkIntToScalar(2)); fPaints.push_back(p); } }
static void test_bigblur(SkCanvas* canvas) { canvas->drawColor(SK_ColorBLACK); SkBitmap orig, mask; SkImageDecoder::DecodeFile("/skimages/app_icon.png", &orig); SkMaskFilter* mf = SkBlurMaskFilter::Create(8, SkBlurMaskFilter::kNormal_BlurStyle); SkPaint paint; paint.setMaskFilter(mf)->unref(); SkIPoint offset; orig.extractAlpha(&mask, &paint, &offset); paint.setColor(0xFFBB8800); paint.setColor(SK_ColorWHITE); int i; canvas->save(); float gamma = 0.8; for (i = 0; i < 5; i++) { paint.setMaskFilter(SkTableMaskFilter::CreateGamma(gamma))->unref(); canvas->drawBitmap(mask, 0, 0, &paint); paint.setMaskFilter(NULL); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); gamma -= 0.1; canvas->translate(120, 0); } canvas->restore(); canvas->translate(0, 160); for (i = 0; i < 5; i++) { paint.setMaskFilter(SkTableMaskFilter::CreateClip(i*30, 255 - 20))->unref(); canvas->drawBitmap(mask, 0, 0, &paint); paint.setMaskFilter(NULL); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); canvas->translate(120, 0); } #if 0 paint.setColor(0xFFFFFFFF); canvas->drawBitmap(mask, 0, 0, &paint); paint.setMaskFilter(NULL); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); canvas->translate(120, 0); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); canvas->translate(120, 0); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); canvas->translate(120, 0); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); canvas->translate(120, 0); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(mask, 0, 0, &paint); canvas->drawBitmap(orig, -offset.fX, -offset.fY, &paint); #endif }
void onDraw(SkCanvas* canvas) override { SkRect dstRect = { 0, 0, SkIntToScalar(64), SkIntToScalar(64)}; static const int kMaxSrcRectSize = 1 << (SkNextLog2(gBmpSize) + 2); static const int kPadX = 30; static const int kPadY = 40; SkPaint paint; paint.setAlpha(0x20); canvas->drawBitmapRect(fLargeBitmap, SkRect::MakeIWH(gSize, gSize), &paint); canvas->translate(SK_Scalar1 * kPadX / 2, SK_Scalar1 * kPadY / 2); SkPaint blackPaint; SkScalar titleHeight = SK_Scalar1 * 24; blackPaint.setColor(SK_ColorBLACK); blackPaint.setTextSize(titleHeight); blackPaint.setAntiAlias(true); sk_tool_utils::set_portable_typeface(&blackPaint); SkString title; title.printf("Bitmap size: %d x %d", gBmpSize, gBmpSize); canvas->drawText(title.c_str(), title.size(), 0, titleHeight, blackPaint); canvas->translate(0, SK_Scalar1 * kPadY / 2 + titleHeight); int rowCount = 0; canvas->save(); for (int w = 1; w <= kMaxSrcRectSize; w *= 4) { for (int h = 1; h <= kMaxSrcRectSize; h *= 4) { SkIRect srcRect = SkIRect::MakeXYWH((gBmpSize - w) / 2, (gBmpSize - h) / 2, w, h); fProc(canvas, fImage, fLargeBitmap, srcRect, dstRect); SkString label; label.appendf("%d x %d", w, h); blackPaint.setAntiAlias(true); blackPaint.setStyle(SkPaint::kFill_Style); blackPaint.setTextSize(SK_Scalar1 * 10); SkScalar baseline = dstRect.height() + blackPaint.getTextSize() + SK_Scalar1 * 3; canvas->drawText(label.c_str(), label.size(), 0, baseline, blackPaint); blackPaint.setStyle(SkPaint::kStroke_Style); blackPaint.setStrokeWidth(SK_Scalar1); blackPaint.setAntiAlias(false); canvas->drawRect(dstRect, blackPaint); canvas->translate(dstRect.width() + SK_Scalar1 * kPadX, 0); ++rowCount; if ((dstRect.width() + kPadX) * rowCount > gSize) { canvas->restore(); canvas->translate(0, dstRect.height() + SK_Scalar1 * kPadY); canvas->save(); rowCount = 0; } } } { // test the following code path: // SkGpuDevice::drawPath() -> SkGpuDevice::drawWithMaskFilter() SkIRect srcRect; SkPaint paint; SkBitmap bm; bm = make_chessbm(5, 5); paint.setFilterQuality(kLow_SkFilterQuality); srcRect.setXYWH(1, 1, 3, 3); SkMaskFilter* mf = SkBlurMaskFilter::Create( kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(SkIntToScalar(5)), SkBlurMaskFilter::kHighQuality_BlurFlag | SkBlurMaskFilter::kIgnoreTransform_BlurFlag); paint.setMaskFilter(mf)->unref(); canvas->drawBitmapRect(bm, srcRect, dstRect, &paint); } }
virtual void onDraw(SkCanvas* canvas) { this->drawBG(canvas); if (true) { SkRect r; r.set(SkIntToScalar(0), SkIntToScalar(0), SkIntToScalar(220), SkIntToScalar(120)); SkPaint p; canvas->saveLayer(&r, &p); canvas->drawColor(0xFFFF0000); p.setAlpha(1); // or 0 p.setXfermodeMode(SkXfermode::kSrc_Mode); canvas->drawOval(r, p); canvas->restore(); return; } if (false) { SkRect r; r.set(SkIntToScalar(0), SkIntToScalar(0), SkIntToScalar(220), SkIntToScalar(120)); SkPaint p; p.setAlpha(0x88); p.setAntiAlias(true); if (true) { canvas->saveLayer(&r, &p); p.setColor(0xFFFF0000); canvas->drawOval(r, p); canvas->restore(); } p.setColor(0xFF0000FF); r.offset(SkIntToScalar(20), SkIntToScalar(50)); canvas->drawOval(r, p); } if (false) { SkPaint p; p.setAlpha(0x88); p.setAntiAlias(true); canvas->translate(SkIntToScalar(300), 0); SkRect r; r.set(SkIntToScalar(0), SkIntToScalar(0), SkIntToScalar(220), SkIntToScalar(60)); canvas->saveLayer(&r, &p, (SkCanvas::SaveFlags)(SkCanvas::kHasAlphaLayer_SaveFlag | SkCanvas::kFullColorLayer_SaveFlag)); // canvas->clipRect(r, SkRegion::kDifference_Op); // canvas->clipRect(r, SkRegion::kIntersect_Op); r.set(SkIntToScalar(0), SkIntToScalar(0), SkIntToScalar(220), SkIntToScalar(120)); p.setColor(SK_ColorBLUE); canvas->drawOval(r, p); canvas->restore(); return; } //canvas->translate(SkIntToScalar(20), SkIntToScalar(20)); test_fade(canvas); return; // canvas->setDrawFilter(new RedFilter)->unref(); SkRect r; SkPaint p; canvas->translate(SkIntToScalar(220), SkIntToScalar(20)); p.setAntiAlias(true); r.set(SkIntToScalar(20), SkIntToScalar(20), SkIntToScalar(220), SkIntToScalar(120)); p.setColor(SK_ColorBLUE); // p.setMaskFilter(SkBlurMaskFilter::Create(SkIntToScalar(8), SkBlurMaskFilter::kNormal_BlurStyle))->unref(); canvas->drawRect(r, p); p.setMaskFilter(NULL); SkRect bounds = r; bounds.fBottom = bounds.centerY(); canvas->saveLayer(&bounds, NULL, SkCanvas::kARGB_NoClipLayer_SaveFlag); p.setColor(SK_ColorRED); canvas->drawOval(r, p); p.setAlpha(0x80); p.setXfermodeMode(SkXfermode::kDstIn_Mode); canvas->drawRect(bounds, p); canvas->restore(); }
void DrawTargetSkia::DrawSurfaceWithShadow(SourceSurface *aSurface, const Point &aDest, const Color &aColor, const Point &aOffset, Float aSigma, CompositionOp aOperator) { MarkChanged(); mCanvas->save(SkCanvas::kMatrix_SaveFlag); mCanvas->resetMatrix(); uint32_t blurFlags = SkBlurMaskFilter::kHighQuality_BlurFlag | SkBlurMaskFilter::kIgnoreTransform_BlurFlag; const SkBitmap& bitmap = static_cast<SourceSurfaceSkia*>(aSurface)->GetBitmap(); SkShader* shader = SkShader::CreateBitmapShader(bitmap, SkShader::kClamp_TileMode, SkShader::kClamp_TileMode); SkMatrix matrix; matrix.reset(); matrix.setTranslateX(SkFloatToScalar(aDest.x)); matrix.setTranslateY(SkFloatToScalar(aDest.y)); shader->setLocalMatrix(matrix); SkLayerDrawLooper* dl = new SkLayerDrawLooper; SkLayerDrawLooper::LayerInfo info; info.fPaintBits |= SkLayerDrawLooper::kShader_Bit; SkPaint *layerPaint = dl->addLayer(info); layerPaint->setShader(shader); info.fPaintBits = 0; info.fPaintBits |= SkLayerDrawLooper::kMaskFilter_Bit; info.fPaintBits |= SkLayerDrawLooper::kColorFilter_Bit; info.fColorMode = SkXfermode::kDst_Mode; info.fOffset.set(SkFloatToScalar(aOffset.x), SkFloatToScalar(aOffset.y)); info.fPostTranslate = true; SkMaskFilter* mf = SkBlurMaskFilter::Create(aSigma, SkBlurMaskFilter::kNormal_BlurStyle, blurFlags); SkColor color = ColorToSkColor(aColor, 1); SkColorFilter* cf = SkColorFilter::CreateModeFilter(color, SkXfermode::kSrcIn_Mode); layerPaint = dl->addLayer(info); SkSafeUnref(layerPaint->setMaskFilter(mf)); SkSafeUnref(layerPaint->setColorFilter(cf)); layerPaint->setColor(color); // TODO: This is using the rasterizer to calculate an alpha mask // on both the shadow and normal layers. We should fix this // properly so it only happens for the shadow layer SkLayerRasterizer *raster = new SkLayerRasterizer(); SkPaint maskPaint; SkSafeUnref(maskPaint.setShader(shader)); raster->addLayer(maskPaint, 0, 0); SkPaint paint; paint.setAntiAlias(true); SkSafeUnref(paint.setRasterizer(raster)); paint.setXfermodeMode(GfxOpToSkiaOp(aOperator)); SkSafeUnref(paint.setLooper(dl)); SkRect rect = RectToSkRect(Rect(Float(aDest.x), Float(aDest.y), Float(bitmap.width()), Float(bitmap.height()))); mCanvas->drawRect(rect, paint); mCanvas->restore(); }
static void test_blur(skiatest::Reporter* reporter) { SkPaint paint; paint.setColor(SK_ColorGRAY); paint.setStyle(SkPaint::kStroke_Style); paint.setStrokeWidth(SkIntToScalar(strokeWidth)); SkScalar radius = SkIntToScalar(5); for (int style = 0; style < SkBlurMaskFilter::kBlurStyleCount; ++style) { SkBlurMaskFilter::BlurStyle blurStyle = static_cast<SkBlurMaskFilter::BlurStyle>(style); const uint32_t flagPermutations = SkBlurMaskFilter::kAll_BlurFlag; for (uint32_t flags = 0; flags < flagPermutations; ++flags) { SkMaskFilter* filter; filter = SkBlurMaskFilter::Create(radius, blurStyle, flags); SkMaskFilter::BlurInfo info; sk_bzero(&info, sizeof(info)); SkMaskFilter::BlurType type = filter->asABlur(&info); REPORTER_ASSERT(reporter, type == static_cast<SkMaskFilter::BlurType>(style + 1)); REPORTER_ASSERT(reporter, info.fRadius == radius); REPORTER_ASSERT(reporter, info.fIgnoreTransform == SkToBool(flags & SkBlurMaskFilter::kIgnoreTransform_BlurFlag)); REPORTER_ASSERT(reporter, info.fHighQuality == SkToBool(flags & SkBlurMaskFilter::kHighQuality_BlurFlag)); paint.setMaskFilter(filter); filter->unref(); for (size_t test = 0; test < SK_ARRAY_COUNT(tests); ++test) { SkPath path; tests[test].addPath(&path); SkPath strokedPath; paint.getFillPath(path, &strokedPath); SkRect refBound = strokedPath.getBounds(); SkIRect iref; refBound.roundOut(&iref); iref.inset(-outset, -outset); SkBitmap refBitmap; create(&refBitmap, iref, SkBitmap::kARGB_8888_Config); SkCanvas refCanvas(refBitmap); refCanvas.translate(SkIntToScalar(-iref.fLeft), SkIntToScalar(-iref.fTop)); drawBG(&refCanvas); refCanvas.drawPath(path, paint); for (int view = 0; view < tests[test].viewLen; ++view) { SkIRect itest = tests[test].views[view]; SkBitmap testBitmap; create(&testBitmap, itest, SkBitmap::kARGB_8888_Config); SkCanvas testCanvas(testBitmap); testCanvas.translate(SkIntToScalar(-itest.fLeft), SkIntToScalar(-itest.fTop)); drawBG(&testCanvas); testCanvas.drawPath(path, paint); REPORTER_ASSERT(reporter, compare(refBitmap, iref, testBitmap, itest)); } } } } }
void GraphicsContext::setPlatformShadow(const FloatSize& size, float blurFloat, const Color& color, ColorSpace colorSpace) { if (paintingDisabled()) return; // Detect when there's no effective shadow and clear the looper. if (!size.width() && !size.height() && !blurFloat) { platformContext()->setDrawLooper(0); return; } double width = size.width(); double height = size.height(); double blur = blurFloat; uint32_t mfFlags = SkBlurMaskFilter::kHighQuality_BlurFlag; SkXfermode::Mode colorMode = SkXfermode::kSrc_Mode; if (m_state.shadowsIgnoreTransforms) { // Currently only the GraphicsContext associated with the // CanvasRenderingContext for HTMLCanvasElement have shadows ignore // Transforms. So with this flag set, we know this state is associated // with a CanvasRenderingContext. mfFlags |= SkBlurMaskFilter::kIgnoreTransform_BlurFlag; // CSS wants us to ignore the original's alpha, but Canvas wants us to // modulate with it. Using shadowsIgnoreTransforms to tell us that we're // in a Canvas, we change the colormode to kDst_Mode, so we don't overwrite // it with our layer's (default opaque-black) color. colorMode = SkXfermode::kDst_Mode; // CG uses natural orientation for Y axis, but the HTML5 canvas spec // does not. // So we now flip the height since it was flipped in // CanvasRenderingContext in order to work with CG. height = -height; } SkColor c; if (color.isValid()) c = color.rgb(); else c = SkColorSetARGB(0xFF/3, 0, 0, 0); // "std" apple shadow color. // TODO(tc): Should we have a max value for the blur? CG clamps at 1000.0 // for perf reasons. SkLayerDrawLooper* dl = new SkLayerDrawLooper; SkAutoUnref aur(dl); // top layer, we just draw unchanged dl->addLayer(); // lower layer contains our offset, blur, and colorfilter SkLayerDrawLooper::LayerInfo info; info.fPaintBits |= SkLayerDrawLooper::kMaskFilter_Bit; // our blur info.fPaintBits |= SkLayerDrawLooper::kColorFilter_Bit; info.fColorMode = colorMode; info.fOffset.set(width, height); info.fPostTranslate = m_state.shadowsIgnoreTransforms; SkMaskFilter* mf = SkBlurMaskFilter::Create(blur / 2, SkBlurMaskFilter::kNormal_BlurStyle, mfFlags); SkColorFilter* cf = SkColorFilter::CreateModeFilter(c, SkXfermode::kSrcIn_Mode); SkPaint* paint = dl->addLayer(info); SkSafeUnref(paint->setMaskFilter(mf)); SkSafeUnref(paint->setColorFilter(cf)); // dl is now built, just install it platformContext()->setDrawLooper(dl); }
virtual void onDrawContent(SkCanvas* canvas) { drawBG(canvas); SkBlurMaskFilter::BlurStyle NONE = SkBlurMaskFilter::BlurStyle(-999); static const struct { SkBlurMaskFilter::BlurStyle fStyle; int fCx, fCy; } gRecs[] = { { NONE, 0, 0 }, { SkBlurMaskFilter::kInner_BlurStyle, -1, 0 }, { SkBlurMaskFilter::kNormal_BlurStyle, 0, 1 }, { SkBlurMaskFilter::kSolid_BlurStyle, 0, -1 }, { SkBlurMaskFilter::kOuter_BlurStyle, 1, 0 }, }; SkPaint paint; paint.setAntiAlias(true); paint.setTextSize(25); canvas->translate(-40, 0); SkBlurMaskFilter::BlurFlags flags = SkBlurMaskFilter::kNone_BlurFlag; for (int j = 0; j < 2; j++) { canvas->save(); paint.setColor(SK_ColorBLUE); for (size_t i = 0; i < SK_ARRAY_COUNT(gRecs); i++) { if (gRecs[i].fStyle != NONE) { SkMaskFilter* mf = SkBlurMaskFilter::Create(20, gRecs[i].fStyle, flags); paint.setMaskFilter(mf)->unref(); } else { paint.setMaskFilter(NULL); } canvas->drawCircle(200 + gRecs[i].fCx*100.f, 200 + gRecs[i].fCy*100.f, 50, paint); } // draw text { SkMaskFilter* mf = SkBlurMaskFilter::Create(4, SkBlurMaskFilter::kNormal_BlurStyle, flags); paint.setMaskFilter(mf)->unref(); SkScalar x = SkIntToScalar(70); SkScalar y = SkIntToScalar(400); paint.setColor(SK_ColorBLACK); canvas->drawText("Hamburgefons Style", 18, x, y, paint); canvas->drawText("Hamburgefons Style", 18, x, y + SkIntToScalar(50), paint); paint.setMaskFilter(NULL); paint.setColor(SK_ColorWHITE); x -= SkIntToScalar(2); y -= SkIntToScalar(2); canvas->drawText("Hamburgefons Style", 18, x, y, paint); } canvas->restore(); flags = SkBlurMaskFilter::kHighQuality_BlurFlag; canvas->translate(350, 0); } }
virtual void onDraw(SkCanvas* canvas) { drawBG(canvas); //return; canvas->translate(SkIntToScalar(10), SkIntToScalar(10)); SkPaint paint; paint.setAntiAlias(true); if (true) { canvas->drawColor(SK_ColorBLACK); paint.setTextSize(24); paint.setColor(SK_ColorWHITE); canvas->translate(10, 30); static const SkBlurMaskFilter::BlurStyle gStyle[] = { SkBlurMaskFilter::kNormal_BlurStyle, SkBlurMaskFilter::kInner_BlurStyle, SkBlurMaskFilter::kOuter_BlurStyle, SkBlurMaskFilter::kSolid_BlurStyle, }; for (int x = 0; x < 5; x++) { SkMaskFilter* mf; SkScalar radius = 4; for (int y = 0; y < 10; y++) { if (x) { mf = SkBlurMaskFilter::Create(radius, gStyle[x - 1]); paint.setMaskFilter(mf)->unref(); } canvas->drawText("Title Bar", 9, x*100, y*30, paint); radius *= 0.75f; } } return; } paint.setColor(SK_ColorBLUE); #if 1 SkPath p; float r = rand.nextUScalar1() + 0.5f; SkScalar x = 0, y = 0; p.moveTo(x, y); #if 0 p.cubicTo(x-75*r, y+75*r, x-40*r, y+125*r, x, y+85*r); p.cubicTo(x+40*r, y+125*r, x+75*r, y+75*r, x, y); #else p.cubicTo(x+75*r, y+75*r, x+40*r, y+125*r, x, y+85*r); p.cubicTo(x-40*r, y+125*r, x-75*r, y+75*r, x, y); #endif p.close(); fPath = p; fPath.offset(100, 0); #endif fPath.setFillType(SkPath::kWinding_FillType); drawSet(canvas, &paint); canvas->translate(0, fPath.getBounds().height() * 5 / 4); fPath.setFillType(SkPath::kEvenOdd_FillType); drawSet(canvas, &paint); }
static void do_fuzz(SkCanvas* canvas) { SkPath path; SkPaint paint; paint.setAntiAlias(true); for (int i=0;i<100;i++) { switch (R(33)) { case 0: paint.setColor(make_fill()); break; case 1: paint.setAlpha(gRand.nextU() & 0xFF); break; case 2: { SkXfermode::Mode mode; switch (R(3)) { case 0: mode = SkXfermode::kSrc_Mode; break; case 1: mode = SkXfermode::kXor_Mode; break; case 2: default: // silence warning mode = SkXfermode::kSrcOver_Mode; break; } paint.setXfermodeMode(mode); } break; case 3: switch (R(2)) { case 0: paint.setStrokeCap(SkPaint::kRound_Cap); break; case 1: paint.setStrokeCap(SkPaint::kButt_Cap); break; } break; case 4: switch (R(2)) { case 0: paint.setStrokeJoin(SkPaint::kRound_Join); break; case 1: paint.setStrokeJoin(SkPaint::kMiter_Join); break; } break; case 5: paint.setStrokeWidth(make_number()); break; case 6: paint.setStrokeMiter(make_number()); break; case 7: if (quick == true) break; SkSafeUnref(paint.setMaskFilter(SkBlurMaskFilter::Create(kNormal_SkBlurStyle, make_number()))); break; case 8: if (quick == true) break; //ctx.shadowColor = make_fill(); break; case 9: if (quick == true) break; //ctx.shadowOffsetX = make_number(); //ctx.shadowOffsetY = make_number(); break; case 10: canvas->restore(); break; case 11: canvas->rotate(make_number()); break; case 12: canvas->save(); break; case 13: canvas->scale(-1,-1); break; case 14: if (quick == true) break; if (transval == 0) { transval = make_number(); canvas->translate(transval,0); } else { canvas->translate(-transval,0); transval = 0; } break; case 15: { SkRect r; r.set(make_number(),make_number(),make_number(),make_number()); SkPaint::Style s = paint.getStyle(); paint.setStyle(SkPaint::kFill_Style); canvas->drawRect(r, paint); paint.setStyle(s); // clearrect } break; case 16: if (quick == true) break; // ctx.drawImage(imgObj,make_number(),make_number(),make_number(),make_number(),make_number(),make_number(),make_number(),make_number()); break; case 17: { SkRect r; r.set(make_number(),make_number(),make_number(),make_number()); SkPaint::Style s = paint.getStyle(); paint.setStyle(SkPaint::kFill_Style); canvas->drawRect(r, paint); paint.setStyle(s); } break; case 18: path.reset(); break; case 19: // ctx.clip() is evil. break; case 20: path.close(); break; case 21: { SkPaint::Style s = paint.getStyle(); paint.setStyle(SkPaint::kFill_Style); canvas->drawPath(path, paint); paint.setStyle(s); } break; case 22: { SkPaint::Style s = paint.getStyle(); paint.setStyle(SkPaint::kFill_Style); canvas->drawPath(path, paint); paint.setStyle(s); } break; case 23: { SkRect r; r.set(make_number(),make_number(),make_number(),make_number()); SkPaint::Style s = paint.getStyle(); paint.setStyle(SkPaint::kStroke_Style); canvas->drawRect(r, paint); paint.setStyle(s); } break; case 24: if (quick == true) break; //ctx.arc(make_number(),make_number(),make_number(),make_number(),make_number(),true); break; case 25: if (quick == true) break; //ctx.arcTo(make_number(),make_number(),make_number(),make_number(),make_number()); break; case 26: if (quick == true) break; //ctx.bezierCurveTo(make_number(),make_number(),make_number(),make_number(),make_number(),make_number()); break; case 27: path.lineTo(make_number(),make_number()); break; case 28: path.moveTo(make_number(),make_number()); break; case 29: if (quick == true) break; path.quadTo(make_number(),make_number(),make_number(),make_number()); break; case 30: { if (quick == true) break; SkMatrix matrix; set2x3(&matrix, make_number(),make_number(),make_number(),make_number(),make_number(),make_number()); canvas->concat(matrix); } break; case 31: { if (quick == true) break; SkMatrix matrix; set2x3(&matrix, make_number(),make_number(),make_number(),make_number(),make_number(),make_number()); canvas->setMatrix(matrix); } break; case 32: if (scale_large == true) { switch (scval) { case 0: canvas->scale(-1000000000,1); canvas->scale(-1000000000,1); scval = 1; break; case 1: canvas->scale(-.000000001f,1); scval = 2; break; case 2: canvas->scale(-.000000001f,1); scval = 0; break; } } break; } } }
void onDraw(SkCanvas* canvas) override { constexpr SkScalar kMaxR = kMaxRadius + kMaxBlurRadius; auto almostCircleMaker = [] (SkScalar radius, SkPath* dst) { dst->reset(); dst->addArc(SkRect::MakeXYWH(-radius, -radius, 2 * radius, 2 * radius), 0, 355); dst->setIsVolatile(true); dst->close(); }; auto blurMaker = [] (SkScalar radius) ->sk_sp<SkMaskFilter> { return SkBlurMaskFilter::Make(kNormal_SkBlurStyle, SkBlurMask::ConvertRadiusToSigma(radius), SkBlurMaskFilter::kHighQuality_BlurFlag); }; SkPaint paint; paint.setColor(SK_ColorBLACK); if (this->getMode() == kSample_Mode) { paint.setMaskFilter(blurMaker(fAnimBlurRadius)); SkISize size = canvas->getBaseLayerSize(); SkPath almostCircle; almostCircleMaker(fAnimRadius, &almostCircle); canvas->save(); canvas->translate(size.fWidth / 2.f, size.fHeight / 4.f); canvas->drawCircle(0, 0, fAnimRadius, paint); canvas->translate(0, 2 * kMaxR); canvas->drawPath(almostCircle, paint); canvas->restore(); } else { bool benchMode = this->getMode() == kBench_Mode; canvas->save(); constexpr SkScalar kPad = 5; constexpr SkScalar kRadiusSteps = 5; constexpr SkScalar kBlurRadiusSteps = 5; canvas->translate(kPad + kMinRadius + kMaxBlurRadius, kPad + kMinRadius + kMaxBlurRadius); constexpr SkScalar kDeltaRadius = (kMaxRadius - kMinRadius) / kRadiusSteps; constexpr SkScalar kDeltaBlurRadius = (kMaxBlurRadius - kMinBlurRadius) / kBlurRadiusSteps; SkScalar lineWidth = 0; if (!benchMode) { for (int r = 0; r < kRadiusSteps - 1; ++r) { const SkScalar radius = r * kDeltaRadius + kMinRadius; lineWidth += 2 * (radius + kMaxBlurRadius) + kPad; } } for (int br = 0; br < kBlurRadiusSteps; ++br) { SkScalar blurRadius = br * kDeltaBlurRadius + kMinBlurRadius; if (benchMode) { blurRadius += fRandom.nextSScalar1() * kDeltaBlurRadius; } const SkScalar maxRowR = blurRadius + kMaxRadius; paint.setMaskFilter(blurMaker(blurRadius)); canvas->save(); for (int r = 0; r < kRadiusSteps; ++r) { SkScalar radius = r * kDeltaRadius + kMinRadius; if (benchMode) { radius += fRandom.nextSScalar1() * kDeltaRadius; } SkPath almostCircle; if (!benchMode) { almostCircleMaker(radius, &almostCircle); } canvas->save(); canvas->drawCircle(0, 0, radius, paint); canvas->translate(0, 2 * maxRowR + kPad); if (!benchMode) { canvas->drawPath(almostCircle, paint); } canvas->restore(); const SkScalar maxColR = radius + kMaxBlurRadius; canvas->translate(maxColR * 2 + kPad, 0); } canvas->restore(); if (!benchMode) { SkPaint blackPaint; blackPaint.setColor(SK_ColorBLACK); const SkScalar lineY = 3 * maxRowR + 1.5f * kPad; if (br != kBlurRadiusSteps - 1) { canvas->drawLine(0, lineY, lineWidth, lineY, blackPaint); } } canvas->translate(0, maxRowR * 4 + 2 * kPad); } canvas->restore(); } }