blob: f8dd5e70738e0b4f85c1dfc1ca6052e30a24d42c [file] [log] [blame]
Mike Klein8f4e2242019-03-20 11:59:00 -05001/*
2 * Copyright 2012 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#include "DrawCommand.h"
9
10#include <algorithm>
11#include "JsonWriteBuffer.h"
12#include "SkAutoMalloc.h"
13#include "SkCanvasPriv.h"
14#include "SkClipOpPriv.h"
15#include "SkColorFilter.h"
16#include "SkDashPathEffect.h"
17#include "SkDrawable.h"
18#include "SkImageFilter.h"
19#include "SkLatticeIter.h"
20#include "SkMaskFilterBase.h"
21#include "SkPaintDefaults.h"
22#include "SkPathEffect.h"
23#include "SkPicture.h"
24#include "SkPngEncoder.h"
25#include "SkReadBuffer.h"
26#include "SkRectPriv.h"
27#include "SkShadowFlags.h"
28#include "SkTHash.h"
29#include "SkTextBlobPriv.h"
30#include "SkTypeface.h"
31#include "SkWriteBuffer.h"
32
Mike Klein17428132019-03-20 13:02:32 -050033#define DEBUGCANVAS_ATTRIBUTE_COMMAND "command"
34#define DEBUGCANVAS_ATTRIBUTE_VISIBLE "visible"
35#define DEBUGCANVAS_ATTRIBUTE_MATRIX "matrix"
36#define DEBUGCANVAS_ATTRIBUTE_DRAWDEPTHTRANS "drawDepthTranslation"
37#define DEBUGCANVAS_ATTRIBUTE_COORDS "coords"
38#define DEBUGCANVAS_ATTRIBUTE_EDGING "edging"
39#define DEBUGCANVAS_ATTRIBUTE_HINTING "hinting"
40#define DEBUGCANVAS_ATTRIBUTE_BOUNDS "bounds"
41#define DEBUGCANVAS_ATTRIBUTE_PAINT "paint"
42#define DEBUGCANVAS_ATTRIBUTE_OUTER "outer"
43#define DEBUGCANVAS_ATTRIBUTE_INNER "inner"
44#define DEBUGCANVAS_ATTRIBUTE_MODE "mode"
45#define DEBUGCANVAS_ATTRIBUTE_POINTS "points"
46#define DEBUGCANVAS_ATTRIBUTE_PATH "path"
47#define DEBUGCANVAS_ATTRIBUTE_TEXT "text"
48#define DEBUGCANVAS_ATTRIBUTE_COLOR "color"
49#define DEBUGCANVAS_ATTRIBUTE_ALPHA "alpha"
50#define DEBUGCANVAS_ATTRIBUTE_BLENDMODE "blendMode"
51#define DEBUGCANVAS_ATTRIBUTE_STYLE "style"
52#define DEBUGCANVAS_ATTRIBUTE_STROKEWIDTH "strokeWidth"
53#define DEBUGCANVAS_ATTRIBUTE_STROKEMITER "strokeMiter"
54#define DEBUGCANVAS_ATTRIBUTE_STROKEJOIN "strokeJoin"
55#define DEBUGCANVAS_ATTRIBUTE_CAP "cap"
56#define DEBUGCANVAS_ATTRIBUTE_ANTIALIAS "antiAlias"
57#define DEBUGCANVAS_ATTRIBUTE_DITHER "dither"
58#define DEBUGCANVAS_ATTRIBUTE_FAKEBOLDTEXT "fakeBoldText"
59#define DEBUGCANVAS_ATTRIBUTE_LINEARTEXT "linearText"
60#define DEBUGCANVAS_ATTRIBUTE_SUBPIXELTEXT "subpixelText"
61#define DEBUGCANVAS_ATTRIBUTE_DEVKERNTEXT "devKernText"
62#define DEBUGCANVAS_ATTRIBUTE_LCDRENDERTEXT "lcdRenderText"
63#define DEBUGCANVAS_ATTRIBUTE_EMBEDDEDBITMAPTEXT "embeddedBitmapText"
64#define DEBUGCANVAS_ATTRIBUTE_AUTOHINTING "forceAutoHinting"
65#define DEBUGCANVAS_ATTRIBUTE_REGION "region"
66#define DEBUGCANVAS_ATTRIBUTE_REGIONOP "op"
67#define DEBUGCANVAS_ATTRIBUTE_EDGESTYLE "edgeStyle"
68#define DEBUGCANVAS_ATTRIBUTE_DEVICEREGION "deviceRegion"
69#define DEBUGCANVAS_ATTRIBUTE_BLUR "blur"
70#define DEBUGCANVAS_ATTRIBUTE_SIGMA "sigma"
71#define DEBUGCANVAS_ATTRIBUTE_QUALITY "quality"
72#define DEBUGCANVAS_ATTRIBUTE_TEXTSIZE "textSize"
73#define DEBUGCANVAS_ATTRIBUTE_TEXTSCALEX "textScaleX"
74#define DEBUGCANVAS_ATTRIBUTE_TEXTSKEWX "textSkewX"
75#define DEBUGCANVAS_ATTRIBUTE_DASHING "dashing"
76#define DEBUGCANVAS_ATTRIBUTE_INTERVALS "intervals"
77#define DEBUGCANVAS_ATTRIBUTE_PHASE "phase"
78#define DEBUGCANVAS_ATTRIBUTE_FILLTYPE "fillType"
79#define DEBUGCANVAS_ATTRIBUTE_VERBS "verbs"
80#define DEBUGCANVAS_ATTRIBUTE_NAME "name"
81#define DEBUGCANVAS_ATTRIBUTE_DATA "data"
82#define DEBUGCANVAS_ATTRIBUTE_VALUES "values"
83#define DEBUGCANVAS_ATTRIBUTE_SHADER "shader"
84#define DEBUGCANVAS_ATTRIBUTE_PATHEFFECT "pathEffect"
85#define DEBUGCANVAS_ATTRIBUTE_MASKFILTER "maskFilter"
86#define DEBUGCANVAS_ATTRIBUTE_XFERMODE "xfermode"
87#define DEBUGCANVAS_ATTRIBUTE_LOOPER "looper"
88#define DEBUGCANVAS_ATTRIBUTE_BACKDROP "backdrop"
89#define DEBUGCANVAS_ATTRIBUTE_COLORFILTER "colorfilter"
90#define DEBUGCANVAS_ATTRIBUTE_IMAGEFILTER "imagefilter"
91#define DEBUGCANVAS_ATTRIBUTE_IMAGE "image"
92#define DEBUGCANVAS_ATTRIBUTE_BITMAP "bitmap"
93#define DEBUGCANVAS_ATTRIBUTE_SRC "src"
94#define DEBUGCANVAS_ATTRIBUTE_DST "dst"
95#define DEBUGCANVAS_ATTRIBUTE_CENTER "center"
96#define DEBUGCANVAS_ATTRIBUTE_STRICT "strict"
97#define DEBUGCANVAS_ATTRIBUTE_DESCRIPTION "description"
98#define DEBUGCANVAS_ATTRIBUTE_X "x"
99#define DEBUGCANVAS_ATTRIBUTE_Y "y"
100#define DEBUGCANVAS_ATTRIBUTE_RUNS "runs"
101#define DEBUGCANVAS_ATTRIBUTE_POSITIONS "positions"
102#define DEBUGCANVAS_ATTRIBUTE_GLYPHS "glyphs"
103#define DEBUGCANVAS_ATTRIBUTE_FONT "font"
104#define DEBUGCANVAS_ATTRIBUTE_TYPEFACE "typeface"
105#define DEBUGCANVAS_ATTRIBUTE_CUBICS "cubics"
106#define DEBUGCANVAS_ATTRIBUTE_COLORS "colors"
107#define DEBUGCANVAS_ATTRIBUTE_TEXTURECOORDS "textureCoords"
108#define DEBUGCANVAS_ATTRIBUTE_FILTERQUALITY "filterQuality"
109#define DEBUGCANVAS_ATTRIBUTE_STARTANGLE "startAngle"
110#define DEBUGCANVAS_ATTRIBUTE_SWEEPANGLE "sweepAngle"
111#define DEBUGCANVAS_ATTRIBUTE_USECENTER "useCenter"
112#define DEBUGCANVAS_ATTRIBUTE_SHORTDESC "shortDesc"
113#define DEBUGCANVAS_ATTRIBUTE_UNIQUE_ID "uniqueID"
114#define DEBUGCANVAS_ATTRIBUTE_WIDTH "width"
115#define DEBUGCANVAS_ATTRIBUTE_HEIGHT "height"
116#define DEBUGCANVAS_ATTRIBUTE_ALPHA "alpha"
117#define DEBUGCANVAS_ATTRIBUTE_LATTICE "lattice"
118#define DEBUGCANVAS_ATTRIBUTE_LATTICEXCOUNT "xCount"
119#define DEBUGCANVAS_ATTRIBUTE_LATTICEYCOUNT "yCount"
120#define DEBUGCANVAS_ATTRIBUTE_LATTICEXDIVS "xDivs"
121#define DEBUGCANVAS_ATTRIBUTE_LATTICEYDIVS "yDivs"
122#define DEBUGCANVAS_ATTRIBUTE_LATTICEFLAGS "flags"
123#define DEBUGCANVAS_ATTRIBUTE_ZPLANE "zPlane"
124#define DEBUGCANVAS_ATTRIBUTE_LIGHTPOSITION "lightPositions"
125#define DEBUGCANVAS_ATTRIBUTE_AMBIENTCOLOR "ambientColor"
126#define DEBUGCANVAS_ATTRIBUTE_SPOTCOLOR "spotColor"
127#define DEBUGCANVAS_ATTRIBUTE_LIGHTRADIUS "lightRadius"
Mike Klein8f4e2242019-03-20 11:59:00 -0500128
Mike Klein17428132019-03-20 13:02:32 -0500129#define DEBUGCANVAS_VERB_MOVE "move"
130#define DEBUGCANVAS_VERB_LINE "line"
131#define DEBUGCANVAS_VERB_QUAD "quad"
132#define DEBUGCANVAS_VERB_CUBIC "cubic"
133#define DEBUGCANVAS_VERB_CONIC "conic"
134#define DEBUGCANVAS_VERB_CLOSE "close"
Mike Klein8f4e2242019-03-20 11:59:00 -0500135
Mike Klein17428132019-03-20 13:02:32 -0500136#define DEBUGCANVAS_STYLE_FILL "fill"
137#define DEBUGCANVAS_STYLE_STROKE "stroke"
138#define DEBUGCANVAS_STYLE_STROKEANDFILL "strokeAndFill"
Mike Klein8f4e2242019-03-20 11:59:00 -0500139
Mike Klein17428132019-03-20 13:02:32 -0500140#define DEBUGCANVAS_POINTMODE_POINTS "points"
141#define DEBUGCANVAS_POINTMODE_LINES "lines"
142#define DEBUGCANVAS_POINTMODE_POLYGON "polygon"
Mike Klein8f4e2242019-03-20 11:59:00 -0500143
Mike Klein17428132019-03-20 13:02:32 -0500144#define DEBUGCANVAS_REGIONOP_DIFFERENCE "difference"
145#define DEBUGCANVAS_REGIONOP_INTERSECT "intersect"
146#define DEBUGCANVAS_REGIONOP_UNION "union"
147#define DEBUGCANVAS_REGIONOP_XOR "xor"
148#define DEBUGCANVAS_REGIONOP_REVERSE_DIFFERENCE "reverseDifference"
149#define DEBUGCANVAS_REGIONOP_REPLACE "replace"
Mike Klein8f4e2242019-03-20 11:59:00 -0500150
Mike Klein17428132019-03-20 13:02:32 -0500151#define DEBUGCANVAS_BLURSTYLE_NORMAL "normal"
152#define DEBUGCANVAS_BLURSTYLE_SOLID "solid"
153#define DEBUGCANVAS_BLURSTYLE_OUTER "outer"
154#define DEBUGCANVAS_BLURSTYLE_INNER "inner"
Mike Klein8f4e2242019-03-20 11:59:00 -0500155
Mike Klein17428132019-03-20 13:02:32 -0500156#define DEBUGCANVAS_BLURQUALITY_LOW "low"
157#define DEBUGCANVAS_BLURQUALITY_HIGH "high"
Mike Klein8f4e2242019-03-20 11:59:00 -0500158
Mike Klein17428132019-03-20 13:02:32 -0500159#define DEBUGCANVAS_FILLTYPE_WINDING "winding"
160#define DEBUGCANVAS_FILLTYPE_EVENODD "evenOdd"
161#define DEBUGCANVAS_FILLTYPE_INVERSEWINDING "inverseWinding"
162#define DEBUGCANVAS_FILLTYPE_INVERSEEVENODD "inverseEvenOdd"
Mike Klein8f4e2242019-03-20 11:59:00 -0500163
Mike Klein17428132019-03-20 13:02:32 -0500164#define DEBUGCANVAS_CAP_BUTT "butt"
165#define DEBUGCANVAS_CAP_ROUND "round"
166#define DEBUGCANVAS_CAP_SQUARE "square"
Mike Klein8f4e2242019-03-20 11:59:00 -0500167
Mike Klein17428132019-03-20 13:02:32 -0500168#define DEBUGCANVAS_MITER_JOIN "miter"
169#define DEBUGCANVAS_ROUND_JOIN "round"
170#define DEBUGCANVAS_BEVEL_JOIN "bevel"
Mike Klein8f4e2242019-03-20 11:59:00 -0500171
Mike Klein17428132019-03-20 13:02:32 -0500172#define DEBUGCANVAS_COLORTYPE_ARGB4444 "ARGB4444"
173#define DEBUGCANVAS_COLORTYPE_RGBA8888 "RGBA8888"
174#define DEBUGCANVAS_COLORTYPE_BGRA8888 "BGRA8888"
175#define DEBUGCANVAS_COLORTYPE_565 "565"
176#define DEBUGCANVAS_COLORTYPE_GRAY8 "Gray8"
177#define DEBUGCANVAS_COLORTYPE_INDEX8 "Index8"
178#define DEBUGCANVAS_COLORTYPE_ALPHA8 "Alpha8"
Mike Klein8f4e2242019-03-20 11:59:00 -0500179
Mike Klein17428132019-03-20 13:02:32 -0500180#define DEBUGCANVAS_ALPHATYPE_OPAQUE "opaque"
181#define DEBUGCANVAS_ALPHATYPE_PREMUL "premul"
182#define DEBUGCANVAS_ALPHATYPE_UNPREMUL "unpremul"
183#define DEBUGCANVAS_ALPHATYPE_UNKNOWN "unknown"
Mike Klein8f4e2242019-03-20 11:59:00 -0500184
Mike Klein17428132019-03-20 13:02:32 -0500185#define DEBUGCANVAS_FILTERQUALITY_NONE "none"
186#define DEBUGCANVAS_FILTERQUALITY_LOW "low"
187#define DEBUGCANVAS_FILTERQUALITY_MEDIUM "medium"
188#define DEBUGCANVAS_FILTERQUALITY_HIGH "high"
Mike Klein8f4e2242019-03-20 11:59:00 -0500189
Mike Klein17428132019-03-20 13:02:32 -0500190#define DEBUGCANVAS_HINTING_NONE "none"
191#define DEBUGCANVAS_HINTING_SLIGHT "slight"
192#define DEBUGCANVAS_HINTING_NORMAL "normal"
193#define DEBUGCANVAS_HINTING_FULL "full"
Mike Klein8f4e2242019-03-20 11:59:00 -0500194
Mike Klein17428132019-03-20 13:02:32 -0500195#define DEBUGCANVAS_EDGING_ALIAS "alias"
196#define DEBUGCANVAS_EDGING_ANTIALIAS "antialias"
197#define DEBUGCANVAS_EDGING_SUBPIXELANTIALIAS "subpixelantialias"
Mike Klein8f4e2242019-03-20 11:59:00 -0500198
Mike Klein17428132019-03-20 13:02:32 -0500199#define DEBUGCANVAS_SHADOWFLAG_TRANSPARENT_OCC "transparentOccluder"
200#define DEBUGCANVAS_SHADOWFLAG_GEOMETRIC_ONLY "geometricOnly"
Mike Klein8f4e2242019-03-20 11:59:00 -0500201
202static SkString* str_append(SkString* str, const SkRect& r) {
203 str->appendf(" [%g %g %g %g]", r.left(), r.top(), r.right(), r.bottom());
204 return str;
205}
206
207DrawCommand::DrawCommand(OpType type) : fOpType(type), fVisible(true) {}
208
209const char* DrawCommand::GetCommandString(OpType type) {
210 switch (type) {
211 case kBeginDrawPicture_OpType: return "BeginDrawPicture";
212 case kClear_OpType: return "DrawClear";
213 case kClipPath_OpType: return "ClipPath";
214 case kClipRegion_OpType: return "ClipRegion";
215 case kClipRect_OpType: return "ClipRect";
216 case kClipRRect_OpType: return "ClipRRect";
217 case kConcat_OpType: return "Concat";
218 case kDrawAnnotation_OpType: return "DrawAnnotation";
219 case kDrawBitmap_OpType: return "DrawBitmap";
220 case kDrawBitmapLattice_OpType: return "DrawBitmapLattice";
221 case kDrawBitmapNine_OpType: return "DrawBitmapNine";
222 case kDrawBitmapRect_OpType: return "DrawBitmapRect";
223 case kDrawDRRect_OpType: return "DrawDRRect";
224 case kDrawImage_OpType: return "DrawImage";
225 case kDrawImageLattice_OpType: return "DrawImageLattice";
226 case kDrawImageNine_OpType: return "DrawImageNine";
227 case kDrawImageRect_OpType: return "DrawImageRect";
228 case kDrawOval_OpType: return "DrawOval";
229 case kDrawPaint_OpType: return "DrawPaint";
230 case kDrawPatch_OpType: return "DrawPatch";
231 case kDrawPath_OpType: return "DrawPath";
232 case kDrawArc_OpType: return "DrawArc";
233 case kDrawPoints_OpType: return "DrawPoints";
234 case kDrawRect_OpType: return "DrawRect";
235 case kDrawRRect_OpType: return "DrawRRect";
236 case kDrawRegion_OpType: return "DrawRegion";
237 case kDrawShadow_OpType: return "DrawShadow";
238 case kDrawTextBlob_OpType: return "DrawTextBlob";
239 case kDrawVertices_OpType: return "DrawVertices";
240 case kDrawAtlas_OpType: return "DrawAtlas";
241 case kDrawDrawable_OpType: return "DrawDrawable";
242 case kDrawEdgeAAQuad_OpType: return "DrawEdgeAAQuad";
243 case kDrawEdgeAAImageSet_OpType: return "DrawEdgeAAImageSet";
244 case kEndDrawPicture_OpType: return "EndDrawPicture";
245 case kRestore_OpType: return "Restore";
246 case kSave_OpType: return "Save";
247 case kSaveLayer_OpType: return "SaveLayer";
248 case kSetMatrix_OpType: return "SetMatrix";
249 default:
250 SkDebugf("OpType error 0x%08x\n", type);
251 SkASSERT(0);
252 break;
253 }
254 SkDEBUGFAIL("DrawType UNUSED\n");
255 return nullptr;
256}
257
258void DrawCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein17428132019-03-20 13:02:32 -0500259 writer.appendString(DEBUGCANVAS_ATTRIBUTE_COMMAND, this->GetCommandString(fOpType));
260 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_VISIBLE, this->isVisible());
Mike Klein8f4e2242019-03-20 11:59:00 -0500261}
262
263namespace {
264
265void xlate_and_scale_to_bounds(SkCanvas* canvas, const SkRect& bounds) {
266 const SkISize& size = canvas->getBaseLayerSize();
267
268 static const SkScalar kInsetFrac = 0.9f; // Leave a border around object
269
270 canvas->translate(size.fWidth / 2.0f, size.fHeight / 2.0f);
271 if (bounds.width() > bounds.height()) {
272 canvas->scale(SkDoubleToScalar((kInsetFrac * size.fWidth) / bounds.width()),
273 SkDoubleToScalar((kInsetFrac * size.fHeight) / bounds.width()));
274 } else {
275 canvas->scale(SkDoubleToScalar((kInsetFrac * size.fWidth) / bounds.height()),
276 SkDoubleToScalar((kInsetFrac * size.fHeight) / bounds.height()));
277 }
278 canvas->translate(-bounds.centerX(), -bounds.centerY());
279}
280
281void render_path(SkCanvas* canvas, const SkPath& path) {
282 canvas->clear(0xFFFFFFFF);
283
284 const SkRect& bounds = path.getBounds();
285 if (bounds.isEmpty()) {
286 return;
287 }
288
289 SkAutoCanvasRestore acr(canvas, true);
290 xlate_and_scale_to_bounds(canvas, bounds);
291
292 SkPaint p;
293 p.setColor(SK_ColorBLACK);
294 p.setStyle(SkPaint::kStroke_Style);
295
296 canvas->drawPath(path, p);
297}
298
299void render_region(SkCanvas* canvas, const SkRegion& region) {
300 canvas->clear(0xFFFFFFFF);
301
302 const SkIRect& bounds = region.getBounds();
303 if (bounds.isEmpty()) {
304 return;
305 }
306
307 SkAutoCanvasRestore acr(canvas, true);
308 xlate_and_scale_to_bounds(canvas, SkRect::Make(bounds));
309
310 SkPaint p;
311 p.setColor(SK_ColorBLACK);
312 p.setStyle(SkPaint::kStroke_Style);
313
314 canvas->drawRegion(region, p);
315}
316
317void render_bitmap(SkCanvas* canvas, const SkBitmap& input, const SkRect* srcRect = nullptr) {
318 const SkISize& size = canvas->getBaseLayerSize();
319
320 SkScalar xScale = SkIntToScalar(size.fWidth - 2) / input.width();
321 SkScalar yScale = SkIntToScalar(size.fHeight - 2) / input.height();
322
323 if (input.width() > input.height()) {
324 yScale *= input.height() / (float)input.width();
325 } else {
326 xScale *= input.width() / (float)input.height();
327 }
328
329 SkRect dst = SkRect::MakeXYWH(
330 SK_Scalar1, SK_Scalar1, xScale * input.width(), yScale * input.height());
331
332 static const int kNumBlocks = 8;
333
334 canvas->clear(0xFFFFFFFF);
335 SkISize block = {canvas->imageInfo().width() / kNumBlocks,
336 canvas->imageInfo().height() / kNumBlocks};
337 for (int y = 0; y < kNumBlocks; ++y) {
338 for (int x = 0; x < kNumBlocks; ++x) {
339 SkPaint paint;
340 paint.setColor((x + y) % 2 ? SK_ColorLTGRAY : SK_ColorDKGRAY);
341 SkRect r = SkRect::MakeXYWH(SkIntToScalar(x * block.width()),
342 SkIntToScalar(y * block.height()),
343 SkIntToScalar(block.width()),
344 SkIntToScalar(block.height()));
345 canvas->drawRect(r, paint);
346 }
347 }
348
349 canvas->drawBitmapRect(input, dst, nullptr);
350
351 if (srcRect) {
352 SkRect r = SkRect::MakeLTRB(srcRect->fLeft * xScale + SK_Scalar1,
353 srcRect->fTop * yScale + SK_Scalar1,
354 srcRect->fRight * xScale + SK_Scalar1,
355 srcRect->fBottom * yScale + SK_Scalar1);
356 SkPaint p;
357 p.setColor(SK_ColorRED);
358 p.setStyle(SkPaint::kStroke_Style);
359
360 canvas->drawRect(r, p);
361 }
362}
363
364void render_rrect(SkCanvas* canvas, const SkRRect& rrect) {
365 canvas->clear(0xFFFFFFFF);
366 canvas->save();
367
368 const SkRect& bounds = rrect.getBounds();
369
370 xlate_and_scale_to_bounds(canvas, bounds);
371
372 SkPaint p;
373 p.setColor(SK_ColorBLACK);
374 p.setStyle(SkPaint::kStroke_Style);
375
376 canvas->drawRRect(rrect, p);
377 canvas->restore();
378}
379
380void render_drrect(SkCanvas* canvas, const SkRRect& outer, const SkRRect& inner) {
381 canvas->clear(0xFFFFFFFF);
382 canvas->save();
383
384 const SkRect& bounds = outer.getBounds();
385
386 xlate_and_scale_to_bounds(canvas, bounds);
387
388 SkPaint p;
389 p.setColor(SK_ColorBLACK);
390 p.setStyle(SkPaint::kStroke_Style);
391
392 canvas->drawDRRect(outer, inner, p);
393 canvas->restore();
394}
395
396void render_shadow(SkCanvas* canvas, const SkPath& path, SkDrawShadowRec rec) {
397 canvas->clear(0xFFFFFFFF);
398
399 const SkRect& bounds = path.getBounds();
400 if (bounds.isEmpty()) {
401 return;
402 }
403
404 SkAutoCanvasRestore acr(canvas, true);
405 xlate_and_scale_to_bounds(canvas, bounds);
406
407 rec.fAmbientColor = SK_ColorBLACK;
408 rec.fSpotColor = SK_ColorBLACK;
409 canvas->private_draw_shadow_rec(path, rec);
410}
411
412static const char* const gBlendModeMap[] = {
413 "clear", "src", "dst", "srcOver", "dstOver", "srcIn", "dstIn",
414 "srcOut", "dstOut", "srcATop", "dstATop", "xor", "plus", "modulate",
415
416 "screen",
417
418 "overlay", "darken", "lighten", "colorDodge", "colorBurn", "hardLight", "softLight",
419 "difference", "exclusion", "multiply",
420
421 "hue", "saturation", "color", "luminosity",
422};
423
424static_assert(SK_ARRAY_COUNT(gBlendModeMap) == static_cast<size_t>(SkBlendMode::kLastMode) + 1,
425 "blendMode mismatch");
426static_assert(SK_ARRAY_COUNT(gBlendModeMap) == static_cast<size_t>(SkBlendMode::kLuminosity) + 1,
427 "blendMode mismatch");
428
429void apply_paint_blend_mode(const SkPaint& paint, SkJSONWriter& writer) {
430 const auto mode = paint.getBlendMode();
431 if (mode != SkBlendMode::kSrcOver) {
432 SkASSERT(static_cast<size_t>(mode) < SK_ARRAY_COUNT(gBlendModeMap));
Mike Klein17428132019-03-20 13:02:32 -0500433 writer.appendString(DEBUGCANVAS_ATTRIBUTE_BLENDMODE,
Mike Klein8f4e2242019-03-20 11:59:00 -0500434 gBlendModeMap[static_cast<size_t>(mode)]);
435 }
436}
437
438}; // namespace
439
440void DrawCommand::MakeJsonColor(SkJSONWriter& writer, const SkColor color) {
441 writer.beginArray(nullptr, false);
442 writer.appendS32(SkColorGetA(color));
443 writer.appendS32(SkColorGetR(color));
444 writer.appendS32(SkColorGetG(color));
445 writer.appendS32(SkColorGetB(color));
446 writer.endArray();
447}
448
449void DrawCommand::MakeJsonColor4f(SkJSONWriter& writer, const SkColor4f& color) {
450 writer.beginArray(nullptr, false);
451 writer.appendFloat(color.fA);
452 writer.appendFloat(color.fR);
453 writer.appendFloat(color.fG);
454 writer.appendFloat(color.fB);
455 writer.endArray();
456}
457
458void DrawCommand::MakeJsonPoint(SkJSONWriter& writer, const SkPoint& point) {
459 writer.beginArray(nullptr, false);
460 writer.appendFloat(point.x());
461 writer.appendFloat(point.y());
462 writer.endArray();
463}
464
465void DrawCommand::MakeJsonPoint(SkJSONWriter& writer, SkScalar x, SkScalar y) {
466 writer.beginArray(nullptr, false);
467 writer.appendFloat(x);
468 writer.appendFloat(y);
469 writer.endArray();
470}
471
472void DrawCommand::MakeJsonPoint3(SkJSONWriter& writer, const SkPoint3& point) {
473 writer.beginArray(nullptr, false);
474 writer.appendFloat(point.x());
475 writer.appendFloat(point.y());
476 writer.appendFloat(point.z());
477 writer.endArray();
478}
479
480void DrawCommand::MakeJsonRect(SkJSONWriter& writer, const SkRect& rect) {
481 writer.beginArray(nullptr, false);
482 writer.appendFloat(rect.left());
483 writer.appendFloat(rect.top());
484 writer.appendFloat(rect.right());
485 writer.appendFloat(rect.bottom());
486 writer.endArray();
487}
488
489void DrawCommand::MakeJsonIRect(SkJSONWriter& writer, const SkIRect& rect) {
490 writer.beginArray(nullptr, false);
491 writer.appendS32(rect.left());
492 writer.appendS32(rect.top());
493 writer.appendS32(rect.right());
494 writer.appendS32(rect.bottom());
495 writer.endArray();
496}
497
498static void make_json_rrect(SkJSONWriter& writer, const SkRRect& rrect) {
499 writer.beginArray(nullptr, false);
500 DrawCommand::MakeJsonRect(writer, rrect.rect());
501 DrawCommand::MakeJsonPoint(writer, rrect.radii(SkRRect::kUpperLeft_Corner));
502 DrawCommand::MakeJsonPoint(writer, rrect.radii(SkRRect::kUpperRight_Corner));
503 DrawCommand::MakeJsonPoint(writer, rrect.radii(SkRRect::kLowerRight_Corner));
504 DrawCommand::MakeJsonPoint(writer, rrect.radii(SkRRect::kLowerLeft_Corner));
505 writer.endArray();
506}
507
508void DrawCommand::MakeJsonMatrix(SkJSONWriter& writer, const SkMatrix& matrix) {
509 writer.beginArray();
510 for (int r = 0; r < 3; ++r) {
511 writer.beginArray(nullptr, false);
512 for (int c = 0; c < 3; ++c) {
513 writer.appendFloat(matrix[r * 3 + c]);
514 }
515 writer.endArray();
516 }
517 writer.endArray();
518}
519
520void DrawCommand::MakeJsonPath(SkJSONWriter& writer, const SkPath& path) {
521 writer.beginObject();
522 switch (path.getFillType()) {
523 case SkPath::kWinding_FillType:
Mike Klein17428132019-03-20 13:02:32 -0500524 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILLTYPE, DEBUGCANVAS_FILLTYPE_WINDING);
Mike Klein8f4e2242019-03-20 11:59:00 -0500525 break;
526 case SkPath::kEvenOdd_FillType:
Mike Klein17428132019-03-20 13:02:32 -0500527 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILLTYPE, DEBUGCANVAS_FILLTYPE_EVENODD);
Mike Klein8f4e2242019-03-20 11:59:00 -0500528 break;
529 case SkPath::kInverseWinding_FillType:
Mike Klein17428132019-03-20 13:02:32 -0500530 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILLTYPE,
531 DEBUGCANVAS_FILLTYPE_INVERSEWINDING);
Mike Klein8f4e2242019-03-20 11:59:00 -0500532 break;
533 case SkPath::kInverseEvenOdd_FillType:
Mike Klein17428132019-03-20 13:02:32 -0500534 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILLTYPE,
535 DEBUGCANVAS_FILLTYPE_INVERSEEVENODD);
Mike Klein8f4e2242019-03-20 11:59:00 -0500536 break;
537 }
Mike Klein17428132019-03-20 13:02:32 -0500538 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_VERBS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500539 SkPath::Iter iter(path, false);
540 SkPoint pts[4];
541 SkPath::Verb verb;
542 while ((verb = iter.next(pts)) != SkPath::kDone_Verb) {
543 if (verb == SkPath::kClose_Verb) {
Mike Klein17428132019-03-20 13:02:32 -0500544 writer.appendString(DEBUGCANVAS_VERB_CLOSE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500545 continue;
546 }
547 writer.beginObject(); // verb
548 switch (verb) {
549 case SkPath::kLine_Verb: {
Mike Klein17428132019-03-20 13:02:32 -0500550 writer.appendName(DEBUGCANVAS_VERB_LINE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500551 MakeJsonPoint(writer, pts[1]);
552 break;
553 }
554 case SkPath::kQuad_Verb: {
Mike Klein17428132019-03-20 13:02:32 -0500555 writer.beginArray(DEBUGCANVAS_VERB_QUAD);
Mike Klein8f4e2242019-03-20 11:59:00 -0500556 MakeJsonPoint(writer, pts[1]);
557 MakeJsonPoint(writer, pts[2]);
558 writer.endArray(); // quad coords
559 break;
560 }
561 case SkPath::kCubic_Verb: {
Mike Klein17428132019-03-20 13:02:32 -0500562 writer.beginArray(DEBUGCANVAS_VERB_CUBIC);
Mike Klein8f4e2242019-03-20 11:59:00 -0500563 MakeJsonPoint(writer, pts[1]);
564 MakeJsonPoint(writer, pts[2]);
565 MakeJsonPoint(writer, pts[3]);
566 writer.endArray(); // cubic coords
567 break;
568 }
569 case SkPath::kConic_Verb: {
Mike Klein17428132019-03-20 13:02:32 -0500570 writer.beginArray(DEBUGCANVAS_VERB_CONIC);
Mike Klein8f4e2242019-03-20 11:59:00 -0500571 MakeJsonPoint(writer, pts[1]);
572 MakeJsonPoint(writer, pts[2]);
573 writer.appendFloat(iter.conicWeight());
574 writer.endArray(); // conic coords
575 break;
576 }
577 case SkPath::kMove_Verb: {
Mike Klein17428132019-03-20 13:02:32 -0500578 writer.appendName(DEBUGCANVAS_VERB_MOVE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500579 MakeJsonPoint(writer, pts[0]);
580 break;
581 }
582 case SkPath::kClose_Verb:
583 case SkPath::kDone_Verb:
584 // Unreachable
585 break;
586 }
587 writer.endObject(); // verb
588 }
589 writer.endArray(); // verbs
590 writer.endObject(); // path
591}
592
593void DrawCommand::MakeJsonRegion(SkJSONWriter& writer, const SkRegion& region) {
594 // TODO: Actually serialize the rectangles, rather than just devolving to path
595 SkPath path;
596 region.getBoundaryPath(&path);
597 MakeJsonPath(writer, path);
598}
599
600static const char* regionop_name(SkClipOp op) {
601 switch (op) {
Mike Klein17428132019-03-20 13:02:32 -0500602 case kDifference_SkClipOp: return DEBUGCANVAS_REGIONOP_DIFFERENCE;
603 case kIntersect_SkClipOp: return DEBUGCANVAS_REGIONOP_INTERSECT;
604 case kUnion_SkClipOp: return DEBUGCANVAS_REGIONOP_UNION;
605 case kXOR_SkClipOp: return DEBUGCANVAS_REGIONOP_XOR;
606 case kReverseDifference_SkClipOp: return DEBUGCANVAS_REGIONOP_REVERSE_DIFFERENCE;
607 case kReplace_SkClipOp: return DEBUGCANVAS_REGIONOP_REPLACE;
Mike Klein8f4e2242019-03-20 11:59:00 -0500608 default: SkASSERT(false); return "<invalid region op>";
609 }
610}
611
612static const char* pointmode_name(SkCanvas::PointMode mode) {
613 switch (mode) {
Mike Klein17428132019-03-20 13:02:32 -0500614 case SkCanvas::kPoints_PointMode: return DEBUGCANVAS_POINTMODE_POINTS;
615 case SkCanvas::kLines_PointMode: return DEBUGCANVAS_POINTMODE_LINES;
616 case SkCanvas::kPolygon_PointMode: return DEBUGCANVAS_POINTMODE_POLYGON;
Mike Klein8f4e2242019-03-20 11:59:00 -0500617 default: SkASSERT(false); return "<invalid point mode>";
618 }
619}
620
621static void store_scalar(SkJSONWriter& writer,
622 const char* key,
623 SkScalar value,
624 SkScalar defaultValue) {
625 if (value != defaultValue) {
626 writer.appendFloat(key, value);
627 }
628}
629
630static void store_bool(SkJSONWriter& writer, const char* key, bool value, bool defaultValue) {
631 if (value != defaultValue) {
632 writer.appendBool(key, value);
633 }
634}
635
636static SkString encode_data(const void* bytes,
637 size_t count,
638 const char* contentType,
639 UrlDataManager& urlDataManager) {
640 sk_sp<SkData> data(SkData::MakeWithCopy(bytes, count));
641 return urlDataManager.addData(data.get(), contentType);
642}
643
644void DrawCommand::flatten(const SkFlattenable* flattenable,
645 SkJSONWriter& writer,
646 UrlDataManager& urlDataManager) {
647 SkBinaryWriteBuffer buffer;
648 flattenable->flatten(buffer);
649 void* data = sk_malloc_throw(buffer.bytesWritten());
650 buffer.writeToMemory(data);
651 SkString url =
652 encode_data(data, buffer.bytesWritten(), "application/octet-stream", urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -0500653 writer.appendString(DEBUGCANVAS_ATTRIBUTE_NAME, flattenable->getTypeName());
654 writer.appendString(DEBUGCANVAS_ATTRIBUTE_DATA, url.c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -0500655
Mike Klein17428132019-03-20 13:02:32 -0500656 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_VALUES);
Mike Klein8f4e2242019-03-20 11:59:00 -0500657 JsonWriteBuffer jsonBuffer(&writer, &urlDataManager);
658 flattenable->flatten(jsonBuffer);
659 writer.endObject(); // values
660
661 sk_free(data);
662}
663
664void DrawCommand::WritePNG(SkBitmap bitmap, SkWStream& out) {
665 SkPixmap pm;
666 SkAssertResult(bitmap.peekPixels(&pm));
667
668 SkPngEncoder::Options options;
669 options.fZLibLevel = 1;
670 options.fFilterFlags = SkPngEncoder::FilterFlag::kNone;
671 SkPngEncoder::Encode(&out, pm, options);
672}
673
674bool DrawCommand::flatten(const SkImage& image,
675 SkJSONWriter& writer,
676 UrlDataManager& urlDataManager) {
677 size_t rowBytes = 4 * image.width();
678 SkAutoMalloc buffer(rowBytes * image.height());
679 SkImageInfo dstInfo =
680 SkImageInfo::Make(image.width(), image.height(), kN32_SkColorType, kPremul_SkAlphaType);
681 if (!image.readPixels(dstInfo, buffer.get(), rowBytes, 0, 0)) {
682 SkDebugf("readPixels failed\n");
683 return false;
684 }
685
686 SkBitmap bm;
687 bm.installPixels(dstInfo, buffer.get(), rowBytes);
688
689 SkDynamicMemoryWStream out;
690 DrawCommand::WritePNG(bm, out);
691 sk_sp<SkData> encoded = out.detachAsData();
692 SkString url = encode_data(encoded->data(), encoded->size(), "image/png", urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -0500693 writer.appendString(DEBUGCANVAS_ATTRIBUTE_DATA, url.c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -0500694 return true;
695}
696
697static const char* color_type_name(SkColorType colorType) {
698 switch (colorType) {
Mike Klein17428132019-03-20 13:02:32 -0500699 case kARGB_4444_SkColorType: return DEBUGCANVAS_COLORTYPE_ARGB4444;
700 case kRGBA_8888_SkColorType: return DEBUGCANVAS_COLORTYPE_RGBA8888;
701 case kBGRA_8888_SkColorType: return DEBUGCANVAS_COLORTYPE_BGRA8888;
702 case kRGB_565_SkColorType: return DEBUGCANVAS_COLORTYPE_565;
703 case kGray_8_SkColorType: return DEBUGCANVAS_COLORTYPE_GRAY8;
704 case kAlpha_8_SkColorType: return DEBUGCANVAS_COLORTYPE_ALPHA8;
705 default: SkASSERT(false); return DEBUGCANVAS_COLORTYPE_RGBA8888;
Mike Klein8f4e2242019-03-20 11:59:00 -0500706 }
707}
708
709static const char* alpha_type_name(SkAlphaType alphaType) {
710 switch (alphaType) {
Mike Klein17428132019-03-20 13:02:32 -0500711 case kOpaque_SkAlphaType: return DEBUGCANVAS_ALPHATYPE_OPAQUE;
712 case kPremul_SkAlphaType: return DEBUGCANVAS_ALPHATYPE_PREMUL;
713 case kUnpremul_SkAlphaType: return DEBUGCANVAS_ALPHATYPE_UNPREMUL;
714 default: SkASSERT(false); return DEBUGCANVAS_ALPHATYPE_OPAQUE;
Mike Klein8f4e2242019-03-20 11:59:00 -0500715 }
716}
717
718bool DrawCommand::flatten(const SkBitmap& bitmap,
719 SkJSONWriter& writer,
720 UrlDataManager& urlDataManager) {
721 sk_sp<SkImage> image(SkImage::MakeFromBitmap(bitmap));
Mike Klein17428132019-03-20 13:02:32 -0500722 writer.appendString(DEBUGCANVAS_ATTRIBUTE_COLOR, color_type_name(bitmap.colorType()));
723 writer.appendString(DEBUGCANVAS_ATTRIBUTE_ALPHA, alpha_type_name(bitmap.alphaType()));
Mike Klein8f4e2242019-03-20 11:59:00 -0500724 bool success = flatten(*image, writer, urlDataManager);
725 return success;
726}
727
728static void apply_font_hinting(const SkFont& font, SkJSONWriter& writer) {
729 SkFontHinting hinting = font.getHinting();
730 if (hinting != SkPaintDefaults_Hinting) {
731 switch (hinting) {
732 case kNo_SkFontHinting:
Mike Klein17428132019-03-20 13:02:32 -0500733 writer.appendString(DEBUGCANVAS_ATTRIBUTE_HINTING, DEBUGCANVAS_HINTING_NONE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500734 break;
735 case kSlight_SkFontHinting:
Mike Klein17428132019-03-20 13:02:32 -0500736 writer.appendString(DEBUGCANVAS_ATTRIBUTE_HINTING, DEBUGCANVAS_HINTING_SLIGHT);
Mike Klein8f4e2242019-03-20 11:59:00 -0500737 break;
738 case kNormal_SkFontHinting:
Mike Klein17428132019-03-20 13:02:32 -0500739 writer.appendString(DEBUGCANVAS_ATTRIBUTE_HINTING, DEBUGCANVAS_HINTING_NORMAL);
Mike Klein8f4e2242019-03-20 11:59:00 -0500740 break;
741 case kFull_SkFontHinting:
Mike Klein17428132019-03-20 13:02:32 -0500742 writer.appendString(DEBUGCANVAS_ATTRIBUTE_HINTING, DEBUGCANVAS_HINTING_FULL);
Mike Klein8f4e2242019-03-20 11:59:00 -0500743 break;
744 }
745 }
746}
747
748static void apply_font_edging(const SkFont& font, SkJSONWriter& writer) {
749 switch (font.getEdging()) {
750 case SkFont::Edging::kAlias:
Mike Klein17428132019-03-20 13:02:32 -0500751 writer.appendString(DEBUGCANVAS_ATTRIBUTE_EDGING, DEBUGCANVAS_EDGING_ALIAS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500752 break;
753 case SkFont::Edging::kAntiAlias:
Mike Klein17428132019-03-20 13:02:32 -0500754 writer.appendString(DEBUGCANVAS_ATTRIBUTE_EDGING, DEBUGCANVAS_EDGING_ANTIALIAS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500755 break;
756 case SkFont::Edging::kSubpixelAntiAlias:
Mike Klein17428132019-03-20 13:02:32 -0500757 writer.appendString(DEBUGCANVAS_ATTRIBUTE_EDGING, DEBUGCANVAS_EDGING_SUBPIXELANTIALIAS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500758 break;
759 }
760}
761
762static void apply_paint_color(const SkPaint& paint, SkJSONWriter& writer) {
763 SkColor color = paint.getColor();
764 if (color != SK_ColorBLACK) {
Mike Klein17428132019-03-20 13:02:32 -0500765 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COLOR);
Mike Klein8f4e2242019-03-20 11:59:00 -0500766 DrawCommand::MakeJsonColor(writer, color);
767 }
768}
769
770static void apply_paint_style(const SkPaint& paint, SkJSONWriter& writer) {
771 SkPaint::Style style = paint.getStyle();
772 if (style != SkPaint::kFill_Style) {
773 switch (style) {
774 case SkPaint::kStroke_Style: {
Mike Klein17428132019-03-20 13:02:32 -0500775 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STYLE, DEBUGCANVAS_STYLE_STROKE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500776 break;
777 }
778 case SkPaint::kStrokeAndFill_Style: {
Mike Klein17428132019-03-20 13:02:32 -0500779 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STYLE, DEBUGCANVAS_STYLE_STROKEANDFILL);
Mike Klein8f4e2242019-03-20 11:59:00 -0500780 break;
781 }
782 default: SkASSERT(false);
783 }
784 }
785}
786
787static void apply_paint_cap(const SkPaint& paint, SkJSONWriter& writer) {
788 SkPaint::Cap cap = paint.getStrokeCap();
789 if (cap != SkPaint::kDefault_Cap) {
790 switch (cap) {
791 case SkPaint::kButt_Cap:
Mike Klein17428132019-03-20 13:02:32 -0500792 writer.appendString(DEBUGCANVAS_ATTRIBUTE_CAP, DEBUGCANVAS_CAP_BUTT);
Mike Klein8f4e2242019-03-20 11:59:00 -0500793 break;
794 case SkPaint::kRound_Cap:
Mike Klein17428132019-03-20 13:02:32 -0500795 writer.appendString(DEBUGCANVAS_ATTRIBUTE_CAP, DEBUGCANVAS_CAP_ROUND);
Mike Klein8f4e2242019-03-20 11:59:00 -0500796 break;
797 case SkPaint::kSquare_Cap:
Mike Klein17428132019-03-20 13:02:32 -0500798 writer.appendString(DEBUGCANVAS_ATTRIBUTE_CAP, DEBUGCANVAS_CAP_SQUARE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500799 break;
800 default: SkASSERT(false);
801 }
802 }
803}
804
805static void apply_paint_join(const SkPaint& paint, SkJSONWriter& writer) {
806 SkPaint::Join join = paint.getStrokeJoin();
807 if (join != SkPaint::kDefault_Join) {
808 switch (join) {
809 case SkPaint::kMiter_Join:
Mike Klein17428132019-03-20 13:02:32 -0500810 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STROKEJOIN, DEBUGCANVAS_MITER_JOIN);
Mike Klein8f4e2242019-03-20 11:59:00 -0500811 break;
812 case SkPaint::kRound_Join:
Mike Klein17428132019-03-20 13:02:32 -0500813 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STROKEJOIN, DEBUGCANVAS_ROUND_JOIN);
Mike Klein8f4e2242019-03-20 11:59:00 -0500814 break;
815 case SkPaint::kBevel_Join:
Mike Klein17428132019-03-20 13:02:32 -0500816 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STROKEJOIN, DEBUGCANVAS_BEVEL_JOIN);
Mike Klein8f4e2242019-03-20 11:59:00 -0500817 break;
818 default: SkASSERT(false);
819 }
820 }
821}
822
823static void apply_paint_filterquality(const SkPaint& paint, SkJSONWriter& writer) {
824 SkFilterQuality quality = paint.getFilterQuality();
825 switch (quality) {
826 case kNone_SkFilterQuality: break;
827 case kLow_SkFilterQuality:
Mike Klein17428132019-03-20 13:02:32 -0500828 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILTERQUALITY, DEBUGCANVAS_FILTERQUALITY_LOW);
Mike Klein8f4e2242019-03-20 11:59:00 -0500829 break;
830 case kMedium_SkFilterQuality:
Mike Klein17428132019-03-20 13:02:32 -0500831 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILTERQUALITY,
832 DEBUGCANVAS_FILTERQUALITY_MEDIUM);
Mike Klein8f4e2242019-03-20 11:59:00 -0500833 break;
834 case kHigh_SkFilterQuality:
Mike Klein17428132019-03-20 13:02:32 -0500835 writer.appendString(DEBUGCANVAS_ATTRIBUTE_FILTERQUALITY,
836 DEBUGCANVAS_FILTERQUALITY_HIGH);
Mike Klein8f4e2242019-03-20 11:59:00 -0500837 break;
838 }
839}
840
841static void apply_paint_maskfilter(const SkPaint& paint,
842 SkJSONWriter& writer,
843 UrlDataManager& urlDataManager) {
844 SkMaskFilter* maskFilter = paint.getMaskFilter();
845 if (maskFilter != nullptr) {
846 SkMaskFilterBase::BlurRec blurRec;
847 if (as_MFB(maskFilter)->asABlur(&blurRec)) {
Mike Klein17428132019-03-20 13:02:32 -0500848 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_BLUR);
849 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_SIGMA, blurRec.fSigma);
Mike Klein8f4e2242019-03-20 11:59:00 -0500850 switch (blurRec.fStyle) {
851 case SkBlurStyle::kNormal_SkBlurStyle:
Mike Klein17428132019-03-20 13:02:32 -0500852 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STYLE, DEBUGCANVAS_BLURSTYLE_NORMAL);
Mike Klein8f4e2242019-03-20 11:59:00 -0500853 break;
854 case SkBlurStyle::kSolid_SkBlurStyle:
Mike Klein17428132019-03-20 13:02:32 -0500855 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STYLE, DEBUGCANVAS_BLURSTYLE_SOLID);
Mike Klein8f4e2242019-03-20 11:59:00 -0500856 break;
857 case SkBlurStyle::kOuter_SkBlurStyle:
Mike Klein17428132019-03-20 13:02:32 -0500858 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STYLE, DEBUGCANVAS_BLURSTYLE_OUTER);
Mike Klein8f4e2242019-03-20 11:59:00 -0500859 break;
860 case SkBlurStyle::kInner_SkBlurStyle:
Mike Klein17428132019-03-20 13:02:32 -0500861 writer.appendString(DEBUGCANVAS_ATTRIBUTE_STYLE, DEBUGCANVAS_BLURSTYLE_INNER);
Mike Klein8f4e2242019-03-20 11:59:00 -0500862 break;
863 default: SkASSERT(false);
864 }
865 writer.endObject(); // blur
866 } else {
Mike Klein17428132019-03-20 13:02:32 -0500867 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_MASKFILTER);
Mike Klein8f4e2242019-03-20 11:59:00 -0500868 DrawCommand::flatten(maskFilter, writer, urlDataManager);
869 writer.endObject(); // maskFilter
870 }
871 }
872}
873
874static void apply_paint_patheffect(const SkPaint& paint,
875 SkJSONWriter& writer,
876 UrlDataManager& urlDataManager) {
877 SkPathEffect* pathEffect = paint.getPathEffect();
878 if (pathEffect != nullptr) {
879 SkPathEffect::DashInfo dashInfo;
880 SkPathEffect::DashType dashType = pathEffect->asADash(&dashInfo);
881 if (dashType == SkPathEffect::kDash_DashType) {
882 dashInfo.fIntervals = (SkScalar*)sk_malloc_throw(dashInfo.fCount * sizeof(SkScalar));
883 pathEffect->asADash(&dashInfo);
Mike Klein17428132019-03-20 13:02:32 -0500884 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_DASHING);
885 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_INTERVALS, false);
Mike Klein8f4e2242019-03-20 11:59:00 -0500886 for (int32_t i = 0; i < dashInfo.fCount; i++) {
887 writer.appendFloat(dashInfo.fIntervals[i]);
888 }
889 writer.endArray(); // intervals
890 sk_free(dashInfo.fIntervals);
Mike Klein17428132019-03-20 13:02:32 -0500891 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_PHASE, dashInfo.fPhase);
Mike Klein8f4e2242019-03-20 11:59:00 -0500892 writer.endObject(); // dashing
893 } else {
Mike Klein17428132019-03-20 13:02:32 -0500894 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_PATHEFFECT);
Mike Klein8f4e2242019-03-20 11:59:00 -0500895 DrawCommand::flatten(pathEffect, writer, urlDataManager);
896 writer.endObject(); // pathEffect
897 }
898 }
899}
900
901static void apply_font_typeface(const SkFont& font,
902 SkJSONWriter& writer,
903 UrlDataManager& urlDataManager) {
904 SkTypeface* typeface = font.getTypefaceOrDefault();
905 if (typeface != nullptr) {
Mike Klein17428132019-03-20 13:02:32 -0500906 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_TYPEFACE);
Mike Klein8f4e2242019-03-20 11:59:00 -0500907 SkDynamicMemoryWStream buffer;
908 typeface->serialize(&buffer);
909 void* data = sk_malloc_throw(buffer.bytesWritten());
910 buffer.copyTo(data);
911 SkString url = encode_data(
912 data, buffer.bytesWritten(), "application/octet-stream", urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -0500913 writer.appendString(DEBUGCANVAS_ATTRIBUTE_DATA, url.c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -0500914 sk_free(data);
915 writer.endObject();
916 }
917}
918
919static void apply_flattenable(const char* key,
920 SkFlattenable* flattenable,
921 SkJSONWriter& writer,
922 UrlDataManager& urlDataManager) {
923 if (flattenable != nullptr) {
924 writer.beginObject(key);
925 DrawCommand::flatten(flattenable, writer, urlDataManager);
926 writer.endObject();
927 }
928}
929
930void DrawCommand::MakeJsonPaint(SkJSONWriter& writer,
931 const SkPaint& paint,
932 UrlDataManager& urlDataManager) {
933 writer.beginObject();
Mike Klein17428132019-03-20 13:02:32 -0500934 store_scalar(writer, DEBUGCANVAS_ATTRIBUTE_STROKEWIDTH, paint.getStrokeWidth(), 0.0f);
Mike Klein8f4e2242019-03-20 11:59:00 -0500935 store_scalar(writer,
Mike Klein17428132019-03-20 13:02:32 -0500936 DEBUGCANVAS_ATTRIBUTE_STROKEMITER,
Mike Klein8f4e2242019-03-20 11:59:00 -0500937 paint.getStrokeMiter(),
938 SkPaintDefaults_MiterLimit);
Mike Klein17428132019-03-20 13:02:32 -0500939 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_ANTIALIAS, paint.isAntiAlias(), false);
940 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_DITHER, paint.isDither(), false);
Mike Klein8f4e2242019-03-20 11:59:00 -0500941
942 apply_paint_color(paint, writer);
943 apply_paint_style(paint, writer);
944 apply_paint_blend_mode(paint, writer);
945 apply_paint_cap(paint, writer);
946 apply_paint_join(paint, writer);
947 apply_paint_filterquality(paint, writer);
948 apply_paint_patheffect(paint, writer, urlDataManager);
949 apply_paint_maskfilter(paint, writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -0500950 apply_flattenable(DEBUGCANVAS_ATTRIBUTE_SHADER, paint.getShader(), writer, urlDataManager);
951 apply_flattenable(DEBUGCANVAS_ATTRIBUTE_LOOPER, paint.getLooper(), writer, urlDataManager);
Mike Klein8f4e2242019-03-20 11:59:00 -0500952 apply_flattenable(
Mike Klein17428132019-03-20 13:02:32 -0500953 DEBUGCANVAS_ATTRIBUTE_IMAGEFILTER, paint.getImageFilter(), writer, urlDataManager);
Mike Klein8f4e2242019-03-20 11:59:00 -0500954 apply_flattenable(
Mike Klein17428132019-03-20 13:02:32 -0500955 DEBUGCANVAS_ATTRIBUTE_COLORFILTER, paint.getColorFilter(), writer, urlDataManager);
Mike Klein8f4e2242019-03-20 11:59:00 -0500956 writer.endObject(); // paint
957}
958
959static void MakeJsonFont(const SkFont& font, SkJSONWriter& writer, UrlDataManager& urlDataManager) {
960 writer.beginObject();
Mike Klein17428132019-03-20 13:02:32 -0500961 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_FAKEBOLDTEXT, font.isEmbolden(), false);
962 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_LINEARTEXT, font.isLinearMetrics(), false);
963 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_SUBPIXELTEXT, font.isSubpixel(), false);
964 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_EMBEDDEDBITMAPTEXT, font.isEmbeddedBitmaps(), false);
965 store_bool(writer, DEBUGCANVAS_ATTRIBUTE_AUTOHINTING, font.isForceAutoHinting(), false);
Mike Klein8f4e2242019-03-20 11:59:00 -0500966
Mike Klein17428132019-03-20 13:02:32 -0500967 store_scalar(writer, DEBUGCANVAS_ATTRIBUTE_TEXTSIZE, font.getSize(), SkPaintDefaults_TextSize);
968 store_scalar(writer, DEBUGCANVAS_ATTRIBUTE_TEXTSCALEX, font.getScaleX(), SK_Scalar1);
969 store_scalar(writer, DEBUGCANVAS_ATTRIBUTE_TEXTSCALEX, font.getSkewX(), 0.0f);
Mike Klein8f4e2242019-03-20 11:59:00 -0500970 apply_font_edging(font, writer);
971 apply_font_hinting(font, writer);
972 apply_font_typeface(font, writer, urlDataManager);
973 writer.endObject(); // font
974}
975
976void DrawCommand::MakeJsonLattice(SkJSONWriter& writer, const SkCanvas::Lattice& lattice) {
977 writer.beginObject();
Mike Klein17428132019-03-20 13:02:32 -0500978 writer.appendS32(DEBUGCANVAS_ATTRIBUTE_LATTICEXCOUNT, lattice.fXCount);
979 writer.appendS32(DEBUGCANVAS_ATTRIBUTE_LATTICEYCOUNT, lattice.fYCount);
Mike Klein8f4e2242019-03-20 11:59:00 -0500980 if (nullptr != lattice.fBounds) {
Mike Klein17428132019-03-20 13:02:32 -0500981 writer.appendName(DEBUGCANVAS_ATTRIBUTE_BOUNDS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500982 MakeJsonIRect(writer, *lattice.fBounds);
983 }
Mike Klein17428132019-03-20 13:02:32 -0500984 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_LATTICEXDIVS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500985 for (int i = 0; i < lattice.fXCount; i++) {
986 writer.appendS32(lattice.fXDivs[i]);
987 }
988 writer.endArray(); // xdivs
Mike Klein17428132019-03-20 13:02:32 -0500989 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_LATTICEYDIVS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500990 for (int i = 0; i < lattice.fYCount; i++) {
991 writer.appendS32(lattice.fYDivs[i]);
992 }
993 writer.endArray(); // ydivs
994 if (nullptr != lattice.fRectTypes) {
Mike Klein17428132019-03-20 13:02:32 -0500995 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_LATTICEFLAGS);
Mike Klein8f4e2242019-03-20 11:59:00 -0500996 int flagCount = 0;
997 for (int row = 0; row < lattice.fYCount + 1; row++) {
998 writer.beginArray();
999 for (int column = 0; column < lattice.fXCount + 1; column++) {
1000 writer.appendS32(lattice.fRectTypes[flagCount++]);
1001 }
1002 writer.endArray(); // row
1003 }
1004 writer.endArray();
1005 }
1006 writer.endObject();
1007}
1008
Mike Klein17428132019-03-20 13:02:32 -05001009ClearCommand::ClearCommand(SkColor color) : INHERITED(kClear_OpType) { fColor = color; }
Mike Klein8f4e2242019-03-20 11:59:00 -05001010
Mike Klein17428132019-03-20 13:02:32 -05001011void ClearCommand::execute(SkCanvas* canvas) const { canvas->clear(fColor); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001012
Mike Klein17428132019-03-20 13:02:32 -05001013void ClearCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001014 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001015 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COLOR);
Mike Klein8f4e2242019-03-20 11:59:00 -05001016 MakeJsonColor(writer, fColor);
1017}
1018
Mike Klein17428132019-03-20 13:02:32 -05001019ClipPathCommand::ClipPathCommand(const SkPath& path, SkClipOp op, bool doAA)
Mike Klein8f4e2242019-03-20 11:59:00 -05001020 : INHERITED(kClipPath_OpType) {
1021 fPath = path;
1022 fOp = op;
1023 fDoAA = doAA;
1024}
1025
Mike Klein17428132019-03-20 13:02:32 -05001026void ClipPathCommand::execute(SkCanvas* canvas) const { canvas->clipPath(fPath, fOp, fDoAA); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001027
Mike Klein17428132019-03-20 13:02:32 -05001028bool ClipPathCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001029 render_path(canvas, fPath);
1030 return true;
1031}
1032
Mike Klein17428132019-03-20 13:02:32 -05001033void ClipPathCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001034 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001035 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PATH);
Mike Klein8f4e2242019-03-20 11:59:00 -05001036 MakeJsonPath(writer, fPath);
Mike Klein17428132019-03-20 13:02:32 -05001037 writer.appendString(DEBUGCANVAS_ATTRIBUTE_REGIONOP, regionop_name(fOp));
1038 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_ANTIALIAS, fDoAA);
Mike Klein8f4e2242019-03-20 11:59:00 -05001039}
1040
Mike Klein17428132019-03-20 13:02:32 -05001041ClipRegionCommand::ClipRegionCommand(const SkRegion& region, SkClipOp op)
Mike Klein8f4e2242019-03-20 11:59:00 -05001042 : INHERITED(kClipRegion_OpType) {
1043 fRegion = region;
1044 fOp = op;
1045}
1046
Mike Klein17428132019-03-20 13:02:32 -05001047void ClipRegionCommand::execute(SkCanvas* canvas) const { canvas->clipRegion(fRegion, fOp); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001048
Mike Klein17428132019-03-20 13:02:32 -05001049void ClipRegionCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001050 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001051 writer.appendName(DEBUGCANVAS_ATTRIBUTE_REGION);
Mike Klein8f4e2242019-03-20 11:59:00 -05001052 MakeJsonRegion(writer, fRegion);
Mike Klein17428132019-03-20 13:02:32 -05001053 writer.appendString(DEBUGCANVAS_ATTRIBUTE_REGIONOP, regionop_name(fOp));
Mike Klein8f4e2242019-03-20 11:59:00 -05001054}
1055
Mike Klein17428132019-03-20 13:02:32 -05001056ClipRectCommand::ClipRectCommand(const SkRect& rect, SkClipOp op, bool doAA)
Mike Klein8f4e2242019-03-20 11:59:00 -05001057 : INHERITED(kClipRect_OpType) {
1058 fRect = rect;
1059 fOp = op;
1060 fDoAA = doAA;
1061}
1062
Mike Klein17428132019-03-20 13:02:32 -05001063void ClipRectCommand::execute(SkCanvas* canvas) const { canvas->clipRect(fRect, fOp, fDoAA); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001064
Mike Klein17428132019-03-20 13:02:32 -05001065void ClipRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001066 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001067 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001068 MakeJsonRect(writer, fRect);
Mike Klein17428132019-03-20 13:02:32 -05001069 writer.appendString(DEBUGCANVAS_ATTRIBUTE_REGIONOP, regionop_name(fOp));
1070 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_ANTIALIAS, fDoAA);
Mike Klein8f4e2242019-03-20 11:59:00 -05001071
1072 SkString desc;
Mike Klein17428132019-03-20 13:02:32 -05001073 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, fRect)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001074}
1075
Mike Klein17428132019-03-20 13:02:32 -05001076ClipRRectCommand::ClipRRectCommand(const SkRRect& rrect, SkClipOp op, bool doAA)
Mike Klein8f4e2242019-03-20 11:59:00 -05001077 : INHERITED(kClipRRect_OpType) {
1078 fRRect = rrect;
1079 fOp = op;
1080 fDoAA = doAA;
1081}
1082
Mike Klein17428132019-03-20 13:02:32 -05001083void ClipRRectCommand::execute(SkCanvas* canvas) const { canvas->clipRRect(fRRect, fOp, fDoAA); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001084
Mike Klein17428132019-03-20 13:02:32 -05001085bool ClipRRectCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001086 render_rrect(canvas, fRRect);
1087 return true;
1088}
1089
Mike Klein17428132019-03-20 13:02:32 -05001090void ClipRRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001091 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001092 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001093 make_json_rrect(writer, fRRect);
Mike Klein17428132019-03-20 13:02:32 -05001094 writer.appendString(DEBUGCANVAS_ATTRIBUTE_REGIONOP, regionop_name(fOp));
1095 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_ANTIALIAS, fDoAA);
Mike Klein8f4e2242019-03-20 11:59:00 -05001096}
1097
Mike Klein17428132019-03-20 13:02:32 -05001098ConcatCommand::ConcatCommand(const SkMatrix& matrix) : INHERITED(kConcat_OpType) {
Mike Klein8f4e2242019-03-20 11:59:00 -05001099 fMatrix = matrix;
1100}
1101
Mike Klein17428132019-03-20 13:02:32 -05001102void ConcatCommand::execute(SkCanvas* canvas) const { canvas->concat(fMatrix); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001103
Mike Klein17428132019-03-20 13:02:32 -05001104void ConcatCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001105 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001106 writer.appendName(DEBUGCANVAS_ATTRIBUTE_MATRIX);
Mike Klein8f4e2242019-03-20 11:59:00 -05001107 MakeJsonMatrix(writer, fMatrix);
1108}
1109
1110////
1111
Mike Klein17428132019-03-20 13:02:32 -05001112DrawAnnotationCommand::DrawAnnotationCommand(const SkRect& rect,
1113 const char key[],
1114 sk_sp<SkData> value)
Mike Klein8f4e2242019-03-20 11:59:00 -05001115 : INHERITED(kDrawAnnotation_OpType), fRect(rect), fKey(key), fValue(std::move(value)) {}
1116
Mike Klein17428132019-03-20 13:02:32 -05001117void DrawAnnotationCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001118 canvas->drawAnnotation(fRect, fKey.c_str(), fValue);
1119}
1120
Mike Klein17428132019-03-20 13:02:32 -05001121void DrawAnnotationCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001122 INHERITED::toJSON(writer, urlDataManager);
1123
Mike Klein17428132019-03-20 13:02:32 -05001124 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001125 MakeJsonRect(writer, fRect);
1126 writer.appendString("key", fKey.c_str());
1127 if (fValue.get()) {
1128 // TODO: dump out the "value"
1129 }
1130
1131 SkString desc;
1132 str_append(&desc, fRect)->appendf(" %s", fKey.c_str());
Mike Klein17428132019-03-20 13:02:32 -05001133 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, desc.c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001134}
1135
1136////
1137
Mike Klein17428132019-03-20 13:02:32 -05001138DrawBitmapCommand::DrawBitmapCommand(const SkBitmap& bitmap,
1139 SkScalar left,
1140 SkScalar top,
1141 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001142 : INHERITED(kDrawBitmap_OpType), fBitmap(bitmap), fLeft(left), fTop(top), fPaint(paint) {}
1143
Mike Klein17428132019-03-20 13:02:32 -05001144void DrawBitmapCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001145 canvas->drawBitmap(fBitmap, fLeft, fTop, fPaint.getMaybeNull());
1146}
1147
Mike Klein17428132019-03-20 13:02:32 -05001148bool DrawBitmapCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001149 render_bitmap(canvas, fBitmap);
1150 return true;
1151}
1152
Mike Klein17428132019-03-20 13:02:32 -05001153void DrawBitmapCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001154 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001155 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_BITMAP);
Mike Klein8f4e2242019-03-20 11:59:00 -05001156 flatten(fBitmap, writer, urlDataManager);
1157 writer.endObject();
Mike Klein17428132019-03-20 13:02:32 -05001158 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001159 MakeJsonPoint(writer, fLeft, fTop);
1160 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001161 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001162 MakeJsonPaint(writer, *fPaint, urlDataManager);
1163 }
1164}
1165
Mike Klein17428132019-03-20 13:02:32 -05001166DrawBitmapLatticeCommand::DrawBitmapLatticeCommand(const SkBitmap& bitmap,
1167 const SkCanvas::Lattice& lattice,
1168 const SkRect& dst,
1169 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001170 : INHERITED(kDrawBitmapLattice_OpType)
1171 , fBitmap(bitmap)
1172 , fLattice(lattice)
1173 , fDst(dst)
1174 , fPaint(paint) {}
1175
Mike Klein17428132019-03-20 13:02:32 -05001176void DrawBitmapLatticeCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001177 canvas->drawBitmapLattice(fBitmap, fLattice, fDst, fPaint.getMaybeNull());
1178}
1179
Mike Klein17428132019-03-20 13:02:32 -05001180bool DrawBitmapLatticeCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001181 SkAutoCanvasRestore acr(canvas, true);
1182 canvas->clear(0xFFFFFFFF);
1183
1184 xlate_and_scale_to_bounds(canvas, fDst);
1185
1186 this->execute(canvas);
1187 return true;
1188}
1189
Mike Klein17428132019-03-20 13:02:32 -05001190void DrawBitmapLatticeCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001191 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001192 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_BITMAP);
Mike Klein8f4e2242019-03-20 11:59:00 -05001193 flatten(fBitmap, writer, urlDataManager);
1194 writer.endObject(); // bitmap
1195
Mike Klein17428132019-03-20 13:02:32 -05001196 writer.appendName(DEBUGCANVAS_ATTRIBUTE_LATTICE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001197 MakeJsonLattice(writer, fLattice);
Mike Klein17428132019-03-20 13:02:32 -05001198 writer.appendName(DEBUGCANVAS_ATTRIBUTE_DST);
Mike Klein8f4e2242019-03-20 11:59:00 -05001199 MakeJsonRect(writer, fDst);
1200 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001201 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001202 MakeJsonPaint(writer, *fPaint, urlDataManager);
1203 }
1204
1205 SkString desc;
Mike Klein17428132019-03-20 13:02:32 -05001206 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, fDst)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001207}
1208
Mike Klein17428132019-03-20 13:02:32 -05001209DrawBitmapNineCommand::DrawBitmapNineCommand(const SkBitmap& bitmap,
1210 const SkIRect& center,
1211 const SkRect& dst,
1212 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001213 : INHERITED(kDrawBitmapNine_OpType)
1214 , fBitmap(bitmap)
1215 , fCenter(center)
1216 , fDst(dst)
1217 , fPaint(paint) {}
1218
Mike Klein17428132019-03-20 13:02:32 -05001219void DrawBitmapNineCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001220 canvas->drawBitmapNine(fBitmap, fCenter, fDst, fPaint.getMaybeNull());
1221}
1222
Mike Klein17428132019-03-20 13:02:32 -05001223bool DrawBitmapNineCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001224 SkRect tmp = SkRect::Make(fCenter);
1225 render_bitmap(canvas, fBitmap, &tmp);
1226 return true;
1227}
1228
Mike Klein17428132019-03-20 13:02:32 -05001229void DrawBitmapNineCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001230 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001231 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_BITMAP);
Mike Klein8f4e2242019-03-20 11:59:00 -05001232 flatten(fBitmap, writer, urlDataManager);
1233 writer.endObject(); // bitmap
1234
Mike Klein17428132019-03-20 13:02:32 -05001235 writer.appendName(DEBUGCANVAS_ATTRIBUTE_CENTER);
Mike Klein8f4e2242019-03-20 11:59:00 -05001236 MakeJsonIRect(writer, fCenter);
Mike Klein17428132019-03-20 13:02:32 -05001237 writer.appendName(DEBUGCANVAS_ATTRIBUTE_DST);
Mike Klein8f4e2242019-03-20 11:59:00 -05001238 MakeJsonRect(writer, fDst);
1239 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001240 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001241 MakeJsonPaint(writer, *fPaint, urlDataManager);
1242 }
1243}
1244
Mike Klein17428132019-03-20 13:02:32 -05001245DrawBitmapRectCommand::DrawBitmapRectCommand(const SkBitmap& bitmap,
1246 const SkRect* src,
1247 const SkRect& dst,
1248 const SkPaint* paint,
1249 SkCanvas::SrcRectConstraint constraint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001250 : INHERITED(kDrawBitmapRect_OpType)
1251 , fBitmap(bitmap)
1252 , fSrc(src)
1253 , fDst(dst)
1254 , fPaint(paint)
1255 , fConstraint(constraint) {}
1256
Mike Klein17428132019-03-20 13:02:32 -05001257void DrawBitmapRectCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001258 canvas->legacy_drawBitmapRect(
1259 fBitmap, fSrc.getMaybeNull(), fDst, fPaint.getMaybeNull(), fConstraint);
1260}
1261
Mike Klein17428132019-03-20 13:02:32 -05001262bool DrawBitmapRectCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001263 render_bitmap(canvas, fBitmap, fSrc.getMaybeNull());
1264 return true;
1265}
1266
Mike Klein17428132019-03-20 13:02:32 -05001267void DrawBitmapRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001268 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001269 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_BITMAP);
Mike Klein8f4e2242019-03-20 11:59:00 -05001270 flatten(fBitmap, writer, urlDataManager);
1271 writer.endObject(); // bitmap
1272
1273 if (fSrc.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001274 writer.appendName(DEBUGCANVAS_ATTRIBUTE_SRC);
Mike Klein8f4e2242019-03-20 11:59:00 -05001275 MakeJsonRect(writer, *fSrc);
1276 }
Mike Klein17428132019-03-20 13:02:32 -05001277 writer.appendName(DEBUGCANVAS_ATTRIBUTE_DST);
Mike Klein8f4e2242019-03-20 11:59:00 -05001278 MakeJsonRect(writer, fDst);
1279 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001280 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001281 MakeJsonPaint(writer, *fPaint, urlDataManager);
1282 }
1283 if (fConstraint == SkCanvas::kStrict_SrcRectConstraint) {
Mike Klein17428132019-03-20 13:02:32 -05001284 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_STRICT, true);
Mike Klein8f4e2242019-03-20 11:59:00 -05001285 }
1286
1287 SkString desc;
Mike Klein17428132019-03-20 13:02:32 -05001288 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, fDst)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001289}
1290
Mike Klein17428132019-03-20 13:02:32 -05001291DrawImageCommand::DrawImageCommand(const SkImage* image,
1292 SkScalar left,
1293 SkScalar top,
1294 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001295 : INHERITED(kDrawImage_OpType)
1296 , fImage(SkRef(image))
1297 , fLeft(left)
1298 , fTop(top)
1299 , fPaint(paint) {}
1300
Mike Klein17428132019-03-20 13:02:32 -05001301void DrawImageCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001302 canvas->drawImage(fImage.get(), fLeft, fTop, fPaint.getMaybeNull());
1303}
1304
Mike Klein17428132019-03-20 13:02:32 -05001305bool DrawImageCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001306 SkAutoCanvasRestore acr(canvas, true);
1307 canvas->clear(0xFFFFFFFF);
1308
1309 xlate_and_scale_to_bounds(
1310 canvas,
1311 SkRect::MakeXYWH(
1312 fLeft, fTop, SkIntToScalar(fImage->width()), SkIntToScalar(fImage->height())));
1313 this->execute(canvas);
1314 return true;
1315}
1316
Mike Klein17428132019-03-20 13:02:32 -05001317void DrawImageCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001318 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001319 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_IMAGE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001320 flatten(*fImage, writer, urlDataManager);
1321 writer.endObject(); // image
1322
Mike Klein17428132019-03-20 13:02:32 -05001323 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001324 MakeJsonPoint(writer, fLeft, fTop);
1325 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001326 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001327 MakeJsonPaint(writer, *fPaint, urlDataManager);
1328 }
1329
Mike Klein17428132019-03-20 13:02:32 -05001330 writer.appendU32(DEBUGCANVAS_ATTRIBUTE_UNIQUE_ID, fImage->uniqueID());
1331 writer.appendS32(DEBUGCANVAS_ATTRIBUTE_WIDTH, fImage->width());
1332 writer.appendS32(DEBUGCANVAS_ATTRIBUTE_HEIGHT, fImage->height());
Mike Klein8f4e2242019-03-20 11:59:00 -05001333 switch (fImage->alphaType()) {
1334 case kOpaque_SkAlphaType:
Mike Klein17428132019-03-20 13:02:32 -05001335 writer.appendString(DEBUGCANVAS_ATTRIBUTE_ALPHA, DEBUGCANVAS_ALPHATYPE_OPAQUE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001336 break;
1337 case kPremul_SkAlphaType:
Mike Klein17428132019-03-20 13:02:32 -05001338 writer.appendString(DEBUGCANVAS_ATTRIBUTE_ALPHA, DEBUGCANVAS_ALPHATYPE_PREMUL);
Mike Klein8f4e2242019-03-20 11:59:00 -05001339 break;
1340 case kUnpremul_SkAlphaType:
Mike Klein17428132019-03-20 13:02:32 -05001341 writer.appendString(DEBUGCANVAS_ATTRIBUTE_ALPHA, DEBUGCANVAS_ALPHATYPE_UNPREMUL);
Mike Klein8f4e2242019-03-20 11:59:00 -05001342 break;
1343 default:
Mike Klein17428132019-03-20 13:02:32 -05001344 writer.appendString(DEBUGCANVAS_ATTRIBUTE_ALPHA, DEBUGCANVAS_ALPHATYPE_UNKNOWN);
Mike Klein8f4e2242019-03-20 11:59:00 -05001345 break;
1346 }
1347}
1348
Mike Klein17428132019-03-20 13:02:32 -05001349DrawImageLatticeCommand::DrawImageLatticeCommand(const SkImage* image,
1350 const SkCanvas::Lattice& lattice,
1351 const SkRect& dst,
1352 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001353 : INHERITED(kDrawImageLattice_OpType)
1354 , fImage(SkRef(image))
1355 , fLattice(lattice)
1356 , fDst(dst)
1357 , fPaint(paint) {}
1358
Mike Klein17428132019-03-20 13:02:32 -05001359void DrawImageLatticeCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001360 canvas->drawImageLattice(fImage.get(), fLattice, fDst, fPaint.getMaybeNull());
1361}
1362
Mike Klein17428132019-03-20 13:02:32 -05001363bool DrawImageLatticeCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001364 SkAutoCanvasRestore acr(canvas, true);
1365 canvas->clear(0xFFFFFFFF);
1366
1367 xlate_and_scale_to_bounds(canvas, fDst);
1368
1369 this->execute(canvas);
1370 return true;
1371}
1372
Mike Klein17428132019-03-20 13:02:32 -05001373void DrawImageLatticeCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001374 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001375 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_IMAGE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001376 flatten(*fImage, writer, urlDataManager);
1377 writer.endObject(); // image
1378
Mike Klein17428132019-03-20 13:02:32 -05001379 writer.appendName(DEBUGCANVAS_ATTRIBUTE_LATTICE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001380 MakeJsonLattice(writer, fLattice);
Mike Klein17428132019-03-20 13:02:32 -05001381 writer.appendName(DEBUGCANVAS_ATTRIBUTE_DST);
Mike Klein8f4e2242019-03-20 11:59:00 -05001382 MakeJsonRect(writer, fDst);
1383 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001384 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001385 MakeJsonPaint(writer, *fPaint, urlDataManager);
1386 }
1387
1388 SkString desc;
Mike Klein17428132019-03-20 13:02:32 -05001389 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, fDst)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001390}
1391
Mike Klein17428132019-03-20 13:02:32 -05001392DrawImageRectCommand::DrawImageRectCommand(const SkImage* image,
1393 const SkRect* src,
1394 const SkRect& dst,
1395 const SkPaint* paint,
1396 SkCanvas::SrcRectConstraint constraint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001397 : INHERITED(kDrawImageRect_OpType)
1398 , fImage(SkRef(image))
1399 , fSrc(src)
1400 , fDst(dst)
1401 , fPaint(paint)
1402 , fConstraint(constraint) {}
1403
Mike Klein17428132019-03-20 13:02:32 -05001404void DrawImageRectCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001405 canvas->legacy_drawImageRect(
1406 fImage.get(), fSrc.getMaybeNull(), fDst, fPaint.getMaybeNull(), fConstraint);
1407}
1408
Mike Klein17428132019-03-20 13:02:32 -05001409bool DrawImageRectCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001410 SkAutoCanvasRestore acr(canvas, true);
1411 canvas->clear(0xFFFFFFFF);
1412
1413 xlate_and_scale_to_bounds(canvas, fDst);
1414
1415 this->execute(canvas);
1416 return true;
1417}
1418
Mike Klein17428132019-03-20 13:02:32 -05001419void DrawImageRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001420 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001421 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_IMAGE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001422 flatten(*fImage, writer, urlDataManager);
1423 writer.endObject(); // image
1424
1425 if (fSrc.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001426 writer.appendName(DEBUGCANVAS_ATTRIBUTE_SRC);
Mike Klein8f4e2242019-03-20 11:59:00 -05001427 MakeJsonRect(writer, *fSrc);
1428 }
Mike Klein17428132019-03-20 13:02:32 -05001429 writer.appendName(DEBUGCANVAS_ATTRIBUTE_DST);
Mike Klein8f4e2242019-03-20 11:59:00 -05001430 MakeJsonRect(writer, fDst);
1431 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001432 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001433 MakeJsonPaint(writer, *fPaint, urlDataManager);
1434 }
1435 if (fConstraint == SkCanvas::kStrict_SrcRectConstraint) {
Mike Klein17428132019-03-20 13:02:32 -05001436 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_STRICT, true);
Mike Klein8f4e2242019-03-20 11:59:00 -05001437 }
1438
1439 SkString desc;
Mike Klein17428132019-03-20 13:02:32 -05001440 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, fDst)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001441}
1442
Mike Klein17428132019-03-20 13:02:32 -05001443DrawImageNineCommand::DrawImageNineCommand(const SkImage* image,
1444 const SkIRect& center,
1445 const SkRect& dst,
1446 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001447 : INHERITED(kDrawImageNine_OpType)
1448 , fImage(SkRef(image))
1449 , fCenter(center)
1450 , fDst(dst)
1451 , fPaint(paint) {}
1452
Mike Klein17428132019-03-20 13:02:32 -05001453void DrawImageNineCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001454 canvas->drawImageNine(fImage.get(), fCenter, fDst, fPaint.getMaybeNull());
1455}
1456
Mike Klein17428132019-03-20 13:02:32 -05001457bool DrawImageNineCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001458 SkAutoCanvasRestore acr(canvas, true);
1459 canvas->clear(0xFFFFFFFF);
1460
1461 xlate_and_scale_to_bounds(canvas, fDst);
1462
1463 this->execute(canvas);
1464 return true;
1465}
1466
Mike Klein17428132019-03-20 13:02:32 -05001467void DrawImageNineCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001468 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001469 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_IMAGE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001470 flatten(*fImage, writer, urlDataManager);
1471 writer.endObject(); // image
1472
Mike Klein17428132019-03-20 13:02:32 -05001473 writer.appendName(DEBUGCANVAS_ATTRIBUTE_CENTER);
Mike Klein8f4e2242019-03-20 11:59:00 -05001474 MakeJsonIRect(writer, fCenter);
Mike Klein17428132019-03-20 13:02:32 -05001475 writer.appendName(DEBUGCANVAS_ATTRIBUTE_DST);
Mike Klein8f4e2242019-03-20 11:59:00 -05001476 MakeJsonRect(writer, fDst);
1477 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05001478 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001479 MakeJsonPaint(writer, *fPaint, urlDataManager);
1480 }
1481}
1482
Mike Klein17428132019-03-20 13:02:32 -05001483DrawOvalCommand::DrawOvalCommand(const SkRect& oval, const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001484 : INHERITED(kDrawOval_OpType) {
1485 fOval = oval;
1486 fPaint = paint;
1487}
1488
Mike Klein17428132019-03-20 13:02:32 -05001489void DrawOvalCommand::execute(SkCanvas* canvas) const { canvas->drawOval(fOval, fPaint); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001490
Mike Klein17428132019-03-20 13:02:32 -05001491bool DrawOvalCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001492 canvas->clear(0xFFFFFFFF);
1493 canvas->save();
1494
1495 xlate_and_scale_to_bounds(canvas, fOval);
1496
1497 SkPaint p;
1498 p.setColor(SK_ColorBLACK);
1499 p.setStyle(SkPaint::kStroke_Style);
1500
1501 canvas->drawOval(fOval, p);
1502 canvas->restore();
1503
1504 return true;
1505}
1506
Mike Klein17428132019-03-20 13:02:32 -05001507void DrawOvalCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001508 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001509 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001510 MakeJsonRect(writer, fOval);
Mike Klein17428132019-03-20 13:02:32 -05001511 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001512 MakeJsonPaint(writer, fPaint, urlDataManager);
1513}
1514
Mike Klein17428132019-03-20 13:02:32 -05001515DrawArcCommand::DrawArcCommand(const SkRect& oval,
1516 SkScalar startAngle,
1517 SkScalar sweepAngle,
1518 bool useCenter,
1519 const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001520 : INHERITED(kDrawArc_OpType) {
1521 fOval = oval;
1522 fStartAngle = startAngle;
1523 fSweepAngle = sweepAngle;
1524 fUseCenter = useCenter;
1525 fPaint = paint;
1526}
1527
Mike Klein17428132019-03-20 13:02:32 -05001528void DrawArcCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001529 canvas->drawArc(fOval, fStartAngle, fSweepAngle, fUseCenter, fPaint);
1530}
1531
Mike Klein17428132019-03-20 13:02:32 -05001532bool DrawArcCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001533 canvas->clear(0xFFFFFFFF);
1534 canvas->save();
1535
1536 xlate_and_scale_to_bounds(canvas, fOval);
1537
1538 SkPaint p;
1539 p.setColor(SK_ColorBLACK);
1540 p.setStyle(SkPaint::kStroke_Style);
1541
1542 canvas->drawArc(fOval, fStartAngle, fSweepAngle, fUseCenter, p);
1543 canvas->restore();
1544
1545 return true;
1546}
1547
Mike Klein17428132019-03-20 13:02:32 -05001548void DrawArcCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001549 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001550 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001551 MakeJsonRect(writer, fOval);
Mike Klein17428132019-03-20 13:02:32 -05001552 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_STARTANGLE, fStartAngle);
1553 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_SWEEPANGLE, fSweepAngle);
1554 writer.appendBool(DEBUGCANVAS_ATTRIBUTE_USECENTER, fUseCenter);
1555 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001556 MakeJsonPaint(writer, fPaint, urlDataManager);
1557}
1558
Mike Klein17428132019-03-20 13:02:32 -05001559DrawPaintCommand::DrawPaintCommand(const SkPaint& paint) : INHERITED(kDrawPaint_OpType) {
Mike Klein8f4e2242019-03-20 11:59:00 -05001560 fPaint = paint;
1561}
1562
Mike Klein17428132019-03-20 13:02:32 -05001563void DrawPaintCommand::execute(SkCanvas* canvas) const { canvas->drawPaint(fPaint); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001564
Mike Klein17428132019-03-20 13:02:32 -05001565bool DrawPaintCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001566 canvas->clear(0xFFFFFFFF);
1567 canvas->drawPaint(fPaint);
1568 return true;
1569}
1570
Mike Klein17428132019-03-20 13:02:32 -05001571void DrawPaintCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001572 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001573 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001574 MakeJsonPaint(writer, fPaint, urlDataManager);
1575}
1576
Mike Klein17428132019-03-20 13:02:32 -05001577DrawPathCommand::DrawPathCommand(const SkPath& path, const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001578 : INHERITED(kDrawPath_OpType) {
1579 fPath = path;
1580 fPaint = paint;
1581}
1582
Mike Klein17428132019-03-20 13:02:32 -05001583void DrawPathCommand::execute(SkCanvas* canvas) const { canvas->drawPath(fPath, fPaint); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001584
Mike Klein17428132019-03-20 13:02:32 -05001585bool DrawPathCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001586 render_path(canvas, fPath);
1587 return true;
1588}
1589
Mike Klein17428132019-03-20 13:02:32 -05001590void DrawPathCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001591 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001592 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PATH);
Mike Klein8f4e2242019-03-20 11:59:00 -05001593 MakeJsonPath(writer, fPath);
Mike Klein17428132019-03-20 13:02:32 -05001594 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001595 MakeJsonPaint(writer, fPaint, urlDataManager);
1596}
1597
Mike Klein17428132019-03-20 13:02:32 -05001598DrawRegionCommand::DrawRegionCommand(const SkRegion& region, const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001599 : INHERITED(kDrawRegion_OpType) {
1600 fRegion = region;
1601 fPaint = paint;
1602}
1603
Mike Klein17428132019-03-20 13:02:32 -05001604void DrawRegionCommand::execute(SkCanvas* canvas) const { canvas->drawRegion(fRegion, fPaint); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001605
Mike Klein17428132019-03-20 13:02:32 -05001606bool DrawRegionCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001607 render_region(canvas, fRegion);
1608 return true;
1609}
1610
Mike Klein17428132019-03-20 13:02:32 -05001611void DrawRegionCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001612 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001613 writer.appendName(DEBUGCANVAS_ATTRIBUTE_REGION);
Mike Klein8f4e2242019-03-20 11:59:00 -05001614 MakeJsonRegion(writer, fRegion);
Mike Klein17428132019-03-20 13:02:32 -05001615 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001616 MakeJsonPaint(writer, fPaint, urlDataManager);
1617}
1618
Mike Klein17428132019-03-20 13:02:32 -05001619BeginDrawPictureCommand::BeginDrawPictureCommand(const SkPicture* picture,
1620 const SkMatrix* matrix,
1621 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001622 : INHERITED(kBeginDrawPicture_OpType)
1623 , fPicture(SkRef(picture))
1624 , fMatrix(matrix)
1625 , fPaint(paint) {}
1626
Mike Klein17428132019-03-20 13:02:32 -05001627void BeginDrawPictureCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001628 if (fPaint.isValid()) {
1629 SkRect bounds = fPicture->cullRect();
1630 if (fMatrix.isValid()) {
1631 fMatrix->mapRect(&bounds);
1632 }
1633 canvas->saveLayer(&bounds, fPaint.get());
1634 }
1635
1636 if (fMatrix.isValid()) {
1637 if (!fPaint.isValid()) {
1638 canvas->save();
1639 }
1640 canvas->concat(*fMatrix);
1641 }
1642}
1643
Mike Klein17428132019-03-20 13:02:32 -05001644bool BeginDrawPictureCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001645 canvas->clear(0xFFFFFFFF);
1646 canvas->save();
1647
1648 xlate_and_scale_to_bounds(canvas, fPicture->cullRect());
1649
1650 canvas->drawPicture(fPicture.get());
1651
1652 canvas->restore();
1653
1654 return true;
1655}
1656
Mike Klein17428132019-03-20 13:02:32 -05001657EndDrawPictureCommand::EndDrawPictureCommand(bool restore)
Mike Klein8f4e2242019-03-20 11:59:00 -05001658 : INHERITED(kEndDrawPicture_OpType), fRestore(restore) {}
1659
Mike Klein17428132019-03-20 13:02:32 -05001660void EndDrawPictureCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001661 if (fRestore) {
1662 canvas->restore();
1663 }
1664}
1665
Mike Klein17428132019-03-20 13:02:32 -05001666DrawPointsCommand::DrawPointsCommand(SkCanvas::PointMode mode,
1667 size_t count,
1668 const SkPoint pts[],
1669 const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001670 : INHERITED(kDrawPoints_OpType), fMode(mode), fPts(pts, count), fPaint(paint) {}
1671
Mike Klein17428132019-03-20 13:02:32 -05001672void DrawPointsCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001673 canvas->drawPoints(fMode, fPts.count(), fPts.begin(), fPaint);
1674}
1675
Mike Klein17428132019-03-20 13:02:32 -05001676bool DrawPointsCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001677 canvas->clear(0xFFFFFFFF);
1678 canvas->save();
1679
1680 SkRect bounds;
1681
1682 bounds.setEmpty();
1683 for (int i = 0; i < fPts.count(); ++i) {
1684 SkRectPriv::GrowToInclude(&bounds, fPts[i]);
1685 }
1686
1687 xlate_and_scale_to_bounds(canvas, bounds);
1688
1689 SkPaint p;
1690 p.setColor(SK_ColorBLACK);
1691 p.setStyle(SkPaint::kStroke_Style);
1692
1693 canvas->drawPoints(fMode, fPts.count(), fPts.begin(), p);
1694 canvas->restore();
1695
1696 return true;
1697}
1698
Mike Klein17428132019-03-20 13:02:32 -05001699void DrawPointsCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001700 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001701 writer.appendString(DEBUGCANVAS_ATTRIBUTE_MODE, pointmode_name(fMode));
1702 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_POINTS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001703 for (int i = 0; i < fPts.count(); i++) {
1704 MakeJsonPoint(writer, fPts[i]);
1705 }
1706 writer.endArray(); // points
Mike Klein17428132019-03-20 13:02:32 -05001707 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001708 MakeJsonPaint(writer, fPaint, urlDataManager);
1709}
1710
Mike Klein17428132019-03-20 13:02:32 -05001711DrawTextBlobCommand::DrawTextBlobCommand(sk_sp<SkTextBlob> blob,
1712 SkScalar x,
1713 SkScalar y,
1714 const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001715 : INHERITED(kDrawTextBlob_OpType)
1716 , fBlob(std::move(blob))
1717 , fXPos(x)
1718 , fYPos(y)
1719 , fPaint(paint) {}
1720
Mike Klein17428132019-03-20 13:02:32 -05001721void DrawTextBlobCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001722 canvas->drawTextBlob(fBlob, fXPos, fYPos, fPaint);
1723}
1724
Mike Klein17428132019-03-20 13:02:32 -05001725bool DrawTextBlobCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001726 canvas->clear(SK_ColorWHITE);
1727 canvas->save();
1728
1729 SkRect bounds = fBlob->bounds().makeOffset(fXPos, fYPos);
1730 xlate_and_scale_to_bounds(canvas, bounds);
1731
1732 canvas->drawTextBlob(fBlob, fXPos, fYPos, fPaint);
1733
1734 canvas->restore();
1735
1736 return true;
1737}
1738
Mike Klein17428132019-03-20 13:02:32 -05001739void DrawTextBlobCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001740 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001741 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_RUNS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001742 SkTextBlobRunIterator iter(fBlob.get());
1743 while (!iter.done()) {
1744 writer.beginObject(); // run
Mike Klein17428132019-03-20 13:02:32 -05001745 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_GLYPHS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001746 for (uint32_t i = 0; i < iter.glyphCount(); i++) {
1747 writer.appendU32(iter.glyphs()[i]);
1748 }
1749 writer.endArray(); // glyphs
1750 if (iter.positioning() != SkTextBlobRunIterator::kDefault_Positioning) {
Mike Klein17428132019-03-20 13:02:32 -05001751 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_POSITIONS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001752 const SkScalar* iterPositions = iter.pos();
1753 for (uint32_t i = 0; i < iter.glyphCount(); i++) {
1754 switch (iter.positioning()) {
1755 case SkTextBlobRunIterator::kFull_Positioning:
1756 MakeJsonPoint(writer, iterPositions[i * 2], iterPositions[i * 2 + 1]);
1757 break;
1758 case SkTextBlobRunIterator::kHorizontal_Positioning:
1759 writer.appendFloat(iterPositions[i]);
1760 break;
1761 case SkTextBlobRunIterator::kDefault_Positioning: break;
1762 case SkTextBlobRunIterator::kRSXform_Positioning:
1763 // TODO_RSXFORM_BLOB
1764 break;
1765 }
1766 }
1767 writer.endArray(); // positions
1768 }
Mike Klein17428132019-03-20 13:02:32 -05001769 writer.appendName(DEBUGCANVAS_ATTRIBUTE_FONT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001770 MakeJsonFont(iter.font(), writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001771 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001772 MakeJsonPoint(writer, iter.offset());
1773
1774 writer.endObject(); // run
1775 iter.next();
1776 }
1777 writer.endArray(); // runs
Mike Klein17428132019-03-20 13:02:32 -05001778 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_X, fXPos);
1779 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_Y, fYPos);
Mike Klein8f4e2242019-03-20 11:59:00 -05001780 SkRect bounds = fBlob->bounds();
Mike Klein17428132019-03-20 13:02:32 -05001781 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001782 MakeJsonRect(writer, bounds);
Mike Klein17428132019-03-20 13:02:32 -05001783 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001784 MakeJsonPaint(writer, fPaint, urlDataManager);
1785
1786 SkString desc;
1787 // make the bounds local by applying the x,y
1788 bounds.offset(fXPos, fYPos);
Mike Klein17428132019-03-20 13:02:32 -05001789 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, bounds)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001790}
1791
Mike Klein17428132019-03-20 13:02:32 -05001792DrawPatchCommand::DrawPatchCommand(const SkPoint cubics[12],
1793 const SkColor colors[4],
1794 const SkPoint texCoords[4],
1795 SkBlendMode bmode,
1796 const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001797 : INHERITED(kDrawPatch_OpType), fBlendMode(bmode) {
1798 memcpy(fCubics, cubics, sizeof(fCubics));
1799 if (colors != nullptr) {
1800 memcpy(fColors, colors, sizeof(fColors));
1801 fColorsPtr = fColors;
1802 } else {
1803 fColorsPtr = nullptr;
1804 }
1805 if (texCoords != nullptr) {
1806 memcpy(fTexCoords, texCoords, sizeof(fTexCoords));
1807 fTexCoordsPtr = fTexCoords;
1808 } else {
1809 fTexCoordsPtr = nullptr;
1810 }
1811 fPaint = paint;
1812}
1813
Mike Klein17428132019-03-20 13:02:32 -05001814void DrawPatchCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001815 canvas->drawPatch(fCubics, fColorsPtr, fTexCoordsPtr, fBlendMode, fPaint);
1816}
1817
Mike Klein17428132019-03-20 13:02:32 -05001818void DrawPatchCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001819 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001820 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_CUBICS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001821 for (int i = 0; i < 12; i++) {
1822 MakeJsonPoint(writer, fCubics[i]);
1823 }
1824 writer.endArray(); // cubics
1825 if (fColorsPtr != nullptr) {
Mike Klein17428132019-03-20 13:02:32 -05001826 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_COLORS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001827 for (int i = 0; i < 4; i++) {
1828 MakeJsonColor(writer, fColorsPtr[i]);
1829 }
1830 writer.endArray(); // colors
1831 }
1832 if (fTexCoordsPtr != nullptr) {
Mike Klein17428132019-03-20 13:02:32 -05001833 writer.beginArray(DEBUGCANVAS_ATTRIBUTE_TEXTURECOORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001834 for (int i = 0; i < 4; i++) {
1835 MakeJsonPoint(writer, fTexCoords[i]);
1836 }
1837 writer.endArray(); // texCoords
1838 }
1839 // fBlendMode
1840}
1841
Mike Klein17428132019-03-20 13:02:32 -05001842DrawRectCommand::DrawRectCommand(const SkRect& rect, const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001843 : INHERITED(kDrawRect_OpType) {
1844 fRect = rect;
1845 fPaint = paint;
1846}
1847
Mike Klein17428132019-03-20 13:02:32 -05001848void DrawRectCommand::execute(SkCanvas* canvas) const { canvas->drawRect(fRect, fPaint); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001849
Mike Klein17428132019-03-20 13:02:32 -05001850void DrawRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001851 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001852 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001853 MakeJsonRect(writer, fRect);
Mike Klein17428132019-03-20 13:02:32 -05001854 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001855 MakeJsonPaint(writer, fPaint, urlDataManager);
1856
1857 SkString desc;
Mike Klein17428132019-03-20 13:02:32 -05001858 writer.appendString(DEBUGCANVAS_ATTRIBUTE_SHORTDESC, str_append(&desc, fRect)->c_str());
Mike Klein8f4e2242019-03-20 11:59:00 -05001859}
1860
Mike Klein17428132019-03-20 13:02:32 -05001861DrawRRectCommand::DrawRRectCommand(const SkRRect& rrect, const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001862 : INHERITED(kDrawRRect_OpType) {
1863 fRRect = rrect;
1864 fPaint = paint;
1865}
1866
Mike Klein17428132019-03-20 13:02:32 -05001867void DrawRRectCommand::execute(SkCanvas* canvas) const { canvas->drawRRect(fRRect, fPaint); }
Mike Klein8f4e2242019-03-20 11:59:00 -05001868
Mike Klein17428132019-03-20 13:02:32 -05001869bool DrawRRectCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001870 render_rrect(canvas, fRRect);
1871 return true;
1872}
1873
Mike Klein17428132019-03-20 13:02:32 -05001874void DrawRRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001875 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001876 writer.appendName(DEBUGCANVAS_ATTRIBUTE_COORDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05001877 make_json_rrect(writer, fRRect);
Mike Klein17428132019-03-20 13:02:32 -05001878 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001879 MakeJsonPaint(writer, fPaint, urlDataManager);
1880}
1881
Mike Klein17428132019-03-20 13:02:32 -05001882DrawDRRectCommand::DrawDRRectCommand(const SkRRect& outer,
1883 const SkRRect& inner,
1884 const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001885 : INHERITED(kDrawDRRect_OpType) {
1886 fOuter = outer;
1887 fInner = inner;
1888 fPaint = paint;
1889}
1890
Mike Klein17428132019-03-20 13:02:32 -05001891void DrawDRRectCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001892 canvas->drawDRRect(fOuter, fInner, fPaint);
1893}
1894
Mike Klein17428132019-03-20 13:02:32 -05001895bool DrawDRRectCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001896 render_drrect(canvas, fOuter, fInner);
1897 return true;
1898}
1899
Mike Klein17428132019-03-20 13:02:32 -05001900void DrawDRRectCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001901 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05001902 writer.appendName(DEBUGCANVAS_ATTRIBUTE_OUTER);
Mike Klein8f4e2242019-03-20 11:59:00 -05001903 make_json_rrect(writer, fOuter);
Mike Klein17428132019-03-20 13:02:32 -05001904 writer.appendName(DEBUGCANVAS_ATTRIBUTE_INNER);
Mike Klein8f4e2242019-03-20 11:59:00 -05001905 make_json_rrect(writer, fInner);
Mike Klein17428132019-03-20 13:02:32 -05001906 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05001907 MakeJsonPaint(writer, fPaint, urlDataManager);
1908}
1909
Mike Klein17428132019-03-20 13:02:32 -05001910DrawShadowCommand::DrawShadowCommand(const SkPath& path, const SkDrawShadowRec& rec)
Mike Klein8f4e2242019-03-20 11:59:00 -05001911 : INHERITED(kDrawShadow_OpType) {
1912 fPath = path;
1913 fShadowRec = rec;
1914}
1915
Mike Klein17428132019-03-20 13:02:32 -05001916void DrawShadowCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001917 canvas->private_draw_shadow_rec(fPath, fShadowRec);
1918}
1919
Mike Klein17428132019-03-20 13:02:32 -05001920bool DrawShadowCommand::render(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001921 render_shadow(canvas, fPath, fShadowRec);
1922 return true;
1923}
1924
Mike Klein17428132019-03-20 13:02:32 -05001925void DrawShadowCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001926 INHERITED::toJSON(writer, urlDataManager);
1927
1928 bool geometricOnly = SkToBool(fShadowRec.fFlags & SkShadowFlags::kGeometricOnly_ShadowFlag);
1929 bool transparentOccluder =
1930 SkToBool(fShadowRec.fFlags & SkShadowFlags::kTransparentOccluder_ShadowFlag);
1931
Mike Klein17428132019-03-20 13:02:32 -05001932 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PATH);
Mike Klein8f4e2242019-03-20 11:59:00 -05001933 MakeJsonPath(writer, fPath);
Mike Klein17428132019-03-20 13:02:32 -05001934 writer.appendName(DEBUGCANVAS_ATTRIBUTE_ZPLANE);
Mike Klein8f4e2242019-03-20 11:59:00 -05001935 MakeJsonPoint3(writer, fShadowRec.fZPlaneParams);
Mike Klein17428132019-03-20 13:02:32 -05001936 writer.appendName(DEBUGCANVAS_ATTRIBUTE_LIGHTPOSITION);
Mike Klein8f4e2242019-03-20 11:59:00 -05001937 MakeJsonPoint3(writer, fShadowRec.fLightPos);
Mike Klein17428132019-03-20 13:02:32 -05001938 writer.appendFloat(DEBUGCANVAS_ATTRIBUTE_LIGHTRADIUS, fShadowRec.fLightRadius);
1939 writer.appendName(DEBUGCANVAS_ATTRIBUTE_AMBIENTCOLOR);
Mike Klein8f4e2242019-03-20 11:59:00 -05001940 MakeJsonColor(writer, fShadowRec.fAmbientColor);
Mike Klein17428132019-03-20 13:02:32 -05001941 writer.appendName(DEBUGCANVAS_ATTRIBUTE_SPOTCOLOR);
Mike Klein8f4e2242019-03-20 11:59:00 -05001942 MakeJsonColor(writer, fShadowRec.fSpotColor);
Mike Klein17428132019-03-20 13:02:32 -05001943 store_bool(writer, DEBUGCANVAS_SHADOWFLAG_TRANSPARENT_OCC, transparentOccluder, false);
1944 store_bool(writer, DEBUGCANVAS_SHADOWFLAG_GEOMETRIC_ONLY, geometricOnly, false);
Mike Klein8f4e2242019-03-20 11:59:00 -05001945}
1946
1947///////////////////////////////////////////////////////////////////////////////////////////////////
1948
Mike Klein17428132019-03-20 13:02:32 -05001949DrawEdgeAAQuadCommand::DrawEdgeAAQuadCommand(const SkRect& rect,
1950 const SkPoint clip[],
1951 SkCanvas::QuadAAFlags aa,
1952 SkColor color,
1953 SkBlendMode mode)
Mike Klein8f4e2242019-03-20 11:59:00 -05001954 : INHERITED(kDrawEdgeAAQuad_OpType)
1955 , fRect(rect)
1956 , fHasClip(clip != nullptr)
1957 , fAA(aa)
1958 , fColor(color)
1959 , fMode(mode) {
1960 if (clip) {
1961 for (int i = 0; i < 4; ++i) {
1962 fClip[i] = clip[i];
1963 }
1964 }
1965}
1966
Mike Klein17428132019-03-20 13:02:32 -05001967void DrawEdgeAAQuadCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001968 canvas->experimental_DrawEdgeAAQuad(fRect, fHasClip ? fClip : nullptr, fAA, fColor, fMode);
1969}
1970
Mike Klein17428132019-03-20 13:02:32 -05001971DrawEdgeAAImageSetCommand::DrawEdgeAAImageSetCommand(const SkCanvas::ImageSetEntry set[],
1972 int count,
1973 const SkPoint dstClips[],
1974 const SkMatrix preViewMatrices[],
1975 const SkPaint* paint,
1976 SkCanvas::SrcRectConstraint constraint)
Mike Klein8f4e2242019-03-20 11:59:00 -05001977 : INHERITED(kDrawEdgeAAImageSet_OpType)
1978 , fSet(count)
1979 , fCount(count)
1980 , fPaint(paint)
1981 , fConstraint(constraint) {
1982 int totalDstClipCount, totalMatrixCount;
1983 SkCanvasPriv::GetDstClipAndMatrixCounts(set, count, &totalDstClipCount, &totalMatrixCount);
1984
1985 std::copy_n(set, count, fSet.get());
1986 fDstClips.reset(totalDstClipCount);
1987 std::copy_n(dstClips, totalDstClipCount, fDstClips.get());
1988 fPreViewMatrices.reset(totalMatrixCount);
1989 std::copy_n(preViewMatrices, totalMatrixCount, fPreViewMatrices.get());
1990}
1991
Mike Klein17428132019-03-20 13:02:32 -05001992void DrawEdgeAAImageSetCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05001993 canvas->experimental_DrawEdgeAAImageSet(fSet.get(),
1994 fCount,
1995 fDstClips.get(),
1996 fPreViewMatrices.get(),
1997 fPaint.getMaybeNull(),
1998 fConstraint);
1999}
2000
2001///////////////////////////////////////////////////////////////////////////////////////////////////
2002
Mike Klein17428132019-03-20 13:02:32 -05002003DrawDrawableCommand::DrawDrawableCommand(SkDrawable* drawable, const SkMatrix* matrix)
Mike Klein8f4e2242019-03-20 11:59:00 -05002004 : INHERITED(kDrawDrawable_OpType), fDrawable(SkRef(drawable)), fMatrix(matrix) {}
2005
Mike Klein17428132019-03-20 13:02:32 -05002006void DrawDrawableCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05002007 canvas->drawDrawable(fDrawable.get(), fMatrix.getMaybeNull());
2008}
2009
2010///////////////////////////////////////////////////////////////////////////////////////////////////
2011
Mike Klein17428132019-03-20 13:02:32 -05002012DrawVerticesCommand::DrawVerticesCommand(sk_sp<SkVertices> vertices,
2013 SkBlendMode bmode,
2014 const SkPaint& paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05002015 : INHERITED(kDrawVertices_OpType)
2016 , fVertices(std::move(vertices))
2017 , fBlendMode(bmode)
2018 , fPaint(paint) {}
2019
Mike Klein17428132019-03-20 13:02:32 -05002020void DrawVerticesCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05002021 canvas->drawVertices(fVertices, fBlendMode, fPaint);
2022}
2023
2024///////////////////////////////////////////////////////////////////////////////////////////////////
2025
Mike Klein17428132019-03-20 13:02:32 -05002026DrawAtlasCommand::DrawAtlasCommand(const SkImage* image,
2027 const SkRSXform xform[],
2028 const SkRect tex[],
2029 const SkColor colors[],
2030 int count,
2031 SkBlendMode bmode,
2032 const SkRect* cull,
2033 const SkPaint* paint)
Mike Klein8f4e2242019-03-20 11:59:00 -05002034 : INHERITED(kDrawAtlas_OpType)
2035 , fImage(SkRef(image))
2036 , fXform(xform, count)
2037 , fTex(tex, count)
2038 , fColors(colors, colors ? count : 0)
2039 , fBlendMode(bmode)
2040 , fCull(cull)
2041 , fPaint(paint) {}
2042
Mike Klein17428132019-03-20 13:02:32 -05002043void DrawAtlasCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05002044 canvas->drawAtlas(fImage.get(),
2045 fXform.begin(),
2046 fTex.begin(),
2047 fColors.isEmpty() ? nullptr : fColors.begin(),
2048 fXform.count(),
2049 fBlendMode,
2050 fCull.getMaybeNull(),
2051 fPaint.getMaybeNull());
2052}
2053
2054///////////////////////////////////////////////////////////////////////////////////////////////////
2055
Mike Klein17428132019-03-20 13:02:32 -05002056RestoreCommand::RestoreCommand() : INHERITED(kRestore_OpType) {}
Mike Klein8f4e2242019-03-20 11:59:00 -05002057
Mike Klein17428132019-03-20 13:02:32 -05002058void RestoreCommand::execute(SkCanvas* canvas) const { canvas->restore(); }
Mike Klein8f4e2242019-03-20 11:59:00 -05002059
Mike Klein17428132019-03-20 13:02:32 -05002060SaveCommand::SaveCommand() : INHERITED(kSave_OpType) {}
Mike Klein8f4e2242019-03-20 11:59:00 -05002061
Mike Klein17428132019-03-20 13:02:32 -05002062void SaveCommand::execute(SkCanvas* canvas) const { canvas->save(); }
Mike Klein8f4e2242019-03-20 11:59:00 -05002063
Mike Klein17428132019-03-20 13:02:32 -05002064SaveLayerCommand::SaveLayerCommand(const SkCanvas::SaveLayerRec& rec)
Mike Klein8f4e2242019-03-20 11:59:00 -05002065 : INHERITED(kSaveLayer_OpType)
2066 , fBounds(rec.fBounds)
2067 , fPaint(rec.fPaint)
2068 , fBackdrop(SkSafeRef(rec.fBackdrop))
2069 , fSaveLayerFlags(rec.fSaveLayerFlags) {}
2070
Mike Klein17428132019-03-20 13:02:32 -05002071void SaveLayerCommand::execute(SkCanvas* canvas) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05002072 canvas->saveLayer(
2073 SkCanvas::SaveLayerRec(fBounds.getMaybeNull(), fPaint.getMaybeNull(), fSaveLayerFlags));
2074}
2075
Mike Klein17428132019-03-20 13:02:32 -05002076void SaveLayerCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05002077 INHERITED::toJSON(writer, urlDataManager);
2078 if (fBounds.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05002079 writer.appendName(DEBUGCANVAS_ATTRIBUTE_BOUNDS);
Mike Klein8f4e2242019-03-20 11:59:00 -05002080 MakeJsonRect(writer, *fBounds);
2081 }
2082 if (fPaint.isValid()) {
Mike Klein17428132019-03-20 13:02:32 -05002083 writer.appendName(DEBUGCANVAS_ATTRIBUTE_PAINT);
Mike Klein8f4e2242019-03-20 11:59:00 -05002084 MakeJsonPaint(writer, *fPaint, urlDataManager);
2085 }
2086 if (fBackdrop != nullptr) {
Mike Klein17428132019-03-20 13:02:32 -05002087 writer.beginObject(DEBUGCANVAS_ATTRIBUTE_BACKDROP);
Mike Klein8f4e2242019-03-20 11:59:00 -05002088 flatten(fBackdrop.get(), writer, urlDataManager);
2089 writer.endObject(); // backdrop
2090 }
2091 if (fSaveLayerFlags != 0) {
2092 SkDebugf("unsupported: saveLayer flags\n");
2093 SkASSERT(false);
2094 }
2095}
2096
Mike Klein17428132019-03-20 13:02:32 -05002097SetMatrixCommand::SetMatrixCommand(const SkMatrix& matrix) : INHERITED(kSetMatrix_OpType) {
Mike Klein8f4e2242019-03-20 11:59:00 -05002098 fMatrix = matrix;
2099}
2100
Mike Klein17428132019-03-20 13:02:32 -05002101void SetMatrixCommand::execute(SkCanvas* canvas) const { canvas->setMatrix(fMatrix); }
Mike Klein8f4e2242019-03-20 11:59:00 -05002102
Mike Klein17428132019-03-20 13:02:32 -05002103void SetMatrixCommand::toJSON(SkJSONWriter& writer, UrlDataManager& urlDataManager) const {
Mike Klein8f4e2242019-03-20 11:59:00 -05002104 INHERITED::toJSON(writer, urlDataManager);
Mike Klein17428132019-03-20 13:02:32 -05002105 writer.appendName(DEBUGCANVAS_ATTRIBUTE_MATRIX);
Mike Klein8f4e2242019-03-20 11:59:00 -05002106 MakeJsonMatrix(writer, fMatrix);
2107}