1#Topic Bitmap
2#Alias Bitmaps
3#Alias Bitmap_Reference
4
5#Subtopic Overview
6    #Subtopic Subtopics
7    #Populate
8    ##
9##
10
11#Class SkBitmap
12
13Bitmap describes a two-dimensional raster pixel array. Bitmap is built on
14Image_Info, containing integer width and height, Color_Type and Alpha_Type
15describing the pixel format, and Color_Space describing the range of colors.
16Bitmap points to Pixel_Ref, which describes the physical array of pixels.
17Image_Info bounds may be located anywhere fully inside Pixel_Ref bounds.
18
19Bitmap can be drawn using Canvas. Bitmap can be a drawing destination for Canvas
20draw methods. Bitmap flexibility as a pixel container limits some optimizations
21available to the target platform.
22
23If pixel array is primarily read-only, use Image for better performance.
24If pixel array is primarily written to, use Surface for better performance.
25
26Declaring SkBitmap const prevents altering Image_Info: the Bitmap height, width,
27and so on cannot change. It does not affect Pixel_Ref: a caller may write its
28pixels. Declaring SkBitmap const affects Bitmap configuration, not its contents.
29
30Bitmap is not thread safe. Each thread must have its own copy of Bitmap fields,
31although threads may share the underlying pixel array.
32
33#Subtopic Row_Bytes
34#Line # interval from one row to the next ##
35Bitmap pixels may be contiguous, or may have a gap at the end of each row.
36Row_Bytes is the interval from one row to the next. Row_Bytes may be specified;
37sometimes passing zero will compute the Row_Bytes from the row width and the
38number of bytes in a pixel. Row_Bytes may be larger than the row requires. This
39is useful to position one or more Bitmaps within a shared pixel array.
40##
41
42#Subtopic Related_Functions
43#Populate
44##
45
46#Subtopic Classes_and_Structs
47#Populate
48##
49
50#Subtopic Constructors
51#Populate
52##
53
54#Subtopic Operators
55#Populate
56##
57
58#Subtopic Member_Functions
59#Populate
60##
61
62# ------------------------------------------------------------------------------
63
64#Class Allocator
65#Line # abstract subclass of HeapAllocator ##
66#Code
67    class Allocator : public SkRefCnt {
68    public:
69        virtual bool allocPixelRef(SkBitmap* bitmap) = 0;
70    };
71##
72
73Abstract subclass of HeapAllocator.
74
75# ------------------------------------------------------------------------------
76
77#Method virtual bool allocPixelRef(SkBitmap* bitmap) = 0
78
79Allocates the pixel memory for the bitmap, given its dimensions and
80Color_Type. Returns true on success, where success means either setPixels
81or setPixelRef was called.
82
83#Param bitmap  Bitmap containing Image_Info as input, and Pixel_Ref as output ##
84
85#Return  true if Pixel_Ref was allocated ##
86
87#NoExample
88##
89
90#SeeAlso HeapAllocator
91
92##
93
94#Class Allocator ##
95
96# ------------------------------------------------------------------------------
97
98#Class HeapAllocator
99#Line # allocates pixel memory from heap ##
100
101#Code
102    class HeapAllocator : public Allocator {
103    public:
104        bool allocPixelRef(SkBitmap* bitmap) override;
105    };
106##
107
108Subclass of Allocator that returns a Pixel_Ref that allocates its pixel
109memory from the heap. This is the default Allocator invoked by
110allocPixels.
111
112# ------------------------------------------------------------------------------
113
114#Method bool allocPixelRef(SkBitmap* bitmap) override
115
116Allocates the pixel memory for the bitmap, given its dimensions and
117Color_Type. Returns true on success, where success means either setPixels
118or setPixelRef was called.
119
120#Param bitmap  Bitmap containing Image_Info as input, and Pixel_Ref as output ##
121
122#Return  true if pixels are allocated ##
123
124#Example
125    SkBitmap bitmap;
126    bitmap.setInfo(SkImageInfo::MakeN32(16, 16, kPremul_SkAlphaType));
127    SkDebugf("pixel address = %p\n", bitmap.getPixels());
128    SkBitmap::HeapAllocator stdalloc;
129    if (!stdalloc.allocPixelRef(&bitmap)) {
130        SkDebugf("pixel allocation failed\n");
131    } else {
132        SkDebugf("pixel address = %p\n", bitmap.getPixels());
133    }
134#StdOut
135#Volatile
136pixel address = (nil)
137pixel address = 0x560ddd0ac670
138##
139##
140
141#SeeAlso Allocator tryAllocPixels
142
143##
144
145#Class HeapAllocator ##
146
147# ------------------------------------------------------------------------------
148
149#Method SkBitmap()
150
151#Line # constructs with default values ##
152Creates an empty Bitmap without pixels, with kUnknown_SkColorType,
153kUnknown_SkAlphaType, and with a width and height of zero. Pixel_Ref origin is
154set to (0, 0). Bitmap is not volatile.
155
156Use setInfo to associate SkColorType, SkAlphaType, width, and height
157after Bitmap has been created.
158
159#Return  empty Bitmap ##
160
161#Example
162void draw(SkCanvas* canvas) {
163    const char* alphas[] = {"Unknown", "Opaque", "Premul", "Unpremul"};
164    const char* colors[] = {"Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
165                            "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16"};
166    SkBitmap bitmap;
167    for (int i = 0; i < 2; ++i) {
168       SkDebugf("width: %2d  height: %2d", bitmap.width(), bitmap.height());
169       SkDebugf("  color: k%s_SkColorType", colors[bitmap.colorType()]);
170       SkDebugf("  alpha: k%s_SkAlphaType\n", alphas[bitmap.alphaType()]);
171       bitmap.setInfo(SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType),
172                      0);
173    }
174}
175#StdOut
176width:  0  height:  0  color: kUnknown_SkColorType  alpha: kUnknown_SkAlphaType
177width: 25  height: 35  color: kRGBA_8888_SkColorType  alpha: kOpaque_SkAlphaType
178##
179##
180
181#SeeAlso setInfo
182
183##
184
185# ------------------------------------------------------------------------------
186
187#Method SkBitmap(const SkBitmap& src)
188
189#Line # shares ownership of pixels ##
190Copies settings from src to returned Bitmap. Shares pixels if src has pixels
191allocated, so both bitmaps reference the same pixels.
192
193#Param src  Bitmap to copy Image_Info, and share Pixel_Ref ##
194
195#Return  copy of src ##
196
197#Example
198void draw(SkCanvas* canvas) {
199    SkBitmap original;
200    original.tryAllocPixels(SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
201    SkDebugf("original has pixels before copy: %s\n", original.getPixels() ? "true" : "false");
202    SkBitmap copy(original);
203    SkDebugf("original has pixels after copy: %s\n", original.getPixels() ? "true" : "false");
204    SkDebugf("copy has pixels: %s\n", copy.getPixels() ? "true" : "false");
205}
206#StdOut
207original has pixels before copy: true
208original has pixels after copy: true
209copy has pixels: true
210##
211##
212
213#SeeAlso setInfo setPixelRef setPixels swap
214
215##
216
217# ------------------------------------------------------------------------------
218
219#Method SkBitmap(SkBitmap&& src)
220
221#Line # takes ownership of pixels ##
222Copies settings from src to returned Bitmap. Moves ownership of src pixels to
223Bitmap.
224
225#Param src  Bitmap to copy Image_Info, and reassign Pixel_Ref ##
226
227#Return  copy of src ##
228
229#Example
230void draw(SkCanvas* canvas) {
231    SkBitmap original;
232    original.tryAllocPixels(SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
233    SkDebugf("original has pixels before move: %s\n", original.getPixels() ? "true" : "false");
234    SkBitmap copy(std::move(original));
235    SkDebugf("original has pixels after move: %s\n", original.getPixels() ? "true" : "false");
236    SkDebugf("copy has pixels: %s\n", copy.getPixels() ? "true" : "false");
237}
238#StdOut
239original has pixels before move: true
240original has pixels after move: false
241copy has pixels: true
242##
243##
244
245#SeeAlso setInfo setPixelRef setPixels swap
246
247##
248
249# ------------------------------------------------------------------------------
250
251#Method ~SkBitmap()
252
253#Line # releases ownership of pixels ##
254Decrements Pixel_Ref reference count, if Pixel_Ref is not nullptr.
255
256#NoExample
257##
258
259#SeeAlso Pixel_Ref
260
261##
262
263# ------------------------------------------------------------------------------
264
265#Method SkBitmap& operator=(const SkBitmap& src)
266
267#Line # shares ownership of pixels ##
268Copies settings from src to returned Bitmap. Shares pixels if src has pixels
269allocated, so both bitmaps reference the same pixels.
270
271#Param src  Bitmap to copy Image_Info, and share Pixel_Ref ##
272
273#Return  copy of src ##
274
275#Example
276void draw(SkCanvas* canvas) {
277    SkBitmap original;
278    original.tryAllocPixels(SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
279    SkDebugf("original has pixels before copy: %s\n", original.getPixels() ? "true" : "false");
280    SkBitmap copy = original;
281    SkDebugf("original has pixels after copy: %s\n", original.getPixels() ? "true" : "false");
282    SkDebugf("copy has pixels: %s\n", copy.getPixels() ? "true" : "false");
283}
284#StdOut
285original has pixels before copy: true
286original has pixels after copy: true
287copy has pixels: true
288##
289##
290
291#SeeAlso setInfo setPixelRef setPixels swap
292
293##
294
295# ------------------------------------------------------------------------------
296
297#Method SkBitmap& operator=(SkBitmap&& src)
298
299#Line # takes ownership of pixels ##
300Copies settings from src to returned Bitmap. Moves ownership of src pixels to
301Bitmap.
302
303#Param src  Bitmap to copy Image_Info, and reassign Pixel_Ref ##
304
305#Return  copy of src ##
306
307#Example
308void draw(SkCanvas* canvas) {
309    SkBitmap original;
310    original.tryAllocPixels(SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
311    SkDebugf("original has pixels before move: %s\n", original.getPixels() ? "true" : "false");
312    SkBitmap copy = std::move(original);
313    SkDebugf("original has pixels after move: %s\n", original.getPixels() ? "true" : "false");
314    SkDebugf("copy has pixels: %s\n", copy.getPixels() ? "true" : "false");
315}
316#StdOut
317original has pixels before move: true
318original has pixels after move: false
319copy has pixels: true
320##
321##
322
323#SeeAlso setInfo setPixelRef setPixels swap
324
325##
326
327# ------------------------------------------------------------------------------
328
329#Method void swap(SkBitmap& other)
330
331#Line # exchanges Bitmap pair ##
332Swaps the fields of the two bitmaps.
333
334#Param other  Bitmap exchanged with original ##
335
336#Example
337void draw(SkCanvas* canvas) {
338    auto debugster = [](const char* prefix, const SkBitmap& b) -> void {
339        const char* alphas[] = {"Unknown", "Opaque", "Premul", "Unpremul"};
340        const char* colors[] = {"Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
341                                "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16"};
342        SkDebugf("%s width:%d height:%d colorType:k%s_SkColorType alphaType:k%s_SkAlphaType\n",
343                 prefix, b.width(), b.height(), colors[b.colorType()], alphas[b.alphaType()]);
344    };
345    SkBitmap one, two;
346    one.tryAllocPixels(SkImageInfo::Make(1, 1, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
347    two.tryAllocPixels(SkImageInfo::Make(2, 2, kBGRA_8888_SkColorType, kPremul_SkAlphaType));
348    for (int index = 0; index < 2; ++index) {
349       debugster("one", one);
350       debugster("two", two);
351       one.swap(two);
352    }
353}
354#StdOut
355one width:1 height:1 colorType:kRGBA_8888_SkColorType alphaType:kOpaque_SkAlphaType
356two width:2 height:2 colorType:kBGRA_8888_SkColorType alphaType:kPremul_SkAlphaType
357one width:2 height:2 colorType:kBGRA_8888_SkColorType alphaType:kPremul_SkAlphaType
358two width:1 height:1 colorType:kRGBA_8888_SkColorType alphaType:kOpaque_SkAlphaType
359##
360##
361
362#SeeAlso SkBitmap(SkBitmap&& src) operator=(SkBitmap&& src)
363
364##
365
366# ------------------------------------------------------------------------------
367
368#Method const SkPixmap& pixmap() const
369
370#Line # returns Pixmap ##
371Returns a constant reference to the Pixmap holding the Bitmap pixel
372address, row bytes, and Image_Info.
373
374#Return reference to Pixmap describing this Bitmap ##
375
376#Example
377    SkBitmap bitmap;
378    bitmap.allocPixels(SkImageInfo::MakeN32Premul(10, 11));
379    SkCanvas offscreen(bitmap);
380    offscreen.clear(SK_ColorWHITE);
381    SkPaint paint;
382    offscreen.drawString("&", 0, 10, paint);
383    const SkPixmap& pixmap = bitmap.pixmap();
384    if (pixmap.addr()) {
385        SkPMColor pmWhite = *pixmap.addr32(0, 0);
386        for (int y = 0; y < pixmap.height(); ++y) {
387            for (int x = 0; x < pixmap.width(); ++x) {
388                SkDebugf("%c", *pixmap.addr32(x, y) == pmWhite ? '-' : 'x');
389            }
390            SkDebugf("\n");
391        }
392    }
393    #StdOut
394----------
395---xx-----
396--x--x----
397--x-------
398--xx------
399--x-x---x-
400-x---x--x-
401-x----xx--
402-xx---x---
403--xxxx-xx-
404----------
405    #StdOut ##
406
407##
408
409#SeeAlso peekPixels installPixels readPixels writePixels
410
411##
412
413# ------------------------------------------------------------------------------
414
415#Method const SkImageInfo& info() const
416
417#Line # returns Image_Info ##
418Returns width, height, Alpha_Type, Color_Type, and Color_Space.
419
420#Return reference to Image_Info  ##
421
422#Example
423#Image 4
424void draw(SkCanvas* canvas) {
425    // SkBitmap source;  // pre-populated with soccer ball by fiddle.skia.org
426    const SkImageInfo& info = source.info();
427    const char* alphas[] = {"Unknown", "Opaque", "Premul", "Unpremul"};
428    const char* colors[] = {"Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
429                            "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16"};
430    SkDebugf("width: %d height: %d color: %s alpha: %s\n", info.width(), info.height(),
431                colors[info.colorType()], alphas[info.alphaType()]);
432#StdOut
433width: 56 height: 56 color: BGRA_8888 alpha: Opaque
434##
435}
436##
437
438#SeeAlso Image_Info
439
440##
441
442# ------------------------------------------------------------------------------
443
444#Method int width() const
445
446#Line # returns pixel column count ##
447Returns pixel count in each row. Should be equal or less than:
448
449#Formula
450rowBytes() / info().bytesPerPixel()
451##
452.
453
454Maybe be less than pixelRef().width(). Will not exceed pixelRef().width() less
455pixelRefOrigin().fX.
456
457#Return  pixel width in Image_Info ##
458
459#Example
460    SkImageInfo info = SkImageInfo::MakeA8(16, 32);
461    SkBitmap bitmap;
462    bitmap.setInfo(info);
463    SkDebugf("bitmap width: %d  info width: %d\n", bitmap.width(), info.width());
464#StdOut
465bitmap width: 16  info width: 16
466##
467##
468
469#SeeAlso height() SkPixelRef::width() SkImageInfo::width()
470
471##
472
473# ------------------------------------------------------------------------------
474
475#Method int height() const
476
477#Line # returns pixel row count ##
478Returns pixel row count.
479
480Maybe be less than pixelRef().height(). Will not exceed pixelRef().height() less
481pixelRefOrigin().fY.
482
483#Return pixel height in Image_Info ##
484
485#Example
486    SkImageInfo info = SkImageInfo::MakeA8(16, 32);
487    SkBitmap bitmap;
488    bitmap.setInfo(info);
489    SkDebugf("bitmap height: %d  info height: %d\n", bitmap.height(), info.height());
490#StdOut
491bitmap height: 32  info height: 32
492##
493##
494
495#SeeAlso width() SkPixelRef::height() SkImageInfo::height()
496
497##
498
499# ------------------------------------------------------------------------------
500
501#Method SkColorType colorType() const
502
503#Line # returns Image_Info Color_Type ##
504Returns Color_Type, one of: kUnknown_SkColorType, kAlpha_8_SkColorType,
505kRGB_565_SkColorType, kARGB_4444_SkColorType, kRGBA_8888_SkColorType,
506kBGRA_8888_SkColorType, kGray_8_SkColorType, kRGBA_F16_SkColorType.
507
508#Return  Color_Type in Image_Info ##
509
510#Example
511    const char* colors[] = {"Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
512                            "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16"};
513    SkBitmap bitmap;
514    bitmap.setInfo(SkImageInfo::MakeA8(16, 32));
515    SkDebugf("color type: k" "%s" "_SkColorType\n", colors[bitmap.colorType()]);
516#StdOut
517color type: kAlpha_8_SkColorType
518##
519##
520
521#SeeAlso alphaType() SkImageInfo::colorType
522
523##
524
525# ------------------------------------------------------------------------------
526
527#Method SkAlphaType alphaType() const
528
529#Line # returns Image_Info Alpha_Type ##
530Returns Alpha_Type, one of: kUnknown_SkAlphaType, kOpaque_SkAlphaType,
531kPremul_SkAlphaType, kUnpremul_SkAlphaType.
532
533#Return  Alpha_Type in Image_Info ##
534
535#Example
536    const char* alphas[] = {"Unknown", "Opaque", "Premul", "Unpremul"};
537    SkPixmap pixmap(SkImageInfo::MakeA8(16, 32), nullptr, 64);
538    SkDebugf("alpha type: k" "%s" "_SkAlphaType\n", alphas[pixmap.alphaType()]);
539#StdOut
540alpha type: kPremul_SkAlphaType
541##
542##
543
544#SeeAlso colorType() SkImageInfo::alphaType
545
546##
547
548# ------------------------------------------------------------------------------
549
550#Method SkColorSpace* colorSpace() const
551
552#Line # returns Image_Info Color_Space ##
553Returns Color_Space, the range of colors, associated with Image_Info. The
554reference count of Color_Space is unchanged. The returned Color_Space is
555immutable.
556
557#Return Color_Space in Image_Info, or nullptr ##
558
559#Example
560#Description
561SkColorSpace::MakeSRGBLinear creates Color_Space with linear gamma
562and an sRGB gamut. This Color_Space gamma is not close to sRGB gamma.
563##
564    SkBitmap bitmap;
565    bitmap.setInfo(SkImageInfo::MakeN32(16, 32, kPremul_SkAlphaType,
566            SkColorSpace::MakeSRGBLinear()));
567    SkColorSpace* colorSpace = bitmap.colorSpace();
568    SkDebugf("gammaCloseToSRGB: %s  gammaIsLinear: %s  isSRGB: %s\n",
569            colorSpace->gammaCloseToSRGB() ? "true" : "false",
570            colorSpace->gammaIsLinear() ? "true" : "false",
571            colorSpace->isSRGB() ? "true" : "false");
572#StdOut
573gammaCloseToSRGB: false  gammaIsLinear: true  isSRGB: false
574##
575##
576
577#SeeAlso Color_Space SkImageInfo::colorSpace
578
579##
580
581# ------------------------------------------------------------------------------
582
583#Method sk_sp<SkColorSpace> refColorSpace() const
584
585#Line # returns Image_Info Color_Space ##
586Returns a smart pointer to Color_Space, the range of colors, associated with
587Image_Info. The smart pointer tracks the number of objects sharing this
588Color_Space reference so the memory is released when the owners destruct.
589
590The returned Color_Space is immutable.
591
592#Return Color_Space in Image_Info wrapped in a smart pointer ##
593
594#Example
595    SkBitmap bitmap1, bitmap2;
596    bitmap1.setInfo(SkImageInfo::MakeN32(16, 32, kPremul_SkAlphaType,
597            SkColorSpace::MakeSRGBLinear()));
598    bitmap2.setInfo(SkImageInfo::MakeN32(16, 32, kPremul_SkAlphaType,
599            bitmap1.refColorSpace()));
600    SkColorSpace* colorSpace = bitmap2.colorSpace();
601    SkDebugf("gammaCloseToSRGB: %s  gammaIsLinear: %s  isSRGB: %s\n",
602            colorSpace->gammaCloseToSRGB() ? "true" : "false",
603            colorSpace->gammaIsLinear() ? "true" : "false",
604            colorSpace->isSRGB() ? "true" : "false");
605#StdOut
606gammaCloseToSRGB: false  gammaIsLinear: true  isSRGB: false
607##
608##
609
610#SeeAlso Color_Space SkImageInfo::colorSpace
611
612##
613
614# ------------------------------------------------------------------------------
615
616#Method int bytesPerPixel() const
617
618#Line # returns number of bytes in pixel based on Color_Type ##
619Returns number of bytes per pixel required by Color_Type.
620Returns zero if colorType( is kUnknown_SkColorType.
621
622#Return  bytes in pixel ##
623
624#Example
625    const char* colors[] = {"Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
626                            "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16"};
627    SkImageInfo info = SkImageInfo::MakeA8(1, 1);
628    SkBitmap bitmap;
629    for (SkColorType colorType : { kUnknown_SkColorType,     kAlpha_8_SkColorType,
630                                   kRGB_565_SkColorType,     kARGB_4444_SkColorType,
631                                   kRGBA_8888_SkColorType,
632                                   kBGRA_8888_SkColorType,   kGray_8_SkColorType,
633                                   kRGBA_F16_SkColorType } ) {
634        bitmap.setInfo(info.makeColorType(colorType));
635        SkDebugf("color: k" "%s" "_SkColorType" "%*s" "bytesPerPixel: %d\n",
636                colors[colorType], 13 - strlen(colors[colorType]), " ",
637                bitmap.bytesPerPixel());
638    }
639#StdOut
640color: kUnknown_SkColorType      bytesPerPixel: 0
641color: kAlpha_8_SkColorType      bytesPerPixel: 1
642color: kRGB_565_SkColorType      bytesPerPixel: 2
643color: kARGB_4444_SkColorType    bytesPerPixel: 2
644color: kRGBA_8888_SkColorType    bytesPerPixel: 4
645color: kBGRA_8888_SkColorType    bytesPerPixel: 4
646color: kGray_8_SkColorType       bytesPerPixel: 1
647color: kRGBA_F16_SkColorType     bytesPerPixel: 8
648##
649##
650
651#SeeAlso rowBytes rowBytesAsPixels width shiftPerPixel
652
653##
654
655# ------------------------------------------------------------------------------
656
657#Method int rowBytesAsPixels() const
658
659#Line # returns interval between rows in pixels ##
660Returns number of pixels that fit on row. Should be greater than or equal to
661width().
662
663#Return  maximum pixels per row ##
664
665#Example
666    SkBitmap bitmap;
667    for (int rowBytes : { 4, 5, 6, 7, 8} ) {
668        bitmap.setInfo(SkImageInfo::MakeN32(1, 1, kPremul_SkAlphaType), rowBytes);
669        SkDebugf("rowBytes: %d rowBytesAsPixels: %d\n", rowBytes, bitmap.rowBytesAsPixels());
670    }
671#StdOut
672rowBytes: 4 rowBytesAsPixels: 1
673rowBytes: 5 rowBytesAsPixels: 1
674rowBytes: 6 rowBytesAsPixels: 1
675rowBytes: 7 rowBytesAsPixels: 1
676rowBytes: 8 rowBytesAsPixels: 2
677##
678##
679
680#SeeAlso rowBytes shiftPerPixel width bytesPerPixel
681
682##
683
684# ------------------------------------------------------------------------------
685
686#Method int shiftPerPixel() const
687
688#Line # returns bit shift from pixels to bytes ##
689Returns bit shift converting row bytes to row pixels.
690Returns zero for kUnknown_SkColorType.
691
692#Return one of: 0, 1, 2, 3; left shift to convert pixels to bytes ##
693
694#Example
695    const char* colors[] = {"Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
696                            "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16"};
697    SkImageInfo info = SkImageInfo::MakeA8(1, 1);
698    SkBitmap bitmap;
699    for (SkColorType colorType : { kUnknown_SkColorType,   kAlpha_8_SkColorType,
700                                   kRGB_565_SkColorType,   kARGB_4444_SkColorType,
701                                   kRGBA_8888_SkColorType, kBGRA_8888_SkColorType,
702                                   kGray_8_SkColorType,    kRGBA_F16_SkColorType } ) {
703        bitmap.setInfo(info.makeColorType(colorType));
704        SkDebugf("color: k" "%s" "_SkColorType" "%*s" "shiftPerPixel: %d\n",
705                colors[colorType], 10 - strlen(colors[colorType]), " ",
706                bitmap.shiftPerPixel());
707    }
708#StdOut
709color: kUnknown_SkColorType   shiftPerPixel: 0
710color: kAlpha_8_SkColorType   shiftPerPixel: 0
711color: kRGB_565_SkColorType   shiftPerPixel: 1
712color: kARGB_4444_SkColorType shiftPerPixel: 1
713color: kRGBA_8888_SkColorType shiftPerPixel: 2
714color: kBGRA_8888_SkColorType shiftPerPixel: 2
715color: kGray_8_SkColorType    shiftPerPixel: 0
716color: kRGBA_F16_SkColorType  shiftPerPixel: 3
717##
718##
719
720#SeeAlso rowBytes rowBytesAsPixels width bytesPerPixel
721
722##
723
724# ------------------------------------------------------------------------------
725
726#Method bool empty() const
727
728#Line # returns true if Image_Info has zero width() or height() ##
729Returns true if either width() or height() are zero.
730
731Does not check if Pixel_Ref is nullptr; call drawsNothing to check width(),
732height(), and Pixel_Ref.
733
734#Return  true if dimensions do not enclose area ##
735
736#Example
737    SkBitmap bitmap;
738    for (int width : { 0, 2 } ) {
739        for (int height : { 0, 2 } ) {
740             bitmap.setInfo(SkImageInfo::MakeA8(width, height));
741             SkDebugf("width: %d height: %d empty: %s\n", width, height,
742                      bitmap.empty() ? "true" : "false");
743        }
744    }
745#StdOut
746width: 0 height: 0 empty: true
747width: 0 height: 2 empty: true
748width: 2 height: 0 empty: true
749width: 2 height: 2 empty: false
750##
751##
752
753#SeeAlso height() width() drawsNothing
754
755##
756
757# ------------------------------------------------------------------------------
758
759#Method bool isNull() const
760
761#Line # returns true if Pixel_Ref is nullptr ##
762Return true if Pixel_Ref is nullptr.
763
764Does not check if width() or height() are zero; call drawsNothing to check
765width(), height(), and Pixel_Ref.
766
767#Return  true if no Pixel_Ref is associated ##
768
769#Example
770    SkBitmap bitmap;
771    SkDebugf("empty bitmap does %shave pixels\n", bitmap.isNull() ? "not " : "");
772    bitmap.setInfo(SkImageInfo::MakeA8(8, 8));
773    SkDebugf("bitmap with dimensions does %shave pixels\n", bitmap.isNull() ? "not " : "");
774    bitmap.allocPixels();
775    SkDebugf("allocated bitmap does %shave pixels\n", bitmap.isNull() ? "not " : "");
776#StdOut
777empty bitmap does not have pixels
778bitmap with dimensions does not have pixels
779allocated bitmap does have pixels
780##
781##
782
783#SeeAlso empty() drawsNothing pixelRef
784
785##
786
787# ------------------------------------------------------------------------------
788
789#Method bool drawsNothing() const
790
791#Line # returns true if no width(), no height(), or no Pixel_Ref ##
792Return true if width() or height() are zero, or if Pixel_Ref is nullptr.
793If true, Bitmap has no effect when drawn or drawn into.
794
795#Return  true if drawing has no effect ##
796
797#Example
798    SkBitmap bitmap;
799    for (int w : { 0, 8 } ) {
800        for (bool allocate : { false, true} ) {
801            bitmap.setInfo(SkImageInfo::MakeA8(w, 8));
802            allocate ? bitmap.allocPixels() : (void) 0 ;
803            SkDebugf("empty:%s isNull:%s drawsNothing:%s\n", bitmap.empty() ? "true " : "false",
804                     bitmap.isNull() ? "true " : "false", bitmap.drawsNothing() ? "true" : "false");
805        }
806    }
807#StdOut
808empty:true  isNull:true  drawsNothing:true
809empty:true  isNull:false drawsNothing:true
810empty:false isNull:true  drawsNothing:true
811empty:false isNull:false drawsNothing:false
812##
813##
814
815#SeeAlso empty() isNull pixelRef
816
817##
818
819# ------------------------------------------------------------------------------
820
821#Method size_t rowBytes() const
822
823#Line # returns interval between rows in bytes ##
824Returns row bytes, the interval from one pixel row to the next. Row bytes
825is at least as large as
826#Formula
827width() * info().bytesPerPixel()
828##
829.
830
831Returns zero if colorType is kUnknown_SkColorType, or if row bytes supplied to
832setInfo is not large enough to hold a row of pixels.
833
834#Return  byte length of pixel row ##
835
836#Example
837   SkBitmap bitmap;
838   for (int rowBytes : { 2, 8 } ) {
839       bool result = bitmap.setInfo(SkImageInfo::MakeA8(4, 4), rowBytes);
840       SkDebugf("setInfo returned:%s rowBytes:%d\n", result ? "true " : "false", bitmap.rowBytes());
841    }
842#StdOut
843setInfo returned:false rowBytes:0
844setInfo returned:true  rowBytes:8
845##
846##
847
848#SeeAlso info() setInfo SkImageInfo::minRowBytes
849
850##
851
852# ------------------------------------------------------------------------------
853
854#Method bool setAlphaType(SkAlphaType alphaType)
855
856#Line # sets Alpha_Type of shared pixels ##
857Sets Alpha_Type, if alphaType is compatible with Color_Type.
858Returns true unless alphaType is kUnknown_SkAlphaType and current Alpha_Type
859is not kUnknown_SkAlphaType.
860
861Returns true if Color_Type is kUnknown_SkColorType. alphaType is ignored, and
862Alpha_Type remains kUnknown_SkAlphaType.
863
864Returns true if Color_Type is kRGB_565_SkColorType or kGray_8_SkColorType.
865alphaType is ignored, and Alpha_Type remains kOpaque_SkAlphaType.
866
867If Color_Type is kARGB_4444_SkColorType, kRGBA_8888_SkColorType,
868kBGRA_8888_SkColorType, or kRGBA_F16_SkColorType: returns true unless
869alphaType is kUnknown_SkAlphaType and Alpha_Type is not kUnknown_SkAlphaType.
870If Alpha_Type is kUnknown_SkAlphaType, alphaType is ignored.
871
872If Color_Type is kAlpha_8_SkColorType, returns true unless
873alphaType is kUnknown_SkAlphaType and Alpha_Type is not kUnknown_SkAlphaType.
874If Alpha_Type is kUnknown_SkAlphaType, alphaType is ignored. If alphaType is
875kUnpremul_SkAlphaType, it is treated as kPremul_SkAlphaType.
876
877This changes Alpha_Type in Pixel_Ref; all bitmaps sharing Pixel_Ref
878are affected.
879
880#Param alphaType  one of: kUnknown_SkAlphaType, kOpaque_SkAlphaType,
881                          kPremul_SkAlphaType, kUnpremul_SkAlphaType
882##
883
884#Return  true if Alpha_Type is set ##
885
886#Example
887void draw(SkCanvas* canvas) {
888    const char* colors[] = { "Unknown", "Alpha_8", "RGB_565", "ARGB_4444", "RGBA_8888", "RGB_888x",
889                             "BGRA_8888", "RGBA_1010102", "RGB_101010x", "Gray_8", "RGBA_F16" };
890    const char* alphas[] = {"Unknown ", "Opaque  ", "Premul  ", "Unpremul"};
891    SkBitmap bitmap;
892    SkAlphaType alphaTypes[] = { kUnknown_SkAlphaType, kOpaque_SkAlphaType,
893                                 kPremul_SkAlphaType, kUnpremul_SkAlphaType };
894    SkDebugf("%88s", "Canonical    Unknown           Opaque            Premul            Unpremul\n");
895    for (SkColorType colorType : { kUnknown_SkColorType, kAlpha_8_SkColorType, kRGB_565_SkColorType,
896                            kARGB_4444_SkColorType, kRGBA_8888_SkColorType, kBGRA_8888_SkColorType,
897                            kGray_8_SkColorType, kRGBA_F16_SkColorType } ) {
898        for (SkAlphaType canonicalAlphaType : alphaTypes) {
899            SkColorTypeValidateAlphaType(colorType, kUnknown_SkAlphaType, &canonicalAlphaType );
900            SkDebugf("%10s %10s ", colors[(int) colorType], alphas[(int) canonicalAlphaType ]);
901            for (SkAlphaType alphaType : alphaTypes) {
902                bitmap.setInfo(SkImageInfo::Make(4, 4, colorType, canonicalAlphaType));
903                bool result = bitmap.setAlphaType(alphaType);
904                SkDebugf("%s %s    ", result ? "true " : "false", alphas[(int) bitmap.alphaType()]);
905            }
906            SkDebugf("\n");
907        }
908    }
909}
910##
911
912#SeeAlso Alpha_Type Color_Type Image_Info setInfo
913
914##
915
916# ------------------------------------------------------------------------------
917
918#Method void* getPixels() const
919
920#Line # returns address of pixels ##
921Returns pixel address, the base address corresponding to the pixel origin.
922
923#Return  pixel address ##
924
925#Example
926    SkBitmap bitmap;
927    bitmap.setInfo(SkImageInfo::MakeN32(4, 4, kPremul_SkAlphaType));
928    bitmap.allocPixels();
929    bitmap.eraseColor(0x00000000);
930    void* baseAddr = bitmap.getPixels();
931    *(SkPMColor*)baseAddr = 0xFFFFFFFF;
932    SkDebugf("bitmap.getColor(0, 1) %c= 0x00000000\n",
933              bitmap.getColor(0, 1)  == 0x00000000 ? '=' : '!');
934    SkDebugf("bitmap.getColor(0, 0) %c= 0xFFFFFFFF\n",
935              bitmap.getColor(0, 0)  == 0xFFFFFFFF ? '=' : '!');
936#StdOut
937bitmap.getColor(0, 1) == 0x00000000
938bitmap.getColor(0, 0) == 0xFFFFFFFF
939##
940##
941
942#SeeAlso isNull drawsNothing
943
944##
945
946# ------------------------------------------------------------------------------
947
948#Method size_t computeByteSize() const
949
950#Line # returns size required for pixels ##
951Returns minimum memory required for pixel storage.
952Does not include unused memory on last row when rowBytesAsPixels exceeds width().
953Returns zero if result does not fit in size_t.
954Returns zero if height() or width() is 0.
955Returns height() times rowBytes if colorType is kUnknown_SkColorType.
956
957#Return size in bytes of image buffer ##
958
959#Example
960    SkBitmap bitmap;
961    for (int width : { 1, 1000, 1000000 } ) {
962        for (int height: { 1, 1000, 1000000 } ) {
963            SkImageInfo imageInfo = SkImageInfo::MakeN32(width, height, kPremul_SkAlphaType);
964            bitmap.setInfo(imageInfo, width * 5);
965            SkDebugf("width: %7d height: %7d computeByteSize: %13lld\n", width, height,
966                     bitmap.computeByteSize());
967        }
968    }
969#StdOut
970width:       1 height:       1 computeByteSize:             4
971width:       1 height:    1000 computeByteSize:          4999
972width:       1 height: 1000000 computeByteSize:       4999999
973width:    1000 height:       1 computeByteSize:          4000
974width:    1000 height:    1000 computeByteSize:       4999000
975width:    1000 height: 1000000 computeByteSize:    4999999000
976width: 1000000 height:       1 computeByteSize:       4000000
977width: 1000000 height:    1000 computeByteSize:    4999000000
978width: 1000000 height: 1000000 computeByteSize: 4999999000000
979##
980##
981
982#SeeAlso SkImageInfo::computeByteSize
983
984##
985
986# ------------------------------------------------------------------------------
987
988#Method bool isImmutable() const
989
990#Line # returns true if pixels will not change ##
991Returns true if pixels can not change.
992
993Most immutable Bitmap checks trigger an assert only on debug builds.
994
995#Return  true if pixels are immutable ##
996
997#Example
998    SkBitmap original;
999    SkImageInfo info = SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType);
1000    if (original.tryAllocPixels(info)) {
1001        original.setImmutable();
1002        SkBitmap copy;
1003        original.extractSubset(&copy, {5, 10, 15, 20});
1004        SkDebugf("original is " "%s" "immutable\n", original.isImmutable() ? "" : "not ");
1005        SkDebugf("copy is " "%s" "immutable\n", copy.isImmutable() ? "" : "not ");
1006    }
1007#StdOut
1008original is immutable
1009copy is immutable
1010##
1011##
1012
1013#SeeAlso setImmutable SkPixelRef::isImmutable SkImage
1014
1015##
1016
1017# ------------------------------------------------------------------------------
1018
1019#Method void setImmutable()
1020
1021#Line # marks that pixels will not change ##
1022Sets internal flag to mark Bitmap as immutable. Once set, pixels can not change.
1023Any other bitmap sharing the same Pixel_Ref are also marked as immutable.
1024Once Pixel_Ref is marked immutable, the setting cannot be cleared.
1025
1026Writing to immutable Bitmap pixels triggers an assert on debug builds.
1027
1028#Example
1029#Description
1030Triggers assert if SK_DEBUG is true, runs fine otherwise.
1031##
1032    SkBitmap bitmap;
1033    bitmap.setInfo(SkImageInfo::MakeN32(4, 4, kPremul_SkAlphaType));
1034    bitmap.allocPixels();
1035    SkCanvas offscreen(bitmap);
1036    SkDebugf("draw white\n");
1037    offscreen.clear(SK_ColorWHITE);
1038    bitmap.setImmutable();
1039    SkDebugf("draw black\n");
1040    offscreen.clear(SK_ColorBLACK);
1041##
1042
1043#SeeAlso isImmutable SkPixelRef::setImmutable SkImage
1044
1045##
1046
1047# ------------------------------------------------------------------------------
1048
1049#Method bool isOpaque() const
1050
1051#Line # returns true if Image_Info describes opaque pixels ##
1052Returns true if Alpha_Type is kOpaque_SkAlphaType.
1053Does not check if Color_Type allows Alpha, or if any pixel value has
1054transparency.
1055
1056#Return  true if Image_Info describes opaque Alpha ##
1057
1058#Example
1059#Description
1060    isOpaque ignores whether all pixels are opaque or not.
1061##
1062    const int height = 2;
1063    const int width = 2;
1064    SkBitmap bitmap;
1065    bitmap.setInfo(SkImageInfo::Make(width, height, kN32_SkColorType, kPremul_SkAlphaType));
1066    for (int index = 0; index < 2; ++index) {
1067        bitmap.allocPixels();
1068        bitmap.eraseColor(0x00000000);
1069        SkDebugf("isOpaque: %s\n", bitmap.isOpaque() ? "true" : "false");
1070        bitmap.eraseColor(0xFFFFFFFF);
1071        SkDebugf("isOpaque: %s\n", bitmap.isOpaque() ? "true" : "false");
1072        bitmap.setInfo(bitmap.info().makeAlphaType(kOpaque_SkAlphaType));
1073    }
1074#StdOut
1075isOpaque: false
1076isOpaque: false
1077isOpaque: true
1078isOpaque: true
1079##
1080##
1081
1082#SeeAlso ComputeIsOpaque SkImageInfo::isOpaque
1083
1084##
1085
1086# ------------------------------------------------------------------------------
1087
1088#Method bool isVolatile() const
1089
1090#Line # returns true if pixels should not be cached ##
1091If true, provides a hint to caller that pixels should not
1092be cached. Only true if setIsVolatile has been called to mark as volatile.
1093
1094Volatile state is not shared by other bitmaps sharing the same Pixel_Ref.
1095
1096#Return  true if marked volatile ##
1097
1098#Example
1099    SkBitmap original;
1100    SkImageInfo info = SkImageInfo::Make(25, 35, kRGBA_8888_SkColorType, kOpaque_SkAlphaType);
1101    if (original.tryAllocPixels(info)) {
1102        original.setIsVolatile(true);
1103        SkBitmap copy;
1104        original.extractSubset(&copy, {5, 10, 15, 20});
1105        SkDebugf("original is " "%s" "volatile\n", original.isVolatile() ? "" : "not ");
1106        SkDebugf("copy is " "%s" "volatile\n", copy.isImmutable() ? "" : "not ");
1107    }
1108#StdOut
1109original is volatile
1110copy is not volatile
1111##
1112##
1113
1114#SeeAlso setIsVolatile
1115
1116##
1117
1118# ------------------------------------------------------------------------------
1119
1120#Method void setIsVolatile(bool isVolatile)
1121
1122#Line # marks if pixels should not be cached ##
1123Sets if pixels should be read from Pixel_Ref on every access. Bitmaps are not
1124volatile by default; a GPU back end may upload pixel values expecting them to be
1125accessed repeatedly. Marking temporary Bitmaps as volatile provides a hint to
1126Device that the Bitmap pixels should not be cached. This can
1127improve performance by avoiding overhead and reducing resource
1128consumption on Device.
1129
1130#Param isVolatile  true if backing pixels are temporary ##
1131
1132#Example
1133#Height 20
1134    SkBitmap bitmap;
1135    bitmap.setInfo(SkImageInfo::Make(1, 1, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
1136    bitmap.allocPixels();
1137    bitmap.eraseColor(SK_ColorRED);
1138    canvas->scale(16, 16);
1139    canvas->drawBitmap(bitmap, 0, 0);
1140    *(SkPMColor*) bitmap.getPixels() = SkPreMultiplyColor(SK_ColorBLUE);
1141    canvas->drawBitmap(bitmap, 2, 0);
1142    bitmap.setIsVolatile(true);
1143    *(SkPMColor*) bitmap.getPixels() = SkPreMultiplyColor(SK_ColorGREEN);
1144    canvas->drawBitmap(bitmap, 4, 0);
1145##
1146
1147#SeeAlso isVolatile
1148
1149##
1150
1151# ------------------------------------------------------------------------------
1152
1153#Method void reset()
1154
1155#Line # sets to default values, releases pixel ownership ##
1156Resets to its initial state; all fields are set to zero, as if Bitmap had
1157been initialized by SkBitmap().
1158
1159Sets width, height, row bytes to zero; pixel address to nullptr; SkColorType to
1160kUnknown_SkColorType; and SkAlphaType to kUnknown_SkAlphaType.
1161
1162If Pixel_Ref is allocated, its reference count is decreased by one, releasing
1163its memory if Bitmap is the sole owner.
1164
1165#Example
1166    SkBitmap bitmap;
1167    bitmap.setInfo(SkImageInfo::Make(1, 1, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
1168    bitmap.allocPixels();
1169    SkDebugf("width:%d height:%d isNull:%s\n", bitmap.width(), bitmap.height(),
1170             bitmap.isNull() ? "true" : "false");
1171    bitmap.reset();
1172    SkDebugf("width:%d height:%d isNull:%s\n", bitmap.width(), bitmap.height(),
1173             bitmap.isNull() ? "true" : "false");
1174#StdOut
1175width:1 height:1 isNull:false
1176width:0 height:0 isNull:true
1177##
1178##
1179
1180#SeeAlso SkBitmap() SkAlphaType SkColorType
1181
1182##
1183
1184# ------------------------------------------------------------------------------
1185
1186#Method static bool ComputeIsOpaque(const SkBitmap& bm)
1187
1188#Line # returns true if all pixels are opaque ##
1189Returns true if all pixels are opaque. Color_Type determines how pixels
1190are encoded, and whether pixel describes Alpha. Returns true for Color_Types
1191without alpha in each pixel; for other Color_Types, returns true if all
1192pixels have alpha values equivalent to 1.0 or greater.
1193
1194For Color_Types kRGB_565_SkColorType or kGray_8_SkColorType: always
1195returns true. For Color_Types kAlpha_8_SkColorType, kBGRA_8888_SkColorType,
1196kRGBA_8888_SkColorType: returns true if all pixel Alpha values are 255.
1197For Color_Type kARGB_4444_SkColorType: returns true if all pixel Alpha values are 15.
1198For kRGBA_F16_SkColorType: returns true if all pixel Alpha values are 1.0 or
1199greater.
1200
1201Returns false for kUnknown_SkColorType.
1202
1203#Param bm  Bitmap to check ##
1204
1205#Return true if all pixels have opaque values or Color_Type is opaque ##
1206
1207#Example
1208    SkBitmap bitmap;
1209    bitmap.setInfo(SkImageInfo::Make(2, 2, kN32_SkColorType, kPremul_SkAlphaType));
1210    for (int index = 0; index < 2; ++index) {
1211        bitmap.allocPixels();
1212        bitmap.eraseColor(0x00000000);
1213        SkDebugf("computeIsOpaque: %s\n", SkBitmap::ComputeIsOpaque(bitmap) ? "true" : "false");
1214        bitmap.eraseColor(0xFFFFFFFF);
1215        SkDebugf("computeIsOpaque: %s\n", SkBitmap::ComputeIsOpaque(bitmap) ? "true" : "false");
1216        bitmap.setInfo(bitmap.info().makeAlphaType(kOpaque_SkAlphaType));
1217    }
1218#StdOut
1219computeIsOpaque: false
1220computeIsOpaque: true
1221computeIsOpaque: false
1222computeIsOpaque: true
1223##
1224##
1225
1226#SeeAlso isOpaque Color_Type Alpha
1227
1228##
1229
1230# ------------------------------------------------------------------------------
1231
1232#Method void getBounds(SkRect* bounds) const
1233
1234#Line # returns width() and height() as Rectangle ##
1235Returns Rect { 0, 0, width(), height() }.
1236
1237#Param bounds container for floating point rectangle ##
1238
1239#Example
1240#Height 160
1241#Image 3
1242    SkRect bounds;
1243    source.getBounds(&bounds);
1244    bounds.offset(100, 100);
1245    SkPaint paint;
1246    paint.setColor(SK_ColorGRAY);
1247    canvas->scale(.25f, .25f);
1248    canvas->drawRect(bounds, paint);
1249    canvas->drawBitmap(source, 40, 40);
1250##
1251
1252#SeeAlso bounds()
1253
1254##
1255
1256# ------------------------------------------------------------------------------
1257
1258#Method void getBounds(SkIRect* bounds) const
1259
1260Returns IRect { 0, 0, width(), height() }.
1261
1262#Param bounds container for integral rectangle ##
1263
1264#Example
1265#Image 3
1266    SkIRect bounds;
1267    source.getBounds(&bounds);
1268    bounds.inset(100, 100);
1269    SkBitmap bitmap;
1270    source.extractSubset(&bitmap, bounds);
1271    canvas->scale(.5f, .5f);
1272    canvas->drawBitmap(bitmap, 10, 10);
1273##
1274
1275#SeeAlso bounds()
1276
1277##
1278
1279# ------------------------------------------------------------------------------
1280
1281#Method SkIRect bounds() const
1282
1283#Line # returns width() and height() as Rectangle ##
1284Returns IRect { 0, 0, width(), height() }.
1285
1286#Return  integral rectangle from origin to width() and height() ##
1287
1288#Example
1289#Height 128
1290#Image 4
1291    canvas->scale(.5f, .5f);
1292    SkIRect bounds = source.bounds();
1293    for (int x : { 0, bounds.width() } ) {
1294        for (int y : { 0, bounds.height() } ) {
1295            canvas->drawBitmap(source, x, y);
1296        }
1297    }
1298##
1299
1300#SeeAlso getBounds
1301
1302##
1303
1304# ------------------------------------------------------------------------------
1305
1306#Method SkISize dimensions() const
1307
1308#Line # returns width() and height() ##
1309Returns ISize { width(), height() }.
1310
1311#Return integral size of width() and height() ##
1312
1313#Example
1314    SkBitmap bitmap;
1315    bitmap.setInfo(SkImageInfo::MakeN32(33, 55, kOpaque_SkAlphaType));
1316    SkISize dimensions = bitmap.dimensions();
1317    SkRect bounds;
1318    bitmap.getBounds(&bounds);
1319    SkRect dimensionsAsBounds = SkRect::Make(dimensions);
1320    SkDebugf("dimensionsAsBounds %c= bounds\n", dimensionsAsBounds == bounds ? '=' : '!');
1321##
1322
1323#SeeAlso height() width()
1324
1325##
1326
1327# ------------------------------------------------------------------------------
1328
1329#Method SkIRect getSubset() const
1330
1331#Line # returns bounds offset by origin ##
1332Returns the bounds of this bitmap, offset by its Pixel_Ref origin.
1333
1334#Return bounds within Pixel_Ref bounds ##
1335
1336#Example
1337#Image 3
1338    SkIRect bounds;
1339    source.getBounds(&bounds);
1340    bounds.inset(100, 100);
1341    SkBitmap subset;
1342    source.extractSubset(&subset, bounds);
1343    SkIRect r = source.getSubset();
1344    SkDebugf("source: %d, %d, %d, %d\n", r.fLeft, r.fTop, r.fRight, r.fBottom);
1345    r = subset.getSubset();
1346    SkDebugf("subset: %d, %d, %d, %d\n", r.fLeft, r.fTop, r.fRight, r.fBottom);
1347#StdOut
1348source: 0, 0, 512, 512
1349subset: 100, 100, 412, 412
1350##
1351##
1352
1353#SeeAlso extractSubset getBounds
1354
1355##
1356
1357# ------------------------------------------------------------------------------
1358
1359#Method bool setInfo(const SkImageInfo& imageInfo, size_t rowBytes = 0)
1360
1361#Line # sets height, width, Color_Type, and so on, releasing pixels ##
1362Sets width, height, Alpha_Type, Color_Type, Color_Space, and optional
1363rowBytes. Frees pixels, and returns true if successful.
1364
1365imageInfo.alphaType may be altered to a value permitted by imageInfo.colorSpace.
1366If imageInfo.colorType is kUnknown_SkColorType, imageInfo.alphaType is
1367set to kUnknown_SkAlphaType.
1368If imageInfo.colorType is kAlpha_8_SkColorType and imageInfo.alphaType is
1369kUnpremul_SkAlphaType, imageInfo.alphaType is replaced by kPremul_SkAlphaType.
1370If imageInfo.colorType is kRGB_565_SkColorType or kGray_8_SkColorType,
1371imageInfo.alphaType is set to kOpaque_SkAlphaType.
1372If imageInfo.colorType is kARGB_4444_SkColorType, kRGBA_8888_SkColorType,
1373kBGRA_8888_SkColorType, or kRGBA_F16_SkColorType: imageInfo.alphaType remains
1374unchanged.
1375
1376rowBytes must equal or exceed imageInfo.minRowBytes. If imageInfo.colorSpace is
1377kUnknown_SkColorType, rowBytes is ignored and treated as zero; for all other
1378Color_Space values, rowBytes of zero is treated as imageInfo.minRowBytes.
1379
1380Calls reset() and returns false if:
1381#List
1382# rowBytes exceeds 31 bits ##
1383# imageInfo.width() is negative ##
1384# imageInfo.height() is negative ##
1385# rowBytes is positive and less than imageInfo.width() times imageInfo.bytesPerPixel ##
1386##
1387
1388#Param imageInfo  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1389#Param rowBytes   imageInfo.minRowBytes or larger; or zero ##
1390
1391#Return  true if Image_Info set successfully ##
1392
1393#Example
1394#Height 96
1395###^
1396SkBitmap bitmap;
1397bitmap.setInfo(SkImageInfo::MakeN32(44, 16, kOpaque_SkAlphaType));
1398bitmap.allocPixels();
1399bitmap.eraseColor(SK_ColorGREEN);
1400SkCanvas offscreen(bitmap);
1401SkPaint paint;
1402offscreen.drawString("!@#$%", 0, 12, paint);
1403canvas->scale(6, 6);
1404canvas->drawBitmap(bitmap, 0, 0);
1405^^^#
1406##
1407
1408#SeeAlso Alpha_Type Color_Type Color_Space height rowBytes width
1409
1410##
1411
1412# ------------------------------------------------------------------------------
1413
1414#Enum AllocFlags
1415
1416#Code
1417    enum AllocFlags {
1418        kZeroPixels_AllocFlag = 1 << 0,
1419    };
1420##
1421
1422AllocFlags provides the option to zero pixel memory when allocated.
1423
1424#Const kZeroPixels_AllocFlag 1
1425    Instructs tryAllocPixelsFlags and allocPixelsFlags to zero pixel memory.
1426##
1427
1428#NoExample
1429##
1430
1431#SeeAlso tryAllocPixelsFlags allocPixelsFlags erase() eraseColor
1432
1433##
1434
1435# ------------------------------------------------------------------------------
1436
1437#Method bool SK_WARN_UNUSED_RESULT tryAllocPixelsFlags(const SkImageInfo& info, uint32_t flags)
1438
1439#Line # allocates pixels from Image_Info with options if possible ##
1440Sets Image_Info to info following the rules in setInfo and allocates pixel
1441memory. If flags is kZeroPixels_AllocFlag, memory is zeroed.
1442
1443Returns false and calls reset() if Image_Info could not be set, or memory could
1444not be allocated, or memory could not optionally be zeroed.
1445
1446On most platforms, allocating pixel memory may succeed even though there is
1447not sufficient memory to hold pixels; allocation does not take place
1448until the pixels are written to. The actual behavior depends on the platform
1449implementation of malloc(), if flags is zero, and calloc(), if flags is
1450kZeroPixels_AllocFlag.
1451
1452Passing kZeroPixels_AllocFlag is usually faster than separately calling
1453eraseColor(SK_ColorTRANSPARENT).
1454
1455#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1456#Param flags  kZeroPixels_AllocFlag, or zero ##
1457
1458#Return  true if pixels allocation is successful ##
1459
1460#Example
1461    SkBitmap bitmap;
1462    if (!bitmap.tryAllocPixelsFlags(SkImageInfo::MakeN32(10000, 10000, kOpaque_SkAlphaType),
1463                                    SkBitmap::kZeroPixels_AllocFlag)) {
1464        SkDebugf("bitmap allocation failed!\n");
1465    } else {
1466        SkDebugf("bitmap allocation succeeded!\n");
1467    }
1468#StdOut
1469bitmap allocation succeeded!
1470##
1471##
1472
1473#SeeAlso allocPixelsFlags tryAllocPixels SkMallocPixelRef::MakeZeroed
1474
1475##
1476
1477# ------------------------------------------------------------------------------
1478
1479#Method void allocPixelsFlags(const SkImageInfo& info, uint32_t flags)
1480
1481#Line # allocates pixels from Image_Info with options, or aborts ##
1482Sets Image_Info to info following the rules in setInfo and allocates pixel
1483memory. If flags is kZeroPixels_AllocFlag, memory is zeroed.
1484
1485Aborts execution if Image_Info could not be set, or memory could
1486not be allocated, or memory could not optionally
1487be zeroed. Abort steps may be provided by the user at compile time by defining
1488SK_ABORT.
1489
1490On most platforms, allocating pixel memory may succeed even though there is
1491not sufficient memory to hold pixels; allocation does not take place
1492until the pixels are written to. The actual behavior depends on the platform
1493implementation of malloc(), if flags is zero, and calloc(), if flags is
1494kZeroPixels_AllocFlag.
1495
1496Passing kZeroPixels_AllocFlag is usually faster than separately calling
1497eraseColor(SK_ColorTRANSPARENT).
1498
1499#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1500#Param flags  kZeroPixels_AllocFlag, or zero ##
1501
1502#Example
1503#Height 128
1504#Description
1505Text is drawn on a transparent background; drawing the bitmap a second time
1506lets the first draw show through.
1507##
1508###^
1509SkBitmap bitmap;
1510bitmap.allocPixelsFlags(SkImageInfo::MakeN32(44, 16, kPremul_SkAlphaType),
1511                        SkBitmap::kZeroPixels_AllocFlag);
1512SkCanvas offscreen(bitmap);
1513SkPaint paint;
1514offscreen.drawString("!@#$%", 0, 12, paint);
1515canvas->scale(6, 6);
1516canvas->drawBitmap(bitmap, 0, 0);
1517canvas->drawBitmap(bitmap, 8, 8);
1518^^^#
1519##
1520
1521#SeeAlso tryAllocPixelsFlags allocPixels SkMallocPixelRef::MakeZeroed
1522
1523##
1524
1525# ------------------------------------------------------------------------------
1526
1527#Method bool SK_WARN_UNUSED_RESULT tryAllocPixels(const SkImageInfo& info, size_t rowBytes)
1528
1529#Line # allocates pixels from Image_Info if possible ##
1530#ToDo  am I ever conflicted about setInfo rules. It needs to be able to be replicated
1531       if, for instance, I generate one-page-per-method HTML-style documentation
1532       I'm not so sure it makes sense to put the indirection in for .h either unless
1533       my mantra is that .h should abbreviate full documentation. And, what to do
1534       for generated markdown? At least there the rules are a click away, although
1535       a pop-down in place would be way better. Hmmm.
1536##
1537
1538Sets Image_Info to info following the rules in setInfo and allocates pixel
1539memory. rowBytes must equal or exceed info.width() times info.bytesPerPixel(),
1540or equal zero. Pass in zero for rowBytes to compute the minimum valid value.
1541
1542Returns false and calls reset() if Image_Info could not be set, or memory could
1543not be allocated.
1544
1545On most platforms, allocating pixel memory may succeed even though there is
1546not sufficient memory to hold pixels; allocation does not take place
1547until the pixels are written to. The actual behavior depends on the platform
1548implementation of malloc().
1549
1550#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1551#Param rowBytes  size of pixel row or larger; may be zero  ##
1552
1553#Return  true if pixel storage is allocated ##
1554
1555#Example
1556#Image 3
1557SkBitmap bitmap;
1558SkImageInfo info = SkImageInfo::Make(64, 256, kGray_8_SkColorType, kOpaque_SkAlphaType);
1559if (bitmap.tryAllocPixels(info, 0)) {
1560    SkCanvas offscreen(bitmap);
1561    offscreen.scale(.5f, .5f);
1562    for (int x : { 0, 64, 128, 192 } ) {
1563        offscreen.drawBitmap(source, -x, 0);
1564        canvas->drawBitmap(bitmap, x, 0);
1565    }
1566}
1567##
1568
1569#SeeAlso tryAllocPixelsFlags allocPixels SkMallocPixelRef::MakeAllocate
1570
1571##
1572
1573# ------------------------------------------------------------------------------
1574
1575#Method void allocPixels(const SkImageInfo& info, size_t rowBytes)
1576
1577#Line # allocates pixels from Image_Info, or aborts ##
1578Sets Image_Info to info following the rules in setInfo and allocates pixel
1579memory. rowBytes must equal or exceed info.width() times info.bytesPerPixel(),
1580or equal zero. Pass in zero for rowBytes to compute the minimum valid value.
1581
1582Aborts execution if Image_Info could not be set, or memory could
1583not be allocated. Abort steps may be provided by
1584the user at compile time by defining SK_ABORT.
1585
1586On most platforms, allocating pixel memory may succeed even though there is
1587not sufficient memory to hold pixels; allocation does not take place
1588until the pixels are written to. The actual behavior depends on the platform
1589implementation of malloc().
1590
1591#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1592#Param rowBytes  size of pixel row or larger; may be zero  ##
1593
1594#Example
1595#Image 3
1596SkBitmap bitmap;
1597SkImageInfo info = SkImageInfo::Make(256, 64, kGray_8_SkColorType, kOpaque_SkAlphaType);
1598bitmap.allocPixels(info, info.width() * info.bytesPerPixel() + 64);
1599SkCanvas offscreen(bitmap);
1600offscreen.scale(.5f, .5f);
1601for (int y : { 0, 64, 128, 192 } ) {
1602    offscreen.drawBitmap(source, 0, -y);
1603    canvas->drawBitmap(bitmap, 0, y);
1604}
1605##
1606
1607#SeeAlso tryAllocPixels allocPixelsFlags SkMallocPixelRef::MakeAllocate
1608
1609##
1610
1611# ------------------------------------------------------------------------------
1612
1613#Method bool SK_WARN_UNUSED_RESULT tryAllocPixels(const SkImageInfo& info)
1614
1615Sets Image_Info to info following the rules in setInfo and allocates pixel
1616memory.
1617
1618Returns false and calls reset() if Image_Info could not be set, or memory could
1619not be allocated.
1620
1621On most platforms, allocating pixel memory may succeed even though there is
1622not sufficient memory to hold pixels; allocation does not take place
1623until the pixels are written to. The actual behavior depends on the platform
1624implementation of malloc().
1625
1626#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1627
1628#Return  true if pixel storage is allocated ##
1629
1630#Example
1631#Image 3
1632SkBitmap bitmap;
1633if (bitmap.tryAllocPixels(SkImageInfo::Make(64, 64, kGray_8_SkColorType, kOpaque_SkAlphaType))) {
1634    SkCanvas offscreen(bitmap);
1635    offscreen.scale(.25f, .5f);
1636    for (int y : { 0, 64, 128, 192 } ) {
1637        offscreen.drawBitmap(source, -y, -y);
1638        canvas->drawBitmap(bitmap, y, y);
1639    }
1640}
1641##
1642
1643#SeeAlso tryAllocPixelsFlags allocPixels SkMallocPixelRef::MakeAllocate
1644
1645##
1646
1647# ------------------------------------------------------------------------------
1648
1649#Method void allocPixels(const SkImageInfo& info)
1650
1651Sets Image_Info to info following the rules in setInfo and allocates pixel
1652memory.
1653
1654Aborts execution if Image_Info could not be set, or memory could
1655not be allocated. Abort steps may be provided by
1656the user at compile time by defining SK_ABORT.
1657
1658On most platforms, allocating pixel memory may succeed even though there is
1659not sufficient memory to hold pixels; allocation does not take place
1660until the pixels are written to. The actual behavior depends on the platform
1661implementation of malloc().
1662
1663#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1664
1665#Example
1666#Image 4
1667SkBitmap bitmap;
1668bitmap.allocPixels(SkImageInfo::Make(64, 64, kGray_8_SkColorType, kOpaque_SkAlphaType));
1669SkCanvas offscreen(bitmap);
1670offscreen.scale(.5f, .5f);
1671for (int y : { 0, 64, 128, 192 } ) {
1672    offscreen.drawBitmap(source, -y, -y);
1673    canvas->drawBitmap(bitmap, y, y);
1674}
1675##
1676
1677#SeeAlso tryAllocPixels allocPixelsFlags SkMallocPixelRef::MakeAllocate
1678
1679##
1680
1681# ------------------------------------------------------------------------------
1682
1683#Method bool SK_WARN_UNUSED_RESULT tryAllocN32Pixels(int width, int height, bool isOpaque = false)
1684
1685#Line # allocates compatible Color_ARGB pixels if possible ##
1686Sets Image_Info to width, height, and Native_Color_Type; and allocates
1687pixel memory. If isOpaque is true, sets Image_Info to kOpaque_SkAlphaType;
1688otherwise, sets to kPremul_SkAlphaType.
1689
1690Calls reset() and returns false if width exceeds 29 bits or is negative,
1691or height is negative.
1692
1693Returns false if allocation fails.
1694
1695Use to create Bitmap that matches SkPMColor, the native pixel arrangement on
1696the platform. Bitmap drawn to output device skips converting its pixel format.
1697
1698#Param width  pixel column count; must be zero or greater ##
1699#Param height  pixel row count; must be zero or greater ##
1700#Param isOpaque  true if pixels do not have transparency ##
1701
1702#Return  true if pixel storage is allocated ##
1703
1704#Example
1705#Height 160
1706    SkBitmap bitmap;
1707    if (bitmap.tryAllocN32Pixels(80, 80)) {
1708        bitmap.eraseColor(SK_ColorTRANSPARENT);
1709        bitmap.erase(0x7f3f7fff, SkIRect::MakeWH(50, 30));
1710        bitmap.erase(0x3f7fff3f, SkIRect::MakeXYWH(20, 10, 50, 30));
1711        bitmap.erase(0x5fff3f7f, SkIRect::MakeXYWH(40, 20, 50, 30));
1712        canvas->drawBitmap(bitmap, 0, 0);
1713        for (int x : { 0, 30, 60, 90 } ) {
1714            canvas->drawBitmap(bitmap, x, 70);
1715        }
1716    }
1717##
1718
1719#SeeAlso tryAllocPixels allocN32Pixels SkMallocPixelRef::MakeAllocate
1720
1721##
1722
1723# ------------------------------------------------------------------------------
1724
1725#Method void allocN32Pixels(int width, int height, bool isOpaque = false)
1726
1727#Line # allocates compatible Color_ARGB pixels, or aborts ##
1728Sets Image_Info to width, height, and the Native_Color_Type; and allocates
1729pixel memory. If isOpaque is true, sets Image_Info to kPremul_SkAlphaType;
1730otherwise, sets to kOpaque_SkAlphaType.
1731
1732Aborts if width exceeds 29 bits or is negative, or height is negative, or
1733allocation fails. Abort steps may be provided by the user at compile time by
1734defining SK_ABORT.
1735
1736Use to create Bitmap that matches SkPMColor, the native pixel arrangement on
1737the platform. Bitmap drawn to output device skips converting its pixel format.
1738
1739#Param width  pixel column count; must be zero or greater ##
1740#Param height  pixel row count; must be zero or greater ##
1741#Param isOpaque  true if pixels do not have transparency ##
1742
1743#Example
1744    SkRandom random;
1745    SkBitmap bitmap;
1746    bitmap.allocN32Pixels(64, 64);
1747    bitmap.eraseColor(SK_ColorTRANSPARENT);
1748    for (int y = 0; y < 256; y += 64) {
1749        for (int x = 0; x < 256; x += 64) {
1750            SkColor color = random.nextU();
1751            uint32_t w = random.nextRangeU(4, 32);
1752            uint32_t cx = random.nextRangeU(0, 64 - w);
1753            uint32_t h = random.nextRangeU(4, 32);
1754            uint32_t cy = random.nextRangeU(0, 64 - h);
1755            bitmap.erase(color, SkIRect::MakeXYWH(cx, cy, w, h));
1756            canvas->drawBitmap(bitmap, x, y);
1757        }
1758    }
1759##
1760
1761#SeeAlso allocPixels tryAllocN32Pixels SkMallocPixelRef::MakeAllocate
1762
1763##
1764
1765# ------------------------------------------------------------------------------
1766
1767#Method bool installPixels(const SkImageInfo& info, void* pixels, size_t rowBytes,
1768                       void (*releaseProc)(void* addr, void* context), void* context)
1769#Line # creates Pixel_Ref, with optional release function ##
1770
1771Sets Image_Info to info following the rules in setInfo, and creates Pixel_Ref
1772containing pixels and rowBytes. releaseProc, if not nullptr, is called
1773immediately on failure or when pixels are no longer referenced. context may be
1774nullptr.
1775
1776If Image_Info could not be set, or rowBytes is less than info.minRowBytes:
1777calls releaseProc if present, calls reset(), and returns false.
1778
1779Otherwise, if pixels equals nullptr: sets Image_Info, calls releaseProc if
1780present, returns true.
1781
1782If Image_Info is set, pixels is not nullptr, and releaseProc is not nullptr:
1783when pixels are no longer referenced, calls releaseProc with pixels and context
1784as parameters.
1785
1786#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1787#Param pixels   address or pixel storage; may be nullptr ##
1788#Param rowBytes  size of pixel row or larger ##
1789#Param releaseProc  function called when pixels can be deleted; may be nullptr ##
1790#Param context   caller state passed to releaseProc; may be nullptr ##
1791
1792#Return  true if Image_Info is set to info ##
1793
1794#Example
1795#Description
1796releaseProc is called immediately because rowBytes is too small for Pixel_Ref.
1797##
1798#Function
1799static void releaseProc(void* addr, void* ) {
1800    SkDebugf("releaseProc called\n");
1801    delete[] (uint32_t*) addr;
1802}
1803
1804##
1805
1806void draw(SkCanvas* canvas) {
1807   SkBitmap bitmap;
1808   void* pixels = new uint32_t[8 * 8];
1809   SkImageInfo info = SkImageInfo::MakeN32(8, 8, kOpaque_SkAlphaType);
1810   SkDebugf("before installPixels\n");
1811   bool installed = bitmap.installPixels(info, pixels, 16, releaseProc, nullptr);
1812   SkDebugf("install " "%s" "successful\n", installed ? "" : "not ");
1813}
1814#StdOut
1815before installPixels
1816releaseProc called
1817install not successful
1818##
1819##
1820
1821#SeeAlso allocPixels
1822
1823##
1824
1825# ------------------------------------------------------------------------------
1826
1827#Method bool installPixels(const SkImageInfo& info, void* pixels, size_t rowBytes)
1828
1829Sets Image_Info to info following the rules in setInfo, and creates Pixel_Ref
1830containing pixels and rowBytes.
1831
1832If Image_Info could not be set, or rowBytes is less than info.minRowBytes:
1833calls reset(), and returns false.
1834
1835Otherwise, if pixels equals nullptr: sets Image_Info, returns true.
1836
1837Caller must ensure that pixels are valid for the lifetime of Bitmap and Pixel_Ref.
1838
1839#Param info  contains width, height, Alpha_Type, Color_Type, Color_Space ##
1840#Param pixels  address or pixel storage; may be nullptr ##
1841#Param rowBytes  size of pixel row or larger ##
1842
1843#Return  true if Image_Info is set to info ##
1844
1845#Example
1846#Description
1847#Bug 7079 ##
1848GPU does not support kUnpremul_SkAlphaType, does not assert that it does not.
1849##
1850void draw(SkCanvas* canvas) {
1851   SkRandom random;
1852   SkBitmap bitmap;
1853   const int width = 8;
1854   const int height = 8;
1855   uint32_t pixels[width * height];
1856   for (unsigned x = 0; x < width * height; ++x) {
1857       pixels[x] = random.nextU();
1858   }
1859   SkImageInfo info = SkImageInfo::MakeN32(width, height, kUnpremul_SkAlphaType);
1860   if (bitmap.installPixels(info, pixels, info.minRowBytes())) {
1861       canvas->scale(32, 32);
1862       canvas->drawBitmap(bitmap, 0, 0);
1863   }
1864}
1865##
1866
1867#SeeAlso allocPixels
1868
1869##
1870
1871# ------------------------------------------------------------------------------
1872
1873#Method bool installPixels(const SkPixmap& pixmap)
1874
1875Sets Image_Info to pixmap.info() following the rules in setInfo, and creates
1876Pixel_Ref containing pixmap.addr() and pixmap.rowBytes.
1877
1878If Image_Info could not be set, or pixmap.rowBytes is less than
1879SkImageInfo::minRowBytes: calls reset(), and returns false.
1880
1881Otherwise, if pixmap.addr() equals nullptr: sets Image_Info, returns true.
1882
1883Caller must ensure that pixmap is valid for the lifetime of Bitmap and Pixel_Ref.
1884
1885#Param pixmap  Image_Info, pixel address, and rowBytes ##
1886
1887#Return  true if Image_Info was set to pixmap.info() ##
1888
1889#Example
1890#Description
1891Draw a five by five bitmap, and draw it again with a center white pixel.
1892##
1893#Height 64
1894    uint8_t storage[][5] = {{ 0xCA, 0xDA, 0xCA, 0xC9, 0xA3 },
1895                            { 0xAC, 0xA8, 0x89, 0x47, 0x87 },
1896                            { 0x4B, 0x25, 0x25, 0x25, 0x46 },
1897                            { 0x90, 0x81, 0x25, 0x41, 0x33 },
1898                            { 0x75, 0x55, 0x44, 0x20, 0x00 }};
1899    SkImageInfo imageInfo = SkImageInfo::Make(5, 5, kGray_8_SkColorType, kOpaque_SkAlphaType);
1900    SkPixmap pixmap(imageInfo, storage[0], sizeof(storage) / 5);
1901    SkBitmap bitmap;
1902    bitmap.installPixels(pixmap);
1903    canvas->scale(10, 10);
1904    canvas->drawBitmap(bitmap, 0, 0);
1905    *pixmap.writable_addr8(2, 2) = 0xFF;
1906    bitmap.installPixels(pixmap);
1907    canvas->drawBitmap(bitmap, 10, 0);
1908##
1909
1910#SeeAlso allocPixels
1911
1912##
1913
1914# ------------------------------------------------------------------------------
1915
1916#Method bool installMaskPixels(const SkMask& mask)
1917
1918#Line # creates Pixel_Ref from Mask ##
1919Sets Image_Info to mask width, mask height, kAlpha_8_SkColorType, and
1920kPremul_SkAlphaType. Sets Pixel_Ref to mask image and mask rowBytes.
1921
1922Returns false and calls reset() if mask format is not SkMask::kA8_Format,
1923or if mask width or mask height is negative, or if mask rowBytes is less
1924than mask width.
1925
1926Caller must ensure that mask is valid for the lifetime of Bitmap and Pixel_Ref.
1927
1928#Param mask  Alpha 8-bit bitmap ##
1929
1930#Return true if Image_Info and Pixel_Ref refer to mask ##
1931
1932#Example
1933#Description
1934Draw a five by five bitmap, and draw it again with a center white pixel.
1935##
1936#Height 64
1937    uint8_t storage[][5] = {{ 0xCA, 0xDA, 0xCA, 0xC9, 0xA3 },
1938                            { 0xAC, 0xA8, 0x89, 0x47, 0x87 },
1939                            { 0x4B, 0x25, 0x25, 0x25, 0x46 },
1940                            { 0x90, 0x81, 0x25, 0x41, 0x33 },
1941                            { 0x75, 0x55, 0x44, 0x20, 0x00 }};
1942    SkMask mask;
1943    mask.fImage = storage[0];
1944    mask.fBounds = SkIRect::MakeWH(5, 5);
1945    mask.fRowBytes = 5;
1946    mask.fFormat = SkMask::kA8_Format;
1947    SkBitmap bitmap;
1948    bitmap.installMaskPixels(mask);
1949    canvas->scale(10, 10);
1950    canvas->drawBitmap(bitmap, 0, 0);
1951    storage[2][2] = 0xFF;
1952    bitmap.installMaskPixels(mask);
1953    canvas->drawBitmap(bitmap, 10, 0);
1954##
1955
1956#SeeAlso installPixels allocPixels
1957
1958##
1959
1960# ------------------------------------------------------------------------------
1961
1962#Method void setPixels(void* pixels)
1963
1964#Line # sets Pixel_Ref without an offset ##
1965Replaces Pixel_Ref with pixels, preserving Image_Info and rowBytes.
1966Sets Pixel_Ref origin to (0, 0).
1967
1968If pixels is nullptr, or if info().colorType equals kUnknown_SkColorType;
1969release reference to Pixel_Ref, and set Pixel_Ref to nullptr.
1970
1971Caller is responsible for handling ownership pixel memory for the lifetime
1972of Bitmap and Pixel_Ref.
1973
1974#Param pixels  address of pixel storage, managed by caller ##
1975
1976#Example
1977#Height 50
1978    uint8_t set1[5] = { 0xCA, 0xDA, 0xCA, 0xC9, 0xA3 };
1979    uint8_t set2[5] = { 0xAC, 0xA8, 0x89, 0x47, 0x87 };
1980    SkBitmap bitmap;
1981    bitmap.installPixels(SkImageInfo::Make(5, 1, kGray_8_SkColorType, kOpaque_SkAlphaType), set1, 5);
1982    canvas->scale(10, 50);
1983    canvas->drawBitmap(bitmap, 0, 0);
1984    bitmap.setPixels(set2);
1985    canvas->drawBitmap(bitmap, 10, 0);
1986##
1987
1988#SeeAlso installPixels allocPixels
1989
1990##
1991
1992# ------------------------------------------------------------------------------
1993
1994#Method bool SK_WARN_UNUSED_RESULT tryAllocPixels()
1995
1996Allocates pixel memory with HeapAllocator, and replaces existing Pixel_Ref.
1997The allocation size is determined by Image_Info width, height, and Color_Type.
1998
1999Returns false if info().colorType is kUnknown_SkColorType, or allocation fails.
2000
2001#Return  true if the allocation succeeds
2002##
2003
2004#Example
2005#Height 50
2006#Description
2007Bitmap hosts and draws gray values in set1. tryAllocPixels replaces Pixel_Ref
2008and erases it to black, but does not alter set1. setPixels replaces black
2009Pixel_Ref with set1.
2010##
2011    uint8_t set1[5] = { 0xCA, 0xDA, 0xCA, 0xC9, 0xA3 };
2012    SkBitmap bitmap;
2013    bitmap.installPixels(SkImageInfo::Make(5, 1, kGray_8_SkColorType, kOpaque_SkAlphaType), set1, 5);
2014    canvas->scale(10, 50);
2015    canvas->drawBitmap(bitmap, 0, 0);
2016    if (bitmap.tryAllocPixels()) {
2017        bitmap.eraseColor(SK_ColorBLACK);
2018        canvas->drawBitmap(bitmap, 8, 0);
2019        bitmap.setPixels(set1);
2020        canvas->drawBitmap(bitmap, 16, 0);
2021    }
2022##
2023
2024#SeeAlso allocPixels installPixels setPixels
2025
2026##
2027
2028# ------------------------------------------------------------------------------
2029
2030#Method void allocPixels()
2031
2032Allocates pixel memory with HeapAllocator, and replaces existing Pixel_Ref.
2033The allocation size is determined by Image_Info width, height, and Color_Type.
2034
2035Aborts if info().colorType is kUnknown_SkColorType, or allocation fails.
2036Abort steps may be provided by the user at compile
2037time by defining SK_ABORT.
2038
2039#Example
2040#Height 50
2041#Description
2042Bitmap hosts and draws gray values in set1. allocPixels replaces Pixel_Ref
2043and erases it to black, but does not alter set1. setPixels replaces black
2044Pixel_Ref with set2.
2045##
2046    uint8_t set1[5] = { 0xCA, 0xDA, 0xCA, 0xC9, 0xA3 };
2047    uint8_t set2[5] = { 0xAC, 0xA8, 0x89, 0x47, 0x87 };
2048    SkBitmap bitmap;
2049    bitmap.installPixels(SkImageInfo::Make(5, 1, kGray_8_SkColorType, kOpaque_SkAlphaType), set1, 5);
2050    canvas->scale(10, 50);
2051    canvas->drawBitmap(bitmap, 0, 0);
2052    bitmap.allocPixels();
2053    bitmap.eraseColor(SK_ColorBLACK);
2054    canvas->drawBitmap(bitmap, 8, 0);
2055    bitmap.setPixels(set2);
2056    canvas->drawBitmap(bitmap, 16, 0);
2057##
2058
2059#SeeAlso tryAllocPixels installPixels setPixels
2060
2061##
2062
2063# ------------------------------------------------------------------------------
2064
2065#Method bool SK_WARN_UNUSED_RESULT tryAllocPixels(Allocator* allocator)
2066
2067Allocates pixel memory with allocator, and replaces existing Pixel_Ref.
2068The allocation size is determined by Image_Info width, height, and Color_Type.
2069If allocator is nullptr, use HeapAllocator instead.
2070
2071Returns false if allocator allocPixelRef return false.
2072
2073#Param allocator  instance of SkBitmap::Allocator instantiation ##
2074
2075#Return  true if custom allocator reports success
2076##
2077
2078#Example
2079#Height 100
2080#Description
2081HeapAllocator limits the maximum size of Bitmap to two gigabytes. Using
2082a custom allocator, this limitation may be relaxed. This example can be
2083modified to allocate an eight gigabyte Bitmap on a 64 bit platform with
2084sufficient memory.
2085##
2086#Function
2087class LargePixelRef : public SkPixelRef {
2088public:
2089    LargePixelRef(const SkImageInfo& info, char* storage, size_t rowBytes)
2090        : SkPixelRef(info.width(), info.height(), storage, rowBytes) {
2091    }
2092
2093    ~LargePixelRef() override {
2094        delete[] (char* ) this->pixels();
2095    }
2096};
2097
2098class LargeAllocator : public SkBitmap::Allocator {
2099public:
2100    bool allocPixelRef(SkBitmap* bitmap) override {
2101        const SkImageInfo& info = bitmap->info();
2102        uint64_t rowBytes = info.minRowBytes64();
2103        uint64_t size = info.height() * rowBytes;
2104        char* addr = new char[size];
2105        if (nullptr == addr) {
2106            return false;
2107        }
2108        sk_sp<SkPixelRef> pr = sk_sp<SkPixelRef>(new LargePixelRef(info, addr, rowBytes));
2109        if (!pr) {
2110            return false;
2111        }
2112        bitmap->setPixelRef(std::move(pr), 0, 0);
2113        return true;
2114    }
2115};
2116
2117##
2118
2119void draw(SkCanvas* canvas) {
2120   LargeAllocator largeAllocator;
2121   SkBitmap bitmap;
2122   int width = 100; // make this 20000
2123   int height = 100; // and this 100000 to allocate 8 gigs on a 64-bit platform
2124   bitmap.setInfo(SkImageInfo::MakeN32(width, height, kOpaque_SkAlphaType));
2125   if (bitmap.tryAllocPixels(&largeAllocator)) {
2126       bitmap.eraseColor(0xff55aa33);
2127       canvas->drawBitmap(bitmap, 0, 0);
2128   }
2129}
2130
2131##
2132
2133#SeeAlso allocPixels Allocator Pixel_Ref
2134
2135##
2136
2137# ------------------------------------------------------------------------------
2138
2139#Method void allocPixels(Allocator* allocator)
2140
2141Allocates pixel memory with allocator, and replaces existing Pixel_Ref.
2142The allocation size is determined by Image_Info width, height, and Color_Type.
2143If allocator is nullptr, use HeapAllocator instead.
2144
2145Aborts if allocator allocPixelRef return false. Abort steps may be provided by
2146the user at compile time by defining SK_ABORT.
2147
2148#Param allocator  instance of SkBitmap::Allocator instantiation ##
2149
2150#Example
2151#Height 32
2152#Function
2153class TinyAllocator : public SkBitmap::Allocator {
2154public:
2155    bool allocPixelRef(SkBitmap* bitmap) override {
2156        const SkImageInfo& info = bitmap->info();
2157        if (info.height() * info.minRowBytes() > sizeof(storage)) {
2158            return false;
2159        }
2160        sk_sp<SkPixelRef> pr = sk_sp<SkPixelRef>(
2161                new SkPixelRef(info.width(), info.height(), storage, info.minRowBytes()));
2162        bitmap->setPixelRef(std::move(pr), 0, 0);
2163        return true;
2164    }
2165
2166    char storage[16];
2167};
2168
2169##
2170
2171void draw(SkCanvas* canvas) {
2172   TinyAllocator tinyAllocator;
2173   SkBitmap bitmap;
2174   bitmap.setInfo(SkImageInfo::MakeN32(2, 2, kOpaque_SkAlphaType));
2175   if (bitmap.tryAllocPixels(&tinyAllocator)) {
2176       bitmap.eraseColor(0xff55aa33);
2177       bitmap.erase(0xffaa3355, SkIRect::MakeXYWH(1, 1, 1, 1));
2178       canvas->scale(16, 16);
2179       canvas->drawBitmap(bitmap, 0, 0);
2180   }
2181}
2182##
2183
2184#SeeAlso allocPixels Allocator Pixel_Ref
2185
2186##
2187
2188# ------------------------------------------------------------------------------
2189
2190#Method SkPixelRef* pixelRef() const
2191
2192#Line # returns Pixel_Ref, or nullptr ##
2193Returns Pixel_Ref, which contains: pixel base address; its dimensions; and
2194rowBytes, the interval from one row to the next. Does not change Pixel_Ref
2195reference count. Pixel_Ref may be shared by multiple bitmaps.
2196If Pixel_Ref has not been set, returns nullptr.
2197
2198#Return  Pixel_Ref, or nullptr ##
2199
2200#Example
2201#Image 3
2202   SkBitmap subset;
2203   source.extractSubset(&subset, SkIRect::MakeXYWH(32, 64, 128, 256));
2204   SkDebugf("src ref %c= sub ref\n", source.pixelRef() == subset.pixelRef() ? '=' : '!');
2205   SkDebugf("src pixels %c= sub pixels\n", source.getPixels() == subset.getPixels() ? '=' : '!');
2206   SkDebugf("src addr %c= sub addr\n", source.getAddr(32, 64) == subset.getAddr(0, 0) ? '=' : '!');
2207##
2208
2209#SeeAlso getPixels getAddr
2210
2211##
2212
2213# ------------------------------------------------------------------------------
2214
2215#Method SkIPoint pixelRefOrigin() const
2216
2217#Line # returns offset within Pixel_Ref ##
2218Returns origin of pixels within Pixel_Ref. Bitmap bounds is always contained
2219by Pixel_Ref bounds, which may be the same size or larger. Multiple Bitmaps
2220can share the same Pixel_Ref, where each Bitmap has different bounds.
2221
2222The returned origin added to Bitmap dimensions equals or is smaller than the
2223Pixel_Ref dimensions.
2224
2225Returns (0, 0) if Pixel_Ref is nullptr.
2226
2227#Return  pixel origin within Pixel_Ref ##
2228
2229#Example
2230#Image 3
2231   SkBitmap subset;
2232   source.extractSubset(&subset, SkIRect::MakeXYWH(32, 64, 128, 256));
2233   SkIPoint sourceOrigin = source.pixelRefOrigin();
2234   SkIPoint subsetOrigin = subset.pixelRefOrigin();
2235   SkDebugf("source origin: %d, %d\n", sourceOrigin.fX, sourceOrigin.fY);
2236   SkDebugf("subset origin: %d, %d\n", subsetOrigin.fX, subsetOrigin.fY);
2237#StdOut
2238source origin: 0, 0
2239subset origin: 32, 64
2240##
2241##
2242
2243#SeeAlso SkPixelRef getSubset setPixelRef
2244
2245##
2246
2247# ------------------------------------------------------------------------------
2248
2249#Method void setPixelRef(sk_sp<SkPixelRef> pixelRef, int dx, int dy)
2250
2251#Line # sets Pixel_Ref and offset ##
2252Replaces pixelRef and origin in Bitmap.  dx and dy specify the offset
2253within the Pixel_Ref pixels for the top-left corner of the bitmap.
2254
2255Asserts in debug builds if dx or dy are out of range. Pins dx and dy
2256to legal range in release builds.
2257
2258The caller is responsible for ensuring that the pixels match the
2259Color_Type and Alpha_Type in Image_Info.
2260
2261#Param pixelRef  Pixel_Ref describing pixel address and rowBytes ##
2262#Param dx   column offset in Pixel_Ref for bitmap origin ##
2263#Param dy   row offset in Pixel_Ref for bitmap origin ##
2264
2265#Example
2266#Height 140
2267#Image 5
2268#Description
2269Treating 32 bit data as 8 bit data is unlikely to produce useful results.
2270##
2271    SkBitmap bitmap;
2272    bitmap.setInfo(SkImageInfo::Make(source.width() - 5, source.height() - 5,
2273                   kGray_8_SkColorType, kOpaque_SkAlphaType), source.rowBytes());
2274    bitmap.setPixelRef(sk_ref_sp(source.pixelRef()), 5, 5);
2275    canvas->drawBitmap(bitmap, 10, 10);
2276##
2277
2278#SeeAlso setInfo
2279
2280##
2281
2282# ------------------------------------------------------------------------------
2283
2284#Method bool readyToDraw() const
2285
2286#Line # returns true if address of pixels is not nullptr ##
2287Returns true if Bitmap is can be drawn.
2288
2289#Return  true if getPixels() is not nullptr ##
2290
2291#Example
2292#Image 5
2293#Height 160
2294    if (source.readyToDraw()) {
2295        canvas->drawBitmap(source, 10, 10);
2296    }
2297##
2298
2299#SeeAlso getPixels drawsNothing
2300
2301##
2302
2303# ------------------------------------------------------------------------------
2304
2305#Method uint32_t getGenerationID() const
2306
2307#Line # returns unique ID ##
2308Returns a unique value corresponding to the pixels in Pixel_Ref.
2309Returns a different value after notifyPixelsChanged has been called.
2310Returns zero if Pixel_Ref is nullptr.
2311
2312Determines if pixels have changed since last examined.
2313
2314#Return unique value for pixels in Pixel_Ref ##
2315
2316#Example
2317    SkBitmap bitmap;
2318    SkDebugf("empty id %u\n", bitmap.getGenerationID());
2319    bitmap.allocPixels(SkImageInfo::MakeN32(64, 64, kOpaque_SkAlphaType));
2320    SkDebugf("alloc id %u\n", bitmap.getGenerationID());
2321    bitmap.eraseColor(SK_ColorRED);
2322    SkDebugf("erase id %u\n", bitmap.getGenerationID());
2323#StdOut
2324#Volatile
2325empty id 0
2326alloc id 4
2327erase id 6
2328##
2329##
2330
2331#SeeAlso notifyPixelsChanged Pixel_Ref
2332
2333##
2334
2335# ------------------------------------------------------------------------------
2336
2337#Method void notifyPixelsChanged() const
2338
2339#Line # marks pixels as changed, altering the unique ID ##
2340Marks that pixels in Pixel_Ref have changed. Subsequent calls to
2341getGenerationID() return a different value.
2342
2343#Example
2344#Height 20
2345    SkBitmap bitmap;
2346    bitmap.setInfo(SkImageInfo::Make(1, 1, kRGBA_8888_SkColorType, kOpaque_SkAlphaType));
2347    bitmap.allocPixels();
2348    bitmap.eraseColor(SK_ColorRED);
2349    canvas->scale(16, 16);
2350    canvas->drawBitmap(bitmap, 0, 0);
2351    *(SkPMColor*) bitmap.getPixels() = SkPreMultiplyColor(SK_ColorBLUE);
2352    canvas->drawBitmap(bitmap, 2, 0);
2353    bitmap.notifyPixelsChanged();
2354    *(SkPMColor*) bitmap.getPixels() = SkPreMultiplyColor(SK_ColorGREEN);
2355    canvas->drawBitmap(bitmap, 4, 0);
2356##
2357
2358#SeeAlso getGenerationID isVolatile Pixel_Ref
2359
2360##
2361
2362# ------------------------------------------------------------------------------
2363
2364#Method void eraseColor(SkColor c) const
2365
2366#Line # writes Color to pixels ##
2367Replaces pixel values with c. All pixels contained by bounds() are affected.
2368If the colorType is kGray_8_SkColorType or k565_SkColorType, then Color_Alpha
2369is ignored; Color_RGB is treated as opaque. If colorType is kAlpha_8_SkColorType,
2370then Color_RGB is ignored.
2371
2372#Param c  Unpremultiplied Color ##
2373
2374#Example
2375#Height 20
2376    SkBitmap bitmap;
2377    bitmap.allocPixels(SkImageInfo::MakeN32(1, 1, kOpaque_SkAlphaType));
2378    bitmap.eraseColor(SK_ColorRED);
2379    canvas->scale(16, 16);
2380    canvas->drawBitmap(bitmap, 0, 0);
2381##
2382
2383#SeeAlso eraseARGB erase
2384
2385##
2386
2387# ------------------------------------------------------------------------------
2388
2389#Method void eraseARGB(U8CPU a, U8CPU r, U8CPU g, U8CPU b) const
2390
2391#Line # writes Color to pixels ##
2392Replaces pixel values with Unpremultiplied Color built from a, r, g, and b.
2393All pixels contained by bounds() are affected.
2394If the colorType is kGray_8_SkColorType or k565_SkColorType, then a
2395is ignored; r, g, and b are treated as opaque. If colorType is kAlpha_8_SkColorType,
2396then r, g, and b are ignored.
2397
2398#Param a    amount of Color_Alpha, from fully transparent (0) to fully opaque (255) ##
2399#Param r    amount of Color_RGB_Red, from no red (0) to full red (255) ##
2400#Param g    amount of Color_RGB_Green, from no green (0) to full green (255) ##
2401#Param b    amount of Color_RGB_Blue, from no blue (0) to full blue (255) ##
2402
2403#Example
2404#Height 80
2405    SkBitmap bitmap;
2406    bitmap.allocPixels(SkImageInfo::MakeN32(1, 1, kPremul_SkAlphaType));
2407    bitmap.eraseARGB(0x7f, 0xff, 0x7f, 0x3f);
2408    canvas->scale(50, 50);
2409    canvas->drawBitmap(bitmap, 0, 0);
2410    canvas->drawBitmap(bitmap, .5f, .5f);
2411##
2412
2413#SeeAlso eraseColor erase
2414
2415##
2416
2417# ------------------------------------------------------------------------------
2418
2419#Method void eraseRGB(U8CPU r, U8CPU g, U8CPU b) const
2420
2421#Line # deprecated ##
2422Deprecated. Use eraseARGB or eraseColor.
2423
2424#Param r    amount of red ##
2425#Param g    amount of green ##
2426#Param b    amount of blue ##
2427
2428#NoExample
2429##
2430
2431#SeeAlso eraseColor eraseARGB erase
2432
2433##
2434
2435# ------------------------------------------------------------------------------
2436
2437#Method void erase(SkColor c, const SkIRect& area) const
2438
2439#Line # writes Color to rectangle of pixels ##
2440Replaces pixel values inside area with c. If area does not intersect bounds(),
2441call has no effect.
2442
2443If the colorType is kGray_8_SkColorType or k565_SkColorType, then Color_Alpha
2444is ignored; Color_RGB is treated as opaque. If colorType is kAlpha_8_SkColorType,
2445then Color_RGB is ignored.
2446
2447#Param c  Unpremultiplied Color ##
2448#Param area  rectangle to fill ##
2449
2450#Example
2451#Height 70
2452    SkBitmap bitmap;
2453    bitmap.allocPixels(SkImageInfo::MakeN32(2, 2, kPremul_SkAlphaType));
2454    bitmap.erase(0x7fff7f3f, SkIRect::MakeWH(1, 1));
2455    bitmap.erase(0x7f7f3fff, SkIRect::MakeXYWH(0, 1, 1, 1));
2456    bitmap.erase(0x7f3fff7f, SkIRect::MakeXYWH(1, 0, 1, 1));
2457    bitmap.erase(0x7f1fbf5f, SkIRect::MakeXYWH(1, 1, 1, 1));
2458    canvas->scale(25, 25);
2459    canvas->drawBitmap(bitmap, 0, 0);
2460    canvas->drawBitmap(bitmap, .5f, .5f);
2461
2462##
2463
2464#SeeAlso eraseColor eraseARGB eraseRGB SkCanvas::drawRect
2465
2466##
2467
2468# ------------------------------------------------------------------------------
2469
2470#Method void eraseArea(const SkIRect& area, SkColor c) const
2471
2472#Line # deprecated ##
2473Legacy call to be deprecated.
2474
2475#Deprecated
2476##
2477
2478##
2479
2480# ------------------------------------------------------------------------------
2481
2482#Method SkColor getColor(int x, int y) const
2483
2484#Line # returns one pixel as Unpremultiplied Color ##
2485Returns pixel at (x, y) as Unpremultiplied Color.
2486Returns black with Alpha if Color_Type is kAlpha_8_SkColorType.
2487
2488Input is not validated: out of bounds values of x or y trigger an assert() if
2489built with SK_DEBUG defined; and returns undefined values or may crash if
2490SK_RELEASE is defined. Fails if Color_Type is kUnknown_SkColorType or
2491pixel address is nullptr.
2492
2493Color_Space in Image_Info is ignored. Some Color precision may be lost in the
2494conversion to Unpremultiplied Color; original pixel data may have additional
2495precision.
2496
2497#Param x  column index, zero or greater, and less than width() ##
2498#Param y  row index, zero or greater, and less than height() ##
2499
2500#Return  pixel converted to Unpremultiplied Color ##
2501
2502#Example
2503    const int w = 4;
2504    const int h = 4;
2505    SkColor colors[][w] = {
2506        0x00000000, 0x2a0e002a, 0x55380055, 0x7f7f007f,
2507        0x2a000e2a, 0x551c1c55, 0x7f542a7f, 0xaaaa38aa,
2508        0x55003855, 0x7f2a547f, 0xaa7171aa, 0xd4d48dd4,
2509        0x7f007f7f, 0xaa38aaaa, 0xd48dd4d4, 0xffffffff,
2510    };
2511    SkDebugf("Premultiplied:\n");
2512    for (int y = 0; y < h; ++y) {
2513        SkDebugf("(0, %d) ", y);
2514        for (int x = 0; x < w; ++x) {
2515            SkDebugf("0x%08x%c", colors[y][x], x == w - 1 ? '\n' : ' ');
2516        }
2517    }
2518    SkPixmap pixmap(SkImageInfo::MakeN32(w, h, kPremul_SkAlphaType), colors, w * 4);
2519    SkBitmap bitmap;
2520    bitmap.installPixels(pixmap);
2521    SkDebugf("Unpremultiplied:\n");
2522    for (int y = 0; y < h; ++y) {
2523        SkDebugf("(0, %d) ", y);
2524        for (int x = 0; x < w; ++x) {
2525            SkDebugf("0x%08x%c", bitmap.getColor(x, y), x == w - 1 ? '\n' : ' ');
2526        }
2527    }
2528#StdOut
2529Premultiplied:
2530(0, 0) 0x00000000 0x2a0e002a 0x55380055 0x7f7f007f
2531(0, 1) 0x2a000e2a 0x551c1c55 0x7f542a7f 0xaaaa38aa
2532(0, 2) 0x55003855 0x7f2a547f 0xaa7171aa 0xd4d48dd4
2533(0, 3) 0x7f007f7f 0xaa38aaaa 0xd48dd4d4 0xffffffff
2534Unpremultiplied:
2535(0, 0) 0x00000000 0x2a5500ff 0x55a800ff 0x7fff00ff
2536(0, 1) 0x2a0055ff 0x555454ff 0x7fa954ff 0xaaff54ff
2537(0, 2) 0x5500a8ff 0x7f54a9ff 0xaaaaaaff 0xd4ffaaff
2538(0, 3) 0x7f00ffff 0xaa54ffff 0xd4aaffff 0xffffffff
2539##
2540##
2541
2542#SeeAlso getAddr readPixels
2543
2544##
2545
2546# ------------------------------------------------------------------------------
2547
2548#Method void* getAddr(int x, int y) const
2549
2550#Line # returns readable pixel address as void pointer ##
2551Returns pixel address at (x, y).
2552
2553Input is not validated: out of bounds values of x or y, or kUnknown_SkColorType,
2554trigger an assert() if built with SK_DEBUG defined. Returns nullptr if
2555Color_Type is kUnknown_SkColorType, or Pixel_Ref is nullptr.
2556
2557Performs a lookup of pixel size; for better performance, call
2558one of: getAddr8, getAddr16, or getAddr32.
2559
2560#Param x  column index, zero or greater, and less than width() ##
2561#Param y  row index, zero or greater, and less than height() ##
2562
2563#Return  generic pointer to pixel ##
2564
2565#Example
2566#Image 3
2567    char* row0 = (char* ) source.getAddr(0, 0);
2568    char* row1 = (char* ) source.getAddr(0, 1);
2569    SkDebugf("addr interval %c= rowBytes\n", row1 - row0 == source.rowBytes() ? '=' : '!');
2570#StdOut
2571addr interval == rowBytes
2572##
2573##
2574
2575#SeeAlso getAddr8 getAddr16 getAddr32 readPixels SkPixmap::addr
2576
2577##
2578
2579# ------------------------------------------------------------------------------
2580
2581#Method inline uint32_t* getAddr32(int x, int y) const
2582
2583#Line # returns readable pixel address as 32-bit pointer ##
2584Returns address at (x, y).
2585
2586Input is not validated. Triggers an assert() if built with SK_DEBUG defined and:
2587#List
2588# Pixel_Ref is nullptr ##
2589# bytesPerPixel() is not four ##
2590# x is negative, or not less than width() ##
2591# y is negative, or not less than height() ##
2592##
2593
2594#Param x  column index, zero or greater, and less than width() ##
2595#Param y  row index, zero or greater, and less than height() ##
2596
2597#Return  unsigned 32-bit pointer to pixel at (x, y) ##
2598
2599#Example
2600#Image 3
2601    uint32_t* row0 = source.getAddr32(0, 0);
2602    uint32_t* row1 = source.getAddr32(0, 1);
2603    size_t interval = (row1 - row0) * source.bytesPerPixel();
2604    SkDebugf("addr interval %c= rowBytes\n", interval == source.rowBytes() ? '=' : '!');
2605#StdOut
2606addr interval == rowBytes
2607##
2608##
2609
2610#SeeAlso getAddr8 getAddr16 getAddr readPixels SkPixmap::addr32
2611
2612##
2613
2614# ------------------------------------------------------------------------------
2615
2616#Method inline uint16_t* getAddr16(int x, int y) const
2617
2618#Line # returns readable pixel address as 16-bit pointer ##
2619Returns address at (x, y).
2620
2621Input is not validated. Triggers an assert() if built with SK_DEBUG defined and:
2622#List
2623# Pixel_Ref is nullptr ##
2624# bytesPerPixel() is not two ##
2625# x is negative, or not less than width() ##
2626# y is negative, or not less than height() ##
2627##
2628
2629#Param x  column index, zero or greater, and less than width() ##
2630#Param y  row index, zero or greater, and less than height() ##
2631
2632#Return  unsigned 16-bit pointer to pixel at (x, y)##
2633
2634#Example
2635#Image 3
2636    SkBitmap bitmap16;
2637    SkImageInfo dstInfo = SkImageInfo::Make(source.width(), source.height(), kARGB_4444_SkColorType,
2638                     kPremul_SkAlphaType);
2639    bitmap16.allocPixels(dstInfo);
2640    if (source.readPixels(dstInfo, bitmap16.getPixels(), bitmap16.rowBytes(), 0, 0)) {
2641        uint16_t* row0 = bitmap16.getAddr16(0, 0);
2642        uint16_t* row1 = bitmap16.getAddr16(0, 1);
2643        size_t interval = (row1 - row0) * bitmap16.bytesPerPixel();
2644        SkDebugf("addr interval %c= rowBytes\n", interval == bitmap16.rowBytes() ? '=' : '!');
2645    }
2646#StdOut
2647addr interval == rowBytes
2648##
2649##
2650
2651#SeeAlso getAddr8 getAddr getAddr32 readPixels SkPixmap::addr16
2652
2653##
2654
2655# ------------------------------------------------------------------------------
2656
2657#Method inline uint8_t* getAddr8(int x, int y) const
2658
2659#Line # returns readable pixel address as 8-bit pointer ##
2660Returns address at (x, y).
2661
2662Input is not validated. Triggers an assert() if built with SK_DEBUG defined and:
2663#List
2664# Pixel_Ref is nullptr ##
2665# bytesPerPixel() is not one ##
2666# x is negative, or not less than width() ##
2667# y is negative, or not less than height() ##
2668##
2669
2670#Param x  column index, zero or greater, and less than width() ##
2671#Param y  row index, zero or greater, and less than height() ##
2672
2673#Return unsigned 8-bit pointer to pixel at (x, y) ##
2674
2675#Example
2676   SkBitmap bitmap;
2677   const int width = 8;
2678   const int height = 8;
2679   uint8_t pixels[height][width];
2680   SkImageInfo info = SkImageInfo::Make(width, height, kGray_8_SkColorType, kOpaque_SkAlphaType);
2681   if (bitmap.installPixels(info, pixels, info.minRowBytes())) {
2682       SkDebugf("&pixels[4][2] %c= bitmap.getAddr8(2, 4)\n",
2683                 &pixels[4][2]  == bitmap.getAddr8(2, 4) ? '=' : '!');
2684   }
2685#StdOut
2686&pixels[4][2] == bitmap.getAddr8(2, 4)
2687##
2688##
2689
2690#SeeAlso getAddr getAddr16 getAddr32 readPixels SkPixmap::addr8
2691
2692##
2693
2694# ------------------------------------------------------------------------------
2695
2696#Method bool extractSubset(SkBitmap* dst, const SkIRect& subset) const
2697
2698#Line # creates Bitmap, sharing pixels if possible ##
2699Shares Pixel_Ref with dst. Pixels are not copied; Bitmap and dst point
2700to the same pixels; dst bounds() are set to the intersection of subset
2701and the original bounds().
2702
2703subset may be larger than bounds(). Any area outside of bounds() is ignored.
2704
2705Any contents of dst are discarded. isVolatile setting is copied to dst.
2706dst is set to colorType, alphaType, and colorSpace.
2707
2708Return false if:
2709#List
2710# dst is nullptr ##
2711# Pixel_Ref is nullptr ##
2712# subset does not intersect bounds() ##
2713##
2714
2715
2716#Param dst  Bitmap set to subset ##
2717#Param subset  rectangle of pixels to reference ##
2718
2719#Return  true if dst is replaced by subset
2720##
2721
2722#Example
2723#Image 3
2724    SkIRect bounds, s;
2725    source.getBounds(&bounds);
2726    SkDebugf("bounds: %d, %d, %d, %d\n", bounds.fLeft, bounds.fTop, bounds.fRight, bounds.fBottom);
2727    SkBitmap subset;
2728    for (int left: { -100, 0, 100, 1000 } ) {
2729         for (int right: { 0, 100, 1000 } ) {
2730             SkIRect b = SkIRect::MakeLTRB(left, 100, right, 200);
2731             bool success = source.extractSubset(&subset, b);
2732             SkDebugf("subset: %4d, %4d, %4d, %4d  ", b.fLeft, b.fTop, b.fRight, b.fBottom);
2733             SkDebugf("success; %s", success ? "true" : "false");
2734             if (success) {
2735                 subset.getBounds(&s);
2736                 SkDebugf("  subset: %d, %d, %d, %d", s.fLeft, s.fTop, s.fRight, s.fBottom);
2737             }
2738             SkDebugf("\n");
2739         }
2740    }
2741#StdOut
2742bounds: 0, 0, 512, 512
2743subset: -100,  100,    0,  200  success; false
2744subset: -100,  100,  100,  200  success; true  subset: 0, 0, 100, 100
2745subset: -100,  100, 1000,  200  success; true  subset: 0, 0, 512, 100
2746subset:    0,  100,    0,  200  success; false
2747subset:    0,  100,  100,  200  success; true  subset: 0, 0, 100, 100
2748subset:    0,  100, 1000,  200  success; true  subset: 0, 0, 512, 100
2749subset:  100,  100,    0,  200  success; false
2750subset:  100,  100,  100,  200  success; false
2751subset:  100,  100, 1000,  200  success; true  subset: 0, 0, 412, 100
2752subset: 1000,  100,    0,  200  success; false
2753subset: 1000,  100,  100,  200  success; false
2754subset: 1000,  100, 1000,  200  success; false
2755##
2756##
2757
2758#SeeAlso readPixels writePixels SkCanvas::drawBitmap
2759
2760##
2761
2762# ------------------------------------------------------------------------------
2763
2764#Method bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes,
2765                    int srcX, int srcY, SkTransferFunctionBehavior behavior) const
2766#Line # copies and converts pixels ##
2767
2768Copies Rect of pixels from Bitmap pixels to dstPixels. Copy starts at (srcX, srcY),
2769and does not exceed Bitmap (width(), height()).
2770
2771dstInfo specifies width, height, Color_Type, Alpha_Type, and
2772Color_Space of destination. dstRowBytes specifics the gap from one destination
2773row to the next. Returns true if pixels are copied. Returns false if:
2774#List
2775# dstInfo.addr() equals nullptr ##
2776# dstRowBytes is less than dstInfo.minRowBytes ##
2777# Pixel_Ref is nullptr ##
2778##
2779
2780Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
2781kGray_8_SkColorType, or kAlpha_8_SkColorType; dstInfo.colorType must match.
2782If Bitmap colorType is kGray_8_SkColorType, dstInfo.colorSpace must match.
2783If Bitmap alphaType is kOpaque_SkAlphaType, dstInfo.alphaType must
2784match. If Bitmap colorSpace is nullptr, dstInfo.colorSpace must match. Returns
2785false if pixel conversion is not possible.
2786
2787srcX and srcY may be negative to copy only top or left of source. Returns
2788false if width() or height() is zero or negative.
2789Returns false if
2790#Formula
2791abs(srcX) >= Bitmap width()
2792##
2793, or if
2794#Formula
2795abs(srcY) >= Bitmap height()
2796##
2797.
2798
2799If behavior is SkTransferFunctionBehavior::kRespect: converts source
2800pixels to a linear space before converting to dstInfo.
2801If behavior is SkTransferFunctionBehavior::kIgnore: source
2802pixels are treated as if they are linear, regardless of how they are encoded.
2803
2804#Param dstInfo  destination width, height, Color_Type, Alpha_Type, Color_Space ##
2805#Param dstPixels  destination pixel storage ##
2806#Param dstRowBytes  destination row length ##
2807#Param srcX  column index whose absolute value is less than width() ##
2808#Param srcY  row index whose absolute value is less than height() ##
2809#Param behavior  one of: SkTransferFunctionBehavior::kRespect,
2810                         SkTransferFunctionBehavior::kIgnore
2811##
2812
2813#Return  true if pixels are copied to dstPixels ##
2814
2815#Example
2816#Height 64
2817void draw(SkCanvas* canvas) {
2818    const int width = 256;
2819    const int height = 32;
2820    std::vector<int32_t> dstPixels;
2821    dstPixels.resize(height * width * 4);
2822    SkImageInfo info = SkImageInfo::MakeN32Premul(width, height);
2823    SkColor  gradColors[] = { 0xFFAA3300, 0x7F881122 };
2824    SkPoint  gradPoints[] = { { 0, 0 }, { width, 0 } };
2825    SkPaint gradPaint;
2826    gradPaint.setShader(SkGradientShader::MakeLinear(gradPoints, gradColors, nullptr,
2827                    SK_ARRAY_COUNT(gradColors), SkShader::kClamp_TileMode));
2828    for (auto behavior : { SkTransferFunctionBehavior::kRespect,
2829                           SkTransferFunctionBehavior::kIgnore} ) {
2830        SkBitmap bitmap;
2831        bitmap.allocPixels(info);
2832        SkCanvas srcCanvas(bitmap);
2833        srcCanvas.drawRect(SkRect::MakeWH(width, height), gradPaint);
2834        if (bitmap.readPixels(info, &dstPixels.front(), width * 4, 0, 0, behavior)) {
2835            SkPixmap dstPixmap(info, &dstPixels.front(), width * 4);
2836            bitmap.installPixels(dstPixmap);
2837            canvas->drawBitmap(bitmap, 0, 0);
2838        }
2839        canvas->translate(0, height);
2840    }
2841}
2842##
2843
2844#SeeAlso writePixels SkPixmap::readPixels SkCanvas::readPixels SkImage::readPixels SkSurface::readPixels
2845
2846##
2847
2848# ------------------------------------------------------------------------------
2849
2850#Method bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes,
2851                    int srcX, int srcY) const
2852
2853Copies a Rect of pixels from Bitmap to dstPixels. Copy starts at (srcX, srcY),
2854and does not exceed Bitmap (width(), height()).
2855
2856dstInfo specifies width, height, Color_Type, Alpha_Type, and Color_Space of
2857destination. dstRowBytes specifics the gap from one destination row to the next.
2858Returns true if pixels are copied. Returns false if:
2859#List
2860# dstInfo.addr() equals nullptr ##
2861# dstRowBytes is less than dstInfo.minRowBytes ##
2862# Pixel_Ref is nullptr ##
2863##
2864
2865Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
2866kGray_8_SkColorType, or kAlpha_8_SkColorType; dstInfo.colorType must match.
2867If Bitmap colorType is kGray_8_SkColorType, dstInfo.colorSpace must match.
2868If Bitmap alphaType is kOpaque_SkAlphaType, dstInfo.alphaType must
2869match. If Bitmap colorSpace is nullptr, dstInfo.colorSpace must match. Returns
2870false if pixel conversion is not possible.
2871
2872srcX and srcY may be negative to copy only top or left of source. Returns
2873false if width() or height() is zero or negative.
2874Returns false if
2875#Formula
2876abs(srcX) >= Bitmap width()
2877##
2878, or if
2879#Formula
2880abs(srcY) >= Bitmap height()
2881##
2882.
2883
2884#Param dstInfo  destination width, height, Color_Type, Alpha_Type, Color_Space ##
2885#Param dstPixels  destination pixel storage ##
2886#Param dstRowBytes  destination row length ##
2887#Param srcX  column index whose absolute value is less than width() ##
2888#Param srcY  row index whose absolute value is less than height() ##
2889
2890#Return  true if pixels are copied to dstPixels ##
2891
2892#Example
2893#Height 128
2894#Description
2895Transferring the gradient from 8 bits per component to 4 bits per component
2896creates visible banding.
2897##
2898    const int width = 256;
2899    const int height = 64;
2900    SkImageInfo srcInfo = SkImageInfo::MakeN32Premul(width, height);
2901    SkColor  gradColors[] = { 0xFFAA3300, 0x7F881122 };
2902    SkPoint  gradPoints[] = { { 0, 0 }, { 256, 0 } };
2903    SkPaint paint;
2904    paint.setShader(SkGradientShader::MakeLinear(gradPoints, gradColors, nullptr,
2905                    SK_ARRAY_COUNT(gradColors), SkShader::kClamp_TileMode));
2906    SkBitmap bitmap;
2907    bitmap.allocPixels(srcInfo);
2908    SkCanvas srcCanvas(bitmap);
2909    srcCanvas.drawRect(SkRect::MakeWH(width, height), paint);
2910    canvas->drawBitmap(bitmap, 0, 0);
2911    SkImageInfo dstInfo = srcInfo.makeColorType(kARGB_4444_SkColorType);
2912    std::vector<int16_t> dstPixels;
2913    dstPixels.resize(height * width);
2914    bitmap.readPixels(dstInfo, &dstPixels.front(), width * 2, 0, 0);
2915    SkPixmap dstPixmap(dstInfo, &dstPixels.front(), width * 2);
2916    bitmap.installPixels(dstPixmap);
2917    canvas->drawBitmap(bitmap, 0, 64);
2918##
2919
2920#SeeAlso writePixels SkPixmap::readPixels SkCanvas::readPixels SkImage::readPixels SkSurface::readPixels
2921
2922##
2923
2924# ------------------------------------------------------------------------------
2925
2926#Method bool readPixels(const SkPixmap& dst, int srcX, int srcY) const
2927
2928Copies a Rect of pixels from Bitmap to dst. Copy starts at (srcX, srcY), and
2929does not exceed Bitmap (width(), height()).
2930
2931dst specifies width, height, Color_Type, Alpha_Type, Color_Space, pixel storage,
2932and row bytes of destination. dst.rowBytes specifics the gap from one destination
2933row to the next. Returns true if pixels are copied. Returns false if:
2934#List
2935# dst pixel storage equals nullptr ##
2936# dst.rowBytes is less than SkImageInfo::minRowBytes ##
2937# Pixel_Ref is nullptr ##
2938##
2939
2940Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
2941kGray_8_SkColorType, or kAlpha_8_SkColorType; dst Color_Type must match.
2942If Bitmap colorType is kGray_8_SkColorType, dst Color_Space must match.
2943If Bitmap alphaType is kOpaque_SkAlphaType, dst Alpha_Type must
2944match. If Bitmap colorSpace is nullptr, dst Color_Space must match. Returns
2945false if pixel conversion is not possible.
2946
2947srcX and srcY may be negative to copy only top or left of source. Returns
2948false if width() or height() is zero or negative.
2949Returns false if
2950#Formula
2951abs(srcX) >= Bitmap width()
2952##
2953, or if
2954#Formula
2955abs(srcY) >= Bitmap height()
2956##
2957.
2958
2959#Param dst  destination Pixmap: Image_Info, pixels, row bytes ##
2960#Param srcX  column index whose absolute value is less than width() ##
2961#Param srcY  row index whose absolute value is less than height() ##
2962
2963#Return  true if pixels are copied to dst ##
2964
2965#Example
2966#Image 3
2967    std::vector<int32_t> srcPixels;
2968    srcPixels.resize(source.height() * source.rowBytes());
2969    for (int y = 0; y < 4; ++y) {
2970        for (int x = 0; x < 4; ++x) {
2971            SkPixmap pixmap(SkImageInfo::MakeN32Premul(source.width() / 4, source.height() / 4),
2972                    &srcPixels.front() + x * source.height() * source.width() / 4 +
2973                    y * source.width() / 4, source.rowBytes());
2974            source.readPixels(pixmap, x * source.width() / 4, y * source.height() / 4);
2975        }
2976    }
2977    canvas->scale(.5f, .5f);
2978    SkBitmap bitmap;
2979    bitmap.installPixels(SkImageInfo::MakeN32Premul(source.width(), source.height()),
2980                             &srcPixels.front(), source.rowBytes());
2981    canvas->drawBitmap(bitmap, 0, 0);
2982##
2983
2984#SeeAlso writePixels SkPixmap::readPixels SkCanvas::readPixels SkImage::readPixels SkSurface::readPixels
2985
2986##
2987
2988# ------------------------------------------------------------------------------
2989
2990#Method bool readPixels(const SkPixmap& dst) const
2991
2992Copies a Rect of pixels from Bitmap to dst. Copy starts at (0, 0), and
2993does not exceed Bitmap (width(), height()).
2994
2995dst specifies width, height, Color_Type, Alpha_Type, Color_Space, pixel storage,
2996and row bytes of destination. dst.rowBytes specifics the gap from one destination
2997row to the next. Returns true if pixels are copied. Returns false if:
2998#List
2999# dst pixel storage equals nullptr ##
3000# dst.rowBytes is less than SkImageInfo::minRowBytes ##
3001# Pixel_Ref is nullptr ##
3002##
3003
3004Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
3005kGray_8_SkColorType, or kAlpha_8_SkColorType; dst Color_Type must match.
3006If Bitmap colorType is kGray_8_SkColorType, dst Color_Space must match.
3007If Bitmap alphaType is kOpaque_SkAlphaType, dst Alpha_Type must
3008match. If Bitmap colorSpace is nullptr, dst Color_Space must match. Returns
3009false if pixel conversion is not possible.
3010
3011#Param dst  destination Pixmap: Image_Info, pixels, row bytes ##
3012
3013#Return  true if pixels are copied to dst ##
3014
3015#Example
3016#Height 128
3017#Image 3
3018    std::vector<int32_t> srcPixels;
3019    srcPixels.resize(source.height() * source.width() * 8);
3020    for (int i = 0;  i < 2; ++i) {
3021    SkPixmap pixmap(SkImageInfo::Make(source.width() * 2, source.height(),
3022                    i ? kRGBA_8888_SkColorType : kBGRA_8888_SkColorType, kPremul_SkAlphaType),
3023                    &srcPixels.front() + i * source.width(), source.rowBytes() * 2);
3024        source.readPixels(pixmap);
3025    }
3026    canvas->scale(.25f, .25f);
3027    SkBitmap bitmap;
3028    bitmap.installPixels(SkImageInfo::MakeN32Premul(source.width() * 2, source.height()),
3029                         &srcPixels.front(), source.rowBytes() * 2);
3030    canvas->drawBitmap(bitmap, 0, 0);
3031##
3032
3033#SeeAlso writePixels SkPixmap::readPixels SkCanvas::readPixels SkImage::readPixels SkSurface::readPixels
3034
3035##
3036
3037# ------------------------------------------------------------------------------
3038
3039#Method bool writePixels(const SkPixmap& src, int dstX, int dstY)
3040
3041#Line # copies and converts pixels ##
3042Copies a Rect of pixels from src. Copy starts at (dstX, dstY), and does not exceed
3043(src.width(), src.height()).
3044
3045src specifies width, height, Color_Type, Alpha_Type, Color_Space, pixel storage,
3046and row bytes of source. src.rowBytes specifics the gap from one source
3047row to the next. Returns true if pixels are copied. Returns false if:
3048#List
3049# src pixel storage equals nullptr ##
3050# src.rowBytes is less than SkImageInfo::minRowBytes ##
3051# Pixel_Ref is nullptr ##
3052##
3053
3054Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
3055kGray_8_SkColorType, or kAlpha_8_SkColorType; src Color_Type must match.
3056If Bitmap colorType is kGray_8_SkColorType, src Color_Space must match.
3057If Bitmap alphaType is kOpaque_SkAlphaType, src Alpha_Type must
3058match. If Bitmap colorSpace is nullptr, src Color_Space must match. Returns
3059false if pixel conversion is not possible.
3060
3061dstX and dstY may be negative to copy only top or left of source. Returns
3062false if width() or height() is zero or negative.
3063Returns false if
3064#Formula
3065abs(dstX) >= Bitmap width()
3066##
3067, or if
3068#Formula
3069abs(dstY) >= Bitmap height()
3070##
3071.
3072
3073#Param src  source Pixmap: Image_Info, pixels, row bytes ##
3074#Param dstX  column index whose absolute value is less than width() ##
3075#Param dstY  row index whose absolute value is less than height() ##
3076
3077#Return  true if src pixels are copied to Bitmap ##
3078
3079#Example
3080#Image 3
3081    std::vector<int32_t> srcPixels;
3082    int width = image->width();
3083    int height = image->height();
3084    srcPixels.resize(height * width  * 4);
3085    SkPixmap pixmap(SkImageInfo::MakeN32Premul(width, height), (const void*) &srcPixels.front(),
3086                    width * 4);
3087    image->readPixels(pixmap, 0, 0);
3088    canvas->scale(.5f, .5f);
3089    width /= 4;
3090    height /= 4;
3091    for (int y = 0; y < 4; ++y) {
3092        for (int x = 0; x < 4; ++x) {
3093            SkBitmap bitmap;
3094            bitmap.allocPixels(SkImageInfo::MakeN32Premul(width, height));
3095            bitmap.writePixels(pixmap, -y * width, -x * height);
3096            canvas->drawBitmap(bitmap, x * width, y * height);
3097        }
3098    }
3099##
3100
3101#SeeAlso readPixels
3102
3103##
3104
3105# ------------------------------------------------------------------------------
3106
3107#Method bool writePixels(const SkPixmap& src)
3108
3109Copies a Rect of pixels from src. Copy starts at (0, 0), and does not exceed
3110(src.width(), src.height()).
3111
3112src specifies width, height, Color_Type, Alpha_Type, Color_Space, pixel storage,
3113and row bytes of source. src.rowBytes specifics the gap from one source
3114row to the next. Returns true if pixels are copied. Returns false if:
3115#List
3116# src pixel storage equals nullptr ##
3117# src.rowBytes is less than SkImageInfo::minRowBytes ##
3118# Pixel_Ref is nullptr ##
3119##
3120
3121Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
3122kGray_8_SkColorType, or kAlpha_8_SkColorType; src Color_Type must match.
3123If Bitmap colorType is kGray_8_SkColorType, src Color_Space must match.
3124If Bitmap alphaType is kOpaque_SkAlphaType, src Alpha_Type must
3125match. If Bitmap colorSpace is nullptr, src Color_Space must match. Returns
3126false if pixel conversion is not possible.
3127
3128#Param src  source Pixmap: Image_Info, pixels, row bytes ##
3129
3130#Return  true if src pixels are copied to Bitmap ##
3131
3132#Example
3133#Height 80
3134    SkBitmap bitmap;
3135    bitmap.allocPixels(SkImageInfo::MakeN32Premul(2, 2));
3136    bitmap.eraseColor(SK_ColorGREEN);
3137    SkPMColor color = 0xFF5599BB;
3138    SkPixmap src(SkImageInfo::MakeN32Premul(1, 1), &color, 4);
3139    bitmap.writePixels(src);
3140    canvas->scale(40, 40);
3141    canvas->drawBitmap(bitmap, 0, 0);
3142##
3143
3144#SeeAlso readPixels
3145
3146##
3147
3148# ------------------------------------------------------------------------------
3149
3150#Method bool writePixels(const SkPixmap& src, int x, int y, SkTransferFunctionBehavior behavior)
3151
3152Copies a Rect of pixels from src. Copy starts at (0, 0), and does not exceed
3153(src.width(), src.height()).
3154
3155src specifies width, height, Color_Type, Alpha_Type, Color_Space, pixel storage,
3156and row bytes of source. src.rowBytes specifics the gap from one source
3157row to the next. Returns true if pixels are copied. Returns false if:
3158#List
3159# src pixel storage equals nullptr ##
3160# src.rowBytes is less than SkImageInfo::minRowBytes ##
3161# Pixel_Ref is nullptr ##
3162##
3163
3164Pixels are copied only if pixel conversion is possible. If Bitmap colorType is
3165kGray_8_SkColorType, or kAlpha_8_SkColorType; src Color_Type must match.
3166If Bitmap colorType is kGray_8_SkColorType, src Color_Space must match.
3167If Bitmap alphaType is kOpaque_SkAlphaType, src Alpha_Type must
3168match. If Bitmap colorSpace is nullptr, src Color_Space must match. Returns
3169false if pixel conversion is not possible. Returns false if width() or height()
3170is zero or negative.
3171
3172If behavior is SkTransferFunctionBehavior::kRespect: converts src
3173pixels to a linear space before converting to Image_Info.
3174If behavior is SkTransferFunctionBehavior::kIgnore: src
3175pixels are treated as if they are linear, regardless of how they are encoded.
3176
3177#Param src  source Pixmap: Image_Info, pixels, row bytes ##
3178#Param x  column index whose absolute value is less than width() ##
3179#Param y  row index whose absolute value is less than height() ##
3180#Param behavior  one of: SkTransferFunctionBehavior::kRespect,
3181                         SkTransferFunctionBehavior::kIgnore
3182##
3183
3184#Return  true if src pixels are copied to Bitmap ##
3185
3186#Example
3187#Height 64
3188    const int width = 256;
3189    const int height = 32;
3190    std::vector<int32_t> dstPixels;
3191    dstPixels.resize(height * width * 4);
3192    SkImageInfo info = SkImageInfo::MakeN32Premul(width, height);
3193    SkColor  gradColors[] = { 0xFFAA3300, 0x7F881122 };
3194    SkPoint  gradPoints[] = { { 0, 0 }, { width, 0 } };
3195    SkPaint gradPaint;
3196    gradPaint.setShader(SkGradientShader::MakeLinear(gradPoints, gradColors, nullptr,
3197                    SK_ARRAY_COUNT(gradColors), SkShader::kClamp_TileMode));
3198    for (auto behavior : { SkTransferFunctionBehavior::kRespect,
3199                           SkTransferFunctionBehavior::kIgnore} ) {
3200        SkPixmap dstPixmap(info, &dstPixels.front(), width * 4);
3201        SkBitmap bitmap;
3202        bitmap.installPixels(dstPixmap);
3203        SkCanvas srcCanvas(bitmap);
3204        srcCanvas.drawRect(SkRect::MakeWH(width, height), gradPaint);
3205        if (bitmap.writePixels(dstPixmap, 0, 0, behavior)) {
3206            canvas->drawBitmap(bitmap, 0, 0);
3207        }
3208        canvas->translate(0, height);
3209    }
3210##
3211
3212#SeeAlso readPixels
3213
3214##
3215
3216# ------------------------------------------------------------------------------
3217
3218#Method bool hasHardwareMipMap() const
3219
3220#Line # returns Mip_Map support present; Android only ##
3221#Private
3222Android framework only.
3223##
3224
3225#Return  true if setHasHardwareMipMap has been called with true ##
3226
3227#NoExample
3228##
3229
3230#SeeAlso setHasHardwareMipMap
3231
3232##
3233
3234# ------------------------------------------------------------------------------
3235
3236#Method void setHasHardwareMipMap(bool hasHardwareMipMap)
3237
3238#Line # sets Mip_Map support present; Android only ##
3239#Private
3240Android framework only.
3241##
3242
3243#Param hasHardwareMipMap  sets state ##
3244
3245#NoExample
3246##
3247
3248#SeeAlso hasHardwareMipMap
3249
3250##
3251
3252# ------------------------------------------------------------------------------
3253
3254#Method bool extractAlpha(SkBitmap* dst) const
3255
3256#Line # creates Bitmap containing Alpha of pixels ##
3257Sets dst to Alpha described by pixels. Returns false if dst cannot be written to
3258or dst pixels cannot be allocated.
3259
3260Uses HeapAllocator to reserve memory for dst Pixel_Ref.
3261
3262#Param dst  holds Pixel_Ref to fill with alpha layer ##
3263
3264#Return  true if Alpha layer was constructed in dst Pixel_Ref ##
3265
3266#Example
3267#Height 100
3268    SkBitmap alpha, bitmap;
3269    bitmap.allocN32Pixels(100, 100);
3270    SkCanvas offscreen(bitmap);
3271    offscreen.clear(0);
3272    SkPaint paint;
3273    paint.setAntiAlias(true);
3274    paint.setColor(SK_ColorBLUE);
3275    paint.setStyle(SkPaint::kStroke_Style);
3276    paint.setStrokeWidth(20);
3277    offscreen.drawCircle(50, 50, 39, paint);
3278    offscreen.flush();
3279    bitmap.extractAlpha(&alpha);
3280    paint.setColor(SK_ColorRED);
3281    canvas->drawBitmap(bitmap, 0, 0, &paint);
3282    canvas->drawBitmap(alpha, 100, 0, &paint);
3283##
3284
3285#SeeAlso extractSubset
3286
3287##
3288
3289# ------------------------------------------------------------------------------
3290
3291#Method bool extractAlpha(SkBitmap* dst, const SkPaint* paint,
3292                      SkIPoint* offset) const
3293
3294Sets dst to Alpha described by pixels. Returns false if dst cannot be written to
3295or dst pixels cannot be allocated.
3296
3297If paint is not nullptr and contains Mask_Filter, SkMaskFilter::filterMask
3298generates Mask_Alpha from Bitmap. Uses HeapAllocator to reserve memory for dst
3299Pixel_Ref. Sets offset to top-left position for dst for alignment with Bitmap;
3300(0, 0) unless SkMaskFilter generates mask.
3301
3302#Param dst  holds Pixel_Ref to fill with alpha layer ##
3303#Param paint  holds optional Mask_Filter; may be nullptr ##
3304#Param offset  top-left position for dst; may be nullptr ##
3305
3306#Return  true if Alpha layer was constructed in dst Pixel_Ref ##
3307
3308#Bug 7103 ##
3309#Example
3310#Height 160
3311    SkBitmap alpha, bitmap;
3312    bitmap.allocN32Pixels(100, 100);
3313    SkCanvas offscreen(bitmap);
3314    offscreen.clear(0);
3315    SkPaint paint;
3316    paint.setAntiAlias(true);
3317    paint.setColor(SK_ColorBLUE);
3318    paint.setStyle(SkPaint::kStroke_Style);
3319    paint.setStrokeWidth(20);
3320    offscreen.drawCircle(50, 50, 39, paint);
3321    offscreen.flush();
3322    const SkScalar kBlurSigma = SkBlurMaskFilter::ConvertRadiusToSigma(SkIntToScalar(25));
3323    paint.setMaskFilter(SkBlurMaskFilter::Make(kNormal_SkBlurStyle, kBlurSigma,
3324                                    SkBlurMaskFilter::kHighQuality_BlurFlag));
3325    SkIPoint offset;
3326    bitmap.extractAlpha(&alpha, &paint, &offset);
3327    paint.setColor(SK_ColorRED);
3328    canvas->drawBitmap(bitmap, 0, -offset.fY, &paint);
3329    canvas->drawBitmap(alpha, 100 + offset.fX, 0, &paint);
3330##
3331
3332#SeeAlso extractSubset
3333
3334##
3335
3336# ------------------------------------------------------------------------------
3337
3338#Method bool extractAlpha(SkBitmap* dst, const SkPaint* paint, Allocator* allocator,
3339                      SkIPoint* offset) const
3340
3341Sets dst to Alpha described by pixels. Returns false if dst cannot be written to
3342or dst pixels cannot be allocated.
3343
3344If paint is not nullptr and contains Mask_Filter, SkMaskFilter::filterMask
3345generates Mask_Alpha from Bitmap. allocator may reference a custom allocation
3346class or be set to nullptr to use HeapAllocator. Sets offset to top-left
3347position for dst for alignment with Bitmap; (0, 0) unless SkMaskFilter generates
3348mask.
3349
3350#Param dst  holds Pixel_Ref to fill with alpha layer ##
3351#Param paint  holds optional Mask_Filter; may be nullptr ##
3352#Param allocator   method to reserve memory for Pixel_Ref; may be nullptr ##
3353#Param offset  top-left position for dst; may be nullptr ##
3354
3355#Return  true if Alpha layer was constructed in dst Pixel_Ref ##
3356
3357#Bug 7104 ##
3358#Example
3359#Height 128
3360    SkBitmap alpha, bitmap;
3361    bitmap.allocN32Pixels(100, 100);
3362    SkCanvas offscreen(bitmap);
3363    offscreen.clear(0);
3364    SkPaint paint;
3365    paint.setAntiAlias(true);
3366    paint.setColor(SK_ColorBLUE);
3367    paint.setStyle(SkPaint::kStroke_Style);
3368    paint.setStrokeWidth(20);
3369    offscreen.drawCircle(50, 50, 39, paint);
3370    offscreen.flush();
3371    paint.setMaskFilter(SkBlurMaskFilter::Make(kOuter_SkBlurStyle, 3));
3372    SkIPoint offset;
3373    bitmap.extractAlpha(&alpha, &paint, nullptr, &offset);
3374    paint.setColor(SK_ColorRED);
3375    canvas->drawBitmap(bitmap, 0, -offset.fY, &paint);
3376    canvas->drawBitmap(alpha, 100 + offset.fX, 0, &paint);
3377##
3378
3379#SeeAlso extractSubset
3380
3381##
3382
3383# ------------------------------------------------------------------------------
3384
3385#Method bool peekPixels(SkPixmap* pixmap) const
3386
3387#Line # returns Pixmap if possible ##
3388Copies Bitmap pixel address, row bytes, and Image_Info to pixmap, if address
3389is available, and returns true. If pixel address is not available, return
3390false and leave pixmap unchanged.
3391
3392pixmap contents become invalid on any future change to Bitmap.
3393
3394#Param pixmap  storage for pixel state if pixels are readable; otherwise, ignored ##
3395
3396#Return true if Bitmap has direct access to pixels ##
3397
3398#Example
3399    SkBitmap bitmap;
3400    bitmap.allocPixels(SkImageInfo::MakeN32Premul(6, 11));
3401    SkCanvas offscreen(bitmap);
3402    offscreen.clear(SK_ColorWHITE);
3403    SkPaint paint;
3404    offscreen.drawString("?", 0, 10, paint);
3405    SkPixmap pixmap;
3406    if (bitmap.peekPixels(&pixmap)) {
3407        const SkPMColor* pixels = pixmap.addr32();
3408        SkPMColor pmWhite = pixels[0];
3409        for (int y = 0; y < bitmap.height(); ++y) {
3410            for (int x = 0; x < bitmap.width(); ++x) {
3411                SkDebugf("%c", *pixels++ == pmWhite ? '-' : 'x');
3412            }
3413            SkDebugf("\n");
3414        }
3415    }
3416    #StdOut
3417------
3418-xxx--
3419x---x-
3420----x-
3421---x--
3422--x---
3423--x---
3424------
3425--x---
3426--x---
3427------
3428    #StdOut ##
3429##
3430
3431#SeeAlso pixmap() installPixels readPixels writePixels
3432
3433##
3434
3435# ------------------------------------------------------------------------------
3436
3437#Method void validate() const;
3438
3439#Line # asserts if Bitmap is invalid (debug only) ##
3440Asserts if internal values are illegal or inconsistent. Only available if
3441SK_DEBUG is defined at compile time.
3442
3443#NoExample
3444##
3445
3446#SeeAlso SkImageInfo::validate()
3447
3448##
3449
3450# ------------------------------------------------------------------------------
3451
3452#Method void toString(SkString* str) const;
3453
3454#Line # converts Bitmap to machine readable form ##
3455#DefinedBy SK_TO_STRING_NONVIRT() ##
3456
3457#Private
3458macro expands to: void toString(SkString* str) const;
3459##
3460
3461Creates string representation of Bitmap. The representation is read by
3462internal debugging tools. The interface and implementation may be
3463suppressed by defining SK_IGNORE_TO_STRING.
3464
3465#Param str  storage for string representation ##
3466
3467#Example
3468    SkBitmap bitmap;
3469    int width = 6;
3470    int height = 11;
3471    bitmap.allocPixels(SkImageInfo::MakeN32Premul(width, height));
3472    SkString string;
3473    bitmap.toString(&string);
3474    SkString match;
3475    match.printf("(%d, %d)", width, height);
3476    int start = string.find(match.c_str());
3477    if (start >= 0) {
3478        SkString whStr(&string.c_str()[start], match.size());
3479        SkDebugf("bitmap dimensions %s\n", whStr.c_str());
3480    }
3481    #StdOut
3482    bitmap dimensions (6, 11)
3483    ##
3484##
3485
3486#SeeAlso SkPaint::toString
3487
3488##
3489
3490#Class SkBitmap ##
3491
3492#Topic Bitmap ##
3493