• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#Topic Illustrations
2
3#Subtopic Image_Info_Color_Type_RGB_565
4#Example
5#Width 415
6#Height 250
7#Function
8###$
9#include "SkTextUtils.h"
10$$$#
11##
12
13void draw(SkCanvas* canvas) {
14    canvas->scale(1.25f, 1.25f);
15    SkPaint paint;
16    paint.setAntiAlias(true);
17    SkFont font(nullptr, 10);
18    SkTextUtils::DrawString(canvas, "16-bit word", 5 + 20 * 8, 20, font, paint, SkTextUtils::kCenter_Align);
19    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
20    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 1.5f, 137, font, paint, SkTextUtils::kCenter_Align);
21    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 6.5f, 187, font, paint, SkTextUtils::kCenter_Align);
22    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
23        SkPaint p(paint);
24        p.setColor(SK_ColorRED);
25        SkScalar xPos = 15;
26        int width = n % 32 + 1;
27        int lastN = n > 32 ? 32 : 0;
28        for (; n >= lastN; --n) {
29            for (int i = 0; i <= count; ++i) {
30                int a = width - e[i];
31                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
32                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
33                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
34                    break;
35                }
36            }
37            xPos += 20;
38        }
39        p.setColor(SK_ColorBLACK);
40        for (int i = 0; i < count; ++i) {
41            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
42        }
43        p.setStyle(SkPaint::kStroke_Style);
44        for (int i = 0; i <= count; ++i) {
45            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
46        }
47        for (int i = 0; i < 2; ++i) {
48            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
49        }
50    };
51    SkScalar edges[] = { 0, 5, 11, 16,
52                         0, 3, 8,
53                         0, 5, 8 };
54    const char* labels[] = { "red", "green", "blue" };
55    drawBoxText(&edges[0], &labels[0], 3, 15, 45);
56    drawBoxText(&edges[4], &labels[1], 2, 7, 110);
57    drawBoxText(&edges[7], &labels[0], 2, 7, 160);
58}
59##
60##
61
62#Subtopic Image_Info_Color_Type_ARGB_4444
63#Example
64#Width 415
65#Height 250
66#Function
67###$
68#include "SkTextUtils.h"
69$$$#
70##
71
72void draw(SkCanvas* canvas) {
73    canvas->scale(1.25f, 1.25f);
74    SkPaint paint;
75    paint.setAntiAlias(true);
76    SkFont font(nullptr, 10);
77    SkTextUtils::DrawString(canvas, "16-bit word", 5 + 20 * 8, 20, font, paint, SkTextUtils::kCenter_Align);
78    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
79    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
80        SkPaint p(paint);
81        p.setColor(SK_ColorRED);
82        SkScalar xPos = 15;
83        int width = n % 32 + 1;
84        int lastN = n > 32 ? 32 : 0;
85        for (; n >= lastN; --n) {
86            for (int i = 0; i <= count; ++i) {
87                int a = width - e[i];
88                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
89                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
90                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
91                    break;
92                }
93            }
94            xPos += 20;
95        }
96        p.setColor(SK_ColorBLACK);
97        for (int i = 0; i < count; ++i) {
98            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
99        }
100        p.setStyle(SkPaint::kStroke_Style);
101        for (int i = 0; i <= count; ++i) {
102            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
103        }
104        for (int i = 0; i < 2; ++i) {
105            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
106        }
107    };
108    SkScalar edges[] = { 0, 4, 8, 12, 16 };
109    const char* labels[] = { "red", "green", "blue", "alpha" };
110    drawBoxText(&edges[0], &labels[0], 4, 15, 45);
111    drawBoxText(&edges[0], &labels[2], 2, 7, 110);
112    drawBoxText(&edges[0], &labels[0], 2, 7, 160);
113}
114##
115##
116
117#Subtopic Image_Info_Color_Type_RGBA_8888
118#Example
119#Width 812
120#Height 365
121#Function
122###$
123#include "SkTextUtils.h"
124$$$#
125##
126
127void draw(SkCanvas* canvas) {
128    canvas->scale(1.25f, 1.25f);
129    SkPaint paint;
130    paint.setAntiAlias(true);
131    SkFont font(nullptr, 10);
132    SkTextUtils::DrawString(canvas, "32-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
133    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
134    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
135        SkPaint p(paint);
136        p.setColor(SK_ColorRED);
137        SkScalar xPos = 15;
138        int width = n % 32 + 1;
139        int lastN = n > 32 ? 32 : 0;
140        for (; n >= lastN; --n) {
141            for (int i = 0; i <= count; ++i) {
142                int a = width - e[i];
143                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
144                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
145                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
146                    break;
147                }
148            }
149            xPos += 20;
150        }
151        p.setColor(SK_ColorBLACK);
152        for (int i = 0; i < count; ++i) {
153            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
154        }
155        p.setStyle(SkPaint::kStroke_Style);
156        for (int i = 0; i <= count; ++i) {
157            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
158        }
159        for (int i = 0; i < 2; ++i) {
160            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
161        }
162    };
163    SkScalar edges[] = { 0, 8, 16, 24, 32 };
164    const char* labels[] = { "alpha", "blue", "green", "red" };
165    drawBoxText(edges, &labels[0], 4, 31, 45);
166    drawBoxText(edges, &labels[3], 1, 7, 110);
167    drawBoxText(edges, &labels[2], 1, 7, 160);
168    drawBoxText(edges, &labels[1], 1, 7, 210);
169    drawBoxText(edges, &labels[0], 1, 7, 260);
170}
171##
172##
173
174#Subtopic Image_Info_Color_Type_RGB_888
175#Example
176#Width 812
177#Height 365
178#Function
179###$
180#include "SkTextUtils.h"
181$$$#
182##
183
184void draw(SkCanvas* canvas) {
185    canvas->scale(1.25f, 1.25f);
186    SkPaint paint;
187    paint.setAntiAlias(true);
188    SkFont font(nullptr, 10);
189    SkTextUtils::DrawString(canvas, "32-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
190    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
191    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
192        SkPaint p(paint);
193        p.setColor(SK_ColorRED);
194        SkScalar xPos = 15;
195        int width = n % 32 + 1;
196        int lastN = n > 32 ? 32 : 0;
197        for (; n >= lastN; --n) {
198            for (int i = 0; i <= count; ++i) {
199                int a = width - e[i];
200                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
201                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
202                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
203                    break;
204                }
205            }
206            xPos += 20;
207        }
208        p.setColor(SK_ColorBLACK);
209        for (int i = 0; i < count; ++i) {
210            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
211        }
212        p.setStyle(SkPaint::kStroke_Style);
213        for (int i = 0; i <= count; ++i) {
214            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
215        }
216        for (int i = 0; i < 2; ++i) {
217            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
218        }
219    };
220    SkScalar edges[] = { 0, 8, 16, 24, 32 };
221    const char* labels[] = { "(unused)", "blue", "green", "red" };
222    drawBoxText(edges, &labels[0], 4, 31, 45);
223    drawBoxText(edges, &labels[3], 1, 7, 110);
224    drawBoxText(edges, &labels[2], 1, 7, 160);
225    drawBoxText(edges, &labels[1], 1, 7, 210);
226    drawBoxText(edges, &labels[0], 1, 7, 260);
227}
228##
229##
230
231#Subtopic Image_Info_Color_Type_BGRA_8888
232#Example
233#Width 812
234#Height 365
235#Function
236###$
237#include "SkTextUtils.h"
238$$$#
239##
240
241void draw(SkCanvas* canvas) {
242    canvas->scale(1.25f, 1.25f);
243    SkPaint paint;
244    paint.setAntiAlias(true);
245    SkFont font(nullptr, 10);
246    SkTextUtils::DrawString(canvas, "32-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
247    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
248    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
249        SkPaint p(paint);
250        p.setColor(SK_ColorRED);
251        SkScalar xPos = 15;
252        int width = n % 32 + 1;
253        int lastN = n > 32 ? 32 : 0;
254        for (; n >= lastN; --n) {
255            for (int i = 0; i <= count; ++i) {
256                int a = width - e[i];
257                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
258                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
259                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
260                    break;
261                }
262            }
263            xPos += 20;
264        }
265        p.setColor(SK_ColorBLACK);
266        for (int i = 0; i < count; ++i) {
267            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
268        }
269        p.setStyle(SkPaint::kStroke_Style);
270        for (int i = 0; i <= count; ++i) {
271            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
272        }
273        for (int i = 0; i < 2; ++i) {
274            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
275        }
276    };
277    SkScalar edges[] = { 0, 8, 16, 24, 32 };
278    const char* labels[] = { "alpha", "red", "green", "blue" };
279    drawBoxText(edges, &labels[0], 4, 31, 45);
280    drawBoxText(edges, &labels[3], 1, 7, 110);
281    drawBoxText(edges, &labels[2], 1, 7, 160);
282    drawBoxText(edges, &labels[1], 1, 7, 210);
283    drawBoxText(edges, &labels[0], 1, 7, 260);
284}
285##
286##
287
288#Subtopic Image_Info_Color_Type_RGBA_1010102
289#Example
290#Width 812
291#Height 380
292#Function
293###$
294#include "SkTextUtils.h"
295$$$#
296##
297
298void draw(SkCanvas* canvas) {
299    canvas->scale(1.25f, 1.25f);
300    SkPaint paint;
301    paint.setAntiAlias(true);
302    SkFont font(nullptr, 10);
303    SkTextUtils::DrawString(canvas, "32-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
304    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
305    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 4, 137, font, paint, SkTextUtils::kCenter_Align);
306    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 3, 187, font, paint, SkTextUtils::kCenter_Align);
307    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 7, 187, font, paint, SkTextUtils::kCenter_Align);
308    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 2, 237, font, paint, SkTextUtils::kCenter_Align);
309    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 6, 237, font, paint, SkTextUtils::kCenter_Align);
310    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 5, 287, font, paint, SkTextUtils::kCenter_Align);
311    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
312        SkPaint p(paint);
313        p.setColor(SK_ColorRED);
314        SkScalar xPos = 15;
315        int width = n % 32 + 1;
316        int lastN = n > 32 ? 32 : 0;
317        for (; n >= lastN; --n) {
318            for (int i = 0; i <= count; ++i) {
319                int a = width - e[i];
320                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
321                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
322                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
323                    break;
324                }
325            }
326            xPos += 20;
327        }
328        p.setColor(SK_ColorBLACK);
329        for (int i = 0; i < count; ++i) {
330            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
331        }
332        p.setStyle(SkPaint::kStroke_Style);
333        for (int i = 0; i <= count; ++i) {
334            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
335        }
336        for (int i = 0; i < 2; ++i) {
337            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
338        }
339    };
340    SkScalar edges[] = { 0, 2, 12, 22, 32,
341                         0, 8,
342                         0, 6, 8,
343                         0, 4, 8,
344                         0, 2, 8
345                        };
346    const char* labels[] = { "alpha", "blue", "green", "red" };
347    drawBoxText(&edges[0], &labels[0], 4, 31, 45);
348    drawBoxText(&edges[5], &labels[3], 1, 7, 110);
349    drawBoxText(&edges[7], &labels[2], 2, 7, 160);
350    drawBoxText(&edges[10], &labels[1], 2, 7, 210);
351    drawBoxText(&edges[13], &labels[0], 2, 7, 260);
352}
353##
354##
355
356#Subtopic Image_Info_Color_Type_RGB_101010
357#Example
358#Width 812
359#Height 380
360#Function
361###$
362#include "SkTextUtils.h"
363$$$#
364##
365
366void draw(SkCanvas* canvas) {
367    canvas->scale(1.25f, 1.25f);
368    SkPaint paint;
369    paint.setAntiAlias(true);
370    SkFont font(nullptr, 10);
371    SkTextUtils::DrawString(canvas, "32-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
372    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 85, font, paint, SkTextUtils::kCenter_Align);
373    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 4, 137, font, paint, SkTextUtils::kCenter_Align);
374    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 3, 187, font, paint, SkTextUtils::kCenter_Align);
375    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 7, 187, font, paint, SkTextUtils::kCenter_Align);
376    SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 2, 237, font, paint, SkTextUtils::kCenter_Align);
377    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 6, 237, font, paint, SkTextUtils::kCenter_Align);
378    SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 5, 287, font, paint, SkTextUtils::kCenter_Align);
379    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
380        SkPaint p(paint);
381        p.setColor(SK_ColorRED);
382        SkScalar xPos = 15;
383        int width = n % 32 + 1;
384        int lastN = n > 32 ? 32 : 0;
385        for (; n >= lastN; --n) {
386            for (int i = 0; i <= count; ++i) {
387                int a = width - e[i];
388                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
389                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
390                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
391                    break;
392                }
393            }
394            xPos += 20;
395        }
396        p.setColor(SK_ColorBLACK);
397        for (int i = 0; i < count; ++i) {
398            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
399        }
400        p.setStyle(SkPaint::kStroke_Style);
401        for (int i = 0; i <= count; ++i) {
402            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
403        }
404        for (int i = 0; i < 2; ++i) {
405            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
406        }
407    };
408    SkScalar edges[] = { 0, 2, 12, 22, 32,
409                         0, 8,
410                         0, 6, 8,
411                         0, 4, 8,
412                         0, 2, 8
413                        };
414    const char* labels[] = { "unused", "blue", "green", "red" };
415    drawBoxText(&edges[0], &labels[0], 4, 31, 45);
416    drawBoxText(&edges[5], &labels[3], 1, 7, 110);
417    drawBoxText(&edges[7], &labels[2], 2, 7, 160);
418    drawBoxText(&edges[10], &labels[1], 2, 7, 210);
419    drawBoxText(&edges[13], &labels[0], 2, 7, 260);
420}
421##
422##
423
424#Subtopic Image_Info_Color_Type_RGBA_F16
425#Example
426#Width 812
427#Height 685
428#Function
429###$
430#include "SkTextUtils.h"
431$$$#
432##
433
434void draw(SkCanvas* canvas) {
435    canvas->scale(1.25f, 1.25f);
436    SkPaint paint;
437    paint.setAntiAlias(true);
438    SkFont font(nullptr, 10);
439    SkTextUtils::DrawString(canvas, "64-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
440    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 135, font, paint, SkTextUtils::kCenter_Align);
441    for (int i = 0; i < 4; ++i) {
442        SkTextUtils::DrawString(canvas, "(low bits)", 5 + 20 * 4, 187 + i * 100, font, paint, SkTextUtils::kCenter_Align);
443        SkTextUtils::DrawString(canvas, "(high bits)", 5 + 20 * 4, 237 + i * 100, font, paint, SkTextUtils::kCenter_Align);
444    }
445    auto drawBoxText = [=](SkScalar e[], const char* s[], int count, int n, SkScalar yPos) -> void {
446        SkPaint p(paint);
447        p.setColor(SK_ColorRED);
448        SkScalar xPos = 15;
449        int width = n % 32 + 1;
450        int lastN = n > 32 ? 32 : 0;
451        for (; n >= lastN; --n) {
452            for (int i = 0; i <= count; ++i) {
453                int a = width - e[i];
454                if (a == n || a == n + 1 || a == n - 32 || a == n - 31) {
455                    char num[3] = {(char) ('0' + n / 10), (char) ('0' + n % 10), '\0'};
456                    SkTextUtils::DrawString(canvas, n >= 10 ? num : &num[1], xPos, yPos - 5, font, p, SkTextUtils::kCenter_Align);
457                    break;
458                }
459            }
460            xPos += 20;
461        }
462        p.setColor(SK_ColorBLACK);
463        for (int i = 0; i < count; ++i) {
464            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 10, yPos + 10, font, p, SkTextUtils::kCenter_Align);
465        }
466        p.setStyle(SkPaint::kStroke_Style);
467        for (int i = 0; i <= count; ++i) {
468            canvas->drawLine(5 + e[i] * 20, yPos, 5 + e[i] * 20, yPos + 15, p);
469        }
470        for (int i = 0; i < 2; ++i) {
471            canvas->drawLine(5 + e[0] * 20, yPos + i * 15, 5 + e[count] * 20, yPos + i * 15, p);
472        }
473    };
474    SkScalar edges[] = { 0, 16, 32,
475                         0, 8
476                       };
477    const char* labels[] = { "alpha", "blue", "green", "red" };
478    drawBoxText(&edges[0], &labels[0], 2, 63, 45);
479    drawBoxText(&edges[0], &labels[2], 2, 31, 95);
480    drawBoxText(&edges[3], &labels[3], 1, 7, 160);
481    drawBoxText(&edges[3], &labels[3], 1, 7, 210);
482    drawBoxText(&edges[3], &labels[2], 1, 7, 260);
483    drawBoxText(&edges[3], &labels[2], 1, 7, 310);
484    drawBoxText(&edges[3], &labels[1], 1, 7, 360);
485    drawBoxText(&edges[3], &labels[1], 1, 7, 410);
486    drawBoxText(&edges[3], &labels[0], 1, 7, 460);
487    drawBoxText(&edges[3], &labels[0], 1, 7, 510);
488}
489##
490##
491
492#Subtopic Image_Info_Color_Type_RGBA_F32
493#Example
494#Width 812
495#Height 685
496#Function
497###$
498#include "SkTextUtils.h"
499$$$#
500##
501
502void draw(SkCanvas* canvas) {
503    canvas->scale(1.25f, 1.25f);
504    SkPaint paint;
505    paint.setAntiAlias(true);
506    SkFont font(nullptr, 10);
507    SkTextUtils::DrawString(canvas, "128-bit word", 5 + 20 * 16, 20, font, paint, SkTextUtils::kCenter_Align);
508    SkTextUtils::DrawString(canvas, "little endian byte order", 5 + 20 * 4, 135, font, paint, SkTextUtils::kCenter_Align);
509    for (int i = 0; i < 4; ++i) {
510        SkTextUtils::DrawString(canvas, "(low bits)", 5 + 10 * 4, 187 + i * 100, font, paint, SkTextUtils::kCenter_Align);
511        SkTextUtils::DrawString(canvas, "(high bits)", 105 + 10 * 4, 237 + i * 100, font, paint, SkTextUtils::kCenter_Align);
512    }
513    auto drawBoxText = [=](SkScalar e[], const char* s[], const char* nums[] ,
514             int count, int n, SkScalar yPos) -> void {
515        SkPaint p(paint);
516        p.setColor(SK_ColorRED);
517        SkScalar xPos = 15;
518        int stringIndex = 0;
519        for (int i = n; i >= 0; --i) {
520            if (0 == i || n == i || 32 == i || 31 == i) {
521                int x = xPos;
522                if (2 == count) {
523                    x += stringIndex * 12 + (stringIndex ? 8 : 0);
524                }
525                SkTextUtils::DrawString(canvas, nums[stringIndex], x, yPos - 5, font, p, SkTextUtils::kCenter_Align);
526                if (1 == count) {
527                    SkTextUtils::DrawString(canvas, nums[stringIndex], xPos + 100, yPos - 5, font, p, SkTextUtils::kCenter_Align);
528                }
529                ++stringIndex;
530            }
531            xPos += 9;
532        }
533        p.setColor(SK_ColorBLACK);
534        for (int i = 0; i < count; ++i) {
535            SkTextUtils::DrawString(canvas, s[i], 5 + (e[i] + e[i + 1]) * 5, yPos + 10, font, p, SkTextUtils::kCenter_Align);
536            if (1 == count) {
537                SkTextUtils::DrawString(canvas, s[i], 105 + (e[i] + e[i + 1]) * 5, yPos + 10, font, p, SkTextUtils::kCenter_Align);
538            }
539        }
540        p.setStyle(SkPaint::kStroke_Style);
541        for (int i = 0; i <= count; ++i) {
542            canvas->drawLine(5 + e[i] * 10, yPos, 5 + e[i] * 10, yPos + 15, p);
543            if (1 == count) {
544                canvas->drawLine(105 + e[i] * 10, yPos, 105 + e[i] * 10, yPos + 15, p);
545            }
546        }
547        for (int i = 0; i < 2; ++i) {
548            canvas->drawLine(5 + e[0] * 10, yPos + i * 15,
549                             5 + e[count] * 10, yPos + i * 15, p);
550            if (1 == count) {
551                canvas->drawLine(105 + e[0] * 10, yPos + i * 15,
552                                 105 + e[count] * 10, yPos + i * 15, p);
553            }
554        }
555    };
556    SkScalar edges[] = { 0, 32, 64,
557                         0, 8
558                       };
559    const char* labels[] = { "alpha", "blue", "green", "red" };
560    const char* nums128[] = { "127", "96", "95", "64"};
561    const char* nums64[] = { "63", "32", "31", "0"};
562    const char* nums8[] = { "7", "0"};
563    drawBoxText(&edges[0], &labels[0], nums128, 2, 63, 45);
564    drawBoxText(&edges[0], &labels[2], nums64, 2, 63, 95);
565    drawBoxText(&edges[3], &labels[3], nums8, 1, 7, 160);
566    drawBoxText(&edges[3], &labels[3], nums8, 1, 7, 210);
567    drawBoxText(&edges[3], &labels[2], nums8, 1, 7, 260);
568    drawBoxText(&edges[3], &labels[2], nums8, 1, 7, 310);
569    drawBoxText(&edges[3], &labels[1], nums8, 1, 7, 360);
570    drawBoxText(&edges[3], &labels[1], nums8, 1, 7, 410);
571    drawBoxText(&edges[3], &labels[0], nums8, 1, 7, 460);
572    drawBoxText(&edges[3], &labels[0], nums8, 1, 7, 510);
573}
574##
575##
576
577#Subtopic Blend_Mode_Overview_Porter_Duff
578#Example
579#Width 480
580#Height 330
581#Function
582###$
583#include "SkTextUtils.h"
584$$$#
585##
586
587void draw(SkCanvas* canvas) {
588    SkPaint srcPaint;
589    srcPaint.setAntiAlias(true);
590    SkPaint labelPaint = srcPaint;
591    SkFont labelFont(nullptr, 16);
592    SkPaint dstPaint = srcPaint;
593    dstPaint.setColor(0xFF606080);
594    SkFont dstFont(SkTypeface::MakeFromName("Roboto", SkFontStyle::Bold()), 80);
595
596    SkBitmap srcBits;
597    srcBits.allocN32Pixels(80, 84);
598    SkCanvas srcCanvas(srcBits);
599    srcPaint.setColor(0xFFcc6633);
600    SkPath srcPath;
601    const SkPoint points[] = {{20, 20}, {80, 45}, {45, 80}};
602    srcPath.addPoly(points, SK_ARRAY_COUNT(points), true);
603    srcBits.eraseColor(0);
604    srcCanvas.drawPath(srcPath, srcPaint);
605
606    canvas->drawColor(0, SkBlendMode::kClear);
607    for (auto blend : { SkBlendMode::kSrc, SkBlendMode::kSrcATop, SkBlendMode::kSrcOver,
608                        SkBlendMode::kSrcIn, SkBlendMode::kSrcOut,
609                        SkBlendMode::kDst, SkBlendMode::kDstATop, SkBlendMode::kDstOver,
610                        SkBlendMode::kDstIn, SkBlendMode::kDstOut,
611                        SkBlendMode::kClear, SkBlendMode::kXor } ) {
612        SkTextUtils::DrawString(canvas, "&", 50, 80, dstFont, dstPaint, SkTextUtils::kCenter_Align);
613        srcPaint.setBlendMode(blend);
614        canvas->drawBitmap(srcBits, 0, 0, &srcPaint);
615        SkTextUtils::DrawString(canvas, SkBlendMode_Name(blend), 50, 100, labelFont, labelPaint, SkTextUtils::kCenter_Align);
616        canvas->translate(80, 0);
617        if (SkBlendMode::kSrcOut == blend || SkBlendMode::kDstOut == blend) {
618            canvas->translate(-80 * 5, 100);
619        }
620    }
621}
622##
623##
624
625#Subtopic Blend_Mode_Overview_Porter_Duff_2
626#Example
627#Width 480
628#Height 330
629#Function
630###$
631#include "SkTextUtils.h"
632$$$#
633##
634
635void draw(SkCanvas* canvas) {
636    SkPaint srcPaint;
637    srcPaint.setAntiAlias(true);
638    SkPaint labelPaint = srcPaint;
639    SkFont labelFont(nullptr, 16);
640    SkPaint dstPaint = srcPaint;
641    dstPaint.setColor(0xFF606080);
642    SkFont dstFont(SkTypeface::MakeFromName("Roboto", SkFontStyle::Bold()), 80);
643
644    srcPaint.setColor(0xFFcc6633);
645    SkPath srcPath;
646    const SkPoint points[] = {{20, 20}, {80, 45}, {45, 80}};
647    srcPath.addPoly(points, SK_ARRAY_COUNT(points), true);
648    canvas->drawColor(0, SkBlendMode::kClear);
649
650    SkBitmap dstBits;
651    dstBits.allocN32Pixels(80, 80);
652    SkCanvas dstCanvas(dstBits);
653    for (auto blend : { SkBlendMode::kSrc, SkBlendMode::kSrcATop, SkBlendMode::kSrcOver,
654                        SkBlendMode::kSrcIn, SkBlendMode::kSrcOut,
655                        SkBlendMode::kDst, SkBlendMode::kDstATop, SkBlendMode::kDstOver,
656                        SkBlendMode::kDstIn, SkBlendMode::kDstOut,
657                        SkBlendMode::kClear, SkBlendMode::kXor } ) {
658        SkTextUtils::DrawString(canvas, "&", 50, 80, dstFont, dstPaint, SkTextUtils::kCenter_Align);
659        srcPaint.setBlendMode(blend);
660        canvas->drawPath(srcPath, srcPaint);
661        SkTextUtils::DrawString(canvas, SkBlendMode_Name(blend), 50, 100, labelFont, labelPaint, SkTextUtils::kCenter_Align);
662        canvas->translate(80, 0);
663        if (SkBlendMode::kSrcOut == blend || SkBlendMode::kDstOut == blend) {
664            canvas->translate(-80 * 5, 100);
665        }
666    }
667}
668##
669##
670
671#Subtopic Blend_Mode_Overview_Lighten_Darken
672#Example
673#Width 480
674#Height 330
675#Function
676###$
677#include "SkTextUtils.h"
678$$$#
679##
680
681void draw(SkCanvas* canvas) {
682    SkPaint srcPaint;
683    srcPaint.setAntiAlias(true);
684    SkPaint labelPaint = srcPaint;
685    SkFont labelFont(nullptr, 16);
686    SkPaint dstPaint = srcPaint;
687    dstPaint.setColor(0xFF606080);
688    SkFont dstFont(SkTypeface::MakeFromName("Roboto", SkFontStyle::Bold()), 80);
689
690    srcPaint.setColor(0xFFcc6633);
691    SkPath srcPath;
692    const SkPoint points[] = {{20, 20}, {80, 45}, {45, 80}};
693    srcPath.addPoly(points, SK_ARRAY_COUNT(points), true);
694    canvas->drawColor(0, SkBlendMode::kClear);
695    for (auto blend : { SkBlendMode::kPlus, SkBlendMode::kScreen, SkBlendMode::kOverlay,
696            SkBlendMode::kDarken, SkBlendMode::kLighten, SkBlendMode::kColorDodge,
697            SkBlendMode::kColorBurn, SkBlendMode::kHardLight, SkBlendMode::kSoftLight,
698            SkBlendMode::kDifference, SkBlendMode::kExclusion, SkBlendMode::kMultiply } ) {
699        SkTextUtils::DrawString(canvas, "&", 50, 80, dstFont, dstPaint, SkTextUtils::kCenter_Align);
700        srcPaint.setBlendMode(blend);
701        canvas->drawPath(srcPath, srcPaint);
702        SkTextUtils::DrawString(canvas, SkBlendMode_Name(blend), 50, 100, labelFont, labelPaint,
703                SkTextUtils::kCenter_Align);
704        canvas->translate(90, 0);
705        if (SkBlendMode::kLighten == blend || SkBlendMode::kDifference == blend) {
706            canvas->translate(-90 * 5, 100);
707        }
708    }
709}
710##
711##
712
713#Subtopic Blend_Mode_Overview_Color_Blends
714#Example
715#Width 480
716#Height 110
717#Function
718###$
719#include "SkTextUtils.h"
720$$$#
721##
722
723void draw(SkCanvas* canvas) {
724    SkPaint srcPaint;
725    srcPaint.setAntiAlias(true);
726    SkPaint labelPaint = srcPaint;
727    SkFont labelFont(nullptr, 16);
728    SkPaint dstPaint = labelPaint;
729    dstPaint.setColor(0xFF606080);
730    SkFont dstFont(SkTypeface::MakeFromName("Roboto", SkFontStyle::Bold()), 80);
731
732    srcPaint.setColor(0xFFcc6633);
733    SkPath srcPath;
734    const SkPoint points[] = {{20, 20}, {80, 45}, {45, 80}};
735    srcPath.addPoly(points, SK_ARRAY_COUNT(points), true);
736    canvas->drawColor(0, SkBlendMode::kClear);
737    for (auto blend : { SkBlendMode::kHue, SkBlendMode::kSaturation, SkBlendMode::kColor,
738                        SkBlendMode::kLuminosity } ) {
739        SkTextUtils::DrawString(canvas, "&", 50, 80, dstFont, dstPaint, SkTextUtils::kCenter_Align);
740        srcPaint.setBlendMode(blend);
741        canvas->drawPath(srcPath, srcPaint);
742        SkTextUtils::DrawString(canvas, SkBlendMode_Name(blend), 50, 100, labelFont, labelPaint,
743                SkTextUtils::kCenter_Align);
744        canvas->translate(90, 0);
745    }
746}
747##
748##
749
750#Subtopic Blend_Mode_Overview_Modulate_Blend
751#Example
752#Width 480
753#Height 110
754#Function
755###$
756#include "SkTextUtils.h"
757$$$#
758##
759
760void draw(SkCanvas* canvas) {
761    SkPaint srcPaint;
762    srcPaint.setAntiAlias(true);
763    SkPaint labelPaint = srcPaint;
764    SkFont labelFont(nullptr, 16);
765    SkPaint dstPaint = srcPaint;
766    dstPaint.setColor(0xFF606080);
767    SkFont dstFont(SkTypeface::MakeFromName("Roboto", SkFontStyle::Bold()), 80);
768
769    SkBitmap srcBits;
770    srcBits.allocN32Pixels(80, 84);
771    SkCanvas srcCanvas(srcBits);
772    srcPaint.setColor(0xFFcc6633);
773    SkPath srcPath;
774    const SkPoint points[] = {{20, 20}, {80, 45}, {45, 80}};
775    srcPath.addPoly(points, SK_ARRAY_COUNT(points), true);
776    srcBits.eraseColor(0);
777    srcCanvas.drawPath(srcPath, srcPaint);
778
779    canvas->drawColor(0, SkBlendMode::kClear);
780    srcPaint.setBlendMode(SkBlendMode::kModulate);
781    for (auto step: { 1, 2 } ) {
782        SkTextUtils::DrawString(canvas, "&", 50, 80, dstFont, dstPaint, SkTextUtils::kCenter_Align);
783        if (1 == step) {
784            canvas->drawBitmap(srcBits, 0, 0, &srcPaint);
785            SkTextUtils::DrawString(canvas, "Bitmap", 50, 18, labelFont, labelPaint, SkTextUtils::kCenter_Align);
786        } else {
787            canvas->drawPath(srcPath, srcPaint);
788            SkTextUtils::DrawString(canvas, "Geometry", 50, 18, labelFont, labelPaint, SkTextUtils::kCenter_Align);
789        }
790        SkTextUtils::DrawString(canvas, SkBlendMode_Name(SkBlendMode::kModulate), 50, 100, labelFont, labelPaint,
791                SkTextUtils::kCenter_Align);
792        canvas->translate(120, 0);
793    }
794}
795##
796##
797
798#Subtopic Path_Arc
799#Example
800#Height 300
801#Width 600
802#Function
803###$
804
805struct data {
806   const char* name;
807   char super;
808   int yn[10];
809};
810
811const data dataSet[] = {
812{ "arcTo sweep",    '1', {1,  3, 1, 0, 0, 0, 0, 1, 0, 0 }},
813{ "drawArc",         0,  {1, -1, 1, 1, 1, 1, 1, 0, 0, 0 }},
814{ "addArc",          0,  {1,  1, 1, 4, 0, 1, 1, 1, 0, 0 }},
815{ "arcTo tangents", '4', {0,  0, 0, 0, 0, 0, 0, 1, 1, 0 }},
816{ "arcTo radii",    '5', {1,  0, 1, 0, 0, 0, 0, 1, 1, 0 }},
817{ "conicTo",         0,  {1,  1, 0, 0, 0, 0, 0, 1, 1, 1 }}
818};
819
820#define __degree_symbol__ "\xC2" "\xB0"
821
822const char* headers[] = {
823    "Oval part",
824    "force moveTo",
825    "can draw 180" __degree_symbol__,
826    "can draw 360" __degree_symbol__,
827    "can draw greater than 360" __degree_symbol__,
828    "ignored if radius is zero",
829    "ignored if sweep is zero",
830    "requires Path",
831    "describes rotation",
832    "describes perspective",
833};
834
835const char* yna[] = {
836     "n/a",
837     "no",
838     "yes"
839};
840$$$#
841##
842void draw(SkCanvas* canvas) {
843    SkPaint lp;
844    lp.setAntiAlias(true);
845    SkPaint tp(lp);
846    SkPaint sp(tp);
847    SkFont bf;
848    bf.setEmbolden(true);
849    SkFont sf(nullptr, 10);
850    lp.setColor(SK_ColorGRAY);
851    canvas->translate(0, 32);
852    const int tl = 115;
853    for (unsigned col = 0; col <= SK_ARRAY_COUNT(headers); ++col) {
854       canvas->drawLine(tl + col * 35, 100, tl + col * 35, 250, lp);
855       if (0 == col) {
856          continue;
857       }
858       canvas->drawLine( tl +        col * 35, 100,  tl + 100  + col * 35,   0, lp);
859       SkPoint pts[] = {{tl - 10.f + col * 35, 98}, {tl + 90.f + col * 35,  -2}};
860       SkVector v = pts[1] - pts[0];
861       v.normalize();
862       SkMatrix matrix;
863       matrix.setSinCos(v.fY, v.fX, pts[0].fX, pts[0].fY);
864       canvas->save();
865       canvas->concat(matrix);
866       canvas->drawSimpleText(headers[col -1], strlen(headers[col -1]), SkTextEncoding::kUTF8,
867            pts[0].fX, pts[0].fY, bf, lp);
868       canvas->restore();
869    }
870    for (unsigned row = 0; row <= SK_ARRAY_COUNT(dataSet); ++row) {
871        if (0 == row) {
872            canvas->drawLine(tl, 100, tl + 350, 100, lp);
873        } else {
874            canvas->drawLine(5, 100 + row * 25, tl + 350, 100 + row * 25, lp);
875        }
876        if (row == SK_ARRAY_COUNT(dataSet)) {
877            break;
878        }
879        canvas->drawSimpleText(dataSet[row].name, strlen(dataSet[row].name),
880              SkTextEncoding::kUTF8, 5, 117 + row * 25, bf, lp);
881        if (dataSet[row].super) {
882            SkScalar width = bf.measureText(dataSet[row].name, strlen(dataSet[row].name),
883                    SkTextEncoding::kUTF8);
884            canvas->drawSimpleText(&dataSet[row].super, 1, SkTextEncoding::kUTF8,
885                    8 + width, 112 + row * 25, sf, lp);
886        }
887        for (unsigned col = 0; col < SK_ARRAY_COUNT(headers); ++col) {
888            int val = dataSet[row].yn[col];
889            canvas->drawString(yna[SkTMin(2, val + 1)], tl + 5 + col * 35, 117 + row * 25, tp);
890            if (val > 1) {
891                char supe = '0' + val - 1;
892                canvas->drawSimpleText(&supe, 1, SkTextEncoding::kUTF8,
893                     tl + 25 + col * 35, 112 + row * 25, sf, lp);
894            }
895        }
896    }
897}
898#Example ##
899##
900
901#Topic Illustrations ##
902