blob: d58b3c935e326cb6d9dae17fa0c2c662f92a5cea [file] [log] [blame]
chudy@google.com902ebe52012-06-29 14:21:22 +00001/*
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
chudy@google.com902ebe52012-06-29 14:21:22 +00008#include "SkDrawCommand.h"
joshualitt6b3cf732016-02-17 11:20:26 -08009
ethannicholas50a8dd02016-02-10 05:40:46 -080010#include "SkBlurMaskFilter.h"
11#include "SkColorFilter.h"
12#include "SkDashPathEffect.h"
13#include "SkImageFilter.h"
brianosmanfad98562016-05-04 11:06:28 -070014#include "SkJsonWriteBuffer.h"
ethannicholas50a8dd02016-02-10 05:40:46 -080015#include "SkMaskFilter.h"
chudy@google.com902ebe52012-06-29 14:21:22 +000016#include "SkObjectParser.h"
ethannicholas50a8dd02016-02-10 05:40:46 -080017#include "SkPaintDefaults.h"
18#include "SkPathEffect.h"
robertphillips9bafc302015-02-13 11:13:00 -080019#include "SkPicture.h"
fmalitab7425172014-08-26 07:56:44 -070020#include "SkTextBlob.h"
fmalitae77f2da2015-12-08 18:59:18 -080021#include "SkTextBlobRunIterator.h"
ethannicholas50a8dd02016-02-10 05:40:46 -080022#include "SkTHash.h"
23#include "SkTypeface.h"
24#include "SkValidatingReadBuffer.h"
25#include "SkWriteBuffer.h"
msaretta5cf4f42016-06-30 10:06:51 -070026#include "picture_utils.h"
ethannicholas50a8dd02016-02-10 05:40:46 -080027
ethannicholas50a8dd02016-02-10 05:40:46 -080028#define SKDEBUGCANVAS_ATTRIBUTE_COMMAND "command"
ethannicholas807dcab2016-02-23 06:53:37 -080029#define SKDEBUGCANVAS_ATTRIBUTE_VISIBLE "visible"
ethannicholas50a8dd02016-02-10 05:40:46 -080030#define SKDEBUGCANVAS_ATTRIBUTE_MATRIX "matrix"
31#define SKDEBUGCANVAS_ATTRIBUTE_COORDS "coords"
32#define SKDEBUGCANVAS_ATTRIBUTE_BOUNDS "bounds"
33#define SKDEBUGCANVAS_ATTRIBUTE_PAINT "paint"
34#define SKDEBUGCANVAS_ATTRIBUTE_OUTER "outer"
35#define SKDEBUGCANVAS_ATTRIBUTE_INNER "inner"
36#define SKDEBUGCANVAS_ATTRIBUTE_MODE "mode"
37#define SKDEBUGCANVAS_ATTRIBUTE_POINTS "points"
38#define SKDEBUGCANVAS_ATTRIBUTE_PATH "path"
39#define SKDEBUGCANVAS_ATTRIBUTE_TEXT "text"
40#define SKDEBUGCANVAS_ATTRIBUTE_COLOR "color"
41#define SKDEBUGCANVAS_ATTRIBUTE_ALPHA "alpha"
42#define SKDEBUGCANVAS_ATTRIBUTE_STYLE "style"
43#define SKDEBUGCANVAS_ATTRIBUTE_STROKEWIDTH "strokeWidth"
44#define SKDEBUGCANVAS_ATTRIBUTE_STROKEMITER "strokeMiter"
ethannicholas1446a9a2016-02-10 14:05:02 -080045#define SKDEBUGCANVAS_ATTRIBUTE_STROKEJOIN "strokeJoin"
ethannicholas50a8dd02016-02-10 05:40:46 -080046#define SKDEBUGCANVAS_ATTRIBUTE_CAP "cap"
47#define SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS "antiAlias"
ethannicholas1446a9a2016-02-10 14:05:02 -080048#define SKDEBUGCANVAS_ATTRIBUTE_DITHER "dither"
ethannicholas50a8dd02016-02-10 05:40:46 -080049#define SKDEBUGCANVAS_ATTRIBUTE_REGION "region"
50#define SKDEBUGCANVAS_ATTRIBUTE_REGIONOP "op"
51#define SKDEBUGCANVAS_ATTRIBUTE_EDGESTYLE "edgeStyle"
52#define SKDEBUGCANVAS_ATTRIBUTE_DEVICEREGION "deviceRegion"
53#define SKDEBUGCANVAS_ATTRIBUTE_BLUR "blur"
54#define SKDEBUGCANVAS_ATTRIBUTE_SIGMA "sigma"
55#define SKDEBUGCANVAS_ATTRIBUTE_QUALITY "quality"
56#define SKDEBUGCANVAS_ATTRIBUTE_TEXTALIGN "textAlign"
57#define SKDEBUGCANVAS_ATTRIBUTE_TEXTSIZE "textSize"
58#define SKDEBUGCANVAS_ATTRIBUTE_TEXTSCALEX "textScaleX"
59#define SKDEBUGCANVAS_ATTRIBUTE_TEXTSKEWX "textSkewX"
60#define SKDEBUGCANVAS_ATTRIBUTE_DASHING "dashing"
61#define SKDEBUGCANVAS_ATTRIBUTE_INTERVALS "intervals"
62#define SKDEBUGCANVAS_ATTRIBUTE_PHASE "phase"
63#define SKDEBUGCANVAS_ATTRIBUTE_FILLTYPE "fillType"
64#define SKDEBUGCANVAS_ATTRIBUTE_VERBS "verbs"
65#define SKDEBUGCANVAS_ATTRIBUTE_NAME "name"
ethannicholasf62a8b72016-02-11 10:35:21 -080066#define SKDEBUGCANVAS_ATTRIBUTE_DATA "data"
brianosmanfad98562016-05-04 11:06:28 -070067#define SKDEBUGCANVAS_ATTRIBUTE_VALUES "values"
ethannicholas50a8dd02016-02-10 05:40:46 -080068#define SKDEBUGCANVAS_ATTRIBUTE_SHADER "shader"
69#define SKDEBUGCANVAS_ATTRIBUTE_PATHEFFECT "pathEffect"
70#define SKDEBUGCANVAS_ATTRIBUTE_MASKFILTER "maskFilter"
71#define SKDEBUGCANVAS_ATTRIBUTE_XFERMODE "xfermode"
ethannicholas1446a9a2016-02-10 14:05:02 -080072#define SKDEBUGCANVAS_ATTRIBUTE_LOOPER "looper"
ethannicholas50a8dd02016-02-10 05:40:46 -080073#define SKDEBUGCANVAS_ATTRIBUTE_BACKDROP "backdrop"
74#define SKDEBUGCANVAS_ATTRIBUTE_COLORFILTER "colorfilter"
75#define SKDEBUGCANVAS_ATTRIBUTE_IMAGEFILTER "imagefilter"
76#define SKDEBUGCANVAS_ATTRIBUTE_IMAGE "image"
77#define SKDEBUGCANVAS_ATTRIBUTE_BITMAP "bitmap"
78#define SKDEBUGCANVAS_ATTRIBUTE_SRC "src"
79#define SKDEBUGCANVAS_ATTRIBUTE_DST "dst"
80#define SKDEBUGCANVAS_ATTRIBUTE_CENTER "center"
81#define SKDEBUGCANVAS_ATTRIBUTE_STRICT "strict"
82#define SKDEBUGCANVAS_ATTRIBUTE_DESCRIPTION "description"
83#define SKDEBUGCANVAS_ATTRIBUTE_X "x"
84#define SKDEBUGCANVAS_ATTRIBUTE_Y "y"
85#define SKDEBUGCANVAS_ATTRIBUTE_RUNS "runs"
86#define SKDEBUGCANVAS_ATTRIBUTE_POSITIONS "positions"
87#define SKDEBUGCANVAS_ATTRIBUTE_GLYPHS "glyphs"
88#define SKDEBUGCANVAS_ATTRIBUTE_FONT "font"
89#define SKDEBUGCANVAS_ATTRIBUTE_TYPEFACE "typeface"
ethannicholas1446a9a2016-02-10 14:05:02 -080090#define SKDEBUGCANVAS_ATTRIBUTE_CUBICS "cubics"
91#define SKDEBUGCANVAS_ATTRIBUTE_COLORS "colors"
92#define SKDEBUGCANVAS_ATTRIBUTE_TEXTURECOORDS "textureCoords"
93#define SKDEBUGCANVAS_ATTRIBUTE_FILTERQUALITY "filterQuality"
ethannicholas50a8dd02016-02-10 05:40:46 -080094
jcgregorioee0c5552016-06-30 09:18:27 -070095#define SKDEBUGCANVAS_ATTRIBUTE_SHORTDESC "shortDesc"
reed67f62fa2016-06-29 11:36:34 -070096
ethannicholas50a8dd02016-02-10 05:40:46 -080097#define SKDEBUGCANVAS_VERB_MOVE "move"
98#define SKDEBUGCANVAS_VERB_LINE "line"
99#define SKDEBUGCANVAS_VERB_QUAD "quad"
100#define SKDEBUGCANVAS_VERB_CUBIC "cubic"
101#define SKDEBUGCANVAS_VERB_CONIC "conic"
102#define SKDEBUGCANVAS_VERB_CLOSE "close"
103
104#define SKDEBUGCANVAS_STYLE_FILL "fill"
105#define SKDEBUGCANVAS_STYLE_STROKE "stroke"
106#define SKDEBUGCANVAS_STYLE_STROKEANDFILL "strokeAndFill"
107
108#define SKDEBUGCANVAS_POINTMODE_POINTS "points"
109#define SKDEBUGCANVAS_POINTMODE_LINES "lines"
110#define SKDEBUGCANVAS_POINTMODE_POLYGON "polygon"
111
112#define SKDEBUGCANVAS_REGIONOP_DIFFERENCE "difference"
113#define SKDEBUGCANVAS_REGIONOP_INTERSECT "intersect"
114#define SKDEBUGCANVAS_REGIONOP_UNION "union"
115#define SKDEBUGCANVAS_REGIONOP_XOR "xor"
116#define SKDEBUGCANVAS_REGIONOP_REVERSE_DIFFERENCE "reverseDifference"
117#define SKDEBUGCANVAS_REGIONOP_REPLACE "replace"
118
119#define SKDEBUGCANVAS_BLURSTYLE_NORMAL "normal"
120#define SKDEBUGCANVAS_BLURSTYLE_SOLID "solid"
121#define SKDEBUGCANVAS_BLURSTYLE_OUTER "outer"
122#define SKDEBUGCANVAS_BLURSTYLE_INNER "inner"
123
124#define SKDEBUGCANVAS_BLURQUALITY_LOW "low"
125#define SKDEBUGCANVAS_BLURQUALITY_HIGH "high"
126
127#define SKDEBUGCANVAS_ALIGN_LEFT "left"
128#define SKDEBUGCANVAS_ALIGN_CENTER "center"
129#define SKDEBUGCANVAS_ALIGN_RIGHT "right"
130
131#define SKDEBUGCANVAS_FILLTYPE_WINDING "winding"
132#define SKDEBUGCANVAS_FILLTYPE_EVENODD "evenOdd"
133#define SKDEBUGCANVAS_FILLTYPE_INVERSEWINDING "inverseWinding"
134#define SKDEBUGCANVAS_FILLTYPE_INVERSEEVENODD "inverseEvenOdd"
135
136#define SKDEBUGCANVAS_CAP_BUTT "butt"
137#define SKDEBUGCANVAS_CAP_ROUND "round"
138#define SKDEBUGCANVAS_CAP_SQUARE "square"
139
ethannicholas1446a9a2016-02-10 14:05:02 -0800140#define SKDEBUGCANVAS_MITER_JOIN "miter"
141#define SKDEBUGCANVAS_ROUND_JOIN "round"
142#define SKDEBUGCANVAS_BEVEL_JOIN "bevel"
143
ethannicholas50a8dd02016-02-10 05:40:46 -0800144#define SKDEBUGCANVAS_COLORTYPE_ARGB4444 "ARGB4444"
145#define SKDEBUGCANVAS_COLORTYPE_RGBA8888 "RGBA8888"
146#define SKDEBUGCANVAS_COLORTYPE_BGRA8888 "BGRA8888"
147#define SKDEBUGCANVAS_COLORTYPE_565 "565"
148#define SKDEBUGCANVAS_COLORTYPE_GRAY8 "Gray8"
149#define SKDEBUGCANVAS_COLORTYPE_INDEX8 "Index8"
150#define SKDEBUGCANVAS_COLORTYPE_ALPHA8 "Alpha8"
151
152#define SKDEBUGCANVAS_ALPHATYPE_OPAQUE "opaque"
153#define SKDEBUGCANVAS_ALPHATYPE_PREMUL "premul"
154#define SKDEBUGCANVAS_ALPHATYPE_UNPREMUL "unpremul"
155
ethannicholas1446a9a2016-02-10 14:05:02 -0800156#define SKDEBUGCANVAS_FILTERQUALITY_NONE "none"
157#define SKDEBUGCANVAS_FILTERQUALITY_LOW "low"
158#define SKDEBUGCANVAS_FILTERQUALITY_MEDIUM "medium"
159#define SKDEBUGCANVAS_FILTERQUALITY_HIGH "high"
160
ethannicholasf62a8b72016-02-11 10:35:21 -0800161typedef SkDrawCommand* (*FROM_JSON)(Json::Value&, UrlDataManager&);
fmalitab7425172014-08-26 07:56:44 -0700162
reed67f62fa2016-06-29 11:36:34 -0700163static SkString* str_append(SkString* str, const SkRect& r) {
164 str->appendf(" [%g %g %g %g]", r.left(), r.top(), r.right(), r.bottom());
165 return str;
166}
167
chudy@google.com902ebe52012-06-29 14:21:22 +0000168// TODO(chudy): Refactor into non subclass model.
169
robertphillips9bafc302015-02-13 11:13:00 -0800170SkDrawCommand::SkDrawCommand(OpType type)
171 : fOpType(type)
robertphillips@google.com0a4805e2013-05-29 13:24:23 +0000172 , fVisible(true) {
173}
174
chudy@google.com902ebe52012-06-29 14:21:22 +0000175SkDrawCommand::~SkDrawCommand() {
chudy@google.com97cee972012-08-07 20:41:37 +0000176 fInfo.deleteAll();
chudy@google.com902ebe52012-06-29 14:21:22 +0000177}
178
robertphillips9bafc302015-02-13 11:13:00 -0800179const char* SkDrawCommand::GetCommandString(OpType type) {
chudy@google.com902ebe52012-06-29 14:21:22 +0000180 switch (type) {
fmalita160ebb22015-04-01 20:58:37 -0700181 case kBeginDrawPicture_OpType: return "BeginDrawPicture";
robertphillips9bafc302015-02-13 11:13:00 -0800182 case kClipPath_OpType: return "ClipPath";
183 case kClipRegion_OpType: return "ClipRegion";
184 case kClipRect_OpType: return "ClipRect";
185 case kClipRRect_OpType: return "ClipRRect";
robertphillips9bafc302015-02-13 11:13:00 -0800186 case kConcat_OpType: return "Concat";
robertphillipsfb409232016-06-29 10:28:11 -0700187 case kDrawAnnotation_OpType: return "DrawAnnotation";
robertphillips9bafc302015-02-13 11:13:00 -0800188 case kDrawBitmap_OpType: return "DrawBitmap";
189 case kDrawBitmapNine_OpType: return "DrawBitmapNine";
190 case kDrawBitmapRect_OpType: return "DrawBitmapRect";
191 case kDrawClear_OpType: return "DrawClear";
192 case kDrawDRRect_OpType: return "DrawDRRect";
fmalita651c9202015-07-22 10:23:01 -0700193 case kDrawImage_OpType: return "DrawImage";
194 case kDrawImageRect_OpType: return "DrawImageRect";
robertphillips9bafc302015-02-13 11:13:00 -0800195 case kDrawOval_OpType: return "DrawOval";
196 case kDrawPaint_OpType: return "DrawPaint";
197 case kDrawPatch_OpType: return "DrawPatch";
198 case kDrawPath_OpType: return "DrawPath";
robertphillips9bafc302015-02-13 11:13:00 -0800199 case kDrawPoints_OpType: return "DrawPoints";
200 case kDrawPosText_OpType: return "DrawPosText";
201 case kDrawPosTextH_OpType: return "DrawPosTextH";
202 case kDrawRect_OpType: return "DrawRect";
203 case kDrawRRect_OpType: return "DrawRRect";
robertphillips9bafc302015-02-13 11:13:00 -0800204 case kDrawText_OpType: return "DrawText";
205 case kDrawTextBlob_OpType: return "DrawTextBlob";
206 case kDrawTextOnPath_OpType: return "DrawTextOnPath";
reed45561a02016-07-07 12:47:17 -0700207 case kDrawTextRSXform_OpType: return "drawTextRSXform";
robertphillips9bafc302015-02-13 11:13:00 -0800208 case kDrawVertices_OpType: return "DrawVertices";
fmalita160ebb22015-04-01 20:58:37 -0700209 case kEndDrawPicture_OpType: return "EndDrawPicture";
robertphillips9bafc302015-02-13 11:13:00 -0800210 case kRestore_OpType: return "Restore";
211 case kSave_OpType: return "Save";
212 case kSaveLayer_OpType: return "SaveLayer";
213 case kSetMatrix_OpType: return "SetMatrix";
chudy@google.com902ebe52012-06-29 14:21:22 +0000214 default:
robertphillips9bafc302015-02-13 11:13:00 -0800215 SkDebugf("OpType error 0x%08x\n", type);
chudy@google.com902ebe52012-06-29 14:21:22 +0000216 SkASSERT(0);
217 break;
218 }
219 SkDEBUGFAIL("DrawType UNUSED\n");
halcanary96fcdcc2015-08-27 07:41:13 -0700220 return nullptr;
chudy@google.com902ebe52012-06-29 14:21:22 +0000221}
222
fmalita8c89c522014-11-08 16:18:56 -0800223SkString SkDrawCommand::toString() const {
robertphillips9bafc302015-02-13 11:13:00 -0800224 return SkString(GetCommandString(fOpType));
chudy@google.com902ebe52012-06-29 14:21:22 +0000225}
226
ethannicholasf62a8b72016-02-11 10:35:21 -0800227Json::Value SkDrawCommand::toJSON(UrlDataManager& urlDataManager) const {
ethannicholas50a8dd02016-02-10 05:40:46 -0800228 Json::Value result;
229 result[SKDEBUGCANVAS_ATTRIBUTE_COMMAND] = this->GetCommandString(fOpType);
ethannicholas807dcab2016-02-23 06:53:37 -0800230 result[SKDEBUGCANVAS_ATTRIBUTE_VISIBLE] = Json::Value(this->isVisible());
ethannicholas50a8dd02016-02-10 05:40:46 -0800231 return result;
232}
233
234#define INSTALL_FACTORY(name) factories.set(SkString(GetCommandString(k ## name ##_OpType)), \
235 (FROM_JSON) Sk ## name ## Command::fromJSON)
ethannicholasf62a8b72016-02-11 10:35:21 -0800236SkDrawCommand* SkDrawCommand::fromJSON(Json::Value& command, UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800237 static SkTHashMap<SkString, FROM_JSON> factories;
238 static bool initialized = false;
239 if (!initialized) {
240 initialized = true;
241 INSTALL_FACTORY(Restore);
242 INSTALL_FACTORY(ClipPath);
243 INSTALL_FACTORY(ClipRegion);
244 INSTALL_FACTORY(ClipRect);
245 INSTALL_FACTORY(ClipRRect);
246 INSTALL_FACTORY(Concat);
reed97660cc2016-06-28 18:54:19 -0700247 INSTALL_FACTORY(DrawAnnotation);
ethannicholas50a8dd02016-02-10 05:40:46 -0800248 INSTALL_FACTORY(DrawBitmap);
249 INSTALL_FACTORY(DrawBitmapRect);
250 INSTALL_FACTORY(DrawBitmapNine);
251 INSTALL_FACTORY(DrawImage);
252 INSTALL_FACTORY(DrawImageRect);
253 INSTALL_FACTORY(DrawOval);
254 INSTALL_FACTORY(DrawPaint);
255 INSTALL_FACTORY(DrawPath);
256 INSTALL_FACTORY(DrawPoints);
257 INSTALL_FACTORY(DrawText);
258 INSTALL_FACTORY(DrawPosText);
bungeman51190df2016-03-09 07:42:54 -0800259 INSTALL_FACTORY(DrawPosTextH);
ethannicholas50a8dd02016-02-10 05:40:46 -0800260 INSTALL_FACTORY(DrawTextOnPath);
reed45561a02016-07-07 12:47:17 -0700261 INSTALL_FACTORY(DrawTextRSXform);
ethannicholas50a8dd02016-02-10 05:40:46 -0800262 INSTALL_FACTORY(DrawTextBlob);
263
264 INSTALL_FACTORY(DrawRect);
265 INSTALL_FACTORY(DrawRRect);
266 INSTALL_FACTORY(DrawDRRect);
ethannicholas1446a9a2016-02-10 14:05:02 -0800267 INSTALL_FACTORY(DrawPatch);
ethannicholas50a8dd02016-02-10 05:40:46 -0800268 INSTALL_FACTORY(Save);
269 INSTALL_FACTORY(SaveLayer);
270 INSTALL_FACTORY(SetMatrix);
271 }
272 SkString name = SkString(command[SKDEBUGCANVAS_ATTRIBUTE_COMMAND].asCString());
273 FROM_JSON* factory = factories.find(name);
274 if (factory == nullptr) {
275 SkDebugf("no JSON factory for '%s'\n", name.c_str());
276 return nullptr;
277 }
ethannicholasf62a8b72016-02-11 10:35:21 -0800278 return (*factory)(command, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -0800279}
280
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000281namespace {
282
283void xlate_and_scale_to_bounds(SkCanvas* canvas, const SkRect& bounds) {
284 const SkISize& size = canvas->getDeviceSize();
285
286 static const SkScalar kInsetFrac = 0.9f; // Leave a border around object
287
288 canvas->translate(size.fWidth/2.0f, size.fHeight/2.0f);
289 if (bounds.width() > bounds.height()) {
290 canvas->scale(SkDoubleToScalar((kInsetFrac*size.fWidth)/bounds.width()),
291 SkDoubleToScalar((kInsetFrac*size.fHeight)/bounds.width()));
292 } else {
293 canvas->scale(SkDoubleToScalar((kInsetFrac*size.fWidth)/bounds.height()),
294 SkDoubleToScalar((kInsetFrac*size.fHeight)/bounds.height()));
295 }
296 canvas->translate(-bounds.centerX(), -bounds.centerY());
297}
skia.committer@gmail.coma0090832013-06-07 07:01:06 +0000298
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000299
300void render_path(SkCanvas* canvas, const SkPath& path) {
301 canvas->clear(0xFFFFFFFF);
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000302
303 const SkRect& bounds = path.getBounds();
fmalitab0cd8b72015-10-06 07:24:03 -0700304 if (bounds.isEmpty()) {
305 return;
306 }
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000307
fmalitab0cd8b72015-10-06 07:24:03 -0700308 SkAutoCanvasRestore acr(canvas, true);
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000309 xlate_and_scale_to_bounds(canvas, bounds);
310
311 SkPaint p;
312 p.setColor(SK_ColorBLACK);
313 p.setStyle(SkPaint::kStroke_Style);
314
315 canvas->drawPath(path, p);
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000316}
317
halcanary96fcdcc2015-08-27 07:41:13 -0700318void render_bitmap(SkCanvas* canvas, const SkBitmap& input, const SkRect* srcRect = nullptr) {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000319 const SkISize& size = canvas->getDeviceSize();
320
321 SkScalar xScale = SkIntToScalar(size.fWidth-2) / input.width();
322 SkScalar yScale = SkIntToScalar(size.fHeight-2) / input.height();
323
324 if (input.width() > input.height()) {
325 yScale *= input.height() / (float) input.width();
326 } else {
327 xScale *= input.width() / (float) input.height();
328 }
329
330 SkRect dst = SkRect::MakeXYWH(SK_Scalar1, SK_Scalar1,
331 xScale * input.width(),
332 yScale * input.height());
skia.committer@gmail.coma0090832013-06-07 07:01:06 +0000333
robertphillips96a5cff2015-09-24 06:56:27 -0700334 static const int kNumBlocks = 8;
335
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000336 canvas->clear(0xFFFFFFFF);
robertphillips96a5cff2015-09-24 06:56:27 -0700337 SkISize block = {
338 canvas->imageInfo().width()/kNumBlocks,
339 canvas->imageInfo().height()/kNumBlocks
340 };
341 for (int y = 0; y < kNumBlocks; ++y) {
342 for (int x = 0; x < kNumBlocks; ++x) {
343 SkPaint paint;
344 paint.setColor((x+y)%2 ? SK_ColorLTGRAY : SK_ColorDKGRAY);
345 SkRect r = SkRect::MakeXYWH(SkIntToScalar(x*block.width()),
346 SkIntToScalar(y*block.height()),
347 SkIntToScalar(block.width()),
348 SkIntToScalar(block.height()));
349 canvas->drawRect(r, paint);
350 }
351 }
352
reede47829b2015-08-06 10:02:53 -0700353 canvas->drawBitmapRect(input, dst, nullptr);
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000354
bsalomon49f085d2014-09-05 13:34:00 -0700355 if (srcRect) {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000356 SkRect r = SkRect::MakeLTRB(srcRect->fLeft * xScale + SK_Scalar1,
357 srcRect->fTop * yScale + SK_Scalar1,
358 srcRect->fRight * xScale + SK_Scalar1,
359 srcRect->fBottom * yScale + SK_Scalar1);
360 SkPaint p;
361 p.setColor(SK_ColorRED);
362 p.setStyle(SkPaint::kStroke_Style);
363
364 canvas->drawRect(r, p);
365 }
366}
367
368void render_rrect(SkCanvas* canvas, const SkRRect& rrect) {
369 canvas->clear(0xFFFFFFFF);
370 canvas->save();
371
372 const SkRect& bounds = rrect.getBounds();
373
374 xlate_and_scale_to_bounds(canvas, bounds);
375
376 SkPaint p;
377 p.setColor(SK_ColorBLACK);
378 p.setStyle(SkPaint::kStroke_Style);
379
380 canvas->drawRRect(rrect, p);
381 canvas->restore();
382}
skia.committer@gmail.coma0090832013-06-07 07:01:06 +0000383
commit-bot@chromium.org3d305202014-02-24 17:28:55 +0000384void render_drrect(SkCanvas* canvas, const SkRRect& outer, const SkRRect& inner) {
385 canvas->clear(0xFFFFFFFF);
386 canvas->save();
387
388 const SkRect& bounds = outer.getBounds();
389
390 xlate_and_scale_to_bounds(canvas, bounds);
391
392 SkPaint p;
393 p.setColor(SK_ColorBLACK);
394 p.setStyle(SkPaint::kStroke_Style);
395
396 canvas->drawDRRect(outer, inner, p);
397 canvas->restore();
398}
399
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +0000400};
401
brianosmanfad98562016-05-04 11:06:28 -0700402Json::Value SkDrawCommand::MakeJsonColor(const SkColor color) {
ethannicholas1446a9a2016-02-10 14:05:02 -0800403 Json::Value result(Json::arrayValue);
404 result.append(Json::Value(SkColorGetA(color)));
405 result.append(Json::Value(SkColorGetR(color)));
406 result.append(Json::Value(SkColorGetG(color)));
407 result.append(Json::Value(SkColorGetB(color)));
408 return result;
409}
410
brianosmanfad98562016-05-04 11:06:28 -0700411Json::Value SkDrawCommand::MakeJsonPoint(const SkPoint& point) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800412 Json::Value result(Json::arrayValue);
413 result.append(Json::Value(point.x()));
414 result.append(Json::Value(point.y()));
415 return result;
416}
417
brianosmanfad98562016-05-04 11:06:28 -0700418Json::Value SkDrawCommand::MakeJsonPoint(SkScalar x, SkScalar y) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800419 Json::Value result(Json::arrayValue);
420 result.append(Json::Value(x));
421 result.append(Json::Value(y));
422 return result;
423}
424
brianosmanfad98562016-05-04 11:06:28 -0700425Json::Value SkDrawCommand::MakeJsonRect(const SkRect& rect) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800426 Json::Value result(Json::arrayValue);
427 result.append(Json::Value(rect.left()));
428 result.append(Json::Value(rect.top()));
429 result.append(Json::Value(rect.right()));
430 result.append(Json::Value(rect.bottom()));
431 return result;
432}
433
joshualittbd724132016-03-03 11:39:38 -0800434Json::Value SkDrawCommand::MakeJsonIRect(const SkIRect& rect) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800435 Json::Value result(Json::arrayValue);
436 result.append(Json::Value(rect.left()));
437 result.append(Json::Value(rect.top()));
438 result.append(Json::Value(rect.right()));
439 result.append(Json::Value(rect.bottom()));
440 return result;
441}
442
443static Json::Value make_json_rrect(const SkRRect& rrect) {
444 Json::Value result(Json::arrayValue);
brianosmanfad98562016-05-04 11:06:28 -0700445 result.append(SkDrawCommand::MakeJsonRect(rrect.rect()));
446 result.append(SkDrawCommand::MakeJsonPoint(rrect.radii(SkRRect::kUpperLeft_Corner)));
447 result.append(SkDrawCommand::MakeJsonPoint(rrect.radii(SkRRect::kUpperRight_Corner)));
448 result.append(SkDrawCommand::MakeJsonPoint(rrect.radii(SkRRect::kLowerRight_Corner)));
449 result.append(SkDrawCommand::MakeJsonPoint(rrect.radii(SkRRect::kLowerLeft_Corner)));
ethannicholas50a8dd02016-02-10 05:40:46 -0800450 return result;
451}
452
joshualittbd724132016-03-03 11:39:38 -0800453Json::Value SkDrawCommand::MakeJsonMatrix(const SkMatrix& matrix) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800454 Json::Value result(Json::arrayValue);
455 Json::Value row1(Json::arrayValue);
456 row1.append(Json::Value(matrix[0]));
457 row1.append(Json::Value(matrix[1]));
458 row1.append(Json::Value(matrix[2]));
459 result.append(row1);
460 Json::Value row2(Json::arrayValue);
461 row2.append(Json::Value(matrix[3]));
462 row2.append(Json::Value(matrix[4]));
463 row2.append(Json::Value(matrix[5]));
464 result.append(row2);
465 Json::Value row3(Json::arrayValue);
466 row3.append(Json::Value(matrix[6]));
467 row3.append(Json::Value(matrix[7]));
468 row3.append(Json::Value(matrix[8]));
469 result.append(row3);
470 return result;
471}
ethannicholas1446a9a2016-02-10 14:05:02 -0800472
brianosmanfad98562016-05-04 11:06:28 -0700473Json::Value SkDrawCommand::MakeJsonPath(const SkPath& path) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800474 Json::Value result(Json::objectValue);
475 switch (path.getFillType()) {
476 case SkPath::kWinding_FillType:
477 result[SKDEBUGCANVAS_ATTRIBUTE_FILLTYPE] = SKDEBUGCANVAS_FILLTYPE_WINDING;
478 break;
479 case SkPath::kEvenOdd_FillType:
480 result[SKDEBUGCANVAS_ATTRIBUTE_FILLTYPE] = SKDEBUGCANVAS_FILLTYPE_EVENODD;
481 break;
482 case SkPath::kInverseWinding_FillType:
483 result[SKDEBUGCANVAS_ATTRIBUTE_FILLTYPE] = SKDEBUGCANVAS_FILLTYPE_INVERSEWINDING;
484 break;
485 case SkPath::kInverseEvenOdd_FillType:
486 result[SKDEBUGCANVAS_ATTRIBUTE_FILLTYPE] = SKDEBUGCANVAS_FILLTYPE_INVERSEEVENODD;
487 break;
halcanary9d524f22016-03-29 09:03:52 -0700488 }
ethannicholas50a8dd02016-02-10 05:40:46 -0800489 Json::Value verbs(Json::arrayValue);
490 SkPath::Iter iter(path, false);
491 SkPoint pts[4];
492 SkPath::Verb verb;
493 while ((verb = iter.next(pts)) != SkPath::kDone_Verb) {
494 switch (verb) {
495 case SkPath::kLine_Verb: {
496 Json::Value line(Json::objectValue);
brianosmanfad98562016-05-04 11:06:28 -0700497 line[SKDEBUGCANVAS_VERB_LINE] = MakeJsonPoint(pts[1]);
ethannicholas50a8dd02016-02-10 05:40:46 -0800498 verbs.append(line);
499 break;
500 }
501 case SkPath::kQuad_Verb: {
502 Json::Value quad(Json::objectValue);
503 Json::Value coords(Json::arrayValue);
brianosmanfad98562016-05-04 11:06:28 -0700504 coords.append(MakeJsonPoint(pts[1]));
505 coords.append(MakeJsonPoint(pts[2]));
ethannicholas50a8dd02016-02-10 05:40:46 -0800506 quad[SKDEBUGCANVAS_VERB_QUAD] = coords;
507 verbs.append(quad);
508 break;
509 }
510 case SkPath::kCubic_Verb: {
511 Json::Value cubic(Json::objectValue);
512 Json::Value coords(Json::arrayValue);
brianosmanfad98562016-05-04 11:06:28 -0700513 coords.append(MakeJsonPoint(pts[1]));
514 coords.append(MakeJsonPoint(pts[2]));
515 coords.append(MakeJsonPoint(pts[3]));
ethannicholas50a8dd02016-02-10 05:40:46 -0800516 cubic[SKDEBUGCANVAS_VERB_CUBIC] = coords;
517 verbs.append(cubic);
518 break;
519 }
520 case SkPath::kConic_Verb: {
521 Json::Value conic(Json::objectValue);
522 Json::Value coords(Json::arrayValue);
brianosmanfad98562016-05-04 11:06:28 -0700523 coords.append(MakeJsonPoint(pts[1]));
524 coords.append(MakeJsonPoint(pts[2]));
ethannicholas50a8dd02016-02-10 05:40:46 -0800525 coords.append(Json::Value(iter.conicWeight()));
526 conic[SKDEBUGCANVAS_VERB_CONIC] = coords;
527 verbs.append(conic);
528 break;
529 }
530 case SkPath::kMove_Verb: {
531 Json::Value move(Json::objectValue);
brianosmanfad98562016-05-04 11:06:28 -0700532 move[SKDEBUGCANVAS_VERB_MOVE] = MakeJsonPoint(pts[0]);
ethannicholas50a8dd02016-02-10 05:40:46 -0800533 verbs.append(move);
534 break;
535 }
536 case SkPath::kClose_Verb:
537 verbs.append(Json::Value(SKDEBUGCANVAS_VERB_CLOSE));
538 break;
539 case SkPath::kDone_Verb:
540 break;
541 }
542 }
543 result[SKDEBUGCANVAS_ATTRIBUTE_VERBS] = verbs;
544 return result;
545}
546
brianosmanfad98562016-05-04 11:06:28 -0700547Json::Value SkDrawCommand::MakeJsonRegion(const SkRegion& region) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800548 return Json::Value("<unimplemented>");
549}
550
551static Json::Value make_json_regionop(SkRegion::Op op) {
552 switch (op) {
553 case SkRegion::kDifference_Op:
554 return Json::Value(SKDEBUGCANVAS_REGIONOP_DIFFERENCE);
555 case SkRegion::kIntersect_Op:
556 return Json::Value(SKDEBUGCANVAS_REGIONOP_INTERSECT);
557 case SkRegion::kUnion_Op:
558 return Json::Value(SKDEBUGCANVAS_REGIONOP_UNION);
559 case SkRegion::kXOR_Op:
560 return Json::Value(SKDEBUGCANVAS_REGIONOP_XOR);
561 case SkRegion::kReverseDifference_Op:
562 return Json::Value(SKDEBUGCANVAS_REGIONOP_REVERSE_DIFFERENCE);
563 case SkRegion::kReplace_Op:
564 return Json::Value(SKDEBUGCANVAS_REGIONOP_REPLACE);
565 default:
566 SkASSERT(false);
567 return Json::Value("<invalid region op>");
568 };
569}
570
571static Json::Value make_json_pointmode(SkCanvas::PointMode mode) {
572 switch (mode) {
573 case SkCanvas::kPoints_PointMode:
574 return Json::Value(SKDEBUGCANVAS_POINTMODE_POINTS);
575 case SkCanvas::kLines_PointMode:
576 return Json::Value(SKDEBUGCANVAS_POINTMODE_LINES);
halcanary9d524f22016-03-29 09:03:52 -0700577 case SkCanvas::kPolygon_PointMode:
ethannicholas50a8dd02016-02-10 05:40:46 -0800578 return Json::Value(SKDEBUGCANVAS_POINTMODE_POLYGON);
579 default:
580 SkASSERT(false);
581 return Json::Value("<invalid point mode>");
582 };
583}
584
halcanary9d524f22016-03-29 09:03:52 -0700585static void store_scalar(Json::Value* target, const char* key, SkScalar value,
ethannicholasbd3dae82016-02-10 12:10:00 -0800586 SkScalar defaultValue) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800587 if (value != defaultValue) {
588 (*target)[key] = Json::Value(value);
589 }
590}
591
ethannicholasbd3dae82016-02-10 12:10:00 -0800592static void store_bool(Json::Value* target, const char* key, bool value, bool defaultValue) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800593 if (value != defaultValue) {
594 (*target)[key] = Json::Value(value);
595 }
596}
597
halcanary9d524f22016-03-29 09:03:52 -0700598static void encode_data(const void* bytes, size_t count, const char* contentType,
ethannicholasf62a8b72016-02-11 10:35:21 -0800599 UrlDataManager& urlDataManager, Json::Value* target) {
600 SkAutoTUnref<SkData> data(SkData::NewWithCopy(bytes, count));
601 SkString url = urlDataManager.addData(data, contentType);
602 *target = Json::Value(url.c_str());
ethannicholas50a8dd02016-02-10 05:40:46 -0800603}
604
brianosmanfad98562016-05-04 11:06:28 -0700605void SkDrawCommand::flatten(const SkFlattenable* flattenable, Json::Value* target,
606 UrlDataManager& urlDataManager) {
607 SkBinaryWriteBuffer buffer;
ethannicholasf62a8b72016-02-11 10:35:21 -0800608 flattenable->flatten(buffer);
609 void* data = sk_malloc_throw(buffer.bytesWritten());
610 buffer.writeToMemory(data);
611 Json::Value jsonData;
612 encode_data(data, buffer.bytesWritten(), "application/octet-stream", urlDataManager, &jsonData);
613 Json::Value jsonFlattenable;
614 jsonFlattenable[SKDEBUGCANVAS_ATTRIBUTE_NAME] = Json::Value(flattenable->getTypeName());
615 jsonFlattenable[SKDEBUGCANVAS_ATTRIBUTE_DATA] = jsonData;
brianosmanfad98562016-05-04 11:06:28 -0700616
617 SkJsonWriteBuffer jsonBuffer(&urlDataManager);
618 flattenable->flatten(jsonBuffer);
619 jsonFlattenable[SKDEBUGCANVAS_ATTRIBUTE_VALUES] = jsonBuffer.getValue();
620
ethannicholasf62a8b72016-02-11 10:35:21 -0800621 (*target) = jsonFlattenable;
622 sk_free(data);
ethannicholas50a8dd02016-02-10 05:40:46 -0800623}
624
ethannicholasf67531f2016-03-21 10:19:39 -0700625static void write_png_callback(png_structp png_ptr, png_bytep data, png_size_t length) {
626 SkWStream* out = (SkWStream*) png_get_io_ptr(png_ptr);
627 out->write(data, length);
628}
629
halcanary9d524f22016-03-29 09:03:52 -0700630void SkDrawCommand::WritePNG(const png_bytep rgba, png_uint_32 width, png_uint_32 height,
msaretta5cf4f42016-06-30 10:06:51 -0700631 SkWStream& out, bool isOpaque) {
ethannicholasf67531f2016-03-21 10:19:39 -0700632 png_structp png = png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL);
633 SkASSERT(png != nullptr);
634 png_infop info_ptr = png_create_info_struct(png);
635 SkASSERT(info_ptr != nullptr);
636 if (setjmp(png_jmpbuf(png))) {
637 SkFAIL("png encode error");
638 }
msaretta5cf4f42016-06-30 10:06:51 -0700639 png_set_write_fn(png, &out, write_png_callback, NULL);
640 int colorType = isOpaque ? PNG_COLOR_TYPE_RGB : PNG_COLOR_TYPE_RGBA;
641 png_set_IHDR(png, info_ptr, width, height, 8, colorType, PNG_INTERLACE_NONE,
ethannicholasf67531f2016-03-21 10:19:39 -0700642 PNG_COMPRESSION_TYPE_DEFAULT, PNG_FILTER_TYPE_DEFAULT);
643 png_set_compression_level(png, 1);
644 png_bytepp rows = (png_bytepp) sk_malloc_throw(height * sizeof(png_byte*));
msaretta5cf4f42016-06-30 10:06:51 -0700645 png_bytep pixels = (png_bytep) sk_malloc_throw(width * height * 4);
ethannicholasf67531f2016-03-21 10:19:39 -0700646 for (png_size_t y = 0; y < height; ++y) {
647 const png_bytep src = rgba + y * width * 4;
msaretta5cf4f42016-06-30 10:06:51 -0700648 rows[y] = pixels + y * width * 4;
ethannicholasf67531f2016-03-21 10:19:39 -0700649 for (png_size_t x = 0; x < width; ++x) {
msaretta5cf4f42016-06-30 10:06:51 -0700650 rows[y][x * 4] = src[x * 4];
651 rows[y][x * 4 + 1] = src[x * 4 + 1];
652 rows[y][x * 4 + 2] = src[x * 4 + 2];
653 rows[y][x * 4 + 3] = src[x * 4 + 3];
ethannicholasf67531f2016-03-21 10:19:39 -0700654 }
655 }
msaretta5cf4f42016-06-30 10:06:51 -0700656 png_write_info(png, info_ptr);
657 if (isOpaque) {
658 png_set_filler(png, 0xFF, PNG_FILLER_AFTER);
659 }
ethannicholasf67531f2016-03-21 10:19:39 -0700660 png_set_filter(png, 0, PNG_NO_FILTERS);
msaretta5cf4f42016-06-30 10:06:51 -0700661 png_write_image(png, &rows[0]);
ethannicholasf67531f2016-03-21 10:19:39 -0700662 png_destroy_write_struct(&png, NULL);
663 sk_free(rows);
664 sk_free(pixels);
665}
666
brianosmanfad98562016-05-04 11:06:28 -0700667bool SkDrawCommand::flatten(const SkImage& image, Json::Value* target,
668 UrlDataManager& urlDataManager) {
ethannicholasf67531f2016-03-21 10:19:39 -0700669 size_t rowBytes = 4 * image.width();
670 SkAutoFree buffer(sk_malloc_throw(rowBytes * image.height()));
halcanary9d524f22016-03-29 09:03:52 -0700671 SkImageInfo dstInfo = SkImageInfo::Make(image.width(), image.height(),
ethannicholasf67531f2016-03-21 10:19:39 -0700672 kN32_SkColorType, kPremul_SkAlphaType);
673 if (!image.readPixels(dstInfo, buffer.get(), rowBytes, 0, 0)) {
674 SkDebugf("readPixels failed\n");
675 return false;
ethannicholas50a8dd02016-02-10 05:40:46 -0800676 }
msaretta5cf4f42016-06-30 10:06:51 -0700677
678 SkBitmap bm;
679 bm.installPixels(dstInfo, buffer.get(), rowBytes);
680 sk_sp<SkData> encodedBitmap = sk_tools::encode_bitmap_for_png(bm);
681
ethannicholasf67531f2016-03-21 10:19:39 -0700682 SkDynamicMemoryWStream out;
msaretta5cf4f42016-06-30 10:06:51 -0700683 SkDrawCommand::WritePNG((const png_bytep) encodedBitmap->bytes(), image.width(), image.height(),
684 out, false);
ethannicholasf67531f2016-03-21 10:19:39 -0700685 SkData* encoded = out.copyToData();
ethannicholasf62a8b72016-02-11 10:35:21 -0800686 Json::Value jsonData;
687 encode_data(encoded->data(), encoded->size(), "image/png", urlDataManager, &jsonData);
688 (*target)[SKDEBUGCANVAS_ATTRIBUTE_DATA] = jsonData;
689 encoded->unref();
ethannicholas50a8dd02016-02-10 05:40:46 -0800690 return true;
691}
692
693static const char* color_type_name(SkColorType colorType) {
694 switch (colorType) {
695 case kARGB_4444_SkColorType:
696 return SKDEBUGCANVAS_COLORTYPE_ARGB4444;
697 case kRGBA_8888_SkColorType:
698 return SKDEBUGCANVAS_COLORTYPE_RGBA8888;
699 case kBGRA_8888_SkColorType:
700 return SKDEBUGCANVAS_COLORTYPE_BGRA8888;
701 case kRGB_565_SkColorType:
702 return SKDEBUGCANVAS_COLORTYPE_565;
703 case kGray_8_SkColorType:
704 return SKDEBUGCANVAS_COLORTYPE_GRAY8;
705 case kIndex_8_SkColorType:
706 return SKDEBUGCANVAS_COLORTYPE_INDEX8;
707 case kAlpha_8_SkColorType:
708 return SKDEBUGCANVAS_COLORTYPE_ALPHA8;
709 default:
710 SkASSERT(false);
711 return SKDEBUGCANVAS_COLORTYPE_RGBA8888;
712 }
713}
714
715static const char* alpha_type_name(SkAlphaType alphaType) {
716 switch (alphaType) {
717 case kOpaque_SkAlphaType:
718 return SKDEBUGCANVAS_ALPHATYPE_OPAQUE;
719 case kPremul_SkAlphaType:
720 return SKDEBUGCANVAS_ALPHATYPE_PREMUL;
721 case kUnpremul_SkAlphaType:
722 return SKDEBUGCANVAS_ALPHATYPE_UNPREMUL;
723 default:
724 SkASSERT(false);
725 return SKDEBUGCANVAS_ALPHATYPE_OPAQUE;
726 }
727}
728
halcanary9d524f22016-03-29 09:03:52 -0700729static Json::ArrayIndex decode_data(Json::Value data, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -0800730 const void** target) {
731 UrlDataManager::UrlData* urlData = urlDataManager.getDataFromUrl(SkString(data.asCString()));
732 if (urlData == nullptr) {
733 SkASSERT(false);
734 *target = nullptr;
735 return 0;
ethannicholas50a8dd02016-02-10 05:40:46 -0800736 }
ethannicholasf62a8b72016-02-11 10:35:21 -0800737 *target = urlData->fData->data();
738 // cast should be safe for any reasonably-sized object...
739 return (Json::ArrayIndex) urlData->fData->size();
ethannicholas50a8dd02016-02-10 05:40:46 -0800740}
741
halcanary9d524f22016-03-29 09:03:52 -0700742static SkFlattenable* load_flattenable(Json::Value jsonFlattenable,
ethannicholasf62a8b72016-02-11 10:35:21 -0800743 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800744 if (!jsonFlattenable.isMember(SKDEBUGCANVAS_ATTRIBUTE_NAME)) {
745 return nullptr;
746 }
747 const char* name = jsonFlattenable[SKDEBUGCANVAS_ATTRIBUTE_NAME].asCString();
748 SkFlattenable::Factory factory = SkFlattenable::NameToFactory(name);
749 if (factory == nullptr) {
750 SkDebugf("no factory for loading '%s'\n", name);
751 return nullptr;
752 }
ethannicholasf62a8b72016-02-11 10:35:21 -0800753 const void* data;
754 int size = decode_data(jsonFlattenable[SKDEBUGCANVAS_ATTRIBUTE_DATA], urlDataManager, &data);
ethannicholas50a8dd02016-02-10 05:40:46 -0800755 SkValidatingReadBuffer buffer(data, size);
reed60c9b582016-04-03 09:11:13 -0700756 sk_sp<SkFlattenable> result = factory(buffer);
ethannicholas50a8dd02016-02-10 05:40:46 -0800757 if (!buffer.isValid()) {
758 SkDebugf("invalid buffer loading flattenable\n");
759 return nullptr;
760 }
reed60c9b582016-04-03 09:11:13 -0700761 return result.release();
ethannicholas50a8dd02016-02-10 05:40:46 -0800762}
763
764static SkColorType colortype_from_name(const char* name) {
765 if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_ARGB4444)) {
766 return kARGB_4444_SkColorType;
767 }
768 else if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_RGBA8888)) {
769 return kRGBA_8888_SkColorType;
770 }
771 else if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_BGRA8888)) {
772 return kBGRA_8888_SkColorType;
773 }
774 else if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_565)) {
775 return kRGB_565_SkColorType;
776 }
777 else if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_GRAY8)) {
778 return kGray_8_SkColorType;
779 }
780 else if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_INDEX8)) {
781 return kIndex_8_SkColorType;
782 }
783 else if (!strcmp(name, SKDEBUGCANVAS_COLORTYPE_ALPHA8)) {
784 return kAlpha_8_SkColorType;
785 }
786 SkASSERT(false);
787 return kN32_SkColorType;
788}
789
790static SkBitmap* convert_colortype(SkBitmap* bitmap, SkColorType colorType) {
791 if (bitmap->colorType() == colorType ) {
792 return bitmap;
793 }
794 SkBitmap* dst = new SkBitmap();
795 if (bitmap->copyTo(dst, colorType)) {
796 delete bitmap;
797 return dst;
798 }
799 SkASSERT(false);
800 delete dst;
801 return bitmap;
802}
803
804// caller is responsible for freeing return value
ethannicholasf62a8b72016-02-11 10:35:21 -0800805static SkBitmap* load_bitmap(const Json::Value& jsonBitmap, UrlDataManager& urlDataManager) {
806 if (!jsonBitmap.isMember(SKDEBUGCANVAS_ATTRIBUTE_DATA)) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800807 SkDebugf("invalid bitmap\n");
808 return nullptr;
809 }
ethannicholasf62a8b72016-02-11 10:35:21 -0800810 const void* data;
811 int size = decode_data(jsonBitmap[SKDEBUGCANVAS_ATTRIBUTE_DATA], urlDataManager, &data);
reed9ce9d672016-03-17 10:51:11 -0700812 sk_sp<SkData> encoded(SkData::NewWithoutCopy(data, size));
813 sk_sp<SkImage> image(SkImage::MakeFromEncoded(std::move(encoded), nullptr));
msarett790f99a2016-03-09 06:16:55 -0800814
815 SkAutoTDelete<SkBitmap> bitmap(new SkBitmap());
816 if (nullptr != image) {
817 if (!image->asLegacyBitmap(bitmap, SkImage::kRW_LegacyBitmapMode)) {
818 SkDebugf("image decode failed\n");
819 return nullptr;
820 }
821
ethannicholas50a8dd02016-02-10 05:40:46 -0800822 if (jsonBitmap.isMember(SKDEBUGCANVAS_ATTRIBUTE_COLOR)) {
823 const char* ctName = jsonBitmap[SKDEBUGCANVAS_ATTRIBUTE_COLOR].asCString();
824 SkColorType ct = colortype_from_name(ctName);
825 if (ct != kIndex_8_SkColorType) {
mtklein18300a32016-03-16 13:53:35 -0700826 bitmap.reset(convert_colortype(bitmap.release(), ct));
ethannicholas50a8dd02016-02-10 05:40:46 -0800827 }
828 }
mtklein18300a32016-03-16 13:53:35 -0700829 return bitmap.release();
ethannicholas50a8dd02016-02-10 05:40:46 -0800830 }
831 SkDebugf("image decode failed\n");
ethannicholas50a8dd02016-02-10 05:40:46 -0800832 return nullptr;
833}
834
reed9ce9d672016-03-17 10:51:11 -0700835static sk_sp<SkImage> load_image(const Json::Value& jsonImage, UrlDataManager& urlDataManager) {
ethannicholasf62a8b72016-02-11 10:35:21 -0800836 SkBitmap* bitmap = load_bitmap(jsonImage, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -0800837 if (bitmap == nullptr) {
838 return nullptr;
839 }
reed9ce9d672016-03-17 10:51:11 -0700840 auto result = SkImage::MakeFromBitmap(*bitmap);
ethannicholas50a8dd02016-02-10 05:40:46 -0800841 delete bitmap;
842 return result;
843}
844
brianosmanfad98562016-05-04 11:06:28 -0700845bool SkDrawCommand::flatten(const SkBitmap& bitmap, Json::Value* target,
846 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800847 bitmap.lockPixels();
reed9ce9d672016-03-17 10:51:11 -0700848 sk_sp<SkImage> image(SkImage::MakeFromBitmap(bitmap));
ethannicholas50a8dd02016-02-10 05:40:46 -0800849 bitmap.unlockPixels();
850 (*target)[SKDEBUGCANVAS_ATTRIBUTE_COLOR] = Json::Value(color_type_name(bitmap.colorType()));
851 (*target)[SKDEBUGCANVAS_ATTRIBUTE_ALPHA] = Json::Value(alpha_type_name(bitmap.alphaType()));
ethannicholasf62a8b72016-02-11 10:35:21 -0800852 bool success = flatten(*image, target, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -0800853 return success;
854}
855
856static void apply_paint_color(const SkPaint& paint, Json::Value* target) {
857 SkColor color = paint.getColor();
858 if (color != SK_ColorBLACK) {
859 Json::Value colorValue(Json::arrayValue);
860 colorValue.append(Json::Value(SkColorGetA(color)));
861 colorValue.append(Json::Value(SkColorGetR(color)));
862 colorValue.append(Json::Value(SkColorGetG(color)));
863 colorValue.append(Json::Value(SkColorGetB(color)));
864 (*target)[SKDEBUGCANVAS_ATTRIBUTE_COLOR] = colorValue;;
865 }
866}
867
868static void apply_paint_style(const SkPaint& paint, Json::Value* target) {
869 SkPaint::Style style = paint.getStyle();
870 if (style != SkPaint::kFill_Style) {
871 switch (style) {
872 case SkPaint::kStroke_Style: {
873 Json::Value stroke(SKDEBUGCANVAS_STYLE_STROKE);
874 (*target)[SKDEBUGCANVAS_ATTRIBUTE_STYLE] = stroke;
875 break;
876 }
877 case SkPaint::kStrokeAndFill_Style: {
878 Json::Value strokeAndFill(SKDEBUGCANVAS_STYLE_STROKEANDFILL);
879 (*target)[SKDEBUGCANVAS_ATTRIBUTE_STYLE] = strokeAndFill;
880 break;
881 }
882 default: SkASSERT(false);
883 }
884 }
885}
886
887static void apply_paint_cap(const SkPaint& paint, Json::Value* target) {
888 SkPaint::Cap cap = paint.getStrokeCap();
889 if (cap != SkPaint::kDefault_Cap) {
890 switch (cap) {
ethannicholas1446a9a2016-02-10 14:05:02 -0800891 case SkPaint::kButt_Cap:
ethannicholas50a8dd02016-02-10 05:40:46 -0800892 (*target)[SKDEBUGCANVAS_ATTRIBUTE_CAP] = Json::Value(SKDEBUGCANVAS_CAP_BUTT);
893 break;
ethannicholas1446a9a2016-02-10 14:05:02 -0800894 case SkPaint::kRound_Cap:
ethannicholas50a8dd02016-02-10 05:40:46 -0800895 (*target)[SKDEBUGCANVAS_ATTRIBUTE_CAP] = Json::Value(SKDEBUGCANVAS_CAP_ROUND);
896 break;
ethannicholas1446a9a2016-02-10 14:05:02 -0800897 case SkPaint::kSquare_Cap:
ethannicholas50a8dd02016-02-10 05:40:46 -0800898 (*target)[SKDEBUGCANVAS_ATTRIBUTE_CAP] = Json::Value(SKDEBUGCANVAS_CAP_SQUARE);
899 break;
ethannicholas50a8dd02016-02-10 05:40:46 -0800900 default: SkASSERT(false);
901 }
902 }
903}
ethannicholas1446a9a2016-02-10 14:05:02 -0800904
905static void apply_paint_join(const SkPaint& paint, Json::Value* target) {
906 SkPaint::Join join = paint.getStrokeJoin();
907 if (join != SkPaint::kDefault_Join) {
908 switch (join) {
909 case SkPaint::kMiter_Join:
910 (*target)[SKDEBUGCANVAS_ATTRIBUTE_STROKEJOIN] = Json::Value(
911 SKDEBUGCANVAS_MITER_JOIN);
912 break;
913 case SkPaint::kRound_Join:
914 (*target)[SKDEBUGCANVAS_ATTRIBUTE_STROKEJOIN] = Json::Value(
915 SKDEBUGCANVAS_ROUND_JOIN);
916 break;
917 case SkPaint::kBevel_Join:
918 (*target)[SKDEBUGCANVAS_ATTRIBUTE_STROKEJOIN] = Json::Value(
919 SKDEBUGCANVAS_BEVEL_JOIN);
920 break;
921 default: SkASSERT(false);
922 }
923 }
924}
925
926static void apply_paint_filterquality(const SkPaint& paint, Json::Value* target) {
927 SkFilterQuality quality = paint.getFilterQuality();
928 switch (quality) {
929 case kNone_SkFilterQuality:
930 break;
931 case kLow_SkFilterQuality:
932 (*target)[SKDEBUGCANVAS_ATTRIBUTE_FILTERQUALITY] = Json::Value(
933 SKDEBUGCANVAS_FILTERQUALITY_LOW);
934 break;
935 case kMedium_SkFilterQuality:
936 (*target)[SKDEBUGCANVAS_ATTRIBUTE_FILTERQUALITY] = Json::Value(
937 SKDEBUGCANVAS_FILTERQUALITY_MEDIUM);
938 break;
939 case kHigh_SkFilterQuality:
940 (*target)[SKDEBUGCANVAS_ATTRIBUTE_FILTERQUALITY] = Json::Value(
941 SKDEBUGCANVAS_FILTERQUALITY_HIGH);
942 break;
943 }
944}
945
halcanary9d524f22016-03-29 09:03:52 -0700946static void apply_paint_maskfilter(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -0800947 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800948 SkMaskFilter* maskFilter = paint.getMaskFilter();
949 if (maskFilter != nullptr) {
950 SkMaskFilter::BlurRec blurRec;
951 if (maskFilter->asABlur(&blurRec)) {
952 Json::Value blur(Json::objectValue);
953 blur[SKDEBUGCANVAS_ATTRIBUTE_SIGMA] = Json::Value(blurRec.fSigma);
954 switch (blurRec.fStyle) {
955 case SkBlurStyle::kNormal_SkBlurStyle:
ethannicholas1446a9a2016-02-10 14:05:02 -0800956 blur[SKDEBUGCANVAS_ATTRIBUTE_STYLE] = Json::Value(
957 SKDEBUGCANVAS_BLURSTYLE_NORMAL);
ethannicholas50a8dd02016-02-10 05:40:46 -0800958 break;
959 case SkBlurStyle::kSolid_SkBlurStyle:
ethannicholas1446a9a2016-02-10 14:05:02 -0800960 blur[SKDEBUGCANVAS_ATTRIBUTE_STYLE] = Json::Value(
961 SKDEBUGCANVAS_BLURSTYLE_SOLID);
ethannicholas50a8dd02016-02-10 05:40:46 -0800962 break;
963 case SkBlurStyle::kOuter_SkBlurStyle:
ethannicholas1446a9a2016-02-10 14:05:02 -0800964 blur[SKDEBUGCANVAS_ATTRIBUTE_STYLE] = Json::Value(
965 SKDEBUGCANVAS_BLURSTYLE_OUTER);
ethannicholas50a8dd02016-02-10 05:40:46 -0800966 break;
967 case SkBlurStyle::kInner_SkBlurStyle:
ethannicholas1446a9a2016-02-10 14:05:02 -0800968 blur[SKDEBUGCANVAS_ATTRIBUTE_STYLE] = Json::Value(
969 SKDEBUGCANVAS_BLURSTYLE_INNER);
ethannicholas50a8dd02016-02-10 05:40:46 -0800970 break;
971 default:
972 SkASSERT(false);
973 }
974 switch (blurRec.fQuality) {
975 case SkBlurQuality::kLow_SkBlurQuality:
ethannicholas1446a9a2016-02-10 14:05:02 -0800976 blur[SKDEBUGCANVAS_ATTRIBUTE_QUALITY] = Json::Value(
977 SKDEBUGCANVAS_BLURQUALITY_LOW);
ethannicholas50a8dd02016-02-10 05:40:46 -0800978 break;
979 case SkBlurQuality::kHigh_SkBlurQuality:
ethannicholas1446a9a2016-02-10 14:05:02 -0800980 blur[SKDEBUGCANVAS_ATTRIBUTE_QUALITY] = Json::Value(
981 SKDEBUGCANVAS_BLURQUALITY_HIGH);
ethannicholas50a8dd02016-02-10 05:40:46 -0800982 break;
983 default:
984 SkASSERT(false);
985 }
986 (*target)[SKDEBUGCANVAS_ATTRIBUTE_BLUR] = blur;
987 } else {
988 Json::Value jsonMaskFilter;
brianosmanfad98562016-05-04 11:06:28 -0700989 SkDrawCommand::flatten(maskFilter, &jsonMaskFilter, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -0800990 (*target)[SKDEBUGCANVAS_ATTRIBUTE_MASKFILTER] = jsonMaskFilter;
991 }
992 }
993}
994
halcanary9d524f22016-03-29 09:03:52 -0700995static void apply_paint_patheffect(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -0800996 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -0800997 SkPathEffect* pathEffect = paint.getPathEffect();
998 if (pathEffect != nullptr) {
999 SkPathEffect::DashInfo dashInfo;
1000 SkPathEffect::DashType dashType = pathEffect->asADash(&dashInfo);
1001 if (dashType == SkPathEffect::kDash_DashType) {
1002 dashInfo.fIntervals = (SkScalar*) sk_malloc_throw(dashInfo.fCount * sizeof(SkScalar));
1003 pathEffect->asADash(&dashInfo);
1004 Json::Value dashing(Json::objectValue);
1005 Json::Value intervals(Json::arrayValue);
1006 for (int32_t i = 0; i < dashInfo.fCount; i++) {
1007 intervals.append(Json::Value(dashInfo.fIntervals[i]));
1008 }
1009 sk_free(dashInfo.fIntervals);
1010 dashing[SKDEBUGCANVAS_ATTRIBUTE_INTERVALS] = intervals;
1011 dashing[SKDEBUGCANVAS_ATTRIBUTE_PHASE] = dashInfo.fPhase;
1012 (*target)[SKDEBUGCANVAS_ATTRIBUTE_DASHING] = dashing;
1013 } else {
1014 Json::Value jsonPathEffect;
brianosmanfad98562016-05-04 11:06:28 -07001015 SkDrawCommand::flatten(pathEffect, &jsonPathEffect, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001016 (*target)[SKDEBUGCANVAS_ATTRIBUTE_PATHEFFECT] = jsonPathEffect;
1017 }
1018 }
1019}
halcanary9d524f22016-03-29 09:03:52 -07001020
ethannicholas50a8dd02016-02-10 05:40:46 -08001021static void apply_paint_textalign(const SkPaint& paint, Json::Value* target) {
1022 SkPaint::Align textAlign = paint.getTextAlign();
1023 if (textAlign != SkPaint::kLeft_Align) {
1024 switch (textAlign) {
1025 case SkPaint::kCenter_Align: {
1026 (*target)[SKDEBUGCANVAS_ATTRIBUTE_TEXTALIGN] = SKDEBUGCANVAS_ALIGN_CENTER;
1027 break;
1028 }
1029 case SkPaint::kRight_Align: {
1030 (*target)[SKDEBUGCANVAS_ATTRIBUTE_TEXTALIGN] = SKDEBUGCANVAS_ALIGN_RIGHT;
1031 break;
1032 }
1033 default: SkASSERT(false);
1034 }
1035 }
1036}
1037
halcanary9d524f22016-03-29 09:03:52 -07001038static void apply_paint_typeface(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -08001039 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001040 SkTypeface* typeface = paint.getTypeface();
1041 if (typeface != nullptr) {
ethannicholasf62a8b72016-02-11 10:35:21 -08001042 Json::Value jsonTypeface;
1043 SkDynamicMemoryWStream buffer;
1044 typeface->serialize(&buffer);
1045 void* data = sk_malloc_throw(buffer.bytesWritten());
1046 buffer.copyTo(data);
1047 Json::Value jsonData;
halcanary9d524f22016-03-29 09:03:52 -07001048 encode_data(data, buffer.bytesWritten(), "application/octet-stream", urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001049 &jsonData);
1050 jsonTypeface[SKDEBUGCANVAS_ATTRIBUTE_DATA] = jsonData;
1051 sk_free(data);
1052 (*target)[SKDEBUGCANVAS_ATTRIBUTE_TYPEFACE] = jsonTypeface;
ethannicholas50a8dd02016-02-10 05:40:46 -08001053 }
1054}
1055
halcanary9d524f22016-03-29 09:03:52 -07001056static void apply_paint_shader(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -08001057 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001058 SkFlattenable* shader = paint.getShader();
1059 if (shader != nullptr) {
1060 Json::Value jsonShader;
brianosmanfad98562016-05-04 11:06:28 -07001061 SkDrawCommand::flatten(shader, &jsonShader, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001062 (*target)[SKDEBUGCANVAS_ATTRIBUTE_SHADER] = jsonShader;
1063 }
1064}
1065
halcanary9d524f22016-03-29 09:03:52 -07001066static void apply_paint_xfermode(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -08001067 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001068 SkFlattenable* xfermode = paint.getXfermode();
1069 if (xfermode != nullptr) {
1070 Json::Value jsonXfermode;
brianosmanfad98562016-05-04 11:06:28 -07001071 SkDrawCommand::flatten(xfermode, &jsonXfermode, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001072 (*target)[SKDEBUGCANVAS_ATTRIBUTE_XFERMODE] = jsonXfermode;
1073 }
1074}
1075
ethannicholasf62a8b72016-02-11 10:35:21 -08001076static void apply_paint_imagefilter(const SkPaint& paint, Json::Value* target,
1077 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001078 SkFlattenable* imageFilter = paint.getImageFilter();
1079 if (imageFilter != nullptr) {
1080 Json::Value jsonImageFilter;
brianosmanfad98562016-05-04 11:06:28 -07001081 SkDrawCommand::flatten(imageFilter, &jsonImageFilter, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001082 (*target)[SKDEBUGCANVAS_ATTRIBUTE_IMAGEFILTER] = jsonImageFilter;
1083 }
1084}
1085
halcanary9d524f22016-03-29 09:03:52 -07001086static void apply_paint_colorfilter(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -08001087 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001088 SkFlattenable* colorFilter = paint.getColorFilter();
1089 if (colorFilter != nullptr) {
1090 Json::Value jsonColorFilter;
brianosmanfad98562016-05-04 11:06:28 -07001091 SkDrawCommand::flatten(colorFilter, &jsonColorFilter, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001092 (*target)[SKDEBUGCANVAS_ATTRIBUTE_COLORFILTER] = jsonColorFilter;
1093 }
1094}
1095
halcanary9d524f22016-03-29 09:03:52 -07001096static void apply_paint_looper(const SkPaint& paint, Json::Value* target,
ethannicholasf62a8b72016-02-11 10:35:21 -08001097 UrlDataManager& urlDataManager) {
ethannicholas1446a9a2016-02-10 14:05:02 -08001098 SkFlattenable* looper = paint.getLooper();
1099 if (looper != nullptr) {
1100 Json::Value jsonLooper;
brianosmanfad98562016-05-04 11:06:28 -07001101 SkDrawCommand::flatten(looper, &jsonLooper, urlDataManager);
ethannicholas1446a9a2016-02-10 14:05:02 -08001102 (*target)[SKDEBUGCANVAS_ATTRIBUTE_LOOPER] = jsonLooper;
1103 }
1104}
1105
brianosmanfad98562016-05-04 11:06:28 -07001106Json::Value SkDrawCommand::MakeJsonPaint(const SkPaint& paint, UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001107 Json::Value result(Json::objectValue);
1108 store_scalar(&result, SKDEBUGCANVAS_ATTRIBUTE_STROKEWIDTH, paint.getStrokeWidth(), 0.0f);
halcanary9d524f22016-03-29 09:03:52 -07001109 store_scalar(&result, SKDEBUGCANVAS_ATTRIBUTE_STROKEMITER, paint.getStrokeMiter(),
ethannicholas50a8dd02016-02-10 05:40:46 -08001110 SkPaintDefaults_MiterLimit);
1111 store_bool(&result, SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS, paint.isAntiAlias(), false);
ethannicholas1446a9a2016-02-10 14:05:02 -08001112 store_bool(&result, SKDEBUGCANVAS_ATTRIBUTE_DITHER, paint.isDither(), false);
halcanary9d524f22016-03-29 09:03:52 -07001113 store_scalar(&result, SKDEBUGCANVAS_ATTRIBUTE_TEXTSIZE, paint.getTextSize(),
ethannicholas50a8dd02016-02-10 05:40:46 -08001114 SkPaintDefaults_TextSize);
1115 store_scalar(&result, SKDEBUGCANVAS_ATTRIBUTE_TEXTSCALEX, paint.getTextScaleX(), SK_Scalar1);
1116 store_scalar(&result, SKDEBUGCANVAS_ATTRIBUTE_TEXTSCALEX, paint.getTextSkewX(), 0.0f);
1117 apply_paint_color(paint, &result);
1118 apply_paint_style(paint, &result);
1119 apply_paint_cap(paint, &result);
ethannicholas1446a9a2016-02-10 14:05:02 -08001120 apply_paint_join(paint, &result);
1121 apply_paint_filterquality(paint, &result);
ethannicholas50a8dd02016-02-10 05:40:46 -08001122 apply_paint_textalign(paint, &result);
ethannicholasf62a8b72016-02-11 10:35:21 -08001123 apply_paint_patheffect(paint, &result, urlDataManager);
1124 apply_paint_maskfilter(paint, &result, urlDataManager);
1125 apply_paint_shader(paint, &result, urlDataManager);
1126 apply_paint_xfermode(paint, &result, urlDataManager);
1127 apply_paint_looper(paint, &result, urlDataManager);
1128 apply_paint_imagefilter(paint, &result, urlDataManager);
1129 apply_paint_colorfilter(paint, &result, urlDataManager);
1130 apply_paint_typeface(paint, &result, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001131 return result;
1132}
1133
ethannicholas1446a9a2016-02-10 14:05:02 -08001134static SkPoint get_json_point(Json::Value point) {
1135 return SkPoint::Make(point[0].asFloat(), point[1].asFloat());
1136}
1137
1138static SkColor get_json_color(Json::Value color) {
1139 return SkColorSetARGB(color[0].asInt(), color[1].asInt(), color[2].asInt(), color[3].asInt());
1140}
1141
ethannicholas50a8dd02016-02-10 05:40:46 -08001142static void extract_json_paint_color(Json::Value& jsonPaint, SkPaint* target) {
1143 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_COLOR)) {
ethannicholas1446a9a2016-02-10 14:05:02 -08001144 target->setColor(get_json_color(jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_COLOR]));
ethannicholas50a8dd02016-02-10 05:40:46 -08001145 }
1146}
1147
halcanary9d524f22016-03-29 09:03:52 -07001148static void extract_json_paint_shader(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001149 SkPaint* target) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001150 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_SHADER)) {
1151 Json::Value jsonShader = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_SHADER];
ethannicholasf62a8b72016-02-11 10:35:21 -08001152 SkShader* shader = (SkShader*) load_flattenable(jsonShader, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001153 if (shader != nullptr) {
reedfe630452016-03-25 09:08:00 -07001154 target->setShader(sk_ref_sp(shader));
ethannicholas50a8dd02016-02-10 05:40:46 -08001155 }
1156 }
1157}
1158
halcanary9d524f22016-03-29 09:03:52 -07001159static void extract_json_paint_patheffect(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001160 SkPaint* target) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001161 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_PATHEFFECT)) {
1162 Json::Value jsonPathEffect = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_PATHEFFECT];
reeda4393342016-03-18 11:22:57 -07001163 sk_sp<SkPathEffect> pathEffect((SkPathEffect*)load_flattenable(jsonPathEffect,
1164 urlDataManager));
ethannicholas50a8dd02016-02-10 05:40:46 -08001165 if (pathEffect != nullptr) {
1166 target->setPathEffect(pathEffect);
ethannicholas50a8dd02016-02-10 05:40:46 -08001167 }
1168 }
1169}
1170
halcanary9d524f22016-03-29 09:03:52 -07001171static void extract_json_paint_maskfilter(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001172 SkPaint* target) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001173 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_MASKFILTER)) {
1174 Json::Value jsonMaskFilter = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_MASKFILTER];
reedefdfd512016-04-04 10:02:58 -07001175 sk_sp<SkMaskFilter> maskFilter((SkMaskFilter*)load_flattenable(jsonMaskFilter,
1176 urlDataManager));
1177 if (maskFilter) {
1178 target->setMaskFilter(std::move(maskFilter));
ethannicholas50a8dd02016-02-10 05:40:46 -08001179 }
1180 }
1181}
1182
halcanary9d524f22016-03-29 09:03:52 -07001183static void extract_json_paint_colorfilter(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001184 SkPaint* target) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001185 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_COLORFILTER)) {
1186 Json::Value jsonColorFilter = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_COLORFILTER];
reedd053ce92016-03-22 10:17:23 -07001187 sk_sp<SkColorFilter> colorFilter((SkColorFilter*)load_flattenable(jsonColorFilter,
1188 urlDataManager));
ethannicholas50a8dd02016-02-10 05:40:46 -08001189 if (colorFilter != nullptr) {
1190 target->setColorFilter(colorFilter);
ethannicholas50a8dd02016-02-10 05:40:46 -08001191 }
1192 }
1193}
1194
halcanary9d524f22016-03-29 09:03:52 -07001195static void extract_json_paint_xfermode(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001196 SkPaint* target) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001197 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_XFERMODE)) {
1198 Json::Value jsonXfermode = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_XFERMODE];
reedcfb6bdf2016-03-29 11:32:50 -07001199 sk_sp<SkXfermode> xfermode((SkXfermode*) load_flattenable(jsonXfermode, urlDataManager));
ethannicholas50a8dd02016-02-10 05:40:46 -08001200 if (xfermode != nullptr) {
1201 target->setXfermode(xfermode);
ethannicholas50a8dd02016-02-10 05:40:46 -08001202 }
1203 }
1204}
1205
halcanary9d524f22016-03-29 09:03:52 -07001206static void extract_json_paint_looper(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001207 SkPaint* target) {
ethannicholas1446a9a2016-02-10 14:05:02 -08001208 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_LOOPER)) {
1209 Json::Value jsonLooper = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_LOOPER];
reed7b380d02016-03-21 13:25:16 -07001210 sk_sp<SkDrawLooper> looper((SkDrawLooper*) load_flattenable(jsonLooper, urlDataManager));
ethannicholas1446a9a2016-02-10 14:05:02 -08001211 if (looper != nullptr) {
reed7b380d02016-03-21 13:25:16 -07001212 target->setLooper(std::move(looper));
ethannicholas1446a9a2016-02-10 14:05:02 -08001213 }
1214 }
1215}
1216
halcanary9d524f22016-03-29 09:03:52 -07001217static void extract_json_paint_imagefilter(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001218 SkPaint* target) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001219 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_IMAGEFILTER)) {
1220 Json::Value jsonImageFilter = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_IMAGEFILTER];
halcanary9d524f22016-03-29 09:03:52 -07001221 SkImageFilter* imageFilter = (SkImageFilter*) load_flattenable(jsonImageFilter,
ethannicholasf62a8b72016-02-11 10:35:21 -08001222 urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001223 if (imageFilter != nullptr) {
1224 target->setImageFilter(imageFilter);
1225 imageFilter->unref();
1226 }
1227 }
1228}
1229
halcanary9d524f22016-03-29 09:03:52 -07001230static void extract_json_paint_typeface(Json::Value& jsonPaint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001231 SkPaint* target) {
1232 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_TYPEFACE)) {
1233 Json::Value jsonTypeface = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_TYPEFACE];
1234 Json::Value jsonData = jsonTypeface[SKDEBUGCANVAS_ATTRIBUTE_DATA];
1235 const void* data;
1236 Json::ArrayIndex length = decode_data(jsonData, urlDataManager, &data);
1237 SkMemoryStream buffer(data, length);
bungeman13b9c952016-05-12 10:09:30 -07001238 target->setTypeface(SkTypeface::MakeDeserialize(&buffer));
ethannicholasf62a8b72016-02-11 10:35:21 -08001239 }
1240}
1241
ethannicholas50a8dd02016-02-10 05:40:46 -08001242static void extract_json_paint_style(Json::Value& jsonPaint, SkPaint* target) {
1243 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_STYLE)) {
1244 const char* style = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_STYLE].asCString();
1245 if (!strcmp(style, SKDEBUGCANVAS_STYLE_FILL)) {
1246 target->setStyle(SkPaint::kFill_Style);
1247 }
1248 else if (!strcmp(style, SKDEBUGCANVAS_STYLE_STROKE)) {
1249 target->setStyle(SkPaint::kStroke_Style);
1250 }
1251 else if (!strcmp(style, SKDEBUGCANVAS_STYLE_STROKEANDFILL)) {
1252 target->setStyle(SkPaint::kStrokeAndFill_Style);
1253 }
1254 }
1255}
1256
1257static void extract_json_paint_strokewidth(Json::Value& jsonPaint, SkPaint* target) {
1258 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_STROKEWIDTH)) {
1259 float strokeWidth = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_STROKEWIDTH].asFloat();
1260 target->setStrokeWidth(strokeWidth);
halcanary9d524f22016-03-29 09:03:52 -07001261 }
ethannicholas50a8dd02016-02-10 05:40:46 -08001262}
1263
1264static void extract_json_paint_strokemiter(Json::Value& jsonPaint, SkPaint* target) {
1265 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_STROKEMITER)) {
1266 float strokeMiter = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_STROKEMITER].asFloat();
1267 target->setStrokeMiter(strokeMiter);
halcanary9d524f22016-03-29 09:03:52 -07001268 }
ethannicholas50a8dd02016-02-10 05:40:46 -08001269}
1270
ethannicholas1446a9a2016-02-10 14:05:02 -08001271static void extract_json_paint_strokejoin(Json::Value& jsonPaint, SkPaint* target) {
1272 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_STROKEJOIN)) {
1273 const char* join = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_STROKEJOIN].asCString();
1274 if (!strcmp(join, SKDEBUGCANVAS_MITER_JOIN)) {
1275 target->setStrokeJoin(SkPaint::kMiter_Join);
1276 }
1277 else if (!strcmp(join, SKDEBUGCANVAS_ROUND_JOIN)) {
1278 target->setStrokeJoin(SkPaint::kRound_Join);
1279 }
1280 else if (!strcmp(join, SKDEBUGCANVAS_BEVEL_JOIN)) {
1281 target->setStrokeJoin(SkPaint::kBevel_Join);
1282 }
1283 else {
1284 SkASSERT(false);
1285 }
1286 }
1287}
1288
ethannicholas50a8dd02016-02-10 05:40:46 -08001289static void extract_json_paint_cap(Json::Value& jsonPaint, SkPaint* target) {
1290 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_CAP)) {
1291 const char* cap = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_CAP].asCString();
1292 if (!strcmp(cap, SKDEBUGCANVAS_CAP_BUTT)) {
1293 target->setStrokeCap(SkPaint::kButt_Cap);
1294 }
1295 else if (!strcmp(cap, SKDEBUGCANVAS_CAP_ROUND)) {
1296 target->setStrokeCap(SkPaint::kRound_Cap);
1297 }
1298 else if (!strcmp(cap, SKDEBUGCANVAS_CAP_SQUARE)) {
1299 target->setStrokeCap(SkPaint::kSquare_Cap);
1300 }
1301 }
1302}
1303
ethannicholas1446a9a2016-02-10 14:05:02 -08001304static void extract_json_paint_filterquality(Json::Value& jsonPaint, SkPaint* target) {
1305 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_FILTERQUALITY)) {
1306 const char* quality = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_FILTERQUALITY].asCString();
1307 if (!strcmp(quality, SKDEBUGCANVAS_FILTERQUALITY_NONE)) {
1308 target->setFilterQuality(kNone_SkFilterQuality);
1309 }
1310 else if (!strcmp(quality, SKDEBUGCANVAS_FILTERQUALITY_LOW)) {
1311 target->setFilterQuality(kLow_SkFilterQuality);
1312 }
1313 else if (!strcmp(quality, SKDEBUGCANVAS_FILTERQUALITY_MEDIUM)) {
1314 target->setFilterQuality(kMedium_SkFilterQuality);
1315 }
1316 else if (!strcmp(quality, SKDEBUGCANVAS_FILTERQUALITY_HIGH)) {
1317 target->setFilterQuality(kHigh_SkFilterQuality);
1318 }
1319 }
1320}
1321
ethannicholas50a8dd02016-02-10 05:40:46 -08001322static void extract_json_paint_antialias(Json::Value& jsonPaint, SkPaint* target) {
1323 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS)) {
1324 target->setAntiAlias(jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS].asBool());
1325 }
1326}
1327
ethannicholas1446a9a2016-02-10 14:05:02 -08001328static void extract_json_paint_dither(Json::Value& jsonPaint, SkPaint* target) {
1329 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_DITHER)) {
1330 target->setDither(jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_DITHER].asBool());
1331 }
1332}
1333
ethannicholas50a8dd02016-02-10 05:40:46 -08001334static void extract_json_paint_blur(Json::Value& jsonPaint, SkPaint* target) {
1335 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_BLUR)) {
1336 Json::Value blur = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_BLUR];
1337 SkScalar sigma = blur[SKDEBUGCANVAS_ATTRIBUTE_SIGMA].asFloat();
1338 SkBlurStyle style;
1339 const char* jsonStyle = blur[SKDEBUGCANVAS_ATTRIBUTE_STYLE].asCString();
1340 if (!strcmp(jsonStyle, SKDEBUGCANVAS_BLURSTYLE_NORMAL)) {
1341 style = SkBlurStyle::kNormal_SkBlurStyle;
1342 }
1343 else if (!strcmp(jsonStyle, SKDEBUGCANVAS_BLURSTYLE_SOLID)) {
1344 style = SkBlurStyle::kSolid_SkBlurStyle;
1345 }
1346 else if (!strcmp(jsonStyle, SKDEBUGCANVAS_BLURSTYLE_OUTER)) {
1347 style = SkBlurStyle::kOuter_SkBlurStyle;
1348 }
1349 else if (!strcmp(jsonStyle, SKDEBUGCANVAS_BLURSTYLE_INNER)) {
1350 style = SkBlurStyle::kInner_SkBlurStyle;
1351 }
1352 else {
1353 SkASSERT(false);
1354 style = SkBlurStyle::kNormal_SkBlurStyle;
1355 }
1356 SkBlurMaskFilter::BlurFlags flags;
1357 const char* jsonQuality = blur[SKDEBUGCANVAS_ATTRIBUTE_QUALITY].asCString();
1358 if (!strcmp(jsonQuality, SKDEBUGCANVAS_BLURQUALITY_LOW)) {
1359 flags = SkBlurMaskFilter::BlurFlags::kNone_BlurFlag;
1360 }
1361 else if (!strcmp(jsonQuality, SKDEBUGCANVAS_BLURQUALITY_HIGH)) {
1362 flags = SkBlurMaskFilter::BlurFlags::kHighQuality_BlurFlag;
1363 }
1364 else {
1365 SkASSERT(false);
1366 flags = SkBlurMaskFilter::BlurFlags::kNone_BlurFlag;
1367 }
reedefdfd512016-04-04 10:02:58 -07001368 target->setMaskFilter(SkBlurMaskFilter::Make(style, sigma, flags));
ethannicholas50a8dd02016-02-10 05:40:46 -08001369 }
1370}
1371
1372static void extract_json_paint_dashing(Json::Value& jsonPaint, SkPaint* target) {
1373 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_DASHING)) {
1374 Json::Value dash = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_DASHING];
1375 Json::Value jsonIntervals = dash[SKDEBUGCANVAS_ATTRIBUTE_INTERVALS];
1376 Json::ArrayIndex count = jsonIntervals.size();
1377 SkScalar* intervals = (SkScalar*) sk_malloc_throw(count * sizeof(SkScalar));
1378 for (Json::ArrayIndex i = 0; i < count; i++) {
1379 intervals[i] = jsonIntervals[i].asFloat();
1380 }
1381 SkScalar phase = dash[SKDEBUGCANVAS_ATTRIBUTE_PHASE].asFloat();
reeda4393342016-03-18 11:22:57 -07001382 target->setPathEffect(SkDashPathEffect::Make(intervals, count, phase));
ethannicholas50a8dd02016-02-10 05:40:46 -08001383 sk_free(intervals);
1384 }
1385}
1386
1387static void extract_json_paint_textalign(Json::Value& jsonPaint, SkPaint* target) {
1388 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_TEXTALIGN)) {
1389 SkPaint::Align textAlign;
1390 const char* jsonAlign = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_TEXTALIGN].asCString();
1391 if (!strcmp(jsonAlign, SKDEBUGCANVAS_ALIGN_LEFT)) {
1392 textAlign = SkPaint::kLeft_Align;
1393 }
1394 else if (!strcmp(jsonAlign, SKDEBUGCANVAS_ALIGN_CENTER)) {
1395 textAlign = SkPaint::kCenter_Align;
1396 }
1397 else if (!strcmp(jsonAlign, SKDEBUGCANVAS_ALIGN_RIGHT)) {
1398 textAlign = SkPaint::kRight_Align;
1399 }
1400 else {
1401 SkASSERT(false);
1402 textAlign = SkPaint::kLeft_Align;
1403 }
1404 target->setTextAlign(textAlign);
1405 }
1406}
1407
1408static void extract_json_paint_textsize(Json::Value& jsonPaint, SkPaint* target) {
1409 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_TEXTSIZE)) {
1410 float textSize = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_TEXTSIZE].asFloat();
1411 target->setTextSize(textSize);
1412 }
1413}
1414
1415static void extract_json_paint_textscalex(Json::Value& jsonPaint, SkPaint* target) {
1416 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_TEXTSCALEX)) {
1417 float textScaleX = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_TEXTSCALEX].asFloat();
1418 target->setTextScaleX(textScaleX);
1419 }
1420}
1421
1422static void extract_json_paint_textskewx(Json::Value& jsonPaint, SkPaint* target) {
1423 if (jsonPaint.isMember(SKDEBUGCANVAS_ATTRIBUTE_TEXTSKEWX)) {
1424 float textSkewX = jsonPaint[SKDEBUGCANVAS_ATTRIBUTE_TEXTSKEWX].asFloat();
1425 target->setTextSkewX(textSkewX);
1426 }
1427}
1428
halcanary9d524f22016-03-29 09:03:52 -07001429static void extract_json_paint(Json::Value& paint, UrlDataManager& urlDataManager,
ethannicholasf62a8b72016-02-11 10:35:21 -08001430 SkPaint* result) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001431 extract_json_paint_color(paint, result);
ethannicholasf62a8b72016-02-11 10:35:21 -08001432 extract_json_paint_shader(paint, urlDataManager, result);
1433 extract_json_paint_patheffect(paint, urlDataManager, result);
1434 extract_json_paint_maskfilter(paint, urlDataManager, result);
1435 extract_json_paint_colorfilter(paint, urlDataManager, result);
1436 extract_json_paint_xfermode(paint, urlDataManager, result);
1437 extract_json_paint_looper(paint, urlDataManager, result);
1438 extract_json_paint_imagefilter(paint, urlDataManager, result);
1439 extract_json_paint_typeface(paint, urlDataManager, result);
ethannicholas50a8dd02016-02-10 05:40:46 -08001440 extract_json_paint_style(paint, result);
1441 extract_json_paint_strokewidth(paint, result);
1442 extract_json_paint_strokemiter(paint, result);
ethannicholas1446a9a2016-02-10 14:05:02 -08001443 extract_json_paint_strokejoin(paint, result);
ethannicholas50a8dd02016-02-10 05:40:46 -08001444 extract_json_paint_cap(paint, result);
ethannicholas1446a9a2016-02-10 14:05:02 -08001445 extract_json_paint_filterquality(paint, result);
ethannicholas50a8dd02016-02-10 05:40:46 -08001446 extract_json_paint_antialias(paint, result);
ethannicholas1446a9a2016-02-10 14:05:02 -08001447 extract_json_paint_dither(paint, result);
ethannicholas50a8dd02016-02-10 05:40:46 -08001448 extract_json_paint_blur(paint, result);
1449 extract_json_paint_dashing(paint, result);
1450 extract_json_paint_textalign(paint, result);
1451 extract_json_paint_textsize(paint, result);
1452 extract_json_paint_textscalex(paint, result);
1453 extract_json_paint_textskewx(paint, result);
ethannicholas50a8dd02016-02-10 05:40:46 -08001454}
1455
1456static void extract_json_rect(Json::Value& rect, SkRect* result) {
1457 result->set(rect[0].asFloat(), rect[1].asFloat(), rect[2].asFloat(), rect[3].asFloat());
1458}
1459
1460static void extract_json_irect(Json::Value& rect, SkIRect* result) {
1461 result->set(rect[0].asInt(), rect[1].asInt(), rect[2].asInt(), rect[3].asInt());
1462}
1463
1464static void extract_json_rrect(Json::Value& rrect, SkRRect* result) {
1465 SkVector radii[4] = {
halcanary9d524f22016-03-29 09:03:52 -07001466 { rrect[1][0].asFloat(), rrect[1][1].asFloat() },
1467 { rrect[2][0].asFloat(), rrect[2][1].asFloat() },
1468 { rrect[3][0].asFloat(), rrect[3][1].asFloat() },
ethannicholas50a8dd02016-02-10 05:40:46 -08001469 { rrect[4][0].asFloat(), rrect[4][1].asFloat() }
1470 };
halcanary9d524f22016-03-29 09:03:52 -07001471 result->setRectRadii(SkRect::MakeLTRB(rrect[0][0].asFloat(), rrect[0][1].asFloat(),
1472 rrect[0][2].asFloat(), rrect[0][3].asFloat()),
ethannicholas50a8dd02016-02-10 05:40:46 -08001473 radii);
1474}
1475
1476static void extract_json_matrix(Json::Value& matrix, SkMatrix* result) {
halcanary9d524f22016-03-29 09:03:52 -07001477 SkScalar values[] = {
ethannicholas50a8dd02016-02-10 05:40:46 -08001478 matrix[0][0].asFloat(), matrix[0][1].asFloat(), matrix[0][2].asFloat(),
1479 matrix[1][0].asFloat(), matrix[1][1].asFloat(), matrix[1][2].asFloat(),
halcanary9d524f22016-03-29 09:03:52 -07001480 matrix[2][0].asFloat(), matrix[2][1].asFloat(), matrix[2][2].asFloat()
ethannicholas50a8dd02016-02-10 05:40:46 -08001481 };
1482 result->set9(values);
1483}
1484
1485static void extract_json_path(Json::Value& path, SkPath* result) {
1486 const char* fillType = path[SKDEBUGCANVAS_ATTRIBUTE_FILLTYPE].asCString();
1487 if (!strcmp(fillType, SKDEBUGCANVAS_FILLTYPE_WINDING)) {
1488 result->setFillType(SkPath::kWinding_FillType);
1489 }
1490 else if (!strcmp(fillType, SKDEBUGCANVAS_FILLTYPE_EVENODD)) {
1491 result->setFillType(SkPath::kEvenOdd_FillType);
1492 }
1493 else if (!strcmp(fillType, SKDEBUGCANVAS_FILLTYPE_INVERSEWINDING)) {
1494 result->setFillType(SkPath::kInverseWinding_FillType);
1495 }
1496 else if (!strcmp(fillType, SKDEBUGCANVAS_FILLTYPE_INVERSEEVENODD)) {
1497 result->setFillType(SkPath::kInverseEvenOdd_FillType);
1498 }
1499 Json::Value verbs = path[SKDEBUGCANVAS_ATTRIBUTE_VERBS];
1500 for (Json::ArrayIndex i = 0; i < verbs.size(); i++) {
1501 Json::Value verb = verbs[i];
1502 if (verb.isString()) {
1503 SkASSERT(!strcmp(verb.asCString(), SKDEBUGCANVAS_VERB_CLOSE));
1504 result->close();
1505 }
1506 else {
1507 if (verb.isMember(SKDEBUGCANVAS_VERB_MOVE)) {
1508 Json::Value move = verb[SKDEBUGCANVAS_VERB_MOVE];
1509 result->moveTo(move[0].asFloat(), move[1].asFloat());
1510 }
1511 else if (verb.isMember(SKDEBUGCANVAS_VERB_LINE)) {
1512 Json::Value line = verb[SKDEBUGCANVAS_VERB_LINE];
1513 result->lineTo(line[0].asFloat(), line[1].asFloat());
1514 }
1515 else if (verb.isMember(SKDEBUGCANVAS_VERB_QUAD)) {
1516 Json::Value quad = verb[SKDEBUGCANVAS_VERB_QUAD];
1517 result->quadTo(quad[0][0].asFloat(), quad[0][1].asFloat(),
1518 quad[1][0].asFloat(), quad[1][1].asFloat());
1519 }
1520 else if (verb.isMember(SKDEBUGCANVAS_VERB_CUBIC)) {
1521 Json::Value cubic = verb[SKDEBUGCANVAS_VERB_CUBIC];
1522 result->cubicTo(cubic[0][0].asFloat(), cubic[0][1].asFloat(),
1523 cubic[1][0].asFloat(), cubic[1][1].asFloat(),
1524 cubic[2][0].asFloat(), cubic[2][1].asFloat());
1525 }
1526 else if (verb.isMember(SKDEBUGCANVAS_VERB_CONIC)) {
1527 Json::Value conic = verb[SKDEBUGCANVAS_VERB_CONIC];
1528 result->conicTo(conic[0][0].asFloat(), conic[0][1].asFloat(),
1529 conic[1][0].asFloat(), conic[1][1].asFloat(),
1530 conic[2].asFloat());
1531 }
1532 else {
1533 SkASSERT(false);
1534 }
1535 }
1536 }
1537}
1538
1539SkRegion::Op get_json_regionop(Json::Value& jsonOp) {
1540 const char* op = jsonOp.asCString();
1541 if (!strcmp(op, SKDEBUGCANVAS_REGIONOP_DIFFERENCE)) {
1542 return SkRegion::kDifference_Op;
1543 }
1544 else if (!strcmp(op, SKDEBUGCANVAS_REGIONOP_INTERSECT)) {
1545 return SkRegion::kIntersect_Op;
1546 }
1547 else if (!strcmp(op, SKDEBUGCANVAS_REGIONOP_UNION)) {
1548 return SkRegion::kUnion_Op;
1549 }
1550 else if (!strcmp(op, SKDEBUGCANVAS_REGIONOP_XOR)) {
1551 return SkRegion::kXOR_Op;
1552 }
1553 else if (!strcmp(op, SKDEBUGCANVAS_REGIONOP_REVERSE_DIFFERENCE)) {
1554 return SkRegion::kReverseDifference_Op;
1555 }
1556 else if (!strcmp(op, SKDEBUGCANVAS_REGIONOP_REPLACE)) {
1557 return SkRegion::kReplace_Op;
1558 }
1559 SkASSERT(false);
1560 return SkRegion::kIntersect_Op;
1561}
1562
ethannicholas1446a9a2016-02-10 14:05:02 -08001563SkClearCommand::SkClearCommand(SkColor color) : INHERITED(kDrawClear_OpType) {
1564 fColor = color;
1565 fInfo.push(SkObjectParser::CustomTextToString("No Parameters"));
1566}
1567
1568void SkClearCommand::execute(SkCanvas* canvas) const {
1569 canvas->clear(fColor);
1570}
1571
ethannicholasf62a8b72016-02-11 10:35:21 -08001572Json::Value SkClearCommand::toJSON(UrlDataManager& urlDataManager) const {
1573 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07001574 result[SKDEBUGCANVAS_ATTRIBUTE_COLOR] = MakeJsonColor(fColor);
ethannicholas1446a9a2016-02-10 14:05:02 -08001575 return result;
1576}
1577
ethannicholasf62a8b72016-02-11 10:35:21 -08001578 SkClearCommand* SkClearCommand::fromJSON(Json::Value& command, UrlDataManager& urlDataManager) {
ethannicholas1446a9a2016-02-10 14:05:02 -08001579 Json::Value color = command[SKDEBUGCANVAS_ATTRIBUTE_COLOR];
1580 return new SkClearCommand(get_json_color(color));
1581}
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00001582
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00001583SkClipPathCommand::SkClipPathCommand(const SkPath& path, SkRegion::Op op, bool doAA)
robertphillips9bafc302015-02-13 11:13:00 -08001584 : INHERITED(kClipPath_OpType) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001585 fPath = path;
1586 fOp = op;
1587 fDoAA = doAA;
chudy@google.com902ebe52012-06-29 14:21:22 +00001588
robertphillips@google.com91217d02013-03-17 18:33:46 +00001589 fInfo.push(SkObjectParser::PathToString(path));
1590 fInfo.push(SkObjectParser::RegionOpToString(op));
1591 fInfo.push(SkObjectParser::BoolToString(doAA));
chudy@google.com902ebe52012-06-29 14:21:22 +00001592}
1593
fmalita8c89c522014-11-08 16:18:56 -08001594void SkClipPathCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001595 canvas->clipPath(fPath, fOp, fDoAA);
chudy@google.com902ebe52012-06-29 14:21:22 +00001596}
1597
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001598bool SkClipPathCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00001599 render_path(canvas, fPath);
1600 return true;
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +00001601}
1602
ethannicholasf62a8b72016-02-11 10:35:21 -08001603Json::Value SkClipPathCommand::toJSON(UrlDataManager& urlDataManager) const {
1604 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07001605 result[SKDEBUGCANVAS_ATTRIBUTE_PATH] = MakeJsonPath(fPath);
ethannicholas50a8dd02016-02-10 05:40:46 -08001606 result[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP] = make_json_regionop(fOp);
1607 result[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS] = fDoAA;
1608 return result;
1609}
1610
halcanary9d524f22016-03-29 09:03:52 -07001611SkClipPathCommand* SkClipPathCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001612 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001613 SkPath path;
1614 extract_json_path(command[SKDEBUGCANVAS_ATTRIBUTE_PATH], &path);
halcanary9d524f22016-03-29 09:03:52 -07001615 return new SkClipPathCommand(path, get_json_regionop(command[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP]),
ethannicholas50a8dd02016-02-10 05:40:46 -08001616 command[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS].asBool());
1617}
1618
skia.committer@gmail.comdb35dab2014-03-27 03:02:48 +00001619SkClipRegionCommand::SkClipRegionCommand(const SkRegion& region, SkRegion::Op op)
robertphillips9bafc302015-02-13 11:13:00 -08001620 : INHERITED(kClipRegion_OpType) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001621 fRegion = region;
1622 fOp = op;
chudy@google.com902ebe52012-06-29 14:21:22 +00001623
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001624 fInfo.push(SkObjectParser::RegionToString(region));
1625 fInfo.push(SkObjectParser::RegionOpToString(op));
chudy@google.com902ebe52012-06-29 14:21:22 +00001626}
1627
fmalita8c89c522014-11-08 16:18:56 -08001628void SkClipRegionCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001629 canvas->clipRegion(fRegion, fOp);
chudy@google.com902ebe52012-06-29 14:21:22 +00001630}
1631
ethannicholasf62a8b72016-02-11 10:35:21 -08001632Json::Value SkClipRegionCommand::toJSON(UrlDataManager& urlDataManager) const {
1633 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07001634 result[SKDEBUGCANVAS_ATTRIBUTE_REGION] = MakeJsonRegion(fRegion);
ethannicholas50a8dd02016-02-10 05:40:46 -08001635 result[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP] = make_json_regionop(fOp);
1636 return result;
1637}
1638
halcanary9d524f22016-03-29 09:03:52 -07001639SkClipRegionCommand* SkClipRegionCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001640 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001641 SkASSERT(false);
1642 return nullptr;
1643}
1644
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00001645SkClipRectCommand::SkClipRectCommand(const SkRect& rect, SkRegion::Op op, bool doAA)
robertphillips9bafc302015-02-13 11:13:00 -08001646 : INHERITED(kClipRect_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00001647 fRect = rect;
1648 fOp = op;
1649 fDoAA = doAA;
chudy@google.com902ebe52012-06-29 14:21:22 +00001650
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00001651 fInfo.push(SkObjectParser::RectToString(rect));
1652 fInfo.push(SkObjectParser::RegionOpToString(op));
1653 fInfo.push(SkObjectParser::BoolToString(doAA));
chudy@google.com902ebe52012-06-29 14:21:22 +00001654}
1655
fmalita8c89c522014-11-08 16:18:56 -08001656void SkClipRectCommand::execute(SkCanvas* canvas) const {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00001657 canvas->clipRect(fRect, fOp, fDoAA);
chudy@google.com902ebe52012-06-29 14:21:22 +00001658}
1659
ethannicholasf62a8b72016-02-11 10:35:21 -08001660Json::Value SkClipRectCommand::toJSON(UrlDataManager& urlDataManager) const {
1661 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07001662 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonRect(fRect);
ethannicholas50a8dd02016-02-10 05:40:46 -08001663 result[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP] = make_json_regionop(fOp);
1664 result[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS] = Json::Value(fDoAA);
reed67f62fa2016-06-29 11:36:34 -07001665
1666 SkString desc;
1667 result[SKDEBUGCANVAS_ATTRIBUTE_SHORTDESC] = Json::Value(str_append(&desc, fRect)->c_str());
1668
ethannicholas50a8dd02016-02-10 05:40:46 -08001669 return result;
1670}
1671
halcanary9d524f22016-03-29 09:03:52 -07001672SkClipRectCommand* SkClipRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001673 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001674 SkRect rect;
1675 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_COORDS], &rect);
halcanary9d524f22016-03-29 09:03:52 -07001676 return new SkClipRectCommand(rect, get_json_regionop(command[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP]),
ethannicholas50a8dd02016-02-10 05:40:46 -08001677 command[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS].asBool());
1678}
1679
skia.committer@gmail.comdb35dab2014-03-27 03:02:48 +00001680SkClipRRectCommand::SkClipRRectCommand(const SkRRect& rrect, SkRegion::Op op, bool doAA)
robertphillips9bafc302015-02-13 11:13:00 -08001681 : INHERITED(kClipRRect_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00001682 fRRect = rrect;
1683 fOp = op;
1684 fDoAA = doAA;
robertphillips@google.com67baba42013-01-02 20:20:31 +00001685
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00001686 fInfo.push(SkObjectParser::RRectToString(rrect));
1687 fInfo.push(SkObjectParser::RegionOpToString(op));
1688 fInfo.push(SkObjectParser::BoolToString(doAA));
robertphillips@google.com67baba42013-01-02 20:20:31 +00001689}
1690
fmalita8c89c522014-11-08 16:18:56 -08001691void SkClipRRectCommand::execute(SkCanvas* canvas) const {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00001692 canvas->clipRRect(fRRect, fOp, fDoAA);
robertphillips@google.com67baba42013-01-02 20:20:31 +00001693}
1694
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001695bool SkClipRRectCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00001696 render_rrect(canvas, fRRect);
1697 return true;
1698}
1699
ethannicholasf62a8b72016-02-11 10:35:21 -08001700Json::Value SkClipRRectCommand::toJSON(UrlDataManager& urlDataManager) const {
1701 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001702 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = make_json_rrect(fRRect);
1703 result[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP] = make_json_regionop(fOp);
1704 result[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS] = Json::Value(fDoAA);
1705 return result;
1706}
1707
halcanary9d524f22016-03-29 09:03:52 -07001708SkClipRRectCommand* SkClipRRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001709 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001710 SkRRect rrect;
1711 extract_json_rrect(command[SKDEBUGCANVAS_ATTRIBUTE_COORDS], &rrect);
halcanary9d524f22016-03-29 09:03:52 -07001712 return new SkClipRRectCommand(rrect,
1713 get_json_regionop(command[SKDEBUGCANVAS_ATTRIBUTE_REGIONOP]),
ethannicholas50a8dd02016-02-10 05:40:46 -08001714 command[SKDEBUGCANVAS_ATTRIBUTE_ANTIALIAS].asBool());
1715}
1716
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00001717SkConcatCommand::SkConcatCommand(const SkMatrix& matrix)
robertphillips9bafc302015-02-13 11:13:00 -08001718 : INHERITED(kConcat_OpType) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001719 fMatrix = matrix;
chudy@google.com902ebe52012-06-29 14:21:22 +00001720
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001721 fInfo.push(SkObjectParser::MatrixToString(matrix));
chudy@google.com902ebe52012-06-29 14:21:22 +00001722}
1723
fmalita8c89c522014-11-08 16:18:56 -08001724void SkConcatCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001725 canvas->concat(fMatrix);
chudy@google.com902ebe52012-06-29 14:21:22 +00001726}
1727
ethannicholasf62a8b72016-02-11 10:35:21 -08001728Json::Value SkConcatCommand::toJSON(UrlDataManager& urlDataManager) const {
1729 Json::Value result = INHERITED::toJSON(urlDataManager);
joshualittbd724132016-03-03 11:39:38 -08001730 result[SKDEBUGCANVAS_ATTRIBUTE_MATRIX] = MakeJsonMatrix(fMatrix);
ethannicholas50a8dd02016-02-10 05:40:46 -08001731 return result;
1732}
1733
ethannicholasf62a8b72016-02-11 10:35:21 -08001734SkConcatCommand* SkConcatCommand::fromJSON(Json::Value& command, UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001735 SkMatrix matrix;
1736 extract_json_matrix(command[SKDEBUGCANVAS_ATTRIBUTE_MATRIX], &matrix);
1737 return new SkConcatCommand(matrix);
1738}
1739
reed97660cc2016-06-28 18:54:19 -07001740////
1741
1742SkDrawAnnotationCommand::SkDrawAnnotationCommand(const SkRect& rect, const char key[],
1743 sk_sp<SkData> value)
1744 : INHERITED(kDrawAnnotation_OpType)
1745 , fRect(rect)
1746 , fKey(key)
1747 , fValue(std::move(value))
robertphillipsfb409232016-06-29 10:28:11 -07001748{
1749 SkString str;
1750 str.appendf("Key: %s Value: ", key);
1751 if (fValue && fValue->size()) {
1752 str.append((const char*) fValue->bytes(), fValue->size());
1753 } else {
1754 str.appendf("no value");
1755 }
1756 str.appendf("\n");
1757 fInfo.push(new SkString(str));
1758}
reed97660cc2016-06-28 18:54:19 -07001759
1760void SkDrawAnnotationCommand::execute(SkCanvas* canvas) const {
1761 canvas->drawAnnotation(fRect, fKey.c_str(), fValue);
1762}
1763
1764Json::Value SkDrawAnnotationCommand::toJSON(UrlDataManager& urlDataManager) const {
1765 Json::Value result = INHERITED::toJSON(urlDataManager);
1766
1767 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonRect(fRect);
1768 result["key"] = Json::Value(fKey.c_str());
1769 if (fValue.get()) {
1770 // TODO: dump out the "value"
1771 }
reed67f62fa2016-06-29 11:36:34 -07001772
1773 SkString desc;
1774 str_append(&desc, fRect)->appendf(" %s", fKey.c_str());
1775 result[SKDEBUGCANVAS_ATTRIBUTE_SHORTDESC] = Json::Value(desc.c_str());
1776
reed97660cc2016-06-28 18:54:19 -07001777 return result;
1778}
1779
1780SkDrawAnnotationCommand* SkDrawAnnotationCommand::fromJSON(Json::Value& command,
1781 UrlDataManager& urlDataManager) {
1782 SkRect rect;
1783 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_COORDS], &rect);
1784 sk_sp<SkData> data(nullptr); // TODO: extract "value" from the Json
1785 return new SkDrawAnnotationCommand(rect, command["key"].asCString(), data);
1786}
1787
1788////
1789
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001790SkDrawBitmapCommand::SkDrawBitmapCommand(const SkBitmap& bitmap, SkScalar left, SkScalar top,
robertphillipsb3f319f2014-08-13 10:46:23 -07001791 const SkPaint* paint)
robertphillips9bafc302015-02-13 11:13:00 -08001792 : INHERITED(kDrawBitmap_OpType) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001793 fBitmap = bitmap;
1794 fLeft = left;
1795 fTop = top;
bsalomon49f085d2014-09-05 13:34:00 -07001796 if (paint) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001797 fPaint = *paint;
1798 fPaintPtr = &fPaint;
1799 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07001800 fPaintPtr = nullptr;
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001801 }
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001802
1803 fInfo.push(SkObjectParser::BitmapToString(bitmap));
1804 fInfo.push(SkObjectParser::ScalarToString(left, "SkScalar left: "));
1805 fInfo.push(SkObjectParser::ScalarToString(top, "SkScalar top: "));
bsalomon49f085d2014-09-05 13:34:00 -07001806 if (paint) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001807 fInfo.push(SkObjectParser::PaintToString(*paint));
robertphillips@google.comb83b6b42013-01-22 14:32:09 +00001808 }
chudy@google.com902ebe52012-06-29 14:21:22 +00001809}
1810
fmalita8c89c522014-11-08 16:18:56 -08001811void SkDrawBitmapCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001812 canvas->drawBitmap(fBitmap, fLeft, fTop, fPaintPtr);
chudy@google.com902ebe52012-06-29 14:21:22 +00001813}
1814
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001815bool SkDrawBitmapCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00001816 render_bitmap(canvas, fBitmap);
1817 return true;
robertphillips@google.com53ec73d2012-11-26 13:09:17 +00001818}
1819
ethannicholasf62a8b72016-02-11 10:35:21 -08001820Json::Value SkDrawBitmapCommand::toJSON(UrlDataManager& urlDataManager) const {
1821 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001822 Json::Value encoded;
ethannicholasf62a8b72016-02-11 10:35:21 -08001823 if (flatten(fBitmap, &encoded, urlDataManager)) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001824 Json::Value command(Json::objectValue);
1825 result[SKDEBUGCANVAS_ATTRIBUTE_BITMAP] = encoded;
brianosmanfad98562016-05-04 11:06:28 -07001826 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonPoint(fLeft, fTop);
ethannicholas50a8dd02016-02-10 05:40:46 -08001827 if (fPaintPtr != nullptr) {
brianosmanfad98562016-05-04 11:06:28 -07001828 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(*fPaintPtr, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001829 }
1830 }
1831 return result;
1832}
1833
halcanary9d524f22016-03-29 09:03:52 -07001834SkDrawBitmapCommand* SkDrawBitmapCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001835 UrlDataManager& urlDataManager) {
1836 SkBitmap* bitmap = load_bitmap(command[SKDEBUGCANVAS_ATTRIBUTE_BITMAP], urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001837 if (bitmap == nullptr) {
1838 return nullptr;
1839 }
1840 Json::Value point = command[SKDEBUGCANVAS_ATTRIBUTE_COORDS];
1841 SkPaint* paintPtr;
1842 SkPaint paint;
1843 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_PAINT)) {
ethannicholasf62a8b72016-02-11 10:35:21 -08001844 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08001845 paintPtr = &paint;
1846 }
1847 else {
1848 paintPtr = nullptr;
1849 }
halcanary9d524f22016-03-29 09:03:52 -07001850 SkDrawBitmapCommand* result = new SkDrawBitmapCommand(*bitmap, point[0].asFloat(),
ethannicholas50a8dd02016-02-10 05:40:46 -08001851 point[1].asFloat(), paintPtr);
1852 delete bitmap;
1853 return result;
1854}
1855
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001856SkDrawBitmapNineCommand::SkDrawBitmapNineCommand(const SkBitmap& bitmap, const SkIRect& center,
skia.committer@gmail.comdb35dab2014-03-27 03:02:48 +00001857 const SkRect& dst, const SkPaint* paint)
robertphillips9bafc302015-02-13 11:13:00 -08001858 : INHERITED(kDrawBitmapNine_OpType) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001859 fBitmap = bitmap;
1860 fCenter = center;
1861 fDst = dst;
bsalomon49f085d2014-09-05 13:34:00 -07001862 if (paint) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001863 fPaint = *paint;
1864 fPaintPtr = &fPaint;
1865 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07001866 fPaintPtr = nullptr;
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001867 }
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001868
1869 fInfo.push(SkObjectParser::BitmapToString(bitmap));
1870 fInfo.push(SkObjectParser::IRectToString(center));
1871 fInfo.push(SkObjectParser::RectToString(dst, "Dst: "));
bsalomon49f085d2014-09-05 13:34:00 -07001872 if (paint) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001873 fInfo.push(SkObjectParser::PaintToString(*paint));
robertphillips@google.comb83b6b42013-01-22 14:32:09 +00001874 }
chudy@google.com902ebe52012-06-29 14:21:22 +00001875}
1876
fmalita8c89c522014-11-08 16:18:56 -08001877void SkDrawBitmapNineCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00001878 canvas->drawBitmapNine(fBitmap, fCenter, fDst, fPaintPtr);
chudy@google.com902ebe52012-06-29 14:21:22 +00001879}
1880
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001881bool SkDrawBitmapNineCommand::render(SkCanvas* canvas) const {
robertphillips2b829822015-11-18 12:59:42 -08001882 SkRect tmp = SkRect::Make(fCenter);
1883 render_bitmap(canvas, fBitmap, &tmp);
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00001884 return true;
robertphillips@google.com53ec73d2012-11-26 13:09:17 +00001885}
1886
ethannicholasf62a8b72016-02-11 10:35:21 -08001887Json::Value SkDrawBitmapNineCommand::toJSON(UrlDataManager& urlDataManager) const {
1888 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001889 Json::Value encoded;
ethannicholasf62a8b72016-02-11 10:35:21 -08001890 if (flatten(fBitmap, &encoded, urlDataManager)) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001891 result[SKDEBUGCANVAS_ATTRIBUTE_BITMAP] = encoded;
joshualittbd724132016-03-03 11:39:38 -08001892 result[SKDEBUGCANVAS_ATTRIBUTE_CENTER] = MakeJsonIRect(fCenter);
brianosmanfad98562016-05-04 11:06:28 -07001893 result[SKDEBUGCANVAS_ATTRIBUTE_DST] = MakeJsonRect(fDst);
ethannicholas50a8dd02016-02-10 05:40:46 -08001894 if (fPaintPtr != nullptr) {
brianosmanfad98562016-05-04 11:06:28 -07001895 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(*fPaintPtr, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001896 }
1897 }
1898 return result;
1899}
1900
halcanary9d524f22016-03-29 09:03:52 -07001901SkDrawBitmapNineCommand* SkDrawBitmapNineCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001902 UrlDataManager& urlDataManager) {
1903 SkBitmap* bitmap = load_bitmap(command[SKDEBUGCANVAS_ATTRIBUTE_BITMAP], urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001904 if (bitmap == nullptr) {
1905 return nullptr;
1906 }
1907 SkIRect center;
1908 extract_json_irect(command[SKDEBUGCANVAS_ATTRIBUTE_CENTER], &center);
1909 SkRect dst;
1910 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_DST], &dst);
1911 SkPaint* paintPtr;
1912 SkPaint paint;
1913 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_PAINT)) {
ethannicholasf62a8b72016-02-11 10:35:21 -08001914 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08001915 paintPtr = &paint;
1916 }
1917 else {
1918 paintPtr = nullptr;
1919 }
1920 SkDrawBitmapNineCommand* result = new SkDrawBitmapNineCommand(*bitmap, center, dst, paintPtr);
1921 delete bitmap;
1922 return result;
1923}
1924
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001925SkDrawBitmapRectCommand::SkDrawBitmapRectCommand(const SkBitmap& bitmap, const SkRect* src,
commit-bot@chromium.orgeed779d2013-08-16 10:24:37 +00001926 const SkRect& dst, const SkPaint* paint,
reeda5517e22015-07-14 10:54:12 -07001927 SkCanvas::SrcRectConstraint constraint)
robertphillips9bafc302015-02-13 11:13:00 -08001928 : INHERITED(kDrawBitmapRect_OpType) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001929 fBitmap = bitmap;
bsalomon49f085d2014-09-05 13:34:00 -07001930 if (src) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001931 fSrc = *src;
1932 } else {
1933 fSrc.setEmpty();
robertphillips@google.comb83b6b42013-01-22 14:32:09 +00001934 }
robertphillips@google.com91217d02013-03-17 18:33:46 +00001935 fDst = dst;
1936
bsalomon49f085d2014-09-05 13:34:00 -07001937 if (paint) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001938 fPaint = *paint;
1939 fPaintPtr = &fPaint;
1940 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07001941 fPaintPtr = nullptr;
robertphillips@google.com91217d02013-03-17 18:33:46 +00001942 }
reeda5517e22015-07-14 10:54:12 -07001943 fConstraint = constraint;
commit-bot@chromium.orgeed779d2013-08-16 10:24:37 +00001944
robertphillips@google.com91217d02013-03-17 18:33:46 +00001945 fInfo.push(SkObjectParser::BitmapToString(bitmap));
bsalomon49f085d2014-09-05 13:34:00 -07001946 if (src) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001947 fInfo.push(SkObjectParser::RectToString(*src, "Src: "));
1948 }
1949 fInfo.push(SkObjectParser::RectToString(dst, "Dst: "));
bsalomon49f085d2014-09-05 13:34:00 -07001950 if (paint) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00001951 fInfo.push(SkObjectParser::PaintToString(*paint));
robertphillips@google.comb83b6b42013-01-22 14:32:09 +00001952 }
reeda5517e22015-07-14 10:54:12 -07001953 fInfo.push(SkObjectParser::IntToString(fConstraint, "Constraint: "));
chudy@google.com902ebe52012-06-29 14:21:22 +00001954}
1955
fmalita8c89c522014-11-08 16:18:56 -08001956void SkDrawBitmapRectCommand::execute(SkCanvas* canvas) const {
reede47829b2015-08-06 10:02:53 -07001957 canvas->legacy_drawBitmapRect(fBitmap, this->srcRect(), fDst, fPaintPtr, fConstraint);
chudy@google.com902ebe52012-06-29 14:21:22 +00001958}
1959
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00001960bool SkDrawBitmapRectCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00001961 render_bitmap(canvas, fBitmap, this->srcRect());
1962 return true;
robertphillips@google.com53ec73d2012-11-26 13:09:17 +00001963}
1964
ethannicholasf62a8b72016-02-11 10:35:21 -08001965Json::Value SkDrawBitmapRectCommand::toJSON(UrlDataManager& urlDataManager) const {
1966 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001967 Json::Value encoded;
ethannicholasf62a8b72016-02-11 10:35:21 -08001968 if (flatten(fBitmap, &encoded, urlDataManager)) {
ethannicholas50a8dd02016-02-10 05:40:46 -08001969 result[SKDEBUGCANVAS_ATTRIBUTE_BITMAP] = encoded;
1970 if (!fSrc.isEmpty()) {
brianosmanfad98562016-05-04 11:06:28 -07001971 result[SKDEBUGCANVAS_ATTRIBUTE_SRC] = MakeJsonRect(fSrc);
ethannicholas50a8dd02016-02-10 05:40:46 -08001972 }
brianosmanfad98562016-05-04 11:06:28 -07001973 result[SKDEBUGCANVAS_ATTRIBUTE_DST] = MakeJsonRect(fDst);
ethannicholas50a8dd02016-02-10 05:40:46 -08001974 if (fPaintPtr != nullptr) {
brianosmanfad98562016-05-04 11:06:28 -07001975 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(*fPaintPtr, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001976 }
1977 if (fConstraint == SkCanvas::kStrict_SrcRectConstraint) {
1978 result[SKDEBUGCANVAS_ATTRIBUTE_STRICT] = Json::Value(true);
1979 }
1980 }
reed67f62fa2016-06-29 11:36:34 -07001981
1982 SkString desc;
1983 result[SKDEBUGCANVAS_ATTRIBUTE_SHORTDESC] = Json::Value(str_append(&desc, fDst)->c_str());
1984
ethannicholas50a8dd02016-02-10 05:40:46 -08001985 return result;
1986}
1987
halcanary9d524f22016-03-29 09:03:52 -07001988SkDrawBitmapRectCommand* SkDrawBitmapRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08001989 UrlDataManager& urlDataManager) {
1990 SkBitmap* bitmap = load_bitmap(command[SKDEBUGCANVAS_ATTRIBUTE_BITMAP], urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08001991 if (bitmap == nullptr) {
1992 return nullptr;
1993 }
1994 SkRect dst;
1995 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_DST], &dst);
1996 SkPaint* paintPtr;
1997 SkPaint paint;
1998 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_PAINT)) {
ethannicholasf62a8b72016-02-11 10:35:21 -08001999 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002000 paintPtr = &paint;
2001 }
2002 else {
2003 paintPtr = nullptr;
2004 }
2005 SkCanvas::SrcRectConstraint constraint;
halcanary9d524f22016-03-29 09:03:52 -07002006 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_STRICT) &&
ethannicholas50a8dd02016-02-10 05:40:46 -08002007 command[SKDEBUGCANVAS_ATTRIBUTE_STRICT].asBool()) {
2008 constraint = SkCanvas::kStrict_SrcRectConstraint;
2009 }
2010 else {
2011 constraint = SkCanvas::kFast_SrcRectConstraint;
2012 }
2013 SkRect* srcPtr;
2014 SkRect src;
2015 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_SRC)) {
2016 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_SRC], &src);
2017 srcPtr = &src;
2018 }
2019 else {
2020 srcPtr = nullptr;
2021 }
2022 SkDrawBitmapRectCommand* result = new SkDrawBitmapRectCommand(*bitmap, srcPtr, dst, paintPtr,
2023 constraint);
2024 delete bitmap;
2025 return result;
2026}
2027
fmalita651c9202015-07-22 10:23:01 -07002028SkDrawImageCommand::SkDrawImageCommand(const SkImage* image, SkScalar left, SkScalar top,
2029 const SkPaint* paint)
2030 : INHERITED(kDrawImage_OpType)
2031 , fImage(SkRef(image))
2032 , fLeft(left)
2033 , fTop(top) {
2034
fmalita7361bf02015-10-29 12:13:48 -07002035 fInfo.push(SkObjectParser::ImageToString(image));
2036 fInfo.push(SkObjectParser::ScalarToString(left, "Left: "));
2037 fInfo.push(SkObjectParser::ScalarToString(top, "Top: "));
2038
fmalita651c9202015-07-22 10:23:01 -07002039 if (paint) {
2040 fPaint.set(*paint);
fmalita7361bf02015-10-29 12:13:48 -07002041 fInfo.push(SkObjectParser::PaintToString(*paint));
fmalita651c9202015-07-22 10:23:01 -07002042 }
2043}
2044
2045void SkDrawImageCommand::execute(SkCanvas* canvas) const {
2046 canvas->drawImage(fImage, fLeft, fTop, fPaint.getMaybeNull());
2047}
2048
2049bool SkDrawImageCommand::render(SkCanvas* canvas) const {
2050 SkAutoCanvasRestore acr(canvas, true);
2051 canvas->clear(0xFFFFFFFF);
2052
2053 xlate_and_scale_to_bounds(canvas, SkRect::MakeXYWH(fLeft, fTop,
2054 SkIntToScalar(fImage->width()),
2055 SkIntToScalar(fImage->height())));
2056 this->execute(canvas);
2057 return true;
2058}
2059
ethannicholasf62a8b72016-02-11 10:35:21 -08002060Json::Value SkDrawImageCommand::toJSON(UrlDataManager& urlDataManager) const {
2061 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002062 Json::Value encoded;
ethannicholasf62a8b72016-02-11 10:35:21 -08002063 if (flatten(*fImage, &encoded, urlDataManager)) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002064 result[SKDEBUGCANVAS_ATTRIBUTE_IMAGE] = encoded;
brianosmanfad98562016-05-04 11:06:28 -07002065 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonPoint(fLeft, fTop);
ethannicholas50a8dd02016-02-10 05:40:46 -08002066 if (fPaint.isValid()) {
brianosmanfad98562016-05-04 11:06:28 -07002067 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(*fPaint.get(), urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002068 }
2069 }
2070 return result;
2071}
2072
halcanary9d524f22016-03-29 09:03:52 -07002073SkDrawImageCommand* SkDrawImageCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002074 UrlDataManager& urlDataManager) {
reed9ce9d672016-03-17 10:51:11 -07002075 sk_sp<SkImage> image = load_image(command[SKDEBUGCANVAS_ATTRIBUTE_IMAGE], urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002076 if (image == nullptr) {
2077 return nullptr;
2078 }
2079 Json::Value point = command[SKDEBUGCANVAS_ATTRIBUTE_COORDS];
2080 SkPaint* paintPtr;
2081 SkPaint paint;
2082 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_PAINT)) {
ethannicholasf62a8b72016-02-11 10:35:21 -08002083 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002084 paintPtr = &paint;
2085 }
2086 else {
2087 paintPtr = nullptr;
2088 }
reed9ce9d672016-03-17 10:51:11 -07002089 SkDrawImageCommand* result = new SkDrawImageCommand(image.get(), point[0].asFloat(),
ethannicholas50a8dd02016-02-10 05:40:46 -08002090 point[1].asFloat(), paintPtr);
ethannicholas50a8dd02016-02-10 05:40:46 -08002091 return result;
2092}
2093
fmalita651c9202015-07-22 10:23:01 -07002094SkDrawImageRectCommand::SkDrawImageRectCommand(const SkImage* image, const SkRect* src,
2095 const SkRect& dst, const SkPaint* paint,
2096 SkCanvas::SrcRectConstraint constraint)
2097 : INHERITED(kDrawImageRect_OpType)
2098 , fImage(SkRef(image))
2099 , fDst(dst)
2100 , fConstraint(constraint) {
2101
2102 if (src) {
2103 fSrc.set(*src);
2104 }
2105
2106 if (paint) {
2107 fPaint.set(*paint);
2108 }
robertphillips80af6452015-08-24 08:27:38 -07002109
2110 fInfo.push(SkObjectParser::ImageToString(image));
2111 if (src) {
2112 fInfo.push(SkObjectParser::RectToString(*src, "Src: "));
2113 }
2114 fInfo.push(SkObjectParser::RectToString(dst, "Dst: "));
2115 if (paint) {
2116 fInfo.push(SkObjectParser::PaintToString(*paint));
2117 }
2118 fInfo.push(SkObjectParser::IntToString(fConstraint, "Constraint: "));
fmalita651c9202015-07-22 10:23:01 -07002119}
2120
2121void SkDrawImageRectCommand::execute(SkCanvas* canvas) const {
halcanary9d524f22016-03-29 09:03:52 -07002122 canvas->legacy_drawImageRect(fImage, fSrc.getMaybeNull(), fDst, fPaint.getMaybeNull(),
ethannicholas1446a9a2016-02-10 14:05:02 -08002123 fConstraint);
fmalita651c9202015-07-22 10:23:01 -07002124}
2125
2126bool SkDrawImageRectCommand::render(SkCanvas* canvas) const {
2127 SkAutoCanvasRestore acr(canvas, true);
2128 canvas->clear(0xFFFFFFFF);
2129
2130 xlate_and_scale_to_bounds(canvas, fDst);
2131
2132 this->execute(canvas);
2133 return true;
2134}
2135
ethannicholasf62a8b72016-02-11 10:35:21 -08002136Json::Value SkDrawImageRectCommand::toJSON(UrlDataManager& urlDataManager) const {
2137 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002138 Json::Value encoded;
ethannicholasf62a8b72016-02-11 10:35:21 -08002139 if (flatten(*fImage.get(), &encoded, urlDataManager)) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002140 result[SKDEBUGCANVAS_ATTRIBUTE_BITMAP] = encoded;
2141 if (fSrc.isValid()) {
brianosmanfad98562016-05-04 11:06:28 -07002142 result[SKDEBUGCANVAS_ATTRIBUTE_SRC] = MakeJsonRect(*fSrc.get());
ethannicholas50a8dd02016-02-10 05:40:46 -08002143 }
brianosmanfad98562016-05-04 11:06:28 -07002144 result[SKDEBUGCANVAS_ATTRIBUTE_DST] = MakeJsonRect(fDst);
ethannicholas50a8dd02016-02-10 05:40:46 -08002145 if (fPaint.isValid()) {
brianosmanfad98562016-05-04 11:06:28 -07002146 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(*fPaint.get(), urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002147 }
2148 if (fConstraint == SkCanvas::kStrict_SrcRectConstraint) {
2149 result[SKDEBUGCANVAS_ATTRIBUTE_STRICT] = Json::Value(true);
2150 }
2151 }
reed67f62fa2016-06-29 11:36:34 -07002152
2153 SkString desc;
2154 result[SKDEBUGCANVAS_ATTRIBUTE_SHORTDESC] = Json::Value(str_append(&desc, fDst)->c_str());
2155
ethannicholas50a8dd02016-02-10 05:40:46 -08002156 return result;
2157}
2158
halcanary9d524f22016-03-29 09:03:52 -07002159SkDrawImageRectCommand* SkDrawImageRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002160 UrlDataManager& urlDataManager) {
reed9ce9d672016-03-17 10:51:11 -07002161 sk_sp<SkImage> image = load_image(command[SKDEBUGCANVAS_ATTRIBUTE_IMAGE], urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002162 if (image == nullptr) {
2163 return nullptr;
2164 }
2165 SkRect dst;
2166 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_DST], &dst);
2167 SkPaint* paintPtr;
2168 SkPaint paint;
2169 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_PAINT)) {
ethannicholasf62a8b72016-02-11 10:35:21 -08002170 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002171 paintPtr = &paint;
2172 }
2173 else {
2174 paintPtr = nullptr;
2175 }
2176 SkCanvas::SrcRectConstraint constraint;
halcanary9d524f22016-03-29 09:03:52 -07002177 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_STRICT) &&
ethannicholas50a8dd02016-02-10 05:40:46 -08002178 command[SKDEBUGCANVAS_ATTRIBUTE_STRICT].asBool()) {
2179 constraint = SkCanvas::kStrict_SrcRectConstraint;
2180 }
2181 else {
2182 constraint = SkCanvas::kFast_SrcRectConstraint;
2183 }
2184 SkRect* srcPtr;
2185 SkRect src;
2186 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_SRC)) {
2187 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_SRC], &src);
2188 srcPtr = &src;
2189 }
2190 else {
2191 srcPtr = nullptr;
2192 }
reed9ce9d672016-03-17 10:51:11 -07002193 SkDrawImageRectCommand* result = new SkDrawImageRectCommand(image.get(), srcPtr, dst, paintPtr,
ethannicholas50a8dd02016-02-10 05:40:46 -08002194 constraint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002195 return result;
2196}
2197
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002198SkDrawOvalCommand::SkDrawOvalCommand(const SkRect& oval, const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002199 : INHERITED(kDrawOval_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002200 fOval = oval;
2201 fPaint = paint;
robertphillips@google.com67baba42013-01-02 20:20:31 +00002202
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002203 fInfo.push(SkObjectParser::RectToString(oval));
2204 fInfo.push(SkObjectParser::PaintToString(paint));
robertphillips@google.com67baba42013-01-02 20:20:31 +00002205}
2206
fmalita8c89c522014-11-08 16:18:56 -08002207void SkDrawOvalCommand::execute(SkCanvas* canvas) const {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002208 canvas->drawOval(fOval, fPaint);
robertphillips@google.com67baba42013-01-02 20:20:31 +00002209}
2210
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002211bool SkDrawOvalCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00002212 canvas->clear(0xFFFFFFFF);
2213 canvas->save();
2214
2215 xlate_and_scale_to_bounds(canvas, fOval);
2216
2217 SkPaint p;
2218 p.setColor(SK_ColorBLACK);
2219 p.setStyle(SkPaint::kStroke_Style);
2220
2221 canvas->drawOval(fOval, p);
2222 canvas->restore();
2223
2224 return true;
2225}
2226
ethannicholasf62a8b72016-02-11 10:35:21 -08002227Json::Value SkDrawOvalCommand::toJSON(UrlDataManager& urlDataManager) const {
2228 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07002229 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonRect(fOval);
2230 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002231 return result;
2232}
2233
halcanary9d524f22016-03-29 09:03:52 -07002234SkDrawOvalCommand* SkDrawOvalCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002235 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002236 SkRect coords;
2237 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_COORDS], &coords);
2238 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002239 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002240 return new SkDrawOvalCommand(coords, paint);
2241}
2242
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002243SkDrawPaintCommand::SkDrawPaintCommand(const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002244 : INHERITED(kDrawPaint_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002245 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002246
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002247 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002248}
2249
fmalita8c89c522014-11-08 16:18:56 -08002250void SkDrawPaintCommand::execute(SkCanvas* canvas) const {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002251 canvas->drawPaint(fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002252}
2253
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002254bool SkDrawPaintCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00002255 canvas->clear(0xFFFFFFFF);
2256 canvas->drawPaint(fPaint);
2257 return true;
2258}
2259
ethannicholasf62a8b72016-02-11 10:35:21 -08002260Json::Value SkDrawPaintCommand::toJSON(UrlDataManager& urlDataManager) const {
2261 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07002262 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002263 return result;
2264}
2265
halcanary9d524f22016-03-29 09:03:52 -07002266SkDrawPaintCommand* SkDrawPaintCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002267 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002268 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002269 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002270 return new SkDrawPaintCommand(paint);
2271}
2272
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002273SkDrawPathCommand::SkDrawPathCommand(const SkPath& path, const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002274 : INHERITED(kDrawPath_OpType) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00002275 fPath = path;
2276 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002277
robertphillips@google.com91217d02013-03-17 18:33:46 +00002278 fInfo.push(SkObjectParser::PathToString(path));
2279 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002280}
2281
fmalita8c89c522014-11-08 16:18:56 -08002282void SkDrawPathCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com91217d02013-03-17 18:33:46 +00002283 canvas->drawPath(fPath, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002284}
2285
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002286bool SkDrawPathCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00002287 render_path(canvas, fPath);
2288 return true;
robertphillips@google.com6dec8fc2012-11-21 17:11:02 +00002289}
2290
ethannicholasf62a8b72016-02-11 10:35:21 -08002291Json::Value SkDrawPathCommand::toJSON(UrlDataManager& urlDataManager) const {
2292 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07002293 result[SKDEBUGCANVAS_ATTRIBUTE_PATH] = MakeJsonPath(fPath);
2294 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002295 return result;
2296}
2297
halcanary9d524f22016-03-29 09:03:52 -07002298SkDrawPathCommand* SkDrawPathCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002299 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002300 SkPath path;
2301 extract_json_path(command[SKDEBUGCANVAS_ATTRIBUTE_PATH], &path);
2302 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002303 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002304 return new SkDrawPathCommand(path, paint);
2305}
2306
fmalita160ebb22015-04-01 20:58:37 -07002307SkBeginDrawPictureCommand::SkBeginDrawPictureCommand(const SkPicture* picture,
2308 const SkMatrix* matrix,
2309 const SkPaint* paint)
2310 : INHERITED(kBeginDrawPicture_OpType)
2311 , fPicture(SkRef(picture)) {
2312
2313 SkString* str = new SkString;
2314 str->appendf("SkPicture: L: %f T: %f R: %f B: %f",
2315 picture->cullRect().fLeft, picture->cullRect().fTop,
2316 picture->cullRect().fRight, picture->cullRect().fBottom);
2317 fInfo.push(str);
robertphillipsb3f319f2014-08-13 10:46:23 -07002318
bsalomon49f085d2014-09-05 13:34:00 -07002319 if (matrix) {
fmalita160ebb22015-04-01 20:58:37 -07002320 fMatrix.set(*matrix);
robertphillipsb3f319f2014-08-13 10:46:23 -07002321 fInfo.push(SkObjectParser::MatrixToString(*matrix));
2322 }
fmalita160ebb22015-04-01 20:58:37 -07002323
bsalomon49f085d2014-09-05 13:34:00 -07002324 if (paint) {
fmalita160ebb22015-04-01 20:58:37 -07002325 fPaint.set(*paint);
robertphillipsb3f319f2014-08-13 10:46:23 -07002326 fInfo.push(SkObjectParser::PaintToString(*paint));
2327 }
fmalita160ebb22015-04-01 20:58:37 -07002328
2329}
2330
2331void SkBeginDrawPictureCommand::execute(SkCanvas* canvas) const {
2332 if (fPaint.isValid()) {
2333 SkRect bounds = fPicture->cullRect();
2334 if (fMatrix.isValid()) {
2335 fMatrix.get()->mapRect(&bounds);
2336 }
2337 canvas->saveLayer(&bounds, fPaint.get());
2338 }
2339
2340 if (fMatrix.isValid()) {
2341 if (!fPaint.isValid()) {
2342 canvas->save();
2343 }
2344 canvas->concat(*fMatrix.get());
2345 }
chudy@google.com902ebe52012-06-29 14:21:22 +00002346}
2347
fmalita160ebb22015-04-01 20:58:37 -07002348bool SkBeginDrawPictureCommand::render(SkCanvas* canvas) const {
commit-bot@chromium.orge898e9c2013-11-21 17:08:12 +00002349 canvas->clear(0xFFFFFFFF);
2350 canvas->save();
2351
robertphillipsa8d7f0b2014-08-29 08:03:56 -07002352 xlate_and_scale_to_bounds(canvas, fPicture->cullRect());
commit-bot@chromium.orge898e9c2013-11-21 17:08:12 +00002353
robertphillips9b14f262014-06-04 05:40:44 -07002354 canvas->drawPicture(fPicture.get());
commit-bot@chromium.orge898e9c2013-11-21 17:08:12 +00002355
2356 canvas->restore();
2357
2358 return true;
2359}
2360
fmalita160ebb22015-04-01 20:58:37 -07002361SkEndDrawPictureCommand::SkEndDrawPictureCommand(bool restore)
2362 : INHERITED(kEndDrawPicture_OpType) , fRestore(restore) { }
2363
2364void SkEndDrawPictureCommand::execute(SkCanvas* canvas) const {
2365 if (fRestore) {
2366 canvas->restore();
2367 }
2368}
2369
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002370SkDrawPointsCommand::SkDrawPointsCommand(SkCanvas::PointMode mode, size_t count,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002371 const SkPoint pts[], const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002372 : INHERITED(kDrawPoints_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002373 fMode = mode;
2374 fCount = count;
2375 fPts = new SkPoint[count];
2376 memcpy(fPts, pts, count * sizeof(SkPoint));
2377 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002378
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002379 fInfo.push(SkObjectParser::PointsToString(pts, count));
2380 fInfo.push(SkObjectParser::ScalarToString(SkIntToScalar((unsigned int)count),
2381 "Points: "));
2382 fInfo.push(SkObjectParser::PointModeToString(mode));
2383 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002384}
2385
fmalita8c89c522014-11-08 16:18:56 -08002386void SkDrawPointsCommand::execute(SkCanvas* canvas) const {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002387 canvas->drawPoints(fMode, fCount, fPts, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002388}
2389
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002390bool SkDrawPointsCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00002391 canvas->clear(0xFFFFFFFF);
2392 canvas->save();
2393
2394 SkRect bounds;
2395
2396 bounds.setEmpty();
2397 for (unsigned int i = 0; i < fCount; ++i) {
2398 bounds.growToInclude(fPts[i].fX, fPts[i].fY);
2399 }
skia.committer@gmail.coma0090832013-06-07 07:01:06 +00002400
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00002401 xlate_and_scale_to_bounds(canvas, bounds);
2402
2403 SkPaint p;
2404 p.setColor(SK_ColorBLACK);
2405 p.setStyle(SkPaint::kStroke_Style);
2406
2407 canvas->drawPoints(fMode, fCount, fPts, p);
2408 canvas->restore();
2409
2410 return true;
2411}
2412
ethannicholasf62a8b72016-02-11 10:35:21 -08002413Json::Value SkDrawPointsCommand::toJSON(UrlDataManager& urlDataManager) const {
2414 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002415 result[SKDEBUGCANVAS_ATTRIBUTE_MODE] = make_json_pointmode(fMode);
2416 Json::Value points(Json::arrayValue);
2417 for (size_t i = 0; i < fCount; i++) {
brianosmanfad98562016-05-04 11:06:28 -07002418 points.append(MakeJsonPoint(fPts[i]));
ethannicholas50a8dd02016-02-10 05:40:46 -08002419 }
2420 result[SKDEBUGCANVAS_ATTRIBUTE_POINTS] = points;
brianosmanfad98562016-05-04 11:06:28 -07002421 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002422 return result;
2423}
2424
halcanary9d524f22016-03-29 09:03:52 -07002425SkDrawPointsCommand* SkDrawPointsCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002426 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002427 SkCanvas::PointMode mode;
2428 const char* jsonMode = command[SKDEBUGCANVAS_ATTRIBUTE_MODE].asCString();
2429 if (!strcmp(jsonMode, SKDEBUGCANVAS_POINTMODE_POINTS)) {
2430 mode = SkCanvas::kPoints_PointMode;
2431 }
2432 else if (!strcmp(jsonMode, SKDEBUGCANVAS_POINTMODE_LINES)) {
2433 mode = SkCanvas::kLines_PointMode;
2434 }
2435 else if (!strcmp(jsonMode, SKDEBUGCANVAS_POINTMODE_POLYGON)) {
2436 mode = SkCanvas::kPolygon_PointMode;
2437 }
2438 else {
2439 SkASSERT(false);
2440 return nullptr;
2441 }
2442 Json::Value jsonPoints = command[SKDEBUGCANVAS_ATTRIBUTE_POINTS];
2443 int count = (int) jsonPoints.size();
2444 SkPoint* points = (SkPoint*) sk_malloc_throw(count * sizeof(SkPoint));
2445 for (int i = 0; i < count; i++) {
2446 points[i] = SkPoint::Make(jsonPoints[i][0].asFloat(), jsonPoints[i][1].asFloat());
2447 }
2448 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002449 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002450 SkDrawPointsCommand* result = new SkDrawPointsCommand(mode, count, points, paint);
2451 sk_free(points);
2452 return result;
2453}
2454
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002455SkDrawPosTextCommand::SkDrawPosTextCommand(const void* text, size_t byteLength,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002456 const SkPoint pos[], const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002457 : INHERITED(kDrawPosText_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002458 size_t numPts = paint.countText(text, byteLength);
chudy@google.com902ebe52012-06-29 14:21:22 +00002459
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002460 fText = new char[byteLength];
2461 memcpy(fText, text, byteLength);
2462 fByteLength = byteLength;
2463
2464 fPos = new SkPoint[numPts];
2465 memcpy(fPos, pos, numPts * sizeof(SkPoint));
2466
2467 fPaint = paint;
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002468
2469 fInfo.push(SkObjectParser::TextToString(text, byteLength, paint.getTextEncoding()));
chudy@google.com902ebe52012-06-29 14:21:22 +00002470 // TODO(chudy): Test that this works.
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002471 fInfo.push(SkObjectParser::PointsToString(pos, 1));
2472 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002473}
2474
fmalita8c89c522014-11-08 16:18:56 -08002475void SkDrawPosTextCommand::execute(SkCanvas* canvas) const {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002476 canvas->drawPosText(fText, fByteLength, fPos, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002477}
2478
ethannicholasf62a8b72016-02-11 10:35:21 -08002479Json::Value SkDrawPosTextCommand::toJSON(UrlDataManager& urlDataManager) const {
2480 Json::Value result = INHERITED::toJSON(urlDataManager);
halcanary9d524f22016-03-29 09:03:52 -07002481 result[SKDEBUGCANVAS_ATTRIBUTE_TEXT] = Json::Value((const char*) fText,
ethannicholas50a8dd02016-02-10 05:40:46 -08002482 ((const char*) fText) + fByteLength);
2483 Json::Value coords(Json::arrayValue);
bungeman51190df2016-03-09 07:42:54 -08002484 size_t numCoords = fPaint.textToGlyphs(fText, fByteLength, nullptr);
2485 for (size_t i = 0; i < numCoords; i++) {
brianosmanfad98562016-05-04 11:06:28 -07002486 coords.append(MakeJsonPoint(fPos[i]));
ethannicholas50a8dd02016-02-10 05:40:46 -08002487 }
2488 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = coords;
brianosmanfad98562016-05-04 11:06:28 -07002489 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002490 return result;
2491}
2492
halcanary9d524f22016-03-29 09:03:52 -07002493SkDrawPosTextCommand* SkDrawPosTextCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002494 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002495 const char* text = command[SKDEBUGCANVAS_ATTRIBUTE_TEXT].asCString();
2496 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002497 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002498 Json::Value coords = command[SKDEBUGCANVAS_ATTRIBUTE_COORDS];
2499 int count = (int) coords.size();
2500 SkPoint* points = (SkPoint*) sk_malloc_throw(count * sizeof(SkPoint));
2501 for (int i = 0; i < count; i++) {
2502 points[i] = SkPoint::Make(coords[i][0].asFloat(), coords[i][1].asFloat());
2503 }
2504 return new SkDrawPosTextCommand(text, strlen(text), points, paint);
2505}
chudy@google.com902ebe52012-06-29 14:21:22 +00002506
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002507SkDrawPosTextHCommand::SkDrawPosTextHCommand(const void* text, size_t byteLength,
2508 const SkScalar xpos[], SkScalar constY,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002509 const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002510 : INHERITED(kDrawPosTextH_OpType) {
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002511 size_t numPts = paint.countText(text, byteLength);
2512
2513 fText = new char[byteLength];
2514 memcpy(fText, text, byteLength);
robertphillips@google.com91217d02013-03-17 18:33:46 +00002515 fByteLength = byteLength;
robertphillips@google.coma3a09ab2013-03-22 12:25:30 +00002516
2517 fXpos = new SkScalar[numPts];
2518 memcpy(fXpos, xpos, numPts * sizeof(SkScalar));
2519
robertphillips@google.com91217d02013-03-17 18:33:46 +00002520 fConstY = constY;
2521 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002522
robertphillips@google.com91217d02013-03-17 18:33:46 +00002523 fInfo.push(SkObjectParser::TextToString(text, byteLength, paint.getTextEncoding()));
2524 fInfo.push(SkObjectParser::ScalarToString(xpos[0], "XPOS: "));
2525 fInfo.push(SkObjectParser::ScalarToString(constY, "SkScalar constY: "));
2526 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002527}
2528
fmalita8c89c522014-11-08 16:18:56 -08002529void SkDrawPosTextHCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com91217d02013-03-17 18:33:46 +00002530 canvas->drawPosTextH(fText, fByteLength, fXpos, fConstY, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002531}
2532
bungeman51190df2016-03-09 07:42:54 -08002533Json::Value SkDrawPosTextHCommand::toJSON(UrlDataManager& urlDataManager) const {
2534 Json::Value result = INHERITED::toJSON(urlDataManager);
2535 result[SKDEBUGCANVAS_ATTRIBUTE_TEXT] = Json::Value((const char*) fText,
2536 ((const char*) fText) + fByteLength);
2537 result[SKDEBUGCANVAS_ATTRIBUTE_Y] = Json::Value(fConstY);
2538 Json::Value xpos(Json::arrayValue);
2539 size_t numXpos = fPaint.textToGlyphs(fText, fByteLength, nullptr);
2540 for (size_t i = 0; i < numXpos; i++) {
2541 xpos.append(Json::Value(fXpos[i]));
2542 }
2543 result[SKDEBUGCANVAS_ATTRIBUTE_POSITIONS] = xpos;
brianosmanfad98562016-05-04 11:06:28 -07002544 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
bungeman51190df2016-03-09 07:42:54 -08002545 return result;
2546}
2547
2548SkDrawPosTextHCommand* SkDrawPosTextHCommand::fromJSON(Json::Value& command,
2549 UrlDataManager& urlDataManager) {
2550 const char* text = command[SKDEBUGCANVAS_ATTRIBUTE_TEXT].asCString();
2551 SkPaint paint;
2552 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
2553 Json::Value jsonXpos = command[SKDEBUGCANVAS_ATTRIBUTE_POSITIONS];
2554 int count = (int) jsonXpos.size();
2555 SkScalar* xpos = (SkScalar*) sk_malloc_throw(count * sizeof(SkScalar));
2556 for (int i = 0; i < count; i++) {
2557 xpos[i] = jsonXpos[i].asFloat();
2558 }
2559 SkScalar y = command[SKDEBUGCANVAS_ATTRIBUTE_Y].asFloat();
2560 return new SkDrawPosTextHCommand(text, strlen(text), xpos, y, paint);
2561}
2562
fmalita0d48e412016-01-04 08:08:04 -08002563static const char* gPositioningLabels[] = {
2564 "kDefault_Positioning",
2565 "kHorizontal_Positioning",
2566 "kFull_Positioning",
2567};
2568
fmalitab7425172014-08-26 07:56:44 -07002569SkDrawTextBlobCommand::SkDrawTextBlobCommand(const SkTextBlob* blob, SkScalar x, SkScalar y,
2570 const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002571 : INHERITED(kDrawTextBlob_OpType)
fmalitae77f2da2015-12-08 18:59:18 -08002572 , fBlob(SkRef(blob))
fmalitab7425172014-08-26 07:56:44 -07002573 , fXPos(x)
2574 , fYPos(y)
2575 , fPaint(paint) {
2576
fmalitae77f2da2015-12-08 18:59:18 -08002577 SkAutoTDelete<SkString> runsStr(new SkString);
fmalitab7425172014-08-26 07:56:44 -07002578 fInfo.push(SkObjectParser::ScalarToString(x, "XPOS: "));
fmalitaff3106c2014-12-09 05:28:20 -08002579 fInfo.push(SkObjectParser::ScalarToString(y, "YPOS: "));
2580 fInfo.push(SkObjectParser::RectToString(fBlob->bounds(), "Bounds: "));
fmalitae77f2da2015-12-08 18:59:18 -08002581 fInfo.push(runsStr);
fmalitab7425172014-08-26 07:56:44 -07002582 fInfo.push(SkObjectParser::PaintToString(paint));
fmalitae77f2da2015-12-08 18:59:18 -08002583
2584 unsigned runs = 0;
2585 SkPaint runPaint(paint);
2586 SkTextBlobRunIterator iter(blob);
2587 while (!iter.done()) {
fmalita0d48e412016-01-04 08:08:04 -08002588 SkAutoTDelete<SkString> tmpStr(new SkString);
2589 tmpStr->printf("==== Run [%d] ====", runs++);
2590 fInfo.push(tmpStr.release());
fmalitae77f2da2015-12-08 18:59:18 -08002591
2592 fInfo.push(SkObjectParser::IntToString(iter.glyphCount(), "GlyphCount: "));
fmalita0d48e412016-01-04 08:08:04 -08002593 tmpStr.reset(new SkString("GlyphPositioning: "));
2594 tmpStr->append(gPositioningLabels[iter.positioning()]);
2595 fInfo.push(tmpStr.release());
2596
fmalitae77f2da2015-12-08 18:59:18 -08002597 iter.applyFontToPaint(&runPaint);
2598 fInfo.push(SkObjectParser::PaintToString(runPaint));
2599
2600 iter.next();
2601 }
2602
2603 runsStr->printf("Runs: %d", runs);
2604 // runStr is owned by fInfo at this point.
2605 runsStr.release();
fmalitab7425172014-08-26 07:56:44 -07002606}
2607
fmalita8c89c522014-11-08 16:18:56 -08002608void SkDrawTextBlobCommand::execute(SkCanvas* canvas) const {
fmalitab7425172014-08-26 07:56:44 -07002609 canvas->drawTextBlob(fBlob, fXPos, fYPos, fPaint);
2610}
2611
fmalita55773872014-08-29 15:08:20 -07002612bool SkDrawTextBlobCommand::render(SkCanvas* canvas) const {
2613 canvas->clear(SK_ColorWHITE);
2614 canvas->save();
2615
2616 SkRect bounds = fBlob->bounds().makeOffset(fXPos, fYPos);
2617 xlate_and_scale_to_bounds(canvas, bounds);
2618
2619 canvas->drawTextBlob(fBlob.get(), fXPos, fYPos, fPaint);
2620
2621 canvas->restore();
2622
2623 return true;
2624}
2625
ethannicholasf62a8b72016-02-11 10:35:21 -08002626Json::Value SkDrawTextBlobCommand::toJSON(UrlDataManager& urlDataManager) const {
2627 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002628 Json::Value runs(Json::arrayValue);
2629 SkTextBlobRunIterator iter(fBlob.get());
2630 while (!iter.done()) {
2631 Json::Value run(Json::objectValue);
2632 Json::Value jsonPositions(Json::arrayValue);
2633 Json::Value jsonGlyphs(Json::arrayValue);
2634 const SkScalar* iterPositions = iter.pos();
2635 const uint16_t* iterGlyphs = iter.glyphs();
2636 for (uint32_t i = 0; i < iter.glyphCount(); i++) {
2637 switch (iter.positioning()) {
2638 case SkTextBlob::kFull_Positioning:
brianosmanfad98562016-05-04 11:06:28 -07002639 jsonPositions.append(MakeJsonPoint(iterPositions[i * 2],
2640 iterPositions[i * 2 + 1]));
ethannicholas50a8dd02016-02-10 05:40:46 -08002641 break;
2642 case SkTextBlob::kHorizontal_Positioning:
2643 jsonPositions.append(Json::Value(iterPositions[i]));
2644 break;
2645 case SkTextBlob::kDefault_Positioning:
2646 break;
2647 }
2648 jsonGlyphs.append(Json::Value(iterGlyphs[i]));
2649 }
2650 if (iter.positioning() != SkTextBlob::kDefault_Positioning) {
2651 run[SKDEBUGCANVAS_ATTRIBUTE_POSITIONS] = jsonPositions;
2652 }
2653 run[SKDEBUGCANVAS_ATTRIBUTE_GLYPHS] = jsonGlyphs;
2654 SkPaint fontPaint;
2655 iter.applyFontToPaint(&fontPaint);
brianosmanfad98562016-05-04 11:06:28 -07002656 run[SKDEBUGCANVAS_ATTRIBUTE_FONT] = MakeJsonPaint(fontPaint, urlDataManager);
2657 run[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonPoint(iter.offset());
ethannicholas50a8dd02016-02-10 05:40:46 -08002658 runs.append(run);
2659 iter.next();
2660 }
2661 result[SKDEBUGCANVAS_ATTRIBUTE_RUNS] = runs;
2662 result[SKDEBUGCANVAS_ATTRIBUTE_X] = Json::Value(fXPos);
2663 result[SKDEBUGCANVAS_ATTRIBUTE_Y] = Json::Value(fYPos);
brianosmanfad98562016-05-04 11:06:28 -07002664 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002665 return result;
2666}
2667
halcanary9d524f22016-03-29 09:03:52 -07002668SkDrawTextBlobCommand* SkDrawTextBlobCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002669 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002670 SkTextBlobBuilder builder;
2671 Json::Value runs = command[SKDEBUGCANVAS_ATTRIBUTE_RUNS];
2672 for (Json::ArrayIndex i = 0 ; i < runs.size(); i++) {
2673 Json::Value run = runs[i];
2674 SkPaint font;
2675 font.setTextEncoding(SkPaint::kGlyphID_TextEncoding);
ethannicholasf62a8b72016-02-11 10:35:21 -08002676 extract_json_paint(run[SKDEBUGCANVAS_ATTRIBUTE_FONT], urlDataManager, &font);
ethannicholas50a8dd02016-02-10 05:40:46 -08002677 Json::Value glyphs = run[SKDEBUGCANVAS_ATTRIBUTE_GLYPHS];
2678 int count = glyphs.size();
2679 Json::Value coords = run[SKDEBUGCANVAS_ATTRIBUTE_COORDS];
2680 SkScalar x = coords[0].asFloat();
2681 SkScalar y = coords[1].asFloat();
2682 if (run.isMember(SKDEBUGCANVAS_ATTRIBUTE_POSITIONS)) {
2683 Json::Value positions = run[SKDEBUGCANVAS_ATTRIBUTE_POSITIONS];
2684 if (positions.size() > 0 && positions[0].isNumeric()) {
2685 SkTextBlobBuilder::RunBuffer buffer = builder.allocRunPosH(font, count, y);
2686 for (int j = 0; j < count; j++) {
2687 buffer.glyphs[j] = glyphs[j].asUInt();
2688 buffer.pos[j] = positions[j].asFloat();
2689 }
2690 }
2691 else {
2692 SkTextBlobBuilder::RunBuffer buffer = builder.allocRunPos(font, count);
2693 for (int j = 0; j < count; j++) {
2694 buffer.glyphs[j] = glyphs[j].asUInt();
2695 buffer.pos[j * 2] = positions[j][0].asFloat();
2696 buffer.pos[j * 2 + 1] = positions[j][1].asFloat();
2697 }
2698 }
2699 }
2700 else {
2701 SkTextBlobBuilder::RunBuffer buffer = builder.allocRun(font, count, x, y);
2702 for (int j = 0; j < count; j++) {
2703 buffer.glyphs[j] = glyphs[j].asUInt();
2704 }
2705 }
2706 }
2707 SkScalar x = command[SKDEBUGCANVAS_ATTRIBUTE_X].asFloat();
2708 SkScalar y = command[SKDEBUGCANVAS_ATTRIBUTE_Y].asFloat();
2709 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002710 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002711 return new SkDrawTextBlobCommand(builder.build(), x, y, paint);
2712}
2713
robertphillips9bafc302015-02-13 11:13:00 -08002714SkDrawPatchCommand::SkDrawPatchCommand(const SkPoint cubics[12], const SkColor colors[4],
2715 const SkPoint texCoords[4], SkXfermode* xfermode,
2716 const SkPaint& paint)
2717 : INHERITED(kDrawPatch_OpType) {
2718 memcpy(fCubics, cubics, sizeof(fCubics));
ethannicholas1446a9a2016-02-10 14:05:02 -08002719 if (colors != nullptr) {
2720 memcpy(fColors, colors, sizeof(fColors));
2721 fColorsPtr = fColors;
2722 } else {
2723 fColorsPtr = nullptr;
2724 }
2725 if (texCoords != nullptr) {
2726 memcpy(fTexCoords, texCoords, sizeof(fTexCoords));
2727 fTexCoordsPtr = fTexCoords;
2728 } else {
2729 fTexCoordsPtr = nullptr;
2730 }
2731 if (xfermode != nullptr) {
2732 fXfermode.reset(SkRef(xfermode));
2733 }
robertphillips9bafc302015-02-13 11:13:00 -08002734 fPaint = paint;
2735
2736 fInfo.push(SkObjectParser::PaintToString(paint));
2737}
2738
2739void SkDrawPatchCommand::execute(SkCanvas* canvas) const {
ethannicholas1446a9a2016-02-10 14:05:02 -08002740 canvas->drawPatch(fCubics, fColorsPtr, fTexCoordsPtr, fXfermode, fPaint);
2741}
2742
ethannicholasf62a8b72016-02-11 10:35:21 -08002743Json::Value SkDrawPatchCommand::toJSON(UrlDataManager& urlDataManager) const {
2744 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas1446a9a2016-02-10 14:05:02 -08002745 Json::Value cubics = Json::Value(Json::arrayValue);
2746 for (int i = 0; i < 12; i++) {
brianosmanfad98562016-05-04 11:06:28 -07002747 cubics.append(MakeJsonPoint(fCubics[i]));
ethannicholas1446a9a2016-02-10 14:05:02 -08002748 }
2749 result[SKDEBUGCANVAS_ATTRIBUTE_CUBICS] = cubics;
2750 if (fColorsPtr != nullptr) {
2751 Json::Value colors = Json::Value(Json::arrayValue);
2752 for (int i = 0; i < 4; i++) {
brianosmanfad98562016-05-04 11:06:28 -07002753 colors.append(MakeJsonColor(fColorsPtr[i]));
ethannicholas1446a9a2016-02-10 14:05:02 -08002754 }
2755 result[SKDEBUGCANVAS_ATTRIBUTE_COLORS] = colors;
2756 }
2757 if (fTexCoordsPtr != nullptr) {
2758 Json::Value texCoords = Json::Value(Json::arrayValue);
2759 for (int i = 0; i < 4; i++) {
brianosmanfad98562016-05-04 11:06:28 -07002760 texCoords.append(MakeJsonPoint(fTexCoords[i]));
ethannicholas1446a9a2016-02-10 14:05:02 -08002761 }
2762 result[SKDEBUGCANVAS_ATTRIBUTE_TEXTURECOORDS] = texCoords;
2763 }
2764 if (fXfermode.get() != nullptr) {
2765 Json::Value jsonXfermode;
ethannicholasf62a8b72016-02-11 10:35:21 -08002766 flatten(fXfermode, &jsonXfermode, urlDataManager);
ethannicholas1446a9a2016-02-10 14:05:02 -08002767 result[SKDEBUGCANVAS_ATTRIBUTE_XFERMODE] = jsonXfermode;
2768 }
2769 return result;
2770}
2771
halcanary9d524f22016-03-29 09:03:52 -07002772SkDrawPatchCommand* SkDrawPatchCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002773 UrlDataManager& urlDataManager) {
ethannicholas1446a9a2016-02-10 14:05:02 -08002774 Json::Value jsonCubics = command[SKDEBUGCANVAS_ATTRIBUTE_CUBICS];
2775 SkPoint cubics[12];
2776 for (int i = 0; i < 12; i++) {
2777 cubics[i] = get_json_point(jsonCubics[i]);
2778 }
2779 SkColor* colorsPtr;
2780 SkColor colors[4];
2781 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_COLORS)) {
2782 Json::Value jsonColors = command[SKDEBUGCANVAS_ATTRIBUTE_COLORS];
2783 for (int i = 0; i < 4; i++) {
2784 colors[i] = get_json_color(jsonColors[i]);
2785 }
2786 colorsPtr = colors;
2787 }
2788 else {
2789 colorsPtr = nullptr;
2790 }
2791 SkPoint* texCoordsPtr;
2792 SkPoint texCoords[4];
2793 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_TEXTURECOORDS)) {
2794 Json::Value jsonTexCoords = command[SKDEBUGCANVAS_ATTRIBUTE_TEXTURECOORDS];
2795 for (int i = 0; i < 4; i++) {
2796 texCoords[i] = get_json_point(jsonTexCoords[i]);
2797 }
2798 texCoordsPtr = texCoords;
2799 }
2800 else {
2801 texCoordsPtr = nullptr;
2802 }
2803 SkAutoTUnref<SkXfermode> xfermode;
2804 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_XFERMODE)) {
2805 Json::Value jsonXfermode = command[SKDEBUGCANVAS_ATTRIBUTE_XFERMODE];
ethannicholasf62a8b72016-02-11 10:35:21 -08002806 xfermode.reset((SkXfermode*) load_flattenable(jsonXfermode, urlDataManager));
ethannicholas1446a9a2016-02-10 14:05:02 -08002807 }
2808 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002809 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas1446a9a2016-02-10 14:05:02 -08002810 return new SkDrawPatchCommand(cubics, colorsPtr, texCoordsPtr, xfermode, paint);
robertphillips9bafc302015-02-13 11:13:00 -08002811}
2812
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002813SkDrawRectCommand::SkDrawRectCommand(const SkRect& rect, const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002814 : INHERITED(kDrawRect_OpType) {
robertphillips@google.com91217d02013-03-17 18:33:46 +00002815 fRect = rect;
2816 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002817
robertphillips@google.com91217d02013-03-17 18:33:46 +00002818 fInfo.push(SkObjectParser::RectToString(rect));
2819 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002820}
2821
fmalita8c89c522014-11-08 16:18:56 -08002822void SkDrawRectCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com91217d02013-03-17 18:33:46 +00002823 canvas->drawRect(fRect, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002824}
2825
ethannicholasf62a8b72016-02-11 10:35:21 -08002826Json::Value SkDrawRectCommand::toJSON(UrlDataManager& urlDataManager) const {
2827 Json::Value result = INHERITED::toJSON(urlDataManager);
brianosmanfad98562016-05-04 11:06:28 -07002828 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonRect(fRect);
2829 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
reed67f62fa2016-06-29 11:36:34 -07002830
2831 SkString desc;
2832 result[SKDEBUGCANVAS_ATTRIBUTE_SHORTDESC] = Json::Value(str_append(&desc, fRect)->c_str());
2833
ethannicholas50a8dd02016-02-10 05:40:46 -08002834 return result;
2835}
2836
halcanary9d524f22016-03-29 09:03:52 -07002837SkDrawRectCommand* SkDrawRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002838 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002839 SkRect coords;
2840 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_COORDS], &coords);
2841 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002842 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002843 return new SkDrawRectCommand(coords, paint);
2844}
2845
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002846SkDrawRRectCommand::SkDrawRRectCommand(const SkRRect& rrect, const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002847 : INHERITED(kDrawRRect_OpType) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002848 fRRect = rrect;
2849 fPaint = paint;
robertphillips@google.com67baba42013-01-02 20:20:31 +00002850
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002851 fInfo.push(SkObjectParser::RRectToString(rrect));
2852 fInfo.push(SkObjectParser::PaintToString(paint));
robertphillips@google.com67baba42013-01-02 20:20:31 +00002853}
2854
fmalita8c89c522014-11-08 16:18:56 -08002855void SkDrawRRectCommand::execute(SkCanvas* canvas) const {
robertphillips@google.comfebc0ec2013-03-11 22:53:11 +00002856 canvas->drawRRect(fRRect, fPaint);
robertphillips@google.com67baba42013-01-02 20:20:31 +00002857}
2858
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002859bool SkDrawRRectCommand::render(SkCanvas* canvas) const {
robertphillips@google.com6ede1fe2013-06-06 23:59:28 +00002860 render_rrect(canvas, fRRect);
2861 return true;
2862}
2863
ethannicholasf62a8b72016-02-11 10:35:21 -08002864Json::Value SkDrawRRectCommand::toJSON(UrlDataManager& urlDataManager) const {
2865 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002866 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = make_json_rrect(fRRect);
brianosmanfad98562016-05-04 11:06:28 -07002867 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002868 return result;
2869}
2870
halcanary9d524f22016-03-29 09:03:52 -07002871SkDrawRRectCommand* SkDrawRRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002872 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002873 SkRRect coords;
2874 extract_json_rrect(command[SKDEBUGCANVAS_ATTRIBUTE_COORDS], &coords);
2875 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002876 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002877 return new SkDrawRRectCommand(coords, paint);
2878}
2879
skia.committer@gmail.com90667ba2014-02-25 03:05:18 +00002880SkDrawDRRectCommand::SkDrawDRRectCommand(const SkRRect& outer,
commit-bot@chromium.org3d305202014-02-24 17:28:55 +00002881 const SkRRect& inner,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002882 const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002883 : INHERITED(kDrawDRRect_OpType) {
commit-bot@chromium.org3d305202014-02-24 17:28:55 +00002884 fOuter = outer;
2885 fInner = inner;
2886 fPaint = paint;
commit-bot@chromium.org3d305202014-02-24 17:28:55 +00002887
2888 fInfo.push(SkObjectParser::RRectToString(outer));
2889 fInfo.push(SkObjectParser::RRectToString(inner));
2890 fInfo.push(SkObjectParser::PaintToString(paint));
2891}
2892
fmalita8c89c522014-11-08 16:18:56 -08002893void SkDrawDRRectCommand::execute(SkCanvas* canvas) const {
commit-bot@chromium.org3d305202014-02-24 17:28:55 +00002894 canvas->drawDRRect(fOuter, fInner, fPaint);
2895}
2896
2897bool SkDrawDRRectCommand::render(SkCanvas* canvas) const {
2898 render_drrect(canvas, fOuter, fInner);
2899 return true;
2900}
2901
ethannicholasf62a8b72016-02-11 10:35:21 -08002902Json::Value SkDrawDRRectCommand::toJSON(UrlDataManager& urlDataManager) const {
2903 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002904 result[SKDEBUGCANVAS_ATTRIBUTE_OUTER] = make_json_rrect(fOuter);
2905 result[SKDEBUGCANVAS_ATTRIBUTE_INNER] = make_json_rrect(fInner);
brianosmanfad98562016-05-04 11:06:28 -07002906 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002907 return result;
2908}
2909
halcanary9d524f22016-03-29 09:03:52 -07002910SkDrawDRRectCommand* SkDrawDRRectCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002911 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002912 SkRRect outer;
2913 extract_json_rrect(command[SKDEBUGCANVAS_ATTRIBUTE_INNER], &outer);
2914 SkRRect inner;
2915 extract_json_rrect(command[SKDEBUGCANVAS_ATTRIBUTE_INNER], &inner);
2916 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002917 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002918 return new SkDrawDRRectCommand(outer, inner, paint);
2919}
2920
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002921SkDrawTextCommand::SkDrawTextCommand(const void* text, size_t byteLength, SkScalar x, SkScalar y,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002922 const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002923 : INHERITED(kDrawText_OpType) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002924 fText = new char[byteLength];
2925 memcpy(fText, text, byteLength);
2926 fByteLength = byteLength;
2927 fX = x;
2928 fY = y;
2929 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002930
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002931 fInfo.push(SkObjectParser::TextToString(text, byteLength, paint.getTextEncoding()));
2932 fInfo.push(SkObjectParser::ScalarToString(x, "SkScalar x: "));
2933 fInfo.push(SkObjectParser::ScalarToString(y, "SkScalar y: "));
2934 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002935}
2936
fmalita8c89c522014-11-08 16:18:56 -08002937void SkDrawTextCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002938 canvas->drawText(fText, fByteLength, fX, fY, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002939}
2940
ethannicholasf62a8b72016-02-11 10:35:21 -08002941Json::Value SkDrawTextCommand::toJSON(UrlDataManager& urlDataManager) const {
2942 Json::Value result = INHERITED::toJSON(urlDataManager);
halcanary9d524f22016-03-29 09:03:52 -07002943 result[SKDEBUGCANVAS_ATTRIBUTE_TEXT] = Json::Value((const char*) fText,
ethannicholas50a8dd02016-02-10 05:40:46 -08002944 ((const char*) fText) + fByteLength);
2945 Json::Value coords(Json::arrayValue);
brianosmanfad98562016-05-04 11:06:28 -07002946 result[SKDEBUGCANVAS_ATTRIBUTE_COORDS] = MakeJsonPoint(fX, fY);
2947 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08002948 return result;
2949}
2950
halcanary9d524f22016-03-29 09:03:52 -07002951SkDrawTextCommand* SkDrawTextCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08002952 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08002953 const char* text = command[SKDEBUGCANVAS_ATTRIBUTE_TEXT].asCString();
2954 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08002955 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08002956 Json::Value coords = command[SKDEBUGCANVAS_ATTRIBUTE_COORDS];
halcanary9d524f22016-03-29 09:03:52 -07002957 return new SkDrawTextCommand(text, strlen(text), coords[0].asFloat(), coords[1].asFloat(),
ethannicholas50a8dd02016-02-10 05:40:46 -08002958 paint);
2959}
2960
reed45561a02016-07-07 12:47:17 -07002961///////////////////////////////////////////////////////////////////////////////////////////////////
2962
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00002963SkDrawTextOnPathCommand::SkDrawTextOnPathCommand(const void* text, size_t byteLength,
2964 const SkPath& path, const SkMatrix* matrix,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00002965 const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08002966 : INHERITED(kDrawTextOnPath_OpType) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002967 fText = new char[byteLength];
2968 memcpy(fText, text, byteLength);
2969 fByteLength = byteLength;
2970 fPath = path;
bsalomon49f085d2014-09-05 13:34:00 -07002971 if (matrix) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002972 fMatrix = *matrix;
2973 } else {
2974 fMatrix.setIdentity();
2975 }
2976 fPaint = paint;
chudy@google.com902ebe52012-06-29 14:21:22 +00002977
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002978 fInfo.push(SkObjectParser::TextToString(text, byteLength, paint.getTextEncoding()));
2979 fInfo.push(SkObjectParser::PathToString(path));
bsalomon49f085d2014-09-05 13:34:00 -07002980 if (matrix) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002981 fInfo.push(SkObjectParser::MatrixToString(*matrix));
2982 }
2983 fInfo.push(SkObjectParser::PaintToString(paint));
chudy@google.com902ebe52012-06-29 14:21:22 +00002984}
2985
fmalita8c89c522014-11-08 16:18:56 -08002986void SkDrawTextOnPathCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002987 canvas->drawTextOnPath(fText, fByteLength, fPath,
halcanary96fcdcc2015-08-27 07:41:13 -07002988 fMatrix.isIdentity() ? nullptr : &fMatrix,
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00002989 fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00002990}
2991
ethannicholasf62a8b72016-02-11 10:35:21 -08002992Json::Value SkDrawTextOnPathCommand::toJSON(UrlDataManager& urlDataManager) const {
2993 Json::Value result = INHERITED::toJSON(urlDataManager);
halcanary9d524f22016-03-29 09:03:52 -07002994 result[SKDEBUGCANVAS_ATTRIBUTE_TEXT] = Json::Value((const char*) fText,
ethannicholas50a8dd02016-02-10 05:40:46 -08002995 ((const char*) fText) + fByteLength);
2996 Json::Value coords(Json::arrayValue);
brianosmanfad98562016-05-04 11:06:28 -07002997 result[SKDEBUGCANVAS_ATTRIBUTE_PATH] = MakeJsonPath(fPath);
ethannicholas50a8dd02016-02-10 05:40:46 -08002998 if (!fMatrix.isIdentity()) {
joshualittbd724132016-03-03 11:39:38 -08002999 result[SKDEBUGCANVAS_ATTRIBUTE_MATRIX] = MakeJsonMatrix(fMatrix);
ethannicholas50a8dd02016-02-10 05:40:46 -08003000 }
brianosmanfad98562016-05-04 11:06:28 -07003001 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08003002 return result;
3003}
3004
halcanary9d524f22016-03-29 09:03:52 -07003005SkDrawTextOnPathCommand* SkDrawTextOnPathCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08003006 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08003007 const char* text = command[SKDEBUGCANVAS_ATTRIBUTE_TEXT].asCString();
3008 SkPaint paint;
ethannicholasf62a8b72016-02-11 10:35:21 -08003009 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08003010 SkPath path;
3011 extract_json_path(command[SKDEBUGCANVAS_ATTRIBUTE_PATH], &path);
3012 SkMatrix* matrixPtr;
3013 SkMatrix matrix;
3014 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_MATRIX)) {
3015 extract_json_matrix(command[SKDEBUGCANVAS_ATTRIBUTE_MATRIX], &matrix);
3016 matrixPtr = &matrix;
3017 }
3018 else {
3019 matrixPtr = nullptr;
3020 }
3021 return new SkDrawTextOnPathCommand(text, strlen(text), path, matrixPtr, paint);
3022}
3023
reed45561a02016-07-07 12:47:17 -07003024///////////////////////////////////////////////////////////////////////////////////////////////////
3025
3026SkDrawTextRSXformCommand::SkDrawTextRSXformCommand(const void* text, size_t byteLength,
3027 const SkRSXform xform[], const SkRect* cull,
3028 const SkPaint& paint)
3029 : INHERITED(kDrawTextOnPath_OpType)
3030{
3031 fText = new char[byteLength];
3032 memcpy(fText, text, byteLength);
3033 fByteLength = byteLength;
3034 int count = paint.countText(text, byteLength);
3035 fXform = new SkRSXform[count];
3036 memcpy(fXform, xform, count * sizeof(SkRSXform));
3037 if (cull) {
3038 fCullStorage = *cull;
3039 fCull = &fCullStorage;
3040 } else {
3041 fCull = nullptr;
3042 }
3043 fPaint = paint;
3044
3045 fInfo.push(SkObjectParser::TextToString(text, byteLength, paint.getTextEncoding()));
3046 fInfo.push(SkObjectParser::PaintToString(paint));
3047}
3048
3049void SkDrawTextRSXformCommand::execute(SkCanvas* canvas) const {
3050 canvas->drawTextRSXform(fText, fByteLength, fXform, fCull, fPaint);
3051}
3052
3053Json::Value SkDrawTextRSXformCommand::toJSON(UrlDataManager& urlDataManager) const {
3054 Json::Value result = INHERITED::toJSON(urlDataManager);
3055 result[SKDEBUGCANVAS_ATTRIBUTE_TEXT] = Json::Value((const char*) fText,
3056 ((const char*) fText) + fByteLength);
3057 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(fPaint, urlDataManager);
3058 return result;
3059}
3060
3061SkDrawTextRSXformCommand* SkDrawTextRSXformCommand::fromJSON(Json::Value& command,
3062 UrlDataManager& urlDataManager) {
3063 const char* text = command[SKDEBUGCANVAS_ATTRIBUTE_TEXT].asCString();
3064 size_t byteLength = strlen(text);
3065 SkPaint paint;
3066 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
3067
3068 // TODO: handle xform and cull
3069 int count = paint.countText(text, byteLength);
3070 SkAutoTArray<SkRSXform> xform(count);
3071 for (int i = 0; i < count; ++i) {
3072 xform[i].fSCos = 1;
3073 xform[i].fSSin = xform[i].fTx = xform[i].fTy = 0;
3074 }
3075 return new SkDrawTextRSXformCommand(text, byteLength, &xform[0], nullptr, paint);
3076}
3077
3078///////////////////////////////////////////////////////////////////////////////////////////////////
3079
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00003080SkDrawVerticesCommand::SkDrawVerticesCommand(SkCanvas::VertexMode vmode, int vertexCount,
3081 const SkPoint vertices[], const SkPoint texs[],
3082 const SkColor colors[], SkXfermode* xfermode,
3083 const uint16_t indices[], int indexCount,
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00003084 const SkPaint& paint)
robertphillips9bafc302015-02-13 11:13:00 -08003085 : INHERITED(kDrawVertices_OpType) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003086 fVmode = vmode;
3087
3088 fVertexCount = vertexCount;
3089
3090 fVertices = new SkPoint[vertexCount];
3091 memcpy(fVertices, vertices, vertexCount * sizeof(SkPoint));
3092
bsalomon49f085d2014-09-05 13:34:00 -07003093 if (texs) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003094 fTexs = new SkPoint[vertexCount];
3095 memcpy(fTexs, texs, vertexCount * sizeof(SkPoint));
3096 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07003097 fTexs = nullptr;
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003098 }
3099
bsalomon49f085d2014-09-05 13:34:00 -07003100 if (colors) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003101 fColors = new SkColor[vertexCount];
3102 memcpy(fColors, colors, vertexCount * sizeof(SkColor));
3103 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07003104 fColors = nullptr;
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003105 }
3106
3107 fXfermode = xfermode;
bsalomon49f085d2014-09-05 13:34:00 -07003108 if (fXfermode) {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003109 fXfermode->ref();
3110 }
3111
3112 if (indexCount > 0) {
3113 fIndices = new uint16_t[indexCount];
3114 memcpy(fIndices, indices, indexCount * sizeof(uint16_t));
3115 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07003116 fIndices = nullptr;
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003117 }
3118
3119 fIndexCount = indexCount;
3120 fPaint = paint;
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003121
chudy@google.com902ebe52012-06-29 14:21:22 +00003122 // TODO(chudy)
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003123 fInfo.push(SkObjectParser::CustomTextToString("To be implemented."));
3124 fInfo.push(SkObjectParser::PaintToString(paint));
3125}
3126
commit-bot@chromium.org7a115912013-06-18 20:20:55 +00003127SkDrawVerticesCommand::~SkDrawVerticesCommand() {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003128 delete [] fVertices;
3129 delete [] fTexs;
3130 delete [] fColors;
3131 SkSafeUnref(fXfermode);
3132 delete [] fIndices;
chudy@google.com902ebe52012-06-29 14:21:22 +00003133}
3134
fmalita8c89c522014-11-08 16:18:56 -08003135void SkDrawVerticesCommand::execute(SkCanvas* canvas) const {
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003136 canvas->drawVertices(fVmode, fVertexCount, fVertices,
3137 fTexs, fColors, fXfermode, fIndices,
3138 fIndexCount, fPaint);
chudy@google.com902ebe52012-06-29 14:21:22 +00003139}
3140
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00003141SkRestoreCommand::SkRestoreCommand()
robertphillips9bafc302015-02-13 11:13:00 -08003142 : INHERITED(kRestore_OpType) {
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003143 fInfo.push(SkObjectParser::CustomTextToString("No Parameters"));
chudy@google.com902ebe52012-06-29 14:21:22 +00003144}
3145
fmalita8c89c522014-11-08 16:18:56 -08003146void SkRestoreCommand::execute(SkCanvas* canvas) const {
chudy@google.com902ebe52012-06-29 14:21:22 +00003147 canvas->restore();
3148}
3149
ethannicholasf62a8b72016-02-11 10:35:21 -08003150SkRestoreCommand* SkRestoreCommand::fromJSON(Json::Value& command, UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08003151 return new SkRestoreCommand();
3152}
3153
Florin Malita5f6102d2014-06-30 10:13:28 -04003154SkSaveCommand::SkSaveCommand()
robertphillips9bafc302015-02-13 11:13:00 -08003155 : INHERITED(kSave_OpType) {
chudy@google.com902ebe52012-06-29 14:21:22 +00003156}
3157
fmalita8c89c522014-11-08 16:18:56 -08003158void SkSaveCommand::execute(SkCanvas* canvas) const {
Florin Malita5f6102d2014-06-30 10:13:28 -04003159 canvas->save();
chudy@google.com902ebe52012-06-29 14:21:22 +00003160}
3161
ethannicholasf62a8b72016-02-11 10:35:21 -08003162SkSaveCommand* SkSaveCommand::fromJSON(Json::Value& command, UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08003163 return new SkSaveCommand();
3164}
3165
reed4960eee2015-12-18 07:09:18 -08003166SkSaveLayerCommand::SkSaveLayerCommand(const SkCanvas::SaveLayerRec& rec)
robertphillips9bafc302015-02-13 11:13:00 -08003167 : INHERITED(kSaveLayer_OpType) {
reed4960eee2015-12-18 07:09:18 -08003168 if (rec.fBounds) {
3169 fBounds = *rec.fBounds;
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003170 } else {
3171 fBounds.setEmpty();
3172 }
chudy@google.com902ebe52012-06-29 14:21:22 +00003173
reed4960eee2015-12-18 07:09:18 -08003174 if (rec.fPaint) {
3175 fPaint = *rec.fPaint;
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003176 fPaintPtr = &fPaint;
3177 } else {
halcanary96fcdcc2015-08-27 07:41:13 -07003178 fPaintPtr = nullptr;
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003179 }
reed4960eee2015-12-18 07:09:18 -08003180 fSaveLayerFlags = rec.fSaveLayerFlags;
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003181
ethannicholas50a8dd02016-02-10 05:40:46 -08003182 if (rec.fBackdrop) {
3183 fBackdrop = rec.fBackdrop;
3184 fBackdrop->ref();
3185 } else {
3186 fBackdrop = nullptr;
3187 }
3188
reed4960eee2015-12-18 07:09:18 -08003189 if (rec.fBounds) {
3190 fInfo.push(SkObjectParser::RectToString(*rec.fBounds, "Bounds: "));
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003191 }
reed4960eee2015-12-18 07:09:18 -08003192 if (rec.fPaint) {
3193 fInfo.push(SkObjectParser::PaintToString(*rec.fPaint));
robertphillips@google.com24bfdac2013-03-22 16:33:31 +00003194 }
reed4960eee2015-12-18 07:09:18 -08003195 fInfo.push(SkObjectParser::SaveLayerFlagsToString(fSaveLayerFlags));
chudy@google.com902ebe52012-06-29 14:21:22 +00003196}
3197
ethannicholas50a8dd02016-02-10 05:40:46 -08003198SkSaveLayerCommand::~SkSaveLayerCommand() {
3199 if (fBackdrop != nullptr) {
3200 fBackdrop->unref();
3201 }
3202}
3203
fmalita8c89c522014-11-08 16:18:56 -08003204void SkSaveLayerCommand::execute(SkCanvas* canvas) const {
reed4960eee2015-12-18 07:09:18 -08003205 canvas->saveLayer(SkCanvas::SaveLayerRec(fBounds.isEmpty() ? nullptr : &fBounds,
3206 fPaintPtr,
3207 fSaveLayerFlags));
chudy@google.com902ebe52012-06-29 14:21:22 +00003208}
3209
fmalita8c89c522014-11-08 16:18:56 -08003210void SkSaveLayerCommand::vizExecute(SkCanvas* canvas) const {
commit-bot@chromium.org1643b2c2014-03-03 23:25:41 +00003211 canvas->save();
3212}
3213
ethannicholasf62a8b72016-02-11 10:35:21 -08003214Json::Value SkSaveLayerCommand::toJSON(UrlDataManager& urlDataManager) const {
3215 Json::Value result = INHERITED::toJSON(urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08003216 if (!fBounds.isEmpty()) {
brianosmanfad98562016-05-04 11:06:28 -07003217 result[SKDEBUGCANVAS_ATTRIBUTE_BOUNDS] = MakeJsonRect(fBounds);
ethannicholas50a8dd02016-02-10 05:40:46 -08003218 }
3219 if (fPaintPtr != nullptr) {
brianosmanfad98562016-05-04 11:06:28 -07003220 result[SKDEBUGCANVAS_ATTRIBUTE_PAINT] = MakeJsonPaint(*fPaintPtr,
ethannicholasf62a8b72016-02-11 10:35:21 -08003221 urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08003222 }
3223 if (fBackdrop != nullptr) {
3224 Json::Value jsonBackdrop;
ethannicholasf62a8b72016-02-11 10:35:21 -08003225 flatten(fBackdrop, &jsonBackdrop, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08003226 result[SKDEBUGCANVAS_ATTRIBUTE_BACKDROP] = jsonBackdrop;
3227 }
3228 if (fSaveLayerFlags != 0) {
3229 SkDebugf("unsupported: saveLayer flags\n");
3230 SkASSERT(false);
3231 }
3232 return result;
3233}
3234
halcanary9d524f22016-03-29 09:03:52 -07003235SkSaveLayerCommand* SkSaveLayerCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08003236 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08003237 SkCanvas::SaveLayerRec rec;
3238 SkRect bounds;
3239 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_BOUNDS)) {
3240 extract_json_rect(command[SKDEBUGCANVAS_ATTRIBUTE_BOUNDS], &bounds);
3241 rec.fBounds = &bounds;
3242 }
3243 SkPaint paint;
3244 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_PAINT)) {
ethannicholasf62a8b72016-02-11 10:35:21 -08003245 extract_json_paint(command[SKDEBUGCANVAS_ATTRIBUTE_PAINT], urlDataManager, &paint);
ethannicholas50a8dd02016-02-10 05:40:46 -08003246 rec.fPaint = &paint;
3247 }
3248 if (command.isMember(SKDEBUGCANVAS_ATTRIBUTE_BACKDROP)) {
3249 Json::Value backdrop = command[SKDEBUGCANVAS_ATTRIBUTE_BACKDROP];
ethannicholasf62a8b72016-02-11 10:35:21 -08003250 rec.fBackdrop = (SkImageFilter*) load_flattenable(backdrop, urlDataManager);
ethannicholas50a8dd02016-02-10 05:40:46 -08003251 }
3252 SkSaveLayerCommand* result = new SkSaveLayerCommand(rec);
3253 if (rec.fBackdrop != nullptr) {
3254 rec.fBackdrop->unref();
3255 }
3256 return result;
3257}
3258
commit-bot@chromium.org57f74e02014-03-25 23:31:33 +00003259SkSetMatrixCommand::SkSetMatrixCommand(const SkMatrix& matrix)
robertphillips9bafc302015-02-13 11:13:00 -08003260 : INHERITED(kSetMatrix_OpType) {
robertphillips70171682014-10-16 14:28:28 -07003261 fUserMatrix.reset();
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003262 fMatrix = matrix;
robertphillips@google.com0df2a9a2013-03-25 11:50:42 +00003263 fInfo.push(SkObjectParser::MatrixToString(matrix));
chudy@google.com902ebe52012-06-29 14:21:22 +00003264}
3265
robertphillips70171682014-10-16 14:28:28 -07003266void SkSetMatrixCommand::setUserMatrix(const SkMatrix& userMatrix) {
3267 fUserMatrix = userMatrix;
3268}
3269
fmalita8c89c522014-11-08 16:18:56 -08003270void SkSetMatrixCommand::execute(SkCanvas* canvas) const {
robertphillips70171682014-10-16 14:28:28 -07003271 SkMatrix temp = SkMatrix::Concat(fUserMatrix, fMatrix);
3272 canvas->setMatrix(temp);
chudy@google.com902ebe52012-06-29 14:21:22 +00003273}
3274
ethannicholasf62a8b72016-02-11 10:35:21 -08003275Json::Value SkSetMatrixCommand::toJSON(UrlDataManager& urlDataManager) const {
3276 Json::Value result = INHERITED::toJSON(urlDataManager);
joshualittbd724132016-03-03 11:39:38 -08003277 result[SKDEBUGCANVAS_ATTRIBUTE_MATRIX] = MakeJsonMatrix(fMatrix);
ethannicholas50a8dd02016-02-10 05:40:46 -08003278 return result;
3279}
3280
halcanary9d524f22016-03-29 09:03:52 -07003281SkSetMatrixCommand* SkSetMatrixCommand::fromJSON(Json::Value& command,
ethannicholasf62a8b72016-02-11 10:35:21 -08003282 UrlDataManager& urlDataManager) {
ethannicholas50a8dd02016-02-10 05:40:46 -08003283 SkMatrix matrix;
3284 extract_json_matrix(command[SKDEBUGCANVAS_ATTRIBUTE_MATRIX], &matrix);
3285 return new SkSetMatrixCommand(matrix);
3286}