diff options
26 files changed, 10204 insertions, 3704 deletions
diff --git a/docs/SkBitmap_Reference.bmh b/docs/SkBitmap_Reference.bmh index 27580233da..75cd57ed99 100644 --- a/docs/SkBitmap_Reference.bmh +++ b/docs/SkBitmap_Reference.bmh @@ -89,8 +89,7 @@ is useful to position one or more Bitmaps within a shared pixel array. # bytesPerPixel # Returns number of bytes in pixel based on Color_Type. ## # colorSpace # Returns Image_Info Color_Space. ## # colorType # Returns Image_Info Color_Type. ## -# computeSafeSize64 # Returns minimum size required for pixels in 64 bits. ## -# computeSize64 # Returns conservative size required for pixels. ## +# computeByteSize # Returns size required for pixels. ## # dimensions # Returns width and height. ## # drawsNothing # Returns true if no width, no height, or no Pixel_Ref. ## # empty() # Returns true if Image_Info has zero width or height. ## @@ -98,7 +97,7 @@ is useful to position one or more Bitmaps within a shared pixel array. # eraseARGB # Writes Color to pixels. ## # eraseArea # Deprecated ## # eraseColor # Writes Color to pixels. ## -# eraseRGB # Writes opaque Color to pixels. ## +# eraseRGB # Deprecated ## # extractAlpha # Creates Bitmap containing Alpha of pixels. ## # extractSubset # Creates Bitmap, sharing pixels if possible. ## # getAddr # Returns readable pixel address as void pointer. ## @@ -109,8 +108,6 @@ is useful to position one or more Bitmaps within a shared pixel array. # getColor # Returns one pixel as Unpremultiplied Color. ## # getGenerationID # Returns unique ID. ## # getPixels # Returns address of pixels. ## -# getSafeSize # Returns minimum size required for pixels in 32 bits. ## -# getSize # Returns conservative size required for pixels in 32 bits. ## # getSubset # Returns bounds offset by origin. ## # hasHardwareMipMap # Returns Mip_Map support present; Android only. ## # height # Returns pixel row count. ## @@ -144,6 +141,7 @@ is useful to position one or more Bitmaps within a shared pixel array. # tryAllocN32Pixels # Allocates compatible Color_ARGB pixels if possible. ## # tryAllocPixels # Allocates pixels from Image_Info if possible. ## # tryAllocPixelsFlags # Allocates pixels from Image_Info with options if possible. ## +# validate() # Asserts if Bitmap is invalid (debug only). ## # width() # Returns pixel column count. ## # writePixels # Copies and converts pixels. ## #Table ## @@ -480,6 +478,7 @@ width: 56 height: 56 color: BGRA_8888 alpha: Opaque #Method int width() const Returns pixel count in each pixel row. Should be equal or less than: + #Formula rowBytes() / info().bytesPerPixel() ## @@ -1004,171 +1003,6 @@ width: 1000000 height: 1000000 computeByteSize: 4999999000000 # ------------------------------------------------------------------------------ -#Method size_t getSize() const - -Returns conservative memory required for pixel storage. -Includes unused memory on last row when rowBytesAsPixels exceeds width(). - -Does not check to see if result fits in 32 bits. Use getSize64() if the -result may exceed 32 bits. - -#Return height() times rowBytes() ## - -#Example -#Description -getSize results are not useful when width() and height() are large. -## -void draw(SkCanvas* canvas) { - SkBitmap bitmap; - for (int width : { 1, 1000, 1000000 } ) { - for (int height: { 1, 1000, 1000000 } ) { - SkImageInfo imageInfo = SkImageInfo::MakeN32(width, height, kPremul_SkAlphaType); - bitmap.setInfo(imageInfo, width * 5); - SkDebugf("width: %7d height: %7d getSize: %9zu\n", width, height, bitmap.getSize()); - } - } -} -#StdOut -width: 1 height: 1 getSize: 5 -width: 1 height: 1000 getSize: 5000 -width: 1 height: 1000000 getSize: 5000000 -width: 1000 height: 1 getSize: 5000 -width: 1000 height: 1000 getSize: 5000000 -width: 1000 height: 1000000 getSize: 705032704 -width: 1000000 height: 1 getSize: 5000000 -width: 1000000 height: 1000 getSize: 705032704 -width: 1000000 height: 1000000 getSize: 658067456 -## -## - -#SeeAlso getSafeSize computeSize64 rowBytes width() - -## - -# ------------------------------------------------------------------------------ - -#Method size_t getSafeSize() const - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when rowBytesAsPixels exceeds width(). - -Returns zero if size does not fit in 32 bits. Use computeSafeSize64 if the -result may exceed 32 bits. - -The pixel storage visible may be a subset of the Pixel_Ref. Accessing memory -beyond the result may generate an exception. - -#Return exact pixel storage size ## - -#Example -#Description -getSafeSize results are not useful when width() and height() are large. -## -void draw(SkCanvas* canvas) { - SkBitmap bitmap; - for (int width : { 1, 1000, 1000000 } ) { - for (int height: { 1, 1000, 1000000 } ) { - SkImageInfo imageInfo = SkImageInfo::MakeN32(width, height, kPremul_SkAlphaType); - bitmap.setInfo(imageInfo, width * 5); - SkDebugf("width: %7d height: %7d getSafeSize: %9zu\n", width, height, bitmap.getSafeSize()); - } - } -} -#StdOut -width: 1 height: 1 getSafeSize: 4 -width: 1 height: 1000 getSafeSize: 4999 -width: 1 height: 1000000 getSafeSize: 4999999 -width: 1000 height: 1 getSafeSize: 4000 -width: 1000 height: 1000 getSafeSize: 4999000 -width: 1000 height: 1000000 getSafeSize: 0 -width: 1000000 height: 1 getSafeSize: 4000000 -width: 1000000 height: 1000 getSafeSize: 0 -width: 1000000 height: 1000000 getSafeSize: 0 -## -## - -#SeeAlso getSize computeSafeSize64 rowBytes width() - -## - -# ------------------------------------------------------------------------------ - -#Method int64_t computeSize64() const - -Returns conservative memory required for pixel storage. -Includes unused memory on last row when rowBytesAsPixels exceeds width(). - -#Return conservative pixel storage size ## - -#Example -void draw(SkCanvas* canvas) { - SkBitmap bitmap; - for (int width : { 1, 1000, 1000000 } ) { - for (int height: { 1, 1000, 1000000 } ) { - SkImageInfo imageInfo = SkImageInfo::MakeN32(width, height, kPremul_SkAlphaType); - bitmap.setInfo(imageInfo, width * 5); - SkDebugf("width: %7d height: %7d computeSize64: %13lld\n", width, height, - bitmap.computeSize64()); - } - } -} -#StdOut -width: 1 height: 1 computeSize64: 5 -width: 1 height: 1000 computeSize64: 5000 -width: 1 height: 1000000 computeSize64: 5000000 -width: 1000 height: 1 computeSize64: 5000 -width: 1000 height: 1000 computeSize64: 5000000 -width: 1000 height: 1000000 computeSize64: 5000000000 -width: 1000000 height: 1 computeSize64: 5000000 -width: 1000000 height: 1000 computeSize64: 5000000000 -width: 1000000 height: 1000000 computeSize64: 5000000000000 -## -## - -#SeeAlso getSize computeSafeSize64 rowBytes width() - -## - -# ------------------------------------------------------------------------------ - -#Method int64_t computeSafeSize64() const - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when rowBytesAsPixels exceeds width(). - -#Return exact pixel storage size ## - -#Example -void draw(SkCanvas* canvas) { - SkBitmap bitmap; - for (int width : { 1, 1000, 1000000 } ) { - for (int height: { 1, 1000, 1000000 } ) { - SkImageInfo imageInfo = SkImageInfo::MakeN32(width, height, kPremul_SkAlphaType); - bitmap.setInfo(imageInfo, width * 5); - SkDebugf("width: %7d height: %7d computeSafeSize64: %13lld\n", width, height, - bitmap.computeSafeSize64()); - } - } -} -#StdOut -width: 1 height: 1 computeSafeSize64: 4 -width: 1 height: 1000 computeSafeSize64: 4999 -width: 1 height: 1000000 computeSafeSize64: 4999999 -width: 1000 height: 1 computeSafeSize64: 4000 -width: 1000 height: 1000 computeSafeSize64: 4999000 -width: 1000 height: 1000000 computeSafeSize64: 4999999000 -width: 1000000 height: 1 computeSafeSize64: 4000000 -width: 1000000 height: 1000 computeSafeSize64: 4999000000 -width: 1000000 height: 1000000 computeSafeSize64: 4999999000000 -## -## - -#SeeAlso getSafeSize computeSize64 rowBytes width() - -## - -# ------------------------------------------------------------------------------ - #Method bool isImmutable() const Returns true if pixels can not change. @@ -1201,9 +1035,9 @@ copy is immutable #Method void setImmutable() -Once set, pixels can not change. Any other bitmap sharing the same Pixel_Ref -are also marked as immutable. Once Pixel_Ref is marked immutable, the setting -cannot be cleared. +Sets internal flag to mark Bitmap as immutable. Once set, pixels can not change. +Any other bitmap sharing the same Pixel_Ref are also marked as immutable. +Once Pixel_Ref is marked immutable, the setting cannot be cleared. Writing to immutable Bitmap pixels triggers an assert on debug builds. @@ -2547,7 +2381,7 @@ then Color_RGB is ignored. canvas->drawBitmap(bitmap, 0, 0); ## -#SeeAlso eraseARGB eraseRGB erase +#SeeAlso eraseARGB erase ## @@ -2576,7 +2410,7 @@ then r, g, and b are ignored. canvas->drawBitmap(bitmap, .5f, .5f); ## -#SeeAlso eraseColor eraseRGB erase +#SeeAlso eraseColor erase ## @@ -2584,22 +2418,13 @@ then r, g, and b are ignored. #Method void eraseRGB(U8CPU r, U8CPU g, U8CPU b) const -Replaces pixel values with Color built from r, g, and b with Color_Alpha set -to 255. All pixels contained by bounds() are affected. -If colorType is kAlpha_8_SkColorType, all pixels are set to 255. +Deprecated. Use eraseARGB or eraseColor. -#Param r amount of Color_RGB_Red, from no red (0) to full red (255) ## -#Param g amount of Color_RGB_Green, from no green (0) to full green (255) ## -#Param b amount of Color_RGB_Blue, from no blue (0) to full blue (255) ## +#Param r amount of red ## +#Param g amount of green ## +#Param b amount of blue ## -#Example -#Height 80 - SkBitmap bitmap; - bitmap.allocPixels(SkImageInfo::MakeN32(1, 1, kPremul_SkAlphaType)); - bitmap.eraseRGB(0xff, 0x7f, 0x3f); - canvas->scale(50, 50); - canvas->drawBitmap(bitmap, 0, 0); - canvas->drawBitmap(bitmap, .5f, .5f); +#NoExample ## #SeeAlso eraseColor eraseARGB erase @@ -2950,7 +2775,8 @@ match. If this->colorSpace is nullptr, dstInfo.colorSpace must match. Returns false if pixel conversion is not possible. srcX and srcY may be negative to copy only top or left of source. Returns -false if width() or height() is zero or negative. Returns false if +false if width() or height() is zero or negative. +Returns false if #Formula abs(srcX) >= this->width() ## @@ -3034,7 +2860,8 @@ match. If this->colorSpace is nullptr, dstInfo.colorSpace must match. Returns false if pixel conversion is not possible. srcX and srcY may be negative to copy only top or left of source. Returns -false if width() or height() is zero or negative. Returns false if +false if width() or height() is zero or negative. +Returns false if #Formula abs(srcX) >= this->width() ## @@ -3108,7 +2935,8 @@ match. If this->colorSpace is nullptr, dst Color_Space must match. Returns false if pixel conversion is not possible. srcX and srcY may be negative to copy only top or left of source. Returns -false if width() or height() is zero or negative. Returns false if +false if width() or height() is zero or negative. +Returns false if #Formula abs(srcX) >= this->width() ## @@ -3220,7 +3048,8 @@ match. If this->colorSpace is nullptr, src Color_Space must match. Returns false if pixel conversion is not possible. dstX and dstY may be negative to copy only top or left of source. Returns -false if width() or height() is zero or negative. Returns false if +false if width() or height() is zero or negative. +Returns false if #Formula abs(dstX) >= this->width() ## @@ -3541,11 +3370,11 @@ mask. #Method bool peekPixels(SkPixmap* pixmap) const -If the pixels are available from this bitmap return true, and fill out the -specified pixmap (if not null). If there are no pixels, return false and -ignore the pixmap parameter. -Note: if this returns true, the results (in the pixmap) are only valid until the bitmap -is changed in any way, in which case the results are invalid. +Copies Bitmap pixel address, row bytes, and Image_Info to pixmap, if address +is available, and returns true. If pixel address is not available, return +false and leave pixmap unchanged. + +pixmap contents become invalid on any future change to Bitmap. #Param pixmap storage for pixel state if pixels are readable; otherwise, ignored ## @@ -3590,6 +3419,20 @@ is changed in any way, in which case the results are invalid. # ------------------------------------------------------------------------------ +#Method void validate() const; + +Asserts if internal values are illegal or inconsistent. Only available if +SK_DEBUG is defined at compile time. + +#NoExample +## + +#SeeAlso SkImageInfo::validate() + +## + +# ------------------------------------------------------------------------------ + #Method void toString(SkString* str) const; #DefinedBy SK_TO_STRING_NONVIRT() ## diff --git a/docs/SkCanvas_Reference.bmh b/docs/SkCanvas_Reference.bmh index 486fe46d71..3c836b41d3 100644 --- a/docs/SkCanvas_Reference.bmh +++ b/docs/SkCanvas_Reference.bmh @@ -975,14 +975,11 @@ Canvas or Surface call may invalidate the pixmap values. #Method bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes, int srcX, int srcY) -Copies rectangle of pixels from Canvas into dstPixels. Matrix and Clip are -ignored. Source rectangle corners are (srcX, srcY) and -#Formula -(this->imageInfo.width(), this->imageInfo.height()) -## -. +Copies Rect of pixels from Canvas into dstPixels. Matrix and Clip are +ignored. Source Rect corners are (srcX, srcY) and +(imageInfo().width(), imageInfo().height()). -Destination rectangle corners are (0, 0) and (bitmap.width(), bitmap.height()). +Destination Rect corners are (0, 0) and (bitmap.width(), bitmap.height()). Copies each readable pixel intersecting both rectangles, without scaling, converting to dstInfo.colorType() and dstInfo.alphaType() if required. @@ -995,7 +992,7 @@ The destination pixel storage must be allocated by the caller. Pixel values are converted only if Image_Color_Type and Image_Alpha_Type do not match. Only pixels within both source and destination rectangles -are copied. dstPixels contents outside the rectangle intersection are unchanged. +are copied. dstPixels contents outside Rect intersection are unchanged. Pass negative values for srcX or srcY to offset pixels across or down destination. @@ -1070,14 +1067,11 @@ Does not copy, and returns false if: #Method bool readPixels(const SkPixmap& pixmap, int srcX, int srcY) -Copies rectangle of pixels from Canvas into pixmap. Matrix and Clip are -ignored. Source rectangle corners are (srcX, srcY) and -#Formula -(this->imageInfo.width(), this->imageInfo.height()) -## -. +Copies Rect of pixels from Canvas into pixmap. Matrix and Clip are +ignored. Source Rect corners are (srcX, srcY) and +(imageInfo().width(), imageInfo().height()). -Destination rectangle corners are (0, 0) and (bitmap.width(), bitmap.height()). +Destination Rect corners are (0, 0) and (bitmap.width(), bitmap.height()). Copies each readable pixel intersecting both rectangles, without scaling, converting to pixmap.colorType() and pixmap.alphaType() if required. @@ -1089,8 +1083,8 @@ class like SkDumpCanvas. Caller must allocate pixel storage in pixmap if needed. Pixel values are converted only if Image_Color_Type and Image_Alpha_Type -do not match. Only pixels within both source and destination rectangles -are copied. pixmap pixels contents outside the rectangle intersection are unchanged. +do not match. Only pixels within both source and destination Rects +are copied. pixmap pixels contents outside Rect intersection are unchanged. Pass negative values for srcX or srcY to offset pixels across or down pixmap. @@ -1136,14 +1130,11 @@ Does not copy, and returns false if: #Method bool readPixels(const SkBitmap& bitmap, int srcX, int srcY) -Copies rectangle of pixels from Canvas into bitmap. Matrix and Clip are -ignored. Source rectangle corners are (srcX, srcY) and -#Formula -(this->imageInfo.width(), this->imageInfo.height()) -## -. +Copies Rect of pixels from Canvas into bitmap. Matrix and Clip are +ignored. Source Rect corners are (srcX, srcY) and +(imageInfo().width(), imageInfo().height()). -Destination rectangle corners are (0, 0) and (bitmap.width(), bitmap.height()). +Destination Rect corners are (0, 0) and (bitmap.width(), bitmap.height()). Copies each readable pixel intersecting both rectangles, without scaling, converting to bitmap.colorType() and bitmap.alphaType() if required. @@ -1156,7 +1147,7 @@ Caller must allocate pixel storage in bitmap if needed. Bitmap values are converted only if Image_Color_Type and Image_Alpha_Type do not match. Only pixels within both source and destination rectangles -are copied. Bitmap pixels outside the rectangle intersection are unchanged. +are copied. Bitmap pixels outside Rect intersection are unchanged. Pass negative values for srcX or srcY to offset pixels across or down bitmap. @@ -1202,24 +1193,13 @@ void draw(SkCanvas* canvas) { #Method bool writePixels(const SkImageInfo& info, const void* pixels, size_t rowBytes, int x, int y) -Copies rectangle from pixels to Canvas. Matrix and Clip are ignored. -Source rectangle corners are (0, 0) and (info.width(), info.height()). -Destination rectangle corners are (x, y) and -#Formula -(this->imageInfo.width(), this->imageInfo.height()) -## -. +Copies Rect from pixels to Canvas. Matrix and Clip are ignored. +Source Rect corners are (0, 0) and (info.width(), info.height()). +Destination Rect corners are (x, y) and +(imageInfo().width(), imageInfo().height()). Copies each readable pixel intersecting both rectangles, without scaling, -converting to -#Formula -this->imageInfo.colorType() -## -and -#Formula -this->imageInfo.alphaType() -## -if required. +converting to imageInfo().colorType() and imageInfo().alphaType() if required. Pixels are writable when Device is raster, or backed by a GPU. Pixels are not writable when SkCanvas is returned by SkDocument::beginPage, @@ -1228,7 +1208,7 @@ class like SkDumpCanvas. Pixel values are converted only if Image_Color_Type and Image_Alpha_Type do not match. Only pixels within both source and destination rectangles -are copied. Canvas pixels outside the rectangle intersection are unchanged. +are copied. Canvas pixels outside Rect intersection are unchanged. Pass negative values for x or y to offset pixels to the left or above Canvas pixels. @@ -1237,8 +1217,8 @@ Does not copy, and returns false if: #List # Source and destination rectangles do not intersect. ## -# pixels could not be converted to this->imageInfo.colorType() or -this->imageInfo.alphaType(). ## +# pixels could not be converted to this->imageInfo().colorType() or +this->imageInfo().alphaType(). ## # Canvas pixels are not writable; for instance, Canvas is document-based. ## # rowBytes is too small to contain one row of pixels. ## ## @@ -1270,25 +1250,14 @@ this->imageInfo.alphaType(). ## #Method bool writePixels(const SkBitmap& bitmap, int x, int y) -Copies rectangle from pixels to Canvas. Matrix and Clip are ignored. -Source rectangle corners are (0, 0) and (bitmap.width(), bitmap.height()). +Copies Rect from pixels to Canvas. Matrix and Clip are ignored. +Source Rect corners are (0, 0) and (bitmap.width(), bitmap.height()). -Destination rectangle corners are (x, y) and -#Formula -(this->imageInfo.width(), this->imageInfo.height()) -## -. +Destination Rect corners are (x, y) and +(imageInfo().width(), imageInfo().height()). Copies each readable pixel intersecting both rectangles, without scaling, -converting to -#Formula -this->imageInfo.colorType() -## -and -#Formula -this->imageInfo.alphaType() -## -if required. +converting to imageInfo().colorType() and imageInfo().alphaType() if required. Pixels are writable when Device is raster, or backed by a GPU. Pixels are not writable when SkCanvas is returned by SkDocument::beginPage, @@ -1297,7 +1266,7 @@ class like SkDumpCanvas. Pixel values are converted only if Image_Color_Type and Image_Alpha_Type do not match. Only pixels within both source and destination rectangles -are copied. Canvas pixels outside the rectangle intersection are unchanged. +are copied. Canvas pixels outside Rect intersection are unchanged. Pass negative values for x or y to offset pixels to the left or above Canvas pixels. @@ -1307,8 +1276,8 @@ Does not copy, and returns false if: #List # Source and destination rectangles do not intersect. ## # bitmap does not have allocated pixels. ## -# bitmap pixels could not be converted to this->imageInfo.colorType() or -this->imageInfo.alphaType(). ## +# bitmap pixels could not be converted to this->imageInfo().colorType() or +this->imageInfo().alphaType(). ## # Canvas pixels are not writable; for instance, Canvas is document based. ## # bitmap pixels are inaccessible; for instance, bitmap wraps a texture. ## ## @@ -4687,14 +4656,6 @@ void draw(SkCanvas* canvas) { # ------------------------------------------------------------------------------ #Struct Lattice - Lattice divides Bitmap or Image into a rectangular grid. - Grid entries on even columns and even rows are fixed; these entries are - always drawn at their original size if the destination is large enough. - If the destination side is too small to hold the fixed entries, all fixed - entries are proportionately scaled down to fit. - The grid entries not on even columns and rows are scaled to fit the - remaining space, if any. - #Code struct Lattice { enum Flags {... @@ -4708,6 +4669,14 @@ void draw(SkCanvas* canvas) { }; ## + Lattice divides Bitmap or Image into a rectangular grid. + Grid entries on even columns and even rows are fixed; these entries are + always drawn at their original size if the destination is large enough. + If the destination side is too small to hold the fixed entries, all fixed + entries are proportionately scaled down to fit. + The grid entries not on even columns and rows are scaled to fit the + remaining space, if any. + #Enum Flags #Code enum Flags : uint8_t { @@ -6142,8 +6111,8 @@ Restores Canvas to saved state. #Method void restore() -Restores Canvas to saved state immediately. Subsequent calls and class -destructor have no effect. +Restores Canvas to saved state immediately. Subsequent calls and +~SkAutoCanvasRestore have no effect. #Example // incomplete diff --git a/docs/SkIRect_Reference.bmh b/docs/SkIRect_Reference.bmh index d92c08715d..bdc694f8d5 100644 --- a/docs/SkIRect_Reference.bmh +++ b/docs/SkIRect_Reference.bmh @@ -1,121 +1,121 @@ -#Topic IRect -#Alias IRect_Reference - -#Struct SkIRect - -SkIRect holds four 32 bit integer coordinates describing the upper and -lower bounds of a rectangle. SkIRect may be created from outer bounds or -from position, width, and height. SkIRect describes an area; if its right -is less than or equal to its left, or if its bottom is less than or equal to -its top, it is considered empty. - -#Topic Overview - -#Subtopic Subtopics -#ToDo manually add subtopics ## -#Table -#Legend -# topics # description ## -#Legend ## -#Table ## -## - -#Subtopic Operators -#Table -#Legend -# description # function ## -#Legend ## -# bool operator!=(const SkIRect& a, const SkIRect& b) # Returns true if members are unequal. ## -# bool operator==(const SkIRect& a, const SkIRect& b) # Returns true if members are equal. ## -#Table ## -#Subtopic ## - -#Subtopic Member_Functions -#Table -#Legend -# description # function ## -#Legend ## -# EmptyIRect # Returns immutable bounds of (0, 0, 0, 0). ## -# Intersects # Returns true if areas overlap. ## -# IntersectsNoEmptyCheck # Returns true if areas overlap. Skips empty check. ## -# MakeEmpty # Returns bounds of (0, 0, 0, 0). ## -# MakeLTRB # Constructs from int left, top, right, bottom. ## -# MakeLargest # Constructs from (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32). ## -# MakeSize # Constructs from ISize returning (0, 0, width, height). ## -# MakeWH # Constructs from int input returning (0, 0, width, height). ## -# MakeXYWH # Constructs from int input returning (x, y, width, height). ## -# bottom() # Returns larger bounds in y, if sorted. ## -# centerX # Returns midpoint in x. ## -# centerY # Returns midpoint in y. ## -# contains() # Returns true if points are equal or inside. ## -# containsNoEmptyCheck # Returns true if points are equal or inside. Skips empty check. ## -# height() # Returns span in y. ## -# inset() # Moves the sides symmetrically about the center. ## -# intersect # Sets to shared area; returns true if not empty. ## -# intersectNoEmptyCheck # Sets to shared area; returns true if not empty. Skips empty check. ## -# is16Bit # Returns true if members fit in 16-bit word. ## -# isEmpty # Returns true if width or height are zero or negative. ## -# isLargest # Returns true if equal to (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32). ## -# join() # Sets to union of bounds. ## -# left() # Returns smaller bounds in x, if sorted. ## -# makeInset # Constructs from sides moved symmetrically about the center. ## -# makeOffset # Constructs from translated sides. ## -# makeOutset # Constructs from sides moved symmetrically about the center. ## -# makeSorted # Constructs, ordering sides from smaller to larger. ## -# offset() # Translates sides without changing width and height. ## -# offsetTo # Translates to (x, y) without changing width and height. ## -# outset() # Moves the sides symmetrically about the center. ## -# quickReject # Returns true if rectangles do not intersect. ## -# right() # Returns larger bounds in x, if sorted. ## -# set() # Sets to (left, top, right, bottom). ## -# setEmpty # Sets to (0, 0, 0, 0). ## -# setLTRB # Sets to SkScalar input (left, top, right, bottom). ## -# setLargest # Sets to (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32). ## -# setLargestInverted # Sets to (SK_MaxS32, SK_MaxS32, SK_MinS32, SK_MinS32). ## -# setXYWH # Sets to (x, y, width, height). ## -# size() # Returns ISize (width, height). ## -# sort() # Orders sides from smaller to larger. ## -# top() # Returns smaller bounds in y, if sorted. ## -# width() # Returns span in x. ## -# x() # Returns bounds left. ## -# y() # Returns bounds top. ## -#Table ## -#Subtopic ## - -#Topic ## - -#Member int32_t fLeft -May contain any value. The smaller of the horizontal values when sorted. -When equal to or greater than fRight, IRect is empty. -## - -#Member int32_t fTop -May contain any value. The smaller of the horizontal values when sorted. -When equal to or greater than fBottom, IRect is empty. -## - -#Member int32_t fRight -May contain any value. The larger of the vertical values when sorted. -When equal to or less than fLeft, IRect is empty. -## - -#Member int32_t fBottom -May contain any value. The larger of the vertical values when sorted. -When equal to or less than fTop, IRect is empty. -## - -# ------------------------------------------------------------------------------ - -#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeEmpty() - -Returns constructed IRect set to (0, 0, 0, 0). -Many other rectangles are empty; if left is equal to or greater than right, -or if top is equal to or greater than bottom. Setting all members to zero -is a convenience, but does not designate a special empty rectangle. - -#Return bounds (0, 0, 0, 0) ## - -#Example +#Topic IRect
+#Alias IRect_Reference
+
+#Struct SkIRect
+
+SkIRect holds four 32 bit integer coordinates describing the upper and
+lower bounds of a rectangle. SkIRect may be created from outer bounds or
+from position, width, and height. SkIRect describes an area; if its right
+is less than or equal to its left, or if its bottom is less than or equal to
+its top, it is considered empty.
+
+#Topic Overview
+
+#Subtopic Subtopics
+#ToDo manually add subtopics ##
+#Table
+#Legend
+# topics # description ##
+#Legend ##
+#Table ##
+##
+
+#Subtopic Operators
+#Table
+#Legend
+# description # function ##
+#Legend ##
+# bool operator!=(const SkIRect& a, const SkIRect& b) # Returns true if members are unequal. ##
+# bool operator==(const SkIRect& a, const SkIRect& b) # Returns true if members are equal. ##
+#Table ##
+#Subtopic ##
+
+#Subtopic Member_Functions
+#Table
+#Legend
+# description # function ##
+#Legend ##
+# EmptyIRect # Returns immutable bounds of (0, 0, 0, 0). ##
+# Intersects # Returns true if areas overlap. ##
+# IntersectsNoEmptyCheck # Returns true if areas overlap. Skips empty check. ##
+# MakeEmpty # Returns bounds of (0, 0, 0, 0). ##
+# MakeLTRB # Constructs from int left, top, right, bottom. ##
+# MakeLargest # Constructs from (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32). ##
+# MakeSize # Constructs from ISize returning (0, 0, width, height). ##
+# MakeWH # Constructs from int input returning (0, 0, width, height). ##
+# MakeXYWH # Constructs from int input returning (x, y, width, height). ##
+# bottom() # Returns larger bounds in y, if sorted. ##
+# centerX # Returns midpoint in x. ##
+# centerY # Returns midpoint in y. ##
+# contains() # Returns true if points are equal or inside. ##
+# containsNoEmptyCheck # Returns true if points are equal or inside. Skips empty check. ##
+# height() # Returns span in y. ##
+# inset() # Moves the sides symmetrically about the center. ##
+# intersect # Sets to shared area; returns true if not empty. ##
+# intersectNoEmptyCheck # Sets to shared area; returns true if not empty. Skips empty check. ##
+# is16Bit # Returns true if members fit in 16-bit word. ##
+# isEmpty # Returns true if width or height are zero or negative. ##
+# isLargest # Returns true if equal to (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32). ##
+# join() # Sets to union of bounds. ##
+# left() # Returns smaller bounds in x, if sorted. ##
+# makeInset # Constructs from sides moved symmetrically about the center. ##
+# makeOffset # Constructs from translated sides. ##
+# makeOutset # Constructs from sides moved symmetrically about the center. ##
+# makeSorted # Constructs, ordering sides from smaller to larger. ##
+# offset() # Translates sides without changing width and height. ##
+# offsetTo # Translates to (x, y) without changing width and height. ##
+# outset() # Moves the sides symmetrically about the center. ##
+# quickReject # Returns true if rectangles do not intersect. ##
+# right() # Returns larger bounds in x, if sorted. ##
+# set() # Sets to (left, top, right, bottom). ##
+# setEmpty # Sets to (0, 0, 0, 0). ##
+# setLTRB # Sets to SkScalar input (left, top, right, bottom). ##
+# setLargest # Sets to (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32). ##
+# setLargestInverted # Sets to (SK_MaxS32, SK_MaxS32, SK_MinS32, SK_MinS32). ##
+# setXYWH # Sets to (x, y, width, height). ##
+# size() # Returns ISize (width, height). ##
+# sort() # Orders sides from smaller to larger. ##
+# top() # Returns smaller bounds in y, if sorted. ##
+# width() # Returns span in x. ##
+# x() # Returns bounds left. ##
+# y() # Returns bounds top. ##
+#Table ##
+#Subtopic ##
+
+#Topic ##
+
+#Member int32_t fLeft
+May contain any value. The smaller of the horizontal values when sorted.
+When equal to or greater than fRight, IRect is empty.
+##
+
+#Member int32_t fTop
+May contain any value. The smaller of the horizontal values when sorted.
+When equal to or greater than fBottom, IRect is empty.
+##
+
+#Member int32_t fRight
+May contain any value. The larger of the vertical values when sorted.
+When equal to or less than fLeft, IRect is empty.
+##
+
+#Member int32_t fBottom
+May contain any value. The larger of the vertical values when sorted.
+When equal to or less than fTop, IRect is empty.
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeEmpty()
+
+Returns constructed IRect set to (0, 0, 0, 0).
+Many other rectangles are empty; if left is equal to or greater than right,
+or if top is equal to or greater than bottom. Setting all members to zero
+is a convenience, but does not designate a special empty rectangle.
+
+#Return bounds (0, 0, 0, 0) ##
+
+#Example
SkIRect rect = SkIRect::MakeEmpty();
SkDebugf("MakeEmpty isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
rect.offset(10, 10);
@@ -130,22 +130,22 @@ offset rect isEmpty: true inset rect isEmpty: true
outset rect isEmpty: false
##
-## - -#SeeAlso EmptyIRect isEmpty setEmpty setLargestInverted SkRect::MakeEmpty - -## - -# ------------------------------------------------------------------------------ - -#Method static SkIRect SK_WARN_UNUSED_RESULT MakeLargest() - -Returns constructed IRect setting left and top to most negative value, and -setting right and bottom to most positive value. - -#Return bounds (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32) ## - -#Example +##
+
+#SeeAlso EmptyIRect isEmpty setEmpty setLargestInverted SkRect::MakeEmpty
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static SkIRect SK_WARN_UNUSED_RESULT MakeLargest()
+
+Returns constructed IRect setting left and top to most negative value, and
+setting right and bottom to most positive value.
+
+#Return bounds (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32) ##
+
+#Example
SkIRect rect = SkIRect::MakeLargest();
SkDebugf("MakeLargest isLargest: %s\n", rect.isLargest() ? "true" : "false");
SkDebugf("MakeLargest isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
@@ -158,335 +158,335 @@ MakeLargest isEmpty: false outset isLargest: false
outset isEmpty: true
##
-## - -#SeeAlso isLargest setLargest SkRect::MakeLargest - -## - -# ------------------------------------------------------------------------------ - -#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeWH(int32_t w, int32_t h) - -Returns constructed IRect set to (0, 0, w, h). Does not validate input; w or h -may be negative. - -#Param w width of constructed Rect ## -#Param h height of constructed Rect ## - -#Return bounds (0, 0, w, h) ## - -#Example +##
+
+#SeeAlso isLargest setLargest SkRect::MakeLargest
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeWH(int32_t w, int32_t h)
+
+Returns constructed IRect set to (0, 0, w, h). Does not validate input; w or h
+may be negative.
+
+#Param w width of constructed Rect ##
+#Param h height of constructed Rect ##
+
+#Return bounds (0, 0, w, h) ##
+
+#Example
SkIRect rect1 = SkIRect::MakeWH(25, 35);
SkIRect rect2 = SkIRect::MakeSize({25, 35});
SkIRect rect3 = SkIRect::MakeXYWH(0, 0, 25, 35);
SkIRect rect4 = SkIRect::MakeLTRB(0, 0, 25, 35);
SkDebugf("all %s" "equal\n", rect1 == rect2 && rect2 == rect3 && rect3 == rect4 ?
"" : "not ");
-#StdOut -all equal -## -## - -#SeeAlso MakeSize MakeXYWH SkRect::MakeWH SkRect::MakeIWH - -## - -# ------------------------------------------------------------------------------ - -#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeSize(const SkISize& size) - -Returns constructed IRect set to (0, 0, size.width(), size.height()). -Does not validate input; size.width() or size.height() may be negative. - -#Param size values for Rect width and height ## - -#Return bounds (0, 0, size.width(), size.height()) ## - -#Example +#StdOut
+all equal
+##
+##
+
+#SeeAlso MakeSize MakeXYWH SkRect::MakeWH SkRect::MakeIWH
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeSize(const SkISize& size)
+
+Returns constructed IRect set to (0, 0, size.width(), size.height()).
+Does not validate input; size.width() or size.height() may be negative.
+
+#Param size values for Rect width and height ##
+
+#Return bounds (0, 0, size.width(), size.height()) ##
+
+#Example
SkSize size = {25.5f, 35.5f};
SkIRect rect = SkIRect::MakeSize(size.toRound());
SkDebugf("round width: %d height: %d\n", rect.width(), rect.height());
rect = SkIRect::MakeSize(size.toFloor());
SkDebugf("floor width: %d height: %d\n", rect.width(), rect.height());
-#StdOut +#StdOut
round width: 26 height: 36
-floor width: 25 height: 35 -## -## - -#SeeAlso MakeWH MakeXYWH SkRect::Make SkRect::MakeIWH - -## - -# ------------------------------------------------------------------------------ - -#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeLTRB(int32_t l, int32_t t, int32_t r, int32_t b) - -Returns constructed IRect set to (l, t, r, b). Does not sort input; Rect may -result in fLeft greater than fRight, or fTop greater than fBottom. - -#Param l integer stored in fLeft ## -#Param t integer stored in fTop ## -#Param r integer stored in fRight ## -#Param b integer stored in fBottom ## - -#Return bounds (l, t, r, b) ## - -#Example +floor width: 25 height: 35
+##
+##
+
+#SeeAlso MakeWH MakeXYWH SkRect::Make SkRect::MakeIWH
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeLTRB(int32_t l, int32_t t, int32_t r, int32_t b)
+
+Returns constructed IRect set to (l, t, r, b). Does not sort input; Rect may
+result in fLeft greater than fRight, or fTop greater than fBottom.
+
+#Param l integer stored in fLeft ##
+#Param t integer stored in fTop ##
+#Param r integer stored in fRight ##
+#Param b integer stored in fBottom ##
+
+#Return bounds (l, t, r, b) ##
+
+#Example
SkIRect rect = SkIRect::MakeLTRB(5, 35, 15, 25);
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
rect.sort();
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
-#StdOut +#StdOut
rect: 5, 35, 15, 25 isEmpty: true
-rect: 5, 25, 15, 35 isEmpty: false -## -## - -#SeeAlso MakeXYWH SkRect::MakeLTRB - -## - -# ------------------------------------------------------------------------------ - -#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeXYWH(int32_t x, int32_t y, int32_t w, int32_t h) - -Returns constructed IRect set to -#Formula -(x, y, x + w, y + h) -## -. Does not validate input; -w or h may be negative. - -#Param x stored in fLeft ## -#Param y stored in fTop ## -#Param w added to x and stored in fRight ## -#Param h added to y and stored in fBottom ## - -#Return bounds at (x, y) with width w and height h ## - -#Example +rect: 5, 25, 15, 35 isEmpty: false
+##
+##
+
+#SeeAlso MakeXYWH SkRect::MakeLTRB
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeXYWH(int32_t x, int32_t y, int32_t w, int32_t h)
+
+Returns constructed IRect set to:
+#Formula
+(x, y, x + w, y + h)
+##
+. Does not validate input;
+w or h may be negative.
+
+#Param x stored in fLeft ##
+#Param y stored in fTop ##
+#Param w added to x and stored in fRight ##
+#Param h added to y and stored in fBottom ##
+
+#Return bounds at (x, y) with width w and height h ##
+
+#Example
SkIRect rect = SkIRect::MakeXYWH(5, 35, -15, 25);
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
rect.sort();
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
-#StdOut +#StdOut
rect: 5, 35, -10, 60 isEmpty: true
-rect: -10, 35, 5, 60 isEmpty: false -## -## - -#SeeAlso MakeLTRB SkRect::MakeXYWH - -## - -# ------------------------------------------------------------------------------ - -#Method int left() const - -Returns left edge of IRect, if sorted. -Call sort() to reverse fLeft and fRight if needed. - -#Return fLeft ## - -#Example +rect: -10, 35, 5, 60 isEmpty: false
+##
+##
+
+#SeeAlso MakeLTRB SkRect::MakeXYWH
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int left() const
+
+Returns left edge of IRect, if sorted.
+Call sort() to reverse fLeft and fRight if needed.
+
+#Return fLeft ##
+
+#Example
SkIRect unsorted = { 15, 5, 10, 25 };
SkDebugf("unsorted.fLeft: %d unsorted.left(): %d\n", unsorted.fLeft, unsorted.left());
SkIRect sorted = unsorted.makeSorted();
SkDebugf("sorted.fLeft: %d sorted.left(): %d\n", sorted.fLeft, sorted.left());
-#StdOut +#StdOut
unsorted.fLeft: 15 unsorted.left(): 15
-sorted.fLeft: 10 sorted.left(): 10 -## -## - -#SeeAlso fLeft x() SkRect::left() - -## - -# ------------------------------------------------------------------------------ - -#Method int top() const - -Returns top edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid, -and sort() to reverse fTop and fBottom if needed. - -#Return fTop ## - -#Example +sorted.fLeft: 10 sorted.left(): 10
+##
+##
+
+#SeeAlso fLeft x() SkRect::left()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int top() const
+
+Returns top edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid,
+and sort() to reverse fTop and fBottom if needed.
+
+#Return fTop ##
+
+#Example
SkIRect unsorted = { 15, 25, 10, 5 };
SkDebugf("unsorted.fTop: %d unsorted.top(): %d\n", unsorted.fTop, unsorted.top());
SkIRect sorted = unsorted.makeSorted();
- SkDebugf("sorted.fTop: %d sorted.top(): %d\n", sorted.fTop, sorted.top()); -#StdOut + SkDebugf("sorted.fTop: %d sorted.top(): %d\n", sorted.fTop, sorted.top());
+#StdOut
unsorted.fTop: 25 unsorted.top(): 25
-sorted.fTop: 5 sorted.top(): 5 -## -## - -#SeeAlso fTop y() SkRect::top() - -## - -# ------------------------------------------------------------------------------ - -#Method int right() const - -Returns right edge of IRect, if sorted. -Call sort() to reverse fLeft and fRight if needed. - -#Return fRight ## - -#Example +sorted.fTop: 5 sorted.top(): 5
+##
+##
+
+#SeeAlso fTop y() SkRect::top()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int right() const
+
+Returns right edge of IRect, if sorted.
+Call sort() to reverse fLeft and fRight if needed.
+
+#Return fRight ##
+
+#Example
SkIRect unsorted = { 15, 25, 10, 5 };
SkDebugf("unsorted.fRight: %d unsorted.right(): %d\n", unsorted.fRight, unsorted.right());
SkIRect sorted = unsorted.makeSorted();
SkDebugf("sorted.fRight: %d sorted.right(): %d\n", sorted.fRight, sorted.right());
-#StdOut +#StdOut
unsorted.fRight: 10 unsorted.right(): 10
-sorted.fRight: 15 sorted.right(): 15 -## -## - -#SeeAlso fRight SkRect::right() - -## - -# ------------------------------------------------------------------------------ - -#Method int bottom() const - -Returns bottom edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid, -and sort() to reverse fTop and fBottom if needed. - -#Return fBottom ## - -#Example +sorted.fRight: 15 sorted.right(): 15
+##
+##
+
+#SeeAlso fRight SkRect::right()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int bottom() const
+
+Returns bottom edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid,
+and sort() to reverse fTop and fBottom if needed.
+
+#Return fBottom ##
+
+#Example
SkIRect unsorted = { 15, 25, 10, 5 };
SkDebugf("unsorted.fBottom: %d unsorted.bottom(): %d\n", unsorted.fBottom, unsorted.bottom());
SkIRect sorted = unsorted.makeSorted();
SkDebugf("sorted.fBottom: %d sorted.bottom(): %d\n", sorted.fBottom, sorted.bottom());
-#StdOut +#StdOut
unsorted.fBottom: 5 unsorted.bottom(): 5
-sorted.fBottom: 25 sorted.bottom(): 25 -## -## - -#SeeAlso fBottom SkRect::bottom() - -## - -# ------------------------------------------------------------------------------ - -#Method int x() const - -Returns left edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid, -and sort() to reverse fLeft and fRight if needed. - -#Return fLeft ## - -#Example +sorted.fBottom: 25 sorted.bottom(): 25
+##
+##
+
+#SeeAlso fBottom SkRect::bottom()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int x() const
+
+Returns left edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid,
+and sort() to reverse fLeft and fRight if needed.
+
+#Return fLeft ##
+
+#Example
SkIRect unsorted = { 15, 5, 10, 25 };
SkDebugf("unsorted.fLeft: %d unsorted.x(): %d\n", unsorted.fLeft, unsorted.x());
SkIRect sorted = unsorted.makeSorted();
SkDebugf("sorted.fLeft: %d sorted.x(): %d\n", sorted.fLeft, sorted.x());
-#StdOut +#StdOut
unsorted.fLeft: 15 unsorted.x(): 15
-sorted.fLeft: 10 sorted.x(): 10 -## -## - -#SeeAlso fLeft left() y() SkRect::x() - -## - -# ------------------------------------------------------------------------------ - -#Method int y() const - -Returns top edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid, -and sort() to reverse fTop and fBottom if needed. - -#Return fTop ## - -#Example +sorted.fLeft: 10 sorted.x(): 10
+##
+##
+
+#SeeAlso fLeft left() y() SkRect::x()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int y() const
+
+Returns top edge of IRect, if sorted. Call isEmpty to see if IRect may be invalid,
+and sort() to reverse fTop and fBottom if needed.
+
+#Return fTop ##
+
+#Example
SkIRect unsorted = { 15, 25, 10, 5 };
SkDebugf("unsorted.fTop: %d unsorted.y(): %d\n", unsorted.fTop, unsorted.y());
SkIRect sorted = unsorted.makeSorted();
- SkDebugf("sorted.fTop: %d sorted.y(): %d\n", sorted.fTop, sorted.y()); -#StdOut + SkDebugf("sorted.fTop: %d sorted.y(): %d\n", sorted.fTop, sorted.y());
+#StdOut
unsorted.fTop: 25 unsorted.y(): 25
-sorted.fTop: 5 sorted.y(): 5 -## -## - -#SeeAlso fTop top() x() SkRect::y() - -## - -# ------------------------------------------------------------------------------ - -#Method int width() const - -Returns span on the x-axis. This does not check if IRect is sorted, or if -result fits in 32-bit signed integer; result may be negative. - -#Return fRight minus fLeft ## - -#Example +sorted.fTop: 5 sorted.y(): 5
+##
+##
+
+#SeeAlso fTop top() x() SkRect::y()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int width() const
+
+Returns span on the x-axis. This does not check if IRect is sorted, or if
+result fits in 32-bit signed integer; result may be negative.
+
+#Return fRight minus fLeft ##
+
+#Example
SkIRect unsorted = { 15, 25, 10, 5 };
SkDebugf("unsorted width: %d\n", unsorted.width());
SkIRect large = { -2147483647, 1, 2147483644, 2 };
SkDebugf("large width: %d\n", large.width());
-#StdOut +#StdOut
unsorted width: -5
-large width: -5 -## -## - -#SeeAlso height() SkRect::width() - -## - -# ------------------------------------------------------------------------------ - -#Method int height() const - -Returns span on the y-axis. This does not check if IRect is sorted, or if -result fits in 32-bit signed integer; result may be negative. - -#Return fBottom minus fTop ## - -#Example +large width: -5
+##
+##
+
+#SeeAlso height() SkRect::width()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int height() const
+
+Returns span on the y-axis. This does not check if IRect is sorted, or if
+result fits in 32-bit signed integer; result may be negative.
+
+#Return fBottom minus fTop ##
+
+#Example
SkIRect unsorted = { 15, 25, 10, 20 };
SkDebugf("unsorted height: %d\n", unsorted.height());
SkIRect large = { 1, -2147483647, 2, 2147483644 };
SkDebugf("large height: %d\n", large.height());
-#StdOut +#StdOut
unsorted height: -5
-large height: -5 -## -## - -#SeeAlso width() SkRect::height() - -## - -# ------------------------------------------------------------------------------ - -#Method SkISize size() const - -Returns spans on the x-axis and y-axis. This does not check if IRect is sorted, -or if result fits in 32-bit signed integer; result may be negative. - -#Return ISize (width, height) ## - -#Example +large height: -5
+##
+##
+
+#SeeAlso width() SkRect::height()
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method SkISize size() const
+
+Returns spans on the x-axis and y-axis. This does not check if IRect is sorted,
+or if result fits in 32-bit signed integer; result may be negative.
+
+#Return ISize (width, height) ##
+
+#Example
auto debugster = [](const char* prefix, const SkIRect& rect) -> void {
SkISize size = rect.size();
SkDebugf("%s ", prefix);
@@ -498,85 +498,85 @@ or if result fits in 32-bit signed integer; result may be negative. rect.offset(20, 20);
debugster(" offset", rect);
rect.outset(20, 20);
- debugster(" outset", rect); -#StdOut + debugster(" outset", rect);
+#StdOut
original rect: 20, 30, 40, 50 size: 20, 20
offset rect: 40, 50, 60, 70 size: 20, 20
- outset rect: 20, 30, 80, 90 size: 60, 60 -## -## - -#SeeAlso height() width() MakeSize - -## - -# ------------------------------------------------------------------------------ - -#Method int centerX() const - -Returns average of left edge and right edge. Result does not change if Rect -is sorted. Result may be incorrect if Rect is far from the origin. - -Result is rounded down. - -#Return midpoint in x ## - -#Example -#Description -Dividing by two rounds towards zero. centerX uses a bit shift and rounds down. -## + outset rect: 20, 30, 80, 90 size: 60, 60
+##
+##
+
+#SeeAlso height() width() MakeSize
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int centerX() const
+
+Returns average of left edge and right edge. Result does not change if Rect
+is sorted. Result may be incorrect if Rect is far from the origin.
+
+Result is rounded down.
+
+#Return midpoint in x ##
+
+#Example
+#Description
+Dividing by two rounds towards zero. centerX uses a bit shift and rounds down.
+##
SkIRect tests[] = {{20, 30, 41, 51}, {-20, -30, -41, -51}, {-10, -10, 11, 11}};
for (auto rect : tests) {
SkDebugf("left: %3d right: %3d centerX: %3d ", rect.left(), rect.right(), rect.centerX());
SkDebugf("div2: %3d\n", (rect.left() + rect.right()) / 2);
}
-#StdOut +#StdOut
left: 20 right: 41 centerX: 30 div2: 30
left: -20 right: -41 centerX: -31 div2: -30
-left: -10 right: 11 centerX: 0 div2: 0 -## -## - -#SeeAlso centerY SkRect::centerX - -## - -# ------------------------------------------------------------------------------ - -#Method int centerY() const - -Returns average of top edge and bottom edge. Result does not change if Rect -is sorted. Result may be incorrect if Rect is far from the origin. - -Result is rounded down. - -#Return midpoint in y ## - -#Example +left: -10 right: 11 centerX: 0 div2: 0
+##
+##
+
+#SeeAlso centerY SkRect::centerX
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method int centerY() const
+
+Returns average of top edge and bottom edge. Result does not change if Rect
+is sorted. Result may be incorrect if Rect is far from the origin.
+
+Result is rounded down.
+
+#Return midpoint in y ##
+
+#Example
SkIRect rect = { 0, 0, 2, 2 };
rect.offset(0x40000000, 0x40000000);
SkDebugf("left: %d right: %d centerX: %d ", rect.left(), rect.right(), rect.centerX());
- SkDebugf("safe mid x: %d\n", rect.left() / 2 + rect.right() / 2); -#StdOut -left: 1073741824 right: 1073741826 centerX: -1073741823 safe mid x: 1073741825 -## -## - -#SeeAlso centerX SkRect::centerY - -## - -# ------------------------------------------------------------------------------ - -#Method bool isEmpty() const - -Returns true if fLeft is equal to or greater than fRight, or if fTop is equal -to or greater than fBottom. Call sort() to reverse rectangles with negative -width() or height(). - -#Return true if width() or height() are zero or negative ## - -#Example + SkDebugf("safe mid x: %d\n", rect.left() / 2 + rect.right() / 2);
+#StdOut
+left: 1073741824 right: 1073741826 centerX: -1073741823 safe mid x: 1073741825
+##
+##
+
+#SeeAlso centerX SkRect::centerY
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool isEmpty() const
+
+Returns true if fLeft is equal to or greater than fRight, or if fTop is equal
+to or greater than fBottom. Call sort() to reverse rectangles with negative
+width() or height().
+
+#Return true if width() or height() are zero or negative ##
+
+#Example
SkIRect tests[] = {{20, 40, 10, 50}, {20, 40, 20, 50}};
for (auto rect : tests) {
SkDebugf("rect: {%d, %d, %d, %d} is" "%s empty\n", rect.left(), rect.top(), rect.right(),
@@ -584,107 +584,107 @@ width() or height(). rect.sort();
SkDebugf("sorted: {%d, %d, %d, %d} is" "%s empty\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "" : " not");
- } + }
#StdOut
rect: {20, 40, 10, 50} is empty
sorted: {10, 40, 20, 50} is not empty
rect: {20, 40, 20, 50} is empty
sorted: {20, 40, 20, 50} is empty
##
-## - -#SeeAlso EmptyIRect MakeEmpty sort SkRect::isEmpty - -## - -# ------------------------------------------------------------------------------ - -#Method bool isLargest() const - -Returns true if IRect encloses largest possible area. - -#Return true if equal to (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32) ## - -#Example -#Description -Note that the width is not negative, yet it cannot be represented as a 32-bit -signed integer. -## +##
+
+#SeeAlso EmptyIRect MakeEmpty sort SkRect::isEmpty
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool isLargest() const
+
+Returns true if IRect encloses largest possible area.
+
+#Return true if equal to (SK_MinS32, SK_MinS32, SK_MaxS32, SK_MaxS32) ##
+
+#Example
+#Description
+Note that the width is not negative, yet it cannot be represented as a 32-bit
+signed integer.
+##
SkIRect large = SkIRect::MakeLargest();
SkDebugf("large is largest: %s\n" ,large.isLargest() ? "true" : "false");
SkDebugf("large width %d\n", large.width());
- SkDebugf("large is empty: %s\n", large.isEmpty() ? "true" : "false"); + SkDebugf("large is empty: %s\n", large.isEmpty() ? "true" : "false");
#StdOut
large is largest: true
large width -2
large is empty: false
##
-## - -#SeeAlso MakeLargest SkRect::isLargest - -## - -# ------------------------------------------------------------------------------ - -#Method bool operator==(const SkIRect& a, const SkIRect& b) - -Returns true if all members in a: fLeft, fTop, fRight, and fBottom; are -identical to corresponding members in b. - -#Param a IRect to compare ## -#Param b IRect to compare ## - -#Return true if members are equal ## - -#Example +##
+
+#SeeAlso MakeLargest SkRect::isLargest
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool operator==(const SkIRect& a, const SkIRect& b)
+
+Returns true if all members in a: fLeft, fTop, fRight, and fBottom; are
+identical to corresponding members in b.
+
+#Param a IRect to compare ##
+#Param b IRect to compare ##
+
+#Return true if members are equal ##
+
+#Example
SkIRect test = {0, 0, 2, 2};
SkIRect sorted = test.makeSorted();
- SkDebugf("test %c= sorted\n", test == sorted ? '=' : '!'); + SkDebugf("test %c= sorted\n", test == sorted ? '=' : '!');
#StdOut
test == sorted
##
-## - -#SeeAlso operator!=(const SkIRect& a, const SkIRect& b) - -## - -# ------------------------------------------------------------------------------ - -#Method bool operator!=(const SkIRect& a, const SkIRect& b) - -Returns true if any member in a: fLeft, fTop, fRight, and fBottom; is not -identical to the corresponding member in b. - -#Param a IRect to compare ## -#Param b IRect to compare ## - -#Return true if members are not equal ## - -#Example +##
+
+#SeeAlso operator!=(const SkIRect& a, const SkIRect& b)
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool operator!=(const SkIRect& a, const SkIRect& b)
+
+Returns true if any member in a: fLeft, fTop, fRight, and fBottom; is not
+identical to the corresponding member in b.
+
+#Param a IRect to compare ##
+#Param b IRect to compare ##
+
+#Return true if members are not equal ##
+
+#Example
SkIRect test = {2, 2, 0, 0};
SkIRect sorted = test.makeSorted();
SkDebugf("test %c= sorted\n", test != sorted ? '!' : '=');
#StdOut
test != sorted
##
-## - -#SeeAlso operator==(const SkIRect& a, const SkIRect& b) - -## - -# ------------------------------------------------------------------------------ - -#Method bool is16Bit() const - -Returns true if all members: fLeft, fTop, fRight, and fBottom; values are -equal to or larger than -32768 and equal to or smaller than 32767. - -#Return true if members fit in 16-bit word ## - -#Example +##
+
+#SeeAlso operator==(const SkIRect& a, const SkIRect& b)
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool is16Bit() const
+
+Returns true if all members: fLeft, fTop, fRight, and fBottom; values are
+equal to or larger than -32768 and equal to or smaller than 32767.
+
+#Return true if members fit in 16-bit word ##
+
+#Example
SkIRect tests[] = {{-32768, -32768, 32767, 32767}, {-32768, -32768, 32768, 32768}};
for (auto rect : tests) {
SkDebugf("{%d, %d, %d, %d} %s in 16 bits\n", rect.fLeft, rect.fTop, rect.fRight,
@@ -694,23 +694,23 @@ equal to or larger than -32768 and equal to or smaller than 32767. {-32768, -32768, 32767, 32767} fits in 16 bits
{-32768, -32768, 32768, 32768} does not fit in 16 bits
##
-## - -#SeeAlso SkTFitsIn - -## - -# ------------------------------------------------------------------------------ - -#Method void setEmpty() - -Sets IRect to (0, 0, 0, 0). - -Many other rectangles are empty; if left is equal to or greater than right, -or if top is equal to or greater than bottom. Setting all members to zero -is a convenience, but does not designate a special empty rectangle. - -#Example +##
+
+#SeeAlso SkTFitsIn
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void setEmpty()
+
+Sets IRect to (0, 0, 0, 0).
+
+Many other rectangles are empty; if left is equal to or greater than right,
+or if top is equal to or greater than bottom. Setting all members to zero
+is a convenience, but does not designate a special empty rectangle.
+
+#Example
SkIRect rect = {3, 4, 1, 2};
for (int i = 0; i < 2; ++i) {
SkDebugf("rect: {%d, %d, %d, %d} is %s" "empty\n", rect.fLeft, rect.fTop,
@@ -721,26 +721,26 @@ is a convenience, but does not designate a special empty rectangle. rect: {3, 4, 1, 2} is empty
rect: {0, 0, 0, 0} is empty
##
-## - -#SeeAlso MakeEmpty SkRect::setEmpty - -## - -# ------------------------------------------------------------------------------ - -#Method void set(int32_t left, int32_t top, int32_t right, int32_t bottom) - -Sets IRect to (left, top, right, bottom). -left and right are not sorted; left is not necessarily less than right. -top and bottom are not sorted; top is not necessarily less than bottom. - -#Param left assigned to fLeft ## -#Param top assigned to fTop ## -#Param right assigned to fRight ## -#Param bottom assigned to fBottom ## - -#Example +##
+
+#SeeAlso MakeEmpty SkRect::setEmpty
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void set(int32_t left, int32_t top, int32_t right, int32_t bottom)
+
+Sets IRect to (left, top, right, bottom).
+left and right are not sorted; left is not necessarily less than right.
+top and bottom are not sorted; top is not necessarily less than bottom.
+
+#Param left assigned to fLeft ##
+#Param top assigned to fTop ##
+#Param right assigned to fRight ##
+#Param bottom assigned to fBottom ##
+
+#Example
SkIRect rect1 = {3, 4, 1, 2};
SkDebugf("rect1: {%d, %d, %d, %d}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom);
SkIRect rect2;
@@ -750,26 +750,26 @@ top and bottom are not sorted; top is not necessarily less than bottom. rect1: {3, 4, 1, 2}
rect2: {3, 4, 1, 2}
##
-## - -#SeeAlso setLTRB setXYWH SkRect::set - -## - -# ------------------------------------------------------------------------------ - -#Method void setLTRB(int32_t left, int32_t top, int32_t right, int32_t bottom) - -Sets IRect to (left, top, right, bottom). -left and right are not sorted; left is not necessarily less than right. -top and bottom are not sorted; top is not necessarily less than bottom. - -#Param left stored in fLeft ## -#Param top stored in fTop ## -#Param right stored in fRight ## -#Param bottom stored in fBottom ## - -#Example +##
+
+#SeeAlso setLTRB setXYWH SkRect::set
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void setLTRB(int32_t left, int32_t top, int32_t right, int32_t bottom)
+
+Sets IRect to (left, top, right, bottom).
+left and right are not sorted; left is not necessarily less than right.
+top and bottom are not sorted; top is not necessarily less than bottom.
+
+#Param left stored in fLeft ##
+#Param top stored in fTop ##
+#Param right stored in fRight ##
+#Param bottom stored in fBottom ##
+
+#Example
SkIRect rect1 = {3, 4, 1, 2};
SkDebugf("rect1: {%d, %d, %d, %d}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom);
SkIRect rect2;
@@ -779,29 +779,29 @@ top and bottom are not sorted; top is not necessarily less than bottom. rect1: {3, 4, 1, 2}
rect2: {3, 4, 1, 2}
##
-## - -#SeeAlso set setXYWH SkRect::setLTRB - -## - -# ------------------------------------------------------------------------------ - -#Method void setXYWH(int32_t x, int32_t y, int32_t width, int32_t height) - -Sets IRect to -#Formula -(x, y, x + width, y + height) -## -. Does not validate input; -width or height may be negative. - -#Param x stored in fLeft ## -#Param y stored in fTop ## -#Param width added to x and stored in fRight ## -#Param height added to y and stored in fBottom ## - -#Example +##
+
+#SeeAlso set setXYWH SkRect::setLTRB
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void setXYWH(int32_t x, int32_t y, int32_t width, int32_t height)
+
+Sets IRect to:
+#Formula
+(x, y, x + width, y + height)
+##
+. Does not validate input;
+width or height may be negative.
+
+#Param x stored in fLeft ##
+#Param y stored in fTop ##
+#Param width added to x and stored in fRight ##
+#Param height added to y and stored in fBottom ##
+
+#Example
SkIRect rect;
rect.setXYWH(5, 35, -15, 25);
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
@@ -809,24 +809,24 @@ width or height may be negative. rect.sort();
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
-#StdOut +#StdOut
rect: 5, 35, -10, 60 isEmpty: true
-rect: -10, 35, 5, 60 isEmpty: false -## -## - -#SeeAlso MakeXYWH setLTRB set SkRect::setXYWH - -## - -# ------------------------------------------------------------------------------ - -#Method void setLargest() - -Sets rectangle left and top to most negative value, and sets -right and bottom to most positive value. - -#Example +rect: -10, 35, 5, 60 isEmpty: false
+##
+##
+
+#SeeAlso MakeXYWH setLTRB set SkRect::setXYWH
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void setLargest()
+
+Sets rectangle left and top to most negative value, and sets
+right and bottom to most positive value.
+
+#Example
SkIRect rect;
rect.setLargest();
SkDebugf("MakeLargest isLargest: %s\n", rect.isLargest() ? "true" : "false");
@@ -840,46 +840,46 @@ MakeLargest isEmpty: false outset isLargest: false
outset isEmpty: true
##
-## - -#SeeAlso MakeLargest isLargest setLargestInverted SK_MinS32 SK_MaxS32 - -## - -# ------------------------------------------------------------------------------ - -#Method void setLargestInverted() -#ToDo move this to private -## - -Sets rectangle left and top to most positive value, and sets -right and bottom to most negative value. This is used internally to -flag that a condition is met, but otherwise has no special purpose. - -#NoExample -## - -#SeeAlso setEmpty setLargest - -## - -# ------------------------------------------------------------------------------ - -#Method SkIRect makeOffset(int32_t dx, int32_t dy) const - -Returns IRect offset by (dx, dy). - -If dx is negative, IRect returned is moved to the left. -If dx is positive, IRect returned is moved to the right. -If dy is negative, IRect returned is moved upward. -If dy is positive, IRect returned is moved downward. - -#Param dx offset added to fLeft and fRight ## -#Param dy offset added to fTop and fBottom ## - -#Return Rect offset in x or y, with original width and height ## - -#Example +##
+
+#SeeAlso MakeLargest isLargest setLargestInverted SK_MinS32 SK_MaxS32
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void setLargestInverted()
+#ToDo move this to private
+##
+
+Sets rectangle left and top to most positive value, and sets
+right and bottom to most negative value. This is used internally to
+flag that a condition is met, but otherwise has no special purpose.
+
+#NoExample
+##
+
+#SeeAlso setEmpty setLargest
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method SkIRect makeOffset(int32_t dx, int32_t dy) const
+
+Returns IRect offset by (dx, dy).
+
+If dx is negative, IRect returned is moved to the left.
+If dx is positive, IRect returned is moved to the right.
+If dy is negative, IRect returned is moved upward.
+If dy is positive, IRect returned is moved downward.
+
+#Param dx offset added to fLeft and fRight ##
+#Param dy offset added to fTop and fBottom ##
+
+#Return Rect offset in x or y, with original width and height ##
+
+#Example
SkIRect rect = { 10, 50, 20, 60 };
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
@@ -890,29 +890,29 @@ If dy is positive, IRect returned is moved downward. rect: 10, 50, 20, 60 isEmpty: false
rect: 25, 82, 35, 92 isEmpty: false
##
-## - -#SeeAlso offset() makeInset makeOutset SkRect::makeOffset - -## - -# ------------------------------------------------------------------------------ - -#Method SkIRect makeInset(int32_t dx, int32_t dy) const - -Returns IRect, inset by (dx, dy). - -If dx is negative, IRect returned is wider. -If dx is positive, IRect returned is narrower. -If dy is negative, IRect returned is taller. -If dy is positive, IRect returned is shorter. - -#Param dx offset added to fLeft and subtracted from fRight ## -#Param dy offset added to fTop and subtracted from fBottom ## - -#Return Rect inset symmetrically left and right, top and bottom ## - -#Example +##
+
+#SeeAlso offset() makeInset makeOutset SkRect::makeOffset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method SkIRect makeInset(int32_t dx, int32_t dy) const
+
+Returns IRect, inset by (dx, dy).
+
+If dx is negative, IRect returned is wider.
+If dx is positive, IRect returned is narrower.
+If dy is negative, IRect returned is taller.
+If dy is positive, IRect returned is shorter.
+
+#Param dx offset added to fLeft and subtracted from fRight ##
+#Param dy offset added to fTop and subtracted from fBottom ##
+
+#Return Rect inset symmetrically left and right, top and bottom ##
+
+#Example
SkIRect rect = { 10, 50, 20, 60 };
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
@@ -923,29 +923,29 @@ If dy is positive, IRect returned is shorter. rect: 10, 50, 20, 60 isEmpty: false
rect: 25, 82, 5, 28 isEmpty: true
##
-## - -#SeeAlso inset() makeOffset makeOutset SkRect::makeInset - -## - -# ------------------------------------------------------------------------------ - -#Method SkIRect makeOutset(int32_t dx, int32_t dy) const - -Returns IRect, outset by (dx, dy). - -If dx is negative, IRect returned is narrower. -If dx is positive, IRect returned is wider. -If dy is negative, IRect returned is shorter. -If dy is positive, IRect returned is taller. - -#Param dx offset subtracted to fLeft and added from fRight ## -#Param dy offset subtracted to fTop and added from fBottom ## - -#Return Rect outset symmetrically left and right, top and bottom ## - -#Example +##
+
+#SeeAlso inset() makeOffset makeOutset SkRect::makeInset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method SkIRect makeOutset(int32_t dx, int32_t dy) const
+
+Returns IRect, outset by (dx, dy).
+
+If dx is negative, IRect returned is narrower.
+If dx is positive, IRect returned is wider.
+If dy is negative, IRect returned is shorter.
+If dy is positive, IRect returned is taller.
+
+#Param dx offset subtracted to fLeft and added from fRight ##
+#Param dy offset subtracted to fTop and added from fBottom ##
+
+#Return Rect outset symmetrically left and right, top and bottom ##
+
+#Example
SkIRect rect = { 10, 50, 20, 60 };
SkDebugf("rect: %d, %d, %d, %d isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
rect.bottom(), rect.isEmpty() ? "true" : "false");
@@ -956,164 +956,164 @@ If dy is positive, IRect returned is taller. rect: 10, 50, 20, 60 isEmpty: false
rect: -5, 18, 35, 92 isEmpty: false
##
-## - -#SeeAlso outset() makeOffset makeInset SkRect::makeOutset - -## - -# ------------------------------------------------------------------------------ - -#Method void offset(int32_t dx, int32_t dy) - -Offsets IRect by adding dx to fLeft, fRight; and by adding dy to fTop, fBottom. - -If dx is negative, moves IRect returned to the left. -If dx is positive, moves IRect returned to the right. -If dy is negative, moves IRect returned upward. -If dy is positive, moves IRect returned downward. - -#Param dx offset added to fLeft and fRight ## -#Param dy offset added to fTop and fBottom ## - -#Example +##
+
+#SeeAlso outset() makeOffset makeInset SkRect::makeOutset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void offset(int32_t dx, int32_t dy)
+
+Offsets IRect by adding dx to fLeft, fRight; and by adding dy to fTop, fBottom.
+
+If dx is negative, moves IRect returned to the left.
+If dx is positive, moves IRect returned to the right.
+If dy is negative, moves IRect returned upward.
+If dy is positive, moves IRect returned downward.
+
+#Param dx offset added to fLeft and fRight ##
+#Param dy offset added to fTop and fBottom ##
+
+#Example
SkIRect rect = { 10, 14, 50, 73 };
rect.offset(5, 13);
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
#StdOut
rect: 15, 27, 55, 86
##
-## - -#SeeAlso offsetTo makeOffset SkRect::offset - -## - -# ------------------------------------------------------------------------------ - -#Method void offset(const SkIPoint& delta) - -Offsets IRect by adding delta.fX to fLeft, fRight; and by adding delta.fY to -fTop, fBottom. - -If delta.fX is negative, moves IRect returned to the left. -If delta.fX is positive, moves IRect returned to the right. -If delta.fY is negative, moves IRect returned upward. -If delta.fY is positive, moves IRect returned downward. - -#Param delta offset added to IRect ## - -#Example +##
+
+#SeeAlso offsetTo makeOffset SkRect::offset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void offset(const SkIPoint& delta)
+
+Offsets IRect by adding delta.fX to fLeft, fRight; and by adding delta.fY to
+fTop, fBottom.
+
+If delta.fX is negative, moves IRect returned to the left.
+If delta.fX is positive, moves IRect returned to the right.
+If delta.fY is negative, moves IRect returned upward.
+If delta.fY is positive, moves IRect returned downward.
+
+#Param delta offset added to IRect ##
+
+#Example
SkIRect rect = { 10, 14, 50, 73 };
rect.offset({5, 13});
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
#StdOut
rect: 15, 27, 55, 86
##
-## - -#SeeAlso offsetTo makeOffset SkRect::offset - -## - -# ------------------------------------------------------------------------------ - -#Method void offsetTo(int32_t newX, int32_t newY) - -Offsets IRect so that fLeft equals newX, and fTop equals newY. width and height -are unchanged. - -#Param newX stored in fLeft, preserving width() ## -#Param newY stored in fTop, preserving height() ## - -#Example +##
+
+#SeeAlso offsetTo makeOffset SkRect::offset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void offsetTo(int32_t newX, int32_t newY)
+
+Offsets IRect so that fLeft equals newX, and fTop equals newY. width and height
+are unchanged.
+
+#Param newX stored in fLeft, preserving width() ##
+#Param newY stored in fTop, preserving height() ##
+
+#Example
SkIRect rect = { 10, 14, 50, 73 };
rect.offsetTo(15, 27);
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
#StdOut
rect: 15, 27, 55, 86
##
-## - -#SeeAlso offset makeOffset setXYWH SkRect::offsetTo - -## - -# ------------------------------------------------------------------------------ - -#Method void inset(int32_t dx, int32_t dy) - -Insets IRect by (dx,dy). - -If dx is positive, makes IRect narrower. -If dx is negative, makes IRect wider. -If dy is positive, makes IRect shorter. -If dy is negative, makes IRect taller. - -#Param dx offset added to fLeft and subtracted from fRight ## -#Param dy offset added to fTop and subtracted from fBottom ## - -#Example +##
+
+#SeeAlso offset makeOffset setXYWH SkRect::offsetTo
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void inset(int32_t dx, int32_t dy)
+
+Insets IRect by (dx,dy).
+
+If dx is positive, makes IRect narrower.
+If dx is negative, makes IRect wider.
+If dy is positive, makes IRect shorter.
+If dy is negative, makes IRect taller.
+
+#Param dx offset added to fLeft and subtracted from fRight ##
+#Param dy offset added to fTop and subtracted from fBottom ##
+
+#Example
SkIRect rect = { 10, 14, 50, 73 };
rect.inset(5, 13);
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
#StdOut
rect: 15, 27, 45, 60
##
-## - -#SeeAlso outset makeInset SkRect::inset - -## - -# ------------------------------------------------------------------------------ - -#Method void outset(int32_t dx, int32_t dy) - -Outsets IRect by (dx, dy). - -If dx is positive, makes Rect wider. -If dx is negative, makes Rect narrower. -If dy is positive, makes Rect taller. -If dy is negative, makes Rect shorter. - -#Param dx subtracted to fLeft and added from fRight ## -#Param dy subtracted to fTop and added from fBottom ## - -#Example +##
+
+#SeeAlso outset makeInset SkRect::inset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void outset(int32_t dx, int32_t dy)
+
+Outsets IRect by (dx, dy).
+
+If dx is positive, makes Rect wider.
+If dx is negative, makes Rect narrower.
+If dy is positive, makes Rect taller.
+If dy is negative, makes Rect shorter.
+
+#Param dx subtracted to fLeft and added from fRight ##
+#Param dy subtracted to fTop and added from fBottom ##
+
+#Example
SkIRect rect = { 10, 14, 50, 73 };
rect.outset(5, 13);
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
#StdOut
rect: 5, 1, 55, 86
##
-## - -#SeeAlso inset makeOutset SkRect::outset - -## - -# ------------------------------------------------------------------------------ - -#Method bool quickReject(int l, int t, int r, int b) const - -Constructs IRect (l, t, r, b) and returns true if constructed IRect does not -intersect IRect. Does not check to see if construction or IRect is empty. - -Is implemented with short circuit logic so that true can be returned after -a single compare. - -#Param l x minimum of constructed Rect ## -#Param t y minimum of constructed Rect ## -#Param r x maximum of constructed Rect ## -#Param b y maximum of constructed Rect ## - -#Return true if construction and IRect have no area in common ## - -#Example -#Description -quickReject is the complement of Intersects. -## +##
+
+#SeeAlso inset makeOutset SkRect::outset
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool quickReject(int l, int t, int r, int b) const
+
+Constructs IRect (l, t, r, b) and returns true if constructed IRect does not
+intersect IRect. Does not check to see if construction or IRect is empty.
+
+Is implemented with short circuit logic so that true can be returned after
+a single compare.
+
+#Param l x minimum of constructed Rect ##
+#Param t y minimum of constructed Rect ##
+#Param r x maximum of constructed Rect ##
+#Param b y maximum of constructed Rect ##
+
+#Return true if construction and IRect have no area in common ##
+
+#Example
+#Description
+quickReject is the complement of Intersects.
+##
const SkIRect rect = {7, 11, 13, 17};
const int32_t* r = &rect.fLeft;
const SkIRect tests[] = { {13, 11, 15, 17}, { 7, 7, 13, 11 }, { 12, 16, 14, 18 } };
@@ -1129,32 +1129,36 @@ rect (7, 11, 13, 17) test(13, 11, 15, 17) quickReject true; intersects false rect (7, 11, 13, 17) test(7, 7, 13, 11) quickReject true; intersects false
rect (7, 11, 13, 17) test(12, 16, 14, 18) quickReject false; intersects true
##
-## - -#SeeAlso Intersects - -## - -# ------------------------------------------------------------------------------ - -#Method bool contains(int32_t x, int32_t y) const - -Returns true if -#Formula -fLeft <= x < fRight && fTop <= y < fBottom -## -. -Returns false if Rect is empty. - -Considers input to describe constructed IRect (x, y, x + 1, y + 1) and -returns true if constructed area is completely enclosed by IRect area. - -#Param x test Point x-coordinate ## -#Param y test Point y-coordinate ## - -#Return true if (x, y) is inside IRect ## - -#Example +##
+
+#SeeAlso Intersects
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool contains(int32_t x, int32_t y) const
+
+Returns true if:
+#Formula
+fLeft <= x < fRight && fTop <= y < fBottom
+##
+.
+Returns false if Rect is empty.
+
+Considers input to describe constructed IRect:
+#Formula
+(x, y, x + 1, y + 1)
+##
+and
+returns true if constructed area is completely enclosed by IRect area.
+
+#Param x test Point x-coordinate ##
+#Param y test Point y-coordinate ##
+
+#Return true if (x, y) is inside IRect ##
+
+#Example
SkIRect rect = { 30, 50, 40, 60 };
SkIPoint pts[] = { { 30, 50}, { 40, 50}, { 30, 60} };
for (auto pt : pts) {
@@ -1167,30 +1171,30 @@ rect: (30, 50, 40, 60) contains (30, 50) rect: (30, 50, 40, 60) does not contain (40, 50)
rect: (30, 50, 40, 60) does not contain (30, 60)
##
-## - -#SeeAlso containsNoEmptyCheck SkRect::contains - -## - -# ------------------------------------------------------------------------------ - -#Method bool contains(int32_t left, int32_t top, int32_t right, int32_t bottom) const - -Constructs Rect to intersect from (left, top, right, bottom). Does not sort -construction. - -Returns true if Rect contains construction. -Returns false if Rect is empty or construction is empty. - -#Param left x minimum of constructed Rect ## -#Param top y minimum of constructed Rect ## -#Param right x maximum of constructed Rect ## -#Param bottom y maximum of constructed Rect ## - -#Return true if all sides of IRect are outside construction ## - -#Example +##
+
+#SeeAlso containsNoEmptyCheck SkRect::contains
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool contains(int32_t left, int32_t top, int32_t right, int32_t bottom) const
+
+Constructs Rect to intersect from (left, top, right, bottom). Does not sort
+construction.
+
+Returns true if Rect contains construction.
+Returns false if Rect is empty or construction is empty.
+
+#Param left x minimum of constructed Rect ##
+#Param top y minimum of constructed Rect ##
+#Param right x maximum of constructed Rect ##
+#Param bottom y maximum of constructed Rect ##
+
+#Return true if all sides of IRect are outside construction ##
+
+#Example
SkIRect rect = { 30, 50, 40, 60 };
SkIRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
for (auto contained : tests) {
@@ -1206,26 +1210,26 @@ rect: (30, 50, 40, 60) contains (30, 50, 31, 51) rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
##
-## - -#SeeAlso containsNoEmptyCheck SkRect::contains - -## - -# ------------------------------------------------------------------------------ - -#Method bool contains(const SkIRect& r) const - -Returns true if Rect contains r. -Returns false if Rect is empty or r is empty. - -Rect contains r when Rect area completely includes r area. - -#Param r IRect contained ## - -#Return true if all sides of IRect are outside r ## - -#Example +##
+
+#SeeAlso containsNoEmptyCheck SkRect::contains
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool contains(const SkIRect& r) const
+
+Returns true if Rect contains r.
+Returns false if Rect is empty or r is empty.
+
+Rect contains r when Rect area completely includes r area.
+
+#Param r IRect contained ##
+
+#Return true if all sides of IRect are outside r ##
+
+#Example
SkIRect rect = { 30, 50, 40, 60 };
SkIRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
for (auto contained : tests) {
@@ -1239,26 +1243,26 @@ rect: (30, 50, 40, 60) contains (30, 50, 31, 51) rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
##
-## - -#SeeAlso containsNoEmptyCheck SkRect::contains - -## - -# ------------------------------------------------------------------------------ - -#Method bool contains(const SkRect& r) const - -Returns true if Rect contains r. -Returns false if Rect is empty or r is empty. - -Rect contains r when Rect area completely includes r area. - -#Param r Rect contained ## - -#Return true if all sides of IRect are outside r ## - -#Example +##
+
+#SeeAlso containsNoEmptyCheck SkRect::contains
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool contains(const SkRect& r) const
+
+Returns true if Rect contains r.
+Returns false if Rect is empty or r is empty.
+
+Rect contains r when Rect area completely includes r area.
+
+#Param r Rect contained ##
+
+#Return true if all sides of IRect are outside r ##
+
+#Example
SkIRect rect = { 30, 50, 40, 60 };
SkRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
for (auto contained : tests) {
@@ -1272,33 +1276,33 @@ rect: (30, 50, 40, 60) contains (30, 50, 31, 51) rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
##
-## - -#SeeAlso containsNoEmptyCheck SkRect::contains - -## - -# ------------------------------------------------------------------------------ - -#Method bool containsNoEmptyCheck(int32_t left, int32_t top, - int32_t right, int32_t bottom) const - -Constructs IRect from (left, top, right, bottom). Does not sort -construction. - -Returns true if Rect contains construction. -Asserts if IRect is empty or construction is empty, and if SK_DEBUG is defined. - -Return is undefined if Rect is empty or construction is empty. - -#Param left x minimum of constructed Rect ## -#Param top y minimum of constructed Rect ## -#Param right x maximum of constructed Rect ## -#Param bottom y maximum of constructed Rect ## - -#Return true if all sides of IRect are outside construction ## - -#Example +##
+
+#SeeAlso containsNoEmptyCheck SkRect::contains
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool containsNoEmptyCheck(int32_t left, int32_t top,
+ int32_t right, int32_t bottom) const
+
+Constructs IRect from (left, top, right, bottom). Does not sort
+construction.
+
+Returns true if Rect contains construction.
+Asserts if IRect is empty or construction is empty, and if SK_DEBUG is defined.
+
+Return is undefined if Rect is empty or construction is empty.
+
+#Param left x minimum of constructed Rect ##
+#Param top y minimum of constructed Rect ##
+#Param right x maximum of constructed Rect ##
+#Param bottom y maximum of constructed Rect ##
+
+#Return true if all sides of IRect are outside construction ##
+
+#Example
SkIRect rect = { 30, 50, 40, 60 };
SkIRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
for (auto contained : tests) {
@@ -1314,26 +1318,26 @@ rect: (30, 50, 40, 60) contains (30, 50, 31, 51) rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
##
-## - -#SeeAlso contains SkRect::contains - -## - -# ------------------------------------------------------------------------------ - -#Method bool containsNoEmptyCheck(const SkIRect& r) const - -Returns true if Rect contains construction. -Asserts if IRect is empty or construction is empty, and if SK_DEBUG is defined. - -Return is undefined if Rect is empty or construction is empty. - -#Param r Rect contained ## - -#Return true if all sides of IRect are outside r ## - -#Example +##
+
+#SeeAlso contains SkRect::contains
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool containsNoEmptyCheck(const SkIRect& r) const
+
+Returns true if Rect contains construction.
+Asserts if IRect is empty or construction is empty, and if SK_DEBUG is defined.
+
+Return is undefined if Rect is empty or construction is empty.
+
+#Param r Rect contained ##
+
+#Return true if all sides of IRect are outside r ##
+
+#Example
SkIRect rect = { 30, 50, 40, 60 };
SkIRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
for (auto contained : tests) {
@@ -1347,321 +1351,321 @@ rect: (30, 50, 40, 60) contains (30, 50, 31, 51) rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
##
-## - -#SeeAlso contains SkRect::contains - -## - -#Topic Intersection - -IRects intersect when they enclose a common area. To intersect, each of the pair -must describe area; fLeft is less than fRight, and fTop is less than fBottom; -empty() returns false. The intersection of IRect a and IRect b can be described by: -#Formula -(max(a.fLeft, b.fLeft), max(a.fTop, b.fTop), - min(a.fRight, b.fRight), min(a.fBottom, b.fBottom)) -## -The intersection is only meaningful if the resulting IRect is not empty and -describes an area: fLeft is less than fRight, and fTop is less than fBottom. - -# ------------------------------------------------------------------------------ - -#Method bool intersect(const SkIRect& r) - -Returns true if IRect intersects r, and sets IRect to intersection. -Returns false if IRect does not intersect r, and leaves IRect unchanged. - -Returns false if either r or IRect is empty, leaving IRect unchanged. - -#Param r limit of result ## - -#Return true if r and Rect have area in common ## - -#Example -#Description -Two SkDebugf calls are required. If the calls are combined, their arguments -may not be evaluated in left to right order: the printed intersection may -be before or after the call to intersect. -## +##
+
+#SeeAlso contains SkRect::contains
+
+##
+
+#Topic Intersection
+
+IRects intersect when they enclose a common area. To intersect, each of the pair
+must describe area; fLeft is less than fRight, and fTop is less than fBottom;
+empty() returns false. The intersection of IRect pair can be described by:
+#Formula
+(max(a.fLeft, b.fLeft), max(a.fTop, b.fTop),
+ min(a.fRight, b.fRight), min(a.fBottom, b.fBottom))
+##
+The intersection is only meaningful if the resulting IRect is not empty and
+describes an area: fLeft is less than fRight, and fTop is less than fBottom.
+
+# ------------------------------------------------------------------------------
+
+#Method bool intersect(const SkIRect& r)
+
+Returns true if IRect intersects r, and sets IRect to intersection.
+Returns false if IRect does not intersect r, and leaves IRect unchanged.
+
+Returns false if either r or IRect is empty, leaving IRect unchanged.
+
+#Param r limit of result ##
+
+#Return true if r and Rect have area in common ##
+
+#Example
+#Description
+Two SkDebugf calls are required. If the calls are combined, their arguments
+may not be evaluated in left to right order: the printed intersection may
+be before or after the call to intersect.
+##
SkIRect leftRect = { 10, 40, 50, 80 };
SkIRect rightRect = { 30, 60, 70, 90 };
SkDebugf("%s intersection: ", leftRect.intersect(rightRect) ? "" : "no ");
SkDebugf("%d, %d, %d, %d\n", leftRect.left(), leftRect.top(),
- leftRect.right(), leftRect.bottom()); -#StdOut - intersection: 30, 60, 50, 80 -## -## - -#SeeAlso Intersects intersectNoEmptyCheck join SkRect::intersect - -## - -# ------------------------------------------------------------------------------ - -#Method bool SK_WARN_UNUSED_RESULT intersect(const SkIRect& a, const SkIRect& b) - -Returns true if a intersects b, and sets IRect to intersection. -Returns false if a does not intersect b, and leaves IRect unchanged. - -Returns false if either a or b is empty, leaving IRect unchanged. - -#Param a IRect to intersect ## -#Param b IRect to intersect ## - -#Return true if a and b have area in common ## - -#Example + leftRect.right(), leftRect.bottom());
+#StdOut
+ intersection: 30, 60, 50, 80
+##
+##
+
+#SeeAlso Intersects intersectNoEmptyCheck join SkRect::intersect
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool SK_WARN_UNUSED_RESULT intersect(const SkIRect& a, const SkIRect& b)
+
+Returns true if a intersects b, and sets IRect to intersection.
+Returns false if a does not intersect b, and leaves IRect unchanged.
+
+Returns false if either a or b is empty, leaving IRect unchanged.
+
+#Param a IRect to intersect ##
+#Param b IRect to intersect ##
+
+#Return true if a and b have area in common ##
+
+#Example
SkIRect result;
bool intersected = result.intersect({ 10, 40, 50, 80 }, { 30, 60, 70, 90 });
SkDebugf("%s intersection: %d, %d, %d, %d\n", intersected ? "" : "no ",
result.left(), result.top(), result.right(), result.bottom());
-#StdOut - intersection: 30, 60, 50, 80 -## -## - -#SeeAlso Intersects intersectNoEmptyCheck join SkRect::intersect - -## - -# ------------------------------------------------------------------------------ - -#Method bool SK_WARN_UNUSED_RESULT intersectNoEmptyCheck(const SkIRect& a, const SkIRect& b) - -Returns true if a intersects b, and sets IRect to intersection. -Returns false if a does not intersect b, and leaves IRect unchanged. - -Asserts if either a or b is empty, and if SK_DEBUG is defined. - -#Param a IRect to intersect ## -#Param b IRect to intersect ## - -#Return true if a and b have area in common ## - -#Example +#StdOut
+ intersection: 30, 60, 50, 80
+##
+##
+
+#SeeAlso Intersects intersectNoEmptyCheck join SkRect::intersect
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool SK_WARN_UNUSED_RESULT intersectNoEmptyCheck(const SkIRect& a, const SkIRect& b)
+
+Returns true if a intersects b, and sets IRect to intersection.
+Returns false if a does not intersect b, and leaves IRect unchanged.
+
+Asserts if either a or b is empty, and if SK_DEBUG is defined.
+
+#Param a IRect to intersect ##
+#Param b IRect to intersect ##
+
+#Return true if a and b have area in common ##
+
+#Example
SkIRect result;
bool intersected = result.intersectNoEmptyCheck({ 10, 40, 50, 80 }, { 30, 60, 70, 90 });
SkDebugf("intersection: %d, %d, %d, %d\n",
result.left(), result.top(), result.right(), result.bottom());
-#StdOut - intersection: 30, 60, 50, 80 -## -## - -#SeeAlso Intersects intersect join SkRect::intersect - -## - -# ------------------------------------------------------------------------------ - -#Method bool intersect(int32_t left, int32_t top, int32_t right, int32_t bottom) - -Constructs IRect to intersect from (left, top, right, bottom). Does not sort -construction. - -Returns true if IRect intersects construction, and sets IRect to intersection. -Returns false if IRect does not intersect construction, and leaves IRect unchanged. - -Returns false if either construction or IRect is empty, leaving IRect unchanged. - -#Param left x minimum of constructed IRect ## -#Param top y minimum of constructed IRect ## -#Param right x maximum of constructed IRect ## -#Param bottom y maximum of constructed IRect ## - -#Return true if construction and IRect have area in common ## - -#Example -#Description -Two SkDebugf calls are required. If the calls are combined, their arguments -may not be evaluated in left to right order: the printed intersection may -be before or after the call to intersect. -## +#StdOut
+ intersection: 30, 60, 50, 80
+##
+##
+
+#SeeAlso Intersects intersect join SkRect::intersect
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method bool intersect(int32_t left, int32_t top, int32_t right, int32_t bottom)
+
+Constructs IRect to intersect from (left, top, right, bottom). Does not sort
+construction.
+
+Returns true if IRect intersects construction, and sets IRect to intersection.
+Returns false if IRect does not intersect construction, and leaves IRect unchanged.
+
+Returns false if either construction or IRect is empty, leaving IRect unchanged.
+
+#Param left x minimum of constructed IRect ##
+#Param top y minimum of constructed IRect ##
+#Param right x maximum of constructed IRect ##
+#Param bottom y maximum of constructed IRect ##
+
+#Return true if construction and IRect have area in common ##
+
+#Example
+#Description
+Two SkDebugf calls are required. If the calls are combined, their arguments
+may not be evaluated in left to right order: the printed intersection may
+be before or after the call to intersect.
+##
SkIRect leftRect = { 10, 40, 50, 80 };
SkDebugf("%s intersection: ", leftRect.intersect(30, 60, 70, 90) ? "" : "no ");
SkDebugf("%d, %d, %d, %d\n", leftRect.left(), leftRect.top(),
- leftRect.right(), leftRect.bottom()); -#StdOut - intersection: 30, 60, 50, 80 -## -## - -#SeeAlso intersectNoEmptyCheck Intersects join SkRect::intersect - -## - -# ------------------------------------------------------------------------------ - -#Method static bool Intersects(const SkIRect& a, const SkIRect& b) - -Returns true if a intersects b. -Returns false if either a or b is empty, or do not intersect. - -#Param a IRect to intersect ## -#Param b IRect to intersect ## - -#Return true if a and b have area in common ## - -#Example + leftRect.right(), leftRect.bottom());
+#StdOut
+ intersection: 30, 60, 50, 80
+##
+##
+
+#SeeAlso intersectNoEmptyCheck Intersects join SkRect::intersect
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static bool Intersects(const SkIRect& a, const SkIRect& b)
+
+Returns true if a intersects b.
+Returns false if either a or b is empty, or do not intersect.
+
+#Param a IRect to intersect ##
+#Param b IRect to intersect ##
+
+#Return true if a and b have area in common ##
+
+#Example
SkDebugf("%s intersection", SkIRect::Intersects({10, 40, 50, 80}, {30, 60, 70, 90}) ? "" : "no ");
-#StdOut - intersection -## -## - -#SeeAlso IntersectsNoEmptyCheck intersect SkRect::intersect - -## - -# ------------------------------------------------------------------------------ - -#Method static bool IntersectsNoEmptyCheck(const SkIRect& a, const SkIRect& b) - -Returns true if a intersects b. -Asserts if either a or b is empty, and if SK_DEBUG is defined. - -#Param a IRect to intersect ## -#Param b IRect to intersect ## - -#Return true if a and b have area in common ## - -#Example +#StdOut
+ intersection
+##
+##
+
+#SeeAlso IntersectsNoEmptyCheck intersect SkRect::intersect
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static bool IntersectsNoEmptyCheck(const SkIRect& a, const SkIRect& b)
+
+Returns true if a intersects b.
+Asserts if either a or b is empty, and if SK_DEBUG is defined.
+
+#Param a IRect to intersect ##
+#Param b IRect to intersect ##
+
+#Return true if a and b have area in common ##
+
+#Example
SkDebugf("%s intersection", SkIRect::IntersectsNoEmptyCheck(
{10, 40, 50, 80}, {30, 60, 70, 90}) ? "" : "no ");
-#StdOut - intersection -## -## - -#SeeAlso Intersects intersect SkRect::intersect - -## - -#Topic Intersection ## - -# ------------------------------------------------------------------------------ - -#Method void join(int32_t left, int32_t top, int32_t right, int32_t bottom) - -Constructs Rect to intersect from (left, top, right, bottom). Does not sort -construction. - -Sets Rect to the union of itself and the construction. - -Has no effect if construction is empty. Otherwise, if Rect is empty, sets -Rect to construction. - -#Param left x minimum of constructed Rect ## -#Param top y minimum of constructed Rect ## -#Param right x maximum of constructed Rect ## -#Param bottom y maximum of constructed Rect ## - -#Example +#StdOut
+ intersection
+##
+##
+
+#SeeAlso Intersects intersect SkRect::intersect
+
+##
+
+#Topic Intersection ##
+
+# ------------------------------------------------------------------------------
+
+#Method void join(int32_t left, int32_t top, int32_t right, int32_t bottom)
+
+Constructs Rect to intersect from (left, top, right, bottom). Does not sort
+construction.
+
+Sets Rect to the union of itself and the construction.
+
+Has no effect if construction is empty. Otherwise, if Rect is empty, sets
+Rect to construction.
+
+#Param left x minimum of constructed Rect ##
+#Param top y minimum of constructed Rect ##
+#Param right x maximum of constructed Rect ##
+#Param bottom y maximum of constructed Rect ##
+
+#Example
SkIRect rect = { 10, 20, 15, 25};
rect.join(50, 60, 55, 65);
SkDebugf("join: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut - join: 10, 20, 55, 65 -## -## - -#SeeAlso set SkRect::join - -## - -# ------------------------------------------------------------------------------ - -#Method void join(const SkIRect& r) - -Sets Rect to the union of itself and r. - -Has no effect if r is empty. Otherwise, if Rect is empty, sets Rect to r. - -#Param r expansion Rect ## - -#Example +#StdOut
+ join: 10, 20, 55, 65
+##
+##
+
+#SeeAlso set SkRect::join
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void join(const SkIRect& r)
+
+Sets Rect to the union of itself and r.
+
+Has no effect if r is empty. Otherwise, if Rect is empty, sets Rect to r.
+
+#Param r expansion Rect ##
+
+#Example
SkIRect rect = { 10, 20, 15, 25};
rect.join({50, 60, 55, 65});
SkDebugf("join: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut - join: 10, 20, 55, 65 -## -## - -#SeeAlso set SkRect::join - -## - -# ------------------------------------------------------------------------------ - -#Method void sort() - -Swaps fLeft and fRight if fLeft is greater than fRight; and swaps -fTop and fBottom if fTop is greater than fBottom. Result may be empty, -and width() and height() will be zero or positive. - -#Example +#StdOut
+ join: 10, 20, 55, 65
+##
+##
+
+#SeeAlso set SkRect::join
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method void sort()
+
+Swaps fLeft and fRight if fLeft is greater than fRight; and swaps
+fTop and fBottom if fTop is greater than fBottom. Result may be empty,
+and width() and height() will be zero or positive.
+
+#Example
SkIRect rect = { 30, 50, 20, 10 };
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
rect.sort();
SkDebugf("sorted: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut +#StdOut
rect: 30, 50, 20, 10
-sorted: 20, 10, 30, 50 -## -## - -#SeeAlso makeSorted SkRect::sort - -## - -# ------------------------------------------------------------------------------ - -#Method SkIRect makeSorted() const - -Returns Rect with fLeft and fRight swapped if fLeft is greater than fRight; and -with fTop and fBottom swapped if fTop is greater than fBottom. Result may be empty; -and width() and height() will be zero or positive. - -#Return sorted IRect ## - -#Example +sorted: 20, 10, 30, 50
+##
+##
+
+#SeeAlso makeSorted SkRect::sort
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method SkIRect makeSorted() const
+
+Returns Rect with fLeft and fRight swapped if fLeft is greater than fRight; and
+with fTop and fBottom swapped if fTop is greater than fBottom. Result may be empty;
+and width() and height() will be zero or positive.
+
+#Return sorted IRect ##
+
+#Example
SkIRect rect = { 30, 50, 20, 10 };
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
SkIRect sort = rect.makeSorted();
SkDebugf("sorted: %d, %d, %d, %d\n", sort.fLeft, sort.fTop, sort.fRight, sort.fBottom);
-#StdOut +#StdOut
rect: 30, 50, 20, 10
-sorted: 20, 10, 30, 50 -## -## - -#SeeAlso sort SkRect::makeSorted - -## - -# ------------------------------------------------------------------------------ - -#Method static const SkIRect& SK_WARN_UNUSED_RESULT EmptyIRect() - -Returns a reference to immutable empty IRect, set to (0, 0, 0, 0). - -#Return global IRect set to all zeroes ## - -#Example +sorted: 20, 10, 30, 50
+##
+##
+
+#SeeAlso sort SkRect::makeSorted
+
+##
+
+# ------------------------------------------------------------------------------
+
+#Method static const SkIRect& SK_WARN_UNUSED_RESULT EmptyIRect()
+
+Returns a reference to immutable empty IRect, set to (0, 0, 0, 0).
+
+#Return global IRect set to all zeroes ##
+
+#Example
const SkIRect& rect = SkIRect::EmptyIRect();
SkDebugf("rect: %d, %d, %d, %d\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut -rect: 0, 0, 0, 0 -## -## - -#SeeAlso MakeEmpty - -## - -#Struct SkIRect ## - -#Topic IRect ## +#StdOut
+rect: 0, 0, 0, 0
+##
+##
+
+#SeeAlso MakeEmpty
+
+##
+
+#Struct SkIRect ##
+
+#Topic IRect ##
diff --git a/docs/SkMatrix_Reference.bmh b/docs/SkMatrix_Reference.bmh index 0db0fa881e..f91e0096b4 100644 --- a/docs/SkMatrix_Reference.bmh +++ b/docs/SkMatrix_Reference.bmh @@ -1,16 +1,20 @@ #Topic Matrix +#Alias Matrices #Alias Matrix_Reference #Class SkMatrix -Matrix holds a 3x3 matrix for transforming coordinates. -Matrix elements are in column major order. +Matrix holds a 3x3 matrix for transforming coordinates. This allows mapping +Points and Vectors with translation, scaling, skewing, rotation, and +perspective. -SkMatrix does not have a constructor, so it must be explicitly initialized -using either reset() - to construct an identity matrix, or one of the set -functions (e.g. setTranslate, setRotate, etc.). +Matrix elements are in row major order. Matrix does not have a constructor, +so it must be explicitly initialized. setIdentity initializes Matrix +so it has no effect. setTranslate, setScale, setSkew, setRotate, set9 and setAll +initializes all Matrix elements with the corresponding mapping. -SkMatrix is not thread safe unless getType is called first. +Matrix includes a hidden variable that classifies the type of matrix to +improve performance. Matrix is not thread safe unless getType is called first. #Topic Overview @@ -26,111 +30,104 @@ SkMatrix is not thread safe unless getType is called first. #Subtopic Operators #Table #Legend -# description # function ## +# function # description ## #Legend ## -# friend SK_API bool operator!=(const SkMatrix& a, const SkMatrix& b) # Returns true if members are unequal. ## -# friend SK_API bool operator==(const SkMatrix& a, const SkMatrix& b) # Returns true if members are equal. ## -# SkScalar operator[](int index) const # Returns one of nine Matrix values. ## -# SkScalar& operator[](int index) # Returns a writable reference to one of nine Matrix values. ## +# operator!=(const SkMatrix& a, const SkMatrix& b) # Returns true if members are unequal. ## +# operator==(const SkMatrix& a, const SkMatrix& b) # Returns true if members are equal. ## +# operator[](int index) const # Returns Matrix value. ## +# operator[](int index) # Returns writable reference to Matrix value. ## #Table ## #Subtopic ## #Subtopic Member_Functions #Table #Legend -# description # function ## +# function # description ## #Legend ## # Concat # Returns the concatenation of Matrix pair. ## -# GetMapPtsProc # Returns optimal function to map Point array. ## -# GetMapXYProc # Returns optimal function to map one Point. ## # I # Returns a reference to a const identity Matrix. ## # InvalidMatrix # Returns a reference to a const invalid Matrix. ## # MakeRectToRect # Constructs from source Rect to destination Rect. ## # MakeScale # Constructs from scale in x and y. ## # MakeTrans # Constructs from translate in x and y. ## -# SetAffineIdentity # Sets 2x3 array to identity. ## -# asAffine # Copies to 2x3 array. ## +# SetAffineIdentity # Sets 3x2 array to identity. ## +# asAffine # Copies to 3x2 array. ## # cheapEqualTo # Compares Matrix pair using memcmp(). ## # decomposeScale # Separates scale if possible. ## -# dirtyMatrixTypeCache # Private; used by testing. ## -# dump # Sends text representation using floats to standard output. ## +# dirtyMatrixTypeCache # Sets internal cache to unknown state. ## +# dump() # Sends text representation using floats to standard output. ## # fixedStepInX # Returns step in x for a position in y. ## -# get # Returns one of nine Matrix values. ## +# get() # Returns one of nine Matrix values. ## # get9 # Returns all nine Matrix values. ## -# getMapPtsProc # Returns optimal function to map Point array. ## -# getMapXYProc # Returns optimal function to map one Point. ## # getMaxScale # Returns maximum scaling, if possible. ## # getMinMaxScales # Returns minimum and maximum scaling, if possible. ## # getMinScale # Returns minimum scaling, if possible. ## -# getPerspX # Returns horizontal perspective factor. ## -# getPerspY # Returns vertical perspective factor. ## +# getPerspX # Returns input x perspective factor. ## +# getPerspY # Returns input y perspective factor. ## # getScaleX # Returns horizontal scale factor. ## -# getScaleY # Returns vertical scale factor.## +# getScaleY # Returns vertical scale factor. ## # getSkewX # Returns horizontal skew factor. ## # getSkewY # Returns vertical skew factor. ## -# getTranslateX # Returns horizontal translation factor. ## -# getTranslateY # Returns vertical translation factor. ## +# getTranslateX # Returns horizontal translation. ## +# getTranslateY # Returns vertical translation. ## # getType # Returns transform complexity. ## # hasPerspective # Returns if transform includes perspective. ## -# invert # Returns inverse, if possible. ## +# invert() # Returns inverse, if possible. ## # isFinite # Returns if all Matrix values are not infinity, NaN. ## # isFixedStepInX # Returns if transformation supports fixed step in x. ## # isIdentity # Returns if matrix equals the identity Matrix .## # isScaleTranslate # Returns if transform is limited to scale and translate. ## # isSimilarity # Returns if transform is limited to square scale and rotation. ## # isTranslate # Returns if transform is limited to translate. ## -# mapHomogeneousPoints # ## -# mapPoints # ## -# mapPointsWithStride # ## -# mapRadius # ## -# mapRect # ## -# mapRectScaleTranslate # ## -# mapRectToQuad # ## -# mapVector # ## -# mapVectors # ## -# mapXY # ## -# postConcat # ## -# postIDiv # ## -# postRotate # ## -# postScale # ## -# postSkew # ## -# postTranslate # ## -# preConcat # ## -# preRotate # ## -# preScale # ## -# preSkew # ## -# preTranslate # ## -# preservesAxisAlignment # ## -# preservesRightAngles # ## -# readFromMemory # ## -# rectStaysRect # ## -# reset # ## -# set # ## -# set9 # ## -# setAffine # ## -# setAll # ## -# setConcat # ## -# setIDiv # ## -# setIdentity # ## -# setPerspX # ## -# setPerspY # ## -# setPolyToPoly # ## -# setRSXform # ## -# setRectToRect # ## -# setRotate # ## -# setScale # ## -# setScaleTranslate # ## -# setScaleX # ## -# setScaleY # ## -# setSinCos # ## -# setSkew # ## -# setSkewX # ## -# setSkewY # ## -# setTranslate # ## -# setTranslateX # ## -# setTranslateY # ## -# toString # ## -# writeToMemory # ## +# mapHomogeneousPoints # Maps Point3 array. ## +# mapPoints # Maps Point array. ## +# mapPointsWithStride # Maps Point array with padding. ## +# mapRadius # Returns mean radius of mapped Circle. ## +# mapRect # Returns bounds of mapped Rect. ## +# mapRectScaleTranslate # Returns bounds of mapped Rect. ## +# mapRectToQuad # Maps Rect to Point array. ## +# mapVector # Maps Vector. ## +# mapVectors # Maps Vector array. ## +# mapXY # Maps Point. ## +# postConcat # Post-multiplies Matrix by Matrix parameter. ## +# postIDiv # Post-multiplies Matrix by inverse scale. ## +# postRotate # Post-multiplies Matrix by rotation. ## +# postScale # Post-multiplies Matrix by scale. ## +# postSkew # Post-multiplies Matrix by skew. ## +# postTranslate # Post-multiplies Matrix by translation. ## +# preConcat # Pre-multiplies Matrix by Matrix parameter.## +# preRotate # Pre-multiplies Matrix by rotation. ## +# preScale # Pre-multiplies Matrix by scale. ## +# preSkew # Pre-multiplies Matrix by skew. ## +# preTranslate # Pre-multiplies Matrix by translation. ## +# preservesAxisAlignment # Returns if mapping restricts to 90 degree multiples and mirroring. ## +# preservesRightAngles # Returns if mapped 90 angle remains 90 degrees. ## +# rectStaysRect # Returns if mapped Rect can be represented by another Rect. ## +# reset() # Sets Matrix to identity. ## +# set() # Sets one value. ## +# set9 # Sets all values from Scalar array. ## +# setAffine # Sets left two columns. ## +# setAll # Sets all values from parameters. ## +# setConcat # Sets to Matrix parameter multiplied by Matrix parameter. ## +# setIdentity # Sets Matrix to identity. ## +# setPerspX # Sets input x perspective factor. ## +# setPerspY # Sets input y perspective factor. ## +# setPolyToPoly # Sets to map one to four points to an equal array of points. ## +# setRSXform # Sets to rotate, scale, and translate. ## +# setRectToRect # Sets to map one Rect to another. ## +# setRotate # Sets to rotate about a point. ## +# setScale # Sets to scale about a point. ## +# setScaleTranslate # Sets to scale and translate. ## +# setScaleX # Sets horizontal scale factor. ## +# setScaleY # Sets vertical scale factor ## +# setSinCos # Sets to rotate and scale about a point. ## +# setSkew # Sets to skew about a point. ## +# setSkewX # Sets horizontal skew factor. ## +# setSkewY # Sets vertical skew factor. ## +# setTranslate # Sets to translate in x and y. ## +# setTranslateX # Sets horizontal translation. ## +# setTranslateY # Sets vertical translation. ## +# toString # Converts Matrix to machine readable form. ## #Table ## #Subtopic ## @@ -140,16 +137,27 @@ SkMatrix is not thread safe unless getType is called first. #Method static SkMatrix SK_WARN_UNUSED_RESULT MakeScale(SkScalar sx, SkScalar sy) -#Param sx incomplete ## -#Param sy incomplete ## +Sets Matrix to scale by (sx, sy). Returned matrix is: -#Return incomplete ## +#Code +#Literal +| sx 0 0 | +| 0 sy 0 | +| 0 0 1 | +## + +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## + +#Return Matrix with scale ## #Example -// incomplete +#Image 4 +canvas->concat(SkMatrix::MakeScale(4, 3)); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso setScale postScale preScale ## @@ -157,15 +165,26 @@ SkMatrix is not thread safe unless getType is called first. #Method static SkMatrix SK_WARN_UNUSED_RESULT MakeScale(SkScalar scale) -#Param scale incomplete ## +Sets Matrix to scale by (scale, scale). Returned matrix is: + +#Code +#Literal +| scale 0 0 | +| 0 scale 0 | +| 0 0 1 | +## + +#Param scale horizontal and vertical scale factor ## -#Return incomplete ## +#Return Matrix with scale ## #Example -// incomplete +#Image 4 +canvas->concat(SkMatrix::MakeScale(4)); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso setScale postScale preScale ## @@ -173,16 +192,30 @@ SkMatrix is not thread safe unless getType is called first. #Method static SkMatrix SK_WARN_UNUSED_RESULT MakeTrans(SkScalar dx, SkScalar dy) -#Param dx incomplete ## -#Param dy incomplete ## +Sets Matrix to translate by (dx, dy). Returned matrix is: -#Return incomplete ## +#Code +#Literal +| 1 0 0 | +| 0 1 0 | +| dx dy 1 | +## + +#Param dx horizontal translation ## +#Param dy vertical translation ## + +#Return Matrix with translation ## #Example -// incomplete +#Image 4 +SkMatrix matrix = SkMatrix::MakeTrans(64, 48); +for (int i = 0; i < 4; ++i) { + canvas->drawBitmap(source, 0, 0); + canvas->concat(matrix); +} ## -#ToDo incomplete ## +#SeeAlso setTranslate postTranslate preTranslate ## @@ -200,29 +233,57 @@ SkMatrix is not thread safe unless getType is called first. }; ## -Enum of bit fields for the mask return by getType(). -Use this to identify the complexity of the matrix. +Enum of bit fields for mask returned by getType. +Used to identify the complexity of Matrix, to optimize performance. -#Const kIdentity_Mask = 0 +#Const kIdentity_Mask 0 +all bits clear if Matrix is identity ## -#Const kTranslate_Mask = 0x01 -set if the matrix has translation +#Const kTranslate_Mask 1 +set if Matrix has translation ## -#Const kScale_Mask = 0x02 -set if the matrix has x or y scale +#Const kScale_Mask 2 +set if Matrix has x or y scale ## -#Const kAffine_Mask = 0x04 -set if the matrix skews or rotates +#Const kAffine_Mask 4 +set if Matrix skews or rotates ## -#Const kPerspective_Mask = 0x08 -set if the matrix is in perspective +#Const kPerspective_Mask 8 +set if Matrix has perspective ## #Example -// incomplete + auto debugster = [](const char* prefix, const SkMatrix& matrix) -> void { + SkString typeMask; + typeMask += SkMatrix::kIdentity_Mask == matrix.getType() ? "kIdentity_Mask " : ""; + typeMask += SkMatrix::kTranslate_Mask & matrix.getType() ? "kTranslate_Mask " : ""; + typeMask += SkMatrix::kScale_Mask & matrix.getType() ? "kScale_Mask " : ""; + typeMask += SkMatrix::kAffine_Mask & matrix.getType() ? "kAffine_Mask " : ""; + typeMask += SkMatrix::kPerspective_Mask & matrix.getType() ? "kPerspective_Mask" : ""; + SkDebugf("after %s: %s\n", prefix, typeMask.c_str()); + }; +SkMatrix matrix; +matrix.reset(); +debugster("reset", matrix); +matrix.postTranslate(1, 0); +debugster("postTranslate", matrix); +matrix.postScale(2, 1); +debugster("postScale", matrix); +matrix.postRotate(45); +debugster("postScale", matrix); +SkPoint polys[][4] = {{{0, 0}, {0, 1}, {1, 1}, {1, 0}}, {{0, 0}, {0, 1}, {2, 1}, {1, 0}}}; +matrix.setPolyToPoly(polys[0], polys[1], 4); +debugster("setPolyToPoly", matrix); +#StdOut +after reset: kIdentity_Mask +after postTranslate: kTranslate_Mask +after postScale: kTranslate_Mask kScale_Mask +after postScale: kTranslate_Mask kScale_Mask kAffine_Mask +after setPolyToPoly: kTranslate_Mask kScale_Mask kAffine_Mask kPerspective_Mask +## ## -#ToDo incomplete ## +#SeeAlso getType ## @@ -232,17 +293,26 @@ set if the matrix is in perspective Returns a bit field describing the transformations the matrix may perform. The bit field is computed conservatively, so it may include -false positives. For example, when kPerspective_Mask is true, all -other bits may be set to true even in the case of a pure perspective -transform. +false positives. For example, when kPerspective_Mask is set, all +other bits are set. -#Return incomplete ## +#Return kIdentity_Mask, or combinations of: kTranslate_Mask, kScale_Mask, + kAffine_Mask, kPerspective_Mask +## #Example -// incomplete +SkMatrix matrix; +matrix.setAll(1, 0, 0, 0, 1, 0, 0, 0, 1); +SkDebugf("identity flags hex: %0x decimal: %d\n", matrix.getType(), matrix.getType()); +matrix.setAll(1, 0, 0, 0, 1, 0, 0, 0, .5f); +SkDebugf("set all flags hex: %0x decimal: %d\n", matrix.getType(), matrix.getType()); +#StdOut +identity flags hex: 0 decimal: 0 +set all flags hex: f decimal: 15 +## ## -#ToDo incomplete ## +#SeeAlso TypeMask ## @@ -250,15 +320,30 @@ transform. #Method bool isIdentity() const -Returns true if the matrix is identity. +Returns true if Matrix is identity. Identity matrix is: + +#Code +#Literal +| 1 0 0 | +| 0 1 0 | +| 0 0 1 | +## -#Return incomplete ## +#Return true if Matrix has no effect ## #Example -// incomplete +SkMatrix matrix; +matrix.setAll(1, 0, 0, 0, 1, 0, 0, 0, 1); +SkDebugf("is identity: %s\n", matrix.isIdentity() ? "true" : "false"); +matrix.setAll(1, 0, 0, 0, 1, 0, 0, 0, 2); +SkDebugf("is identity: %s\n", matrix.isIdentity() ? "true" : "false"); +#StdOut +is identity: true +is identity: false +## ## -#ToDo incomplete ## +#SeeAlso reset() setIdentity getType ## @@ -266,13 +351,35 @@ Returns true if the matrix is identity. #Method bool isScaleTranslate() const -#Return incomplete ## +Returns true if Matrix at most scales and translates. Matrix may be identity, +contain only scale elements, only translate elements, or both. Matrix form is: + +#Code +#Literal +| scale-x 0 translate-x | +| 0 scale-y translate-y | +| 0 0 1 | +## + +#Return true if Matrix is identity; or scales, translates, or both ## #Example -// incomplete +SkMatrix matrix; +for (SkScalar scaleX : { 1, 2 } ) { + for (SkScalar translateX : { 0, 20 } ) { + matrix.setAll(scaleX, 0, translateX, 0, 1, 0, 0, 0, 1); + SkDebugf("is scale-translate: %s\n", matrix.isScaleTranslate() ? "true" : "false"); + } +} +#StdOut +is scale-translate: true +is scale-translate: true +is scale-translate: true +is scale-translate: true +## ## -#ToDo incomplete ## +#SeeAlso setScale isTranslate setTranslate getType ## @@ -280,13 +387,34 @@ Returns true if the matrix is identity. #Method bool isTranslate() const -#Return incomplete ## +Returns true if Matrix is identity, or translates. Matrix form is: + +#Code +#Literal +| 1 0 translate-x | +| 0 1 translate-y | +| 0 0 1 | +## + +#Return true if Matrix is identity, or translates ## #Example -// incomplete +SkMatrix matrix; +for (SkScalar scaleX : { 1, 2 } ) { + for (SkScalar translateX : { 0, 20 } ) { + matrix.setAll(scaleX, 0, translateX, 0, 1, 0, 0, 0, 1); + SkDebugf("is translate: %s\n", matrix.isTranslate() ? "true" : "false"); + } +} +#StdOut +is translate: true +is translate: true +is translate: false +is translate: false +## ## -#ToDo incomplete ## +#SeeAlso setTranslate getType ## @@ -294,17 +422,48 @@ Returns true if the matrix is identity. #Method bool rectStaysRect() const -Returns true if will map a rectangle to another rectangle. This can be -true if the matrix is identity, scale-only, or rotates a multiple of -90 degrees, or mirrors in x or y. +Returns true Matrix maps Rect to another Rect. If true, Matrix is identity, +or scales, or rotates a multiple of 90 degrees, or mirrors in x or y. In all +cases, Matrix may also have translation. Matrix form is either: + +#Code +#Literal +| scale-x 0 translate-x | +| 0 scale-y translate-y | +| 0 0 1 | +## + +or + +#Code +#Literal +| 0 rotate-x translate-x | +| rotate-y 0 translate-y | +| 0 0 1 | +## + +for non-zero values of scale-x, scale-y, rotate-x, and rotate-y. + +Also called preservesAxisAlignment; use the one that provides better inline +documentation. -#Return incomplete ## +#Return true if Matrix maps one Rect into another ## #Example -// incomplete +SkMatrix matrix; +for (SkScalar angle: { 0, 90, 180, 270 } ) { + matrix.setRotate(angle); + SkDebugf("rectStaysRect: %s\n", matrix.rectStaysRect() ? "true" : "false"); +} +#StdOut +rectStaysRect: true +rectStaysRect: true +rectStaysRect: true +rectStaysRect: true +## ## -#ToDo incomplete ## +#SeeAlso preservesAxisAlignment preservesRightAngles ## @@ -312,15 +471,49 @@ true if the matrix is identity, scale-only, or rotates a multiple of #Method bool preservesAxisAlignment() const -alias for rectStaysRect() -#Return incomplete ## +Returns true Matrix maps Rect to another Rect. If true, Matrix is identity, +or scales, or rotates a multiple of 90 degrees, or mirrors in x or y. In all +cases, Matrix may also have translation. Matrix form is either: + +#Code +#Literal +| scale-x 0 translate-x | +| 0 scale-y translate-y | +| 0 0 1 | +## + +or + +#Code +#Literal +| 0 rotate-x translate-x | +| rotate-y 0 translate-y | +| 0 0 1 | +## + +for non-zero values of scale-x, scale-y, rotate-x, and rotate-y. + +Also called rectStaysRect; use the one that provides better inline +documentation. + +#Return true if Matrix maps one Rect into another ## #Example -// incomplete +SkMatrix matrix; +for (SkScalar angle: { 0, 90, 180, 270 } ) { + matrix.setRotate(angle); + SkDebugf("preservesAxisAlignment: %s\n", matrix.preservesAxisAlignment() ? "true" : "false"); +} +#StdOut +preservesAxisAlignment: true +preservesAxisAlignment: true +preservesAxisAlignment: true +preservesAxisAlignment: true +## ## -#ToDo incomplete ## +#SeeAlso rectStaysRect preservesRightAngles ## @@ -328,15 +521,37 @@ alias for rectStaysRect() #Method bool hasPerspective() const -Returns true if the matrix contains perspective elements. +Returns true if the matrix contains perspective elements. Matrix form is: -#Return incomplete ## +#Code +#Literal +| -- -- -- | +| -- -- -- | +| perspective-x perspective-y perspective-scale | +## + +where perspective-x or perspective-y is non-zero, or perspective-scale is +not one. All other elements may have any value. + +#Return true if Matrix is in most general form ## #Example -// incomplete +#Image 4 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +canvas->concat(matrix); +SkString string; +string.printf("hasPerspective %s", matrix.hasPerspective() ? "true" : "false"); +canvas->drawBitmap(source, 0, 0); +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(48); +canvas->drawString(string, 0, source.bounds().height() + 48, paint); ## -#ToDo incomplete ## +#SeeAlso setAll set9 ## @@ -344,18 +559,50 @@ Returns true if the matrix contains perspective elements. #Method bool isSimilarity(SkScalar tol = SK_ScalarNearlyZero) const -Returns true if the matrix contains only translation, rotation/reflection or uniform scale. -Returns false if other transformation types are included or is degenerate +Returns true if Matrix contains only translation, rotation, reflection, and +uniform scale. +Returns false if Matrix contains different scales, skewing, perspective, or +degenerate forms that collapse to a line or point. -#Param tol incomplete ## +Describes that the Matrix makes rendering with and without the matrix are +visually alike; a transformed circle remains a circle. Mathematically, this is +referred to as similarity of a Euclidean space, or a similarity transformation. -#Return incomplete ## +Preserves right angles, keeping the arms of the angle equal lengths. -#Example -// incomplete -## +#Param tol to be deprecated ## + +#Return true if Matrix only rotates, uniformly scales, translates ## -#ToDo incomplete ## +#Example +#Description +String is drawn four times through but only two are visible. Drawing the pair +with isSimilarity false reveals the pair not visible through the matrix. +## + SkPaint p; + p.setAntiAlias(true); + SkMatrix m; + int below = 175; + for (SkScalar sx : { -1, 1 } ) { + for (SkScalar sy : { -1, 1 } ) { + m.setAll(sx, 1, 128, 1, sy, 32, 0, 0, 1); + bool isSimilarity = m.isSimilarity(); + SkString str; + str.printf("sx: %g sy: %g sim: %s", sx, sy, isSimilarity ? "true" : "false"); + { + SkAutoCanvasRestore autoRestore(canvas, true); + canvas->concat(m); + canvas->drawString(str, 0, 0, p); + } + if (!isSimilarity) { + canvas->drawString(str, 40, below, p); + below += 20; + } + } + } +## + +#SeeAlso isScaleTranslate preservesRightAngles rectStaysRect isFixedStepInX ## @@ -363,25 +610,52 @@ Returns false if other transformation types are included or is degenerate #Method bool preservesRightAngles(SkScalar tol = SK_ScalarNearlyZero) const -Returns true if the matrix contains only translation, rotation/reflection or scale -(non-uniform scale is allowed). -Returns false if other transformation types are included or is degenerate +Returns true if Matrix contains only translation, rotation, reflection, and +scale. Scale may differ along rotated axes. +Returns false if Matrix skewing, perspective, or degenerate forms that collapse +to a line or point. -#Param tol incomplete ## +Preserves right angles, but not requiring that the arms of the angle +retain equal lengths. -#Return incomplete ## +#Param tol to be deprecated ## -#Example -// incomplete -## +#Return true if Matrix only rotates, scales, translates ## -#ToDo incomplete ## +#Example +#Height 128 +#Description +Equal scale is both similar and preserves right angles. +Unequal scale is not similar but preserves right angles. +Skews are not similar and do not preserve right angles. +## +SkPaint p; +p.setAntiAlias(true); +SkMatrix m; +int pos = 0; +for (SkScalar sx : { 1, 2 } ) { + for (SkScalar kx : { 0, 1 } ) { + m.setAll(sx, kx, 16, 0, 1, 32, 0, 0, 1); + bool isSimilarity = m.isSimilarity(); + bool preservesRightAngles = m.preservesRightAngles(); + SkString str; + str.printf("sx: %g kx: %g %s %s", sx, kx, isSimilarity ? "sim" : "", + preservesRightAngles ? "right" : ""); + SkAutoCanvasRestore autoRestore(canvas, true); + canvas->concat(m); + canvas->drawString(str, 0, pos, p); + pos += 20; + } +} +## + +#SeeAlso isScaleTranslate isSimilarity rectStaysRect isFixedStepInX ## # ------------------------------------------------------------------------------ -#Enum _anonymous +#Enum #Code enum { @@ -397,36 +671,65 @@ Returns false if other transformation types are included or is degenerate }; ## +Matrix organizes its values in row order. These members correspond to +each value in Matrix. + #Const kMScaleX 0 +horizontal scale factor ## #Const kMSkewX 1 +horizontal skew factor ## #Const kMTransX 2 +horizontal translation ## #Const kMSkewY 3 +vertical skew factor ## #Const kMScaleY 4 +vertical scale factor ## #Const kMTransY 5 +vertical translation ## #Const kMPersp0 6 +input x perspective factor ## #Const kMPersp1 7 +input y perspective factor ## #Const kMPersp2 8 +perspective bias ## #Example -// incomplete -## - -#ToDo incomplete ## +SkPaint black; +black.setAntiAlias(true); +black.setTextSize(48); +SkPaint gray = black; +gray.setColor(0xFF9f9f9f); +SkScalar offset[] = { 1.5f, 1.5f, 20, 1.5f, 1.5f, 20, .03f, .01f, 2 }; +for (int i : { SkMatrix::kMScaleX, SkMatrix::kMSkewX, SkMatrix::kMTransX, + SkMatrix::kMSkewY, SkMatrix::kMScaleY, SkMatrix::kMTransY, + SkMatrix::kMPersp0, SkMatrix::kMPersp1, SkMatrix::kMPersp2 } ) { + SkMatrix m; + m.setIdentity(); + m.set(i, offset[i]); + SkAutoCanvasRestore autoRestore(canvas, true); + canvas->translate(22 + (i % 3) * 88, 44 + (i / 3) * 88); + canvas->drawString("&", 0, 0, gray); + canvas->concat(m); + canvas->drawString("&", 0, 0, black); +} +## + +#SeeAlso get() set() ## # ------------------------------------------------------------------------------ -#Enum _anonymous_2 +#Enum #Code enum { @@ -439,27 +742,32 @@ Returns false if other transformation types are included or is degenerate }; ## -Affine arrays are in column major order -because that is how PDF and XPS like it. +Affine arrays are in column major order to match the matrix used by +PDF and XPS. #Const kAScaleX 0 +horizontal scale factor ## #Const kASkewY 1 +vertical skew factor ## #Const kASkewX 2 +horizontal skew factor ## #Const kAScaleY 3 +vertical scale factor ## #Const kATransX 4 +horizontal translation ## #Const kATransY 5 +vertical translation ## -#Example -// incomplete +#NoExample ## -#ToDo incomplete ## +#SeeAlso SetAffineIdentity asAffine setAffine ## @@ -467,15 +775,27 @@ because that is how PDF and XPS like it. #Method SkScalar operator[](int index) const -#Param index incomplete ## +Returns one matrix value. Asserts if index is out of range and SK_DEBUG is +defined. + +#Param index one of: kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, + kMPersp0, kMPersp1, kMPersp2 +## -#Return incomplete ## +#Return value corresponding to index ## #Example -// incomplete +SkMatrix matrix; +matrix.setScale(42, 24); +SkDebugf("matrix[SkMatrix::kMScaleX] %c= 42\n", matrix[SkMatrix::kMScaleX] == 42 ? '=' : '!'); +SkDebugf("matrix[SkMatrix::kMScaleY] %c= 24\n", matrix[SkMatrix::kMScaleY] == 24 ? '=' : '!'); +#StdOut +matrix[SkMatrix::kMScaleX] == 42 +matrix[SkMatrix::kMScaleY] == 24 +## ## -#ToDo incomplete ## +#SeeAlso get set ## @@ -483,15 +803,29 @@ because that is how PDF and XPS like it. #Method SkScalar get(int index) const -#Param index incomplete ## +Returns one matrix value. Asserts if index is out of range and SK_DEBUG is +defined. -#Return incomplete ## +#Param index one of: kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, + kMPersp0, kMPersp1, kMPersp2 +## + +#Return value corresponding to index ## #Example -// incomplete +SkMatrix matrix; +matrix.setSkew(42, 24); +SkDebugf("matrix.get(SkMatrix::kMSkewX) %c= 42\n", + matrix.get(SkMatrix::kMSkewX) == 42 ? '=' : '!'); +SkDebugf("matrix.get(SkMatrix::kMSkewY) %c= 24\n", + matrix.get(SkMatrix::kMSkewY) == 24 ? '=' : '!'); +#StdOut +matrix.get(SkMatrix::kMSkewX) == 42 +matrix.get(SkMatrix::kMSkewY) == 24 +## ## -#ToDo incomplete ## +#SeeAlso operator[](int index) set ## @@ -499,13 +833,21 @@ because that is how PDF and XPS like it. #Method SkScalar getScaleX() const -#Return incomplete ## +Returns scale factor multiplied by x input, contributing to x output. +With mapPoints, scales Points along the x-axis. + +#Return horizontal scale factor ## #Example -// incomplete +SkMatrix matrix; +matrix.setScale(42, 24); +SkDebugf("matrix.getScaleX() %c= 42\n", matrix.getScaleX() == 42 ? '=' : '!'); +#StdOut +matrix.getScaleX() == 42 +## ## -#ToDo incomplete ## +#SeeAlso get getScaleY setScaleX setScale ## @@ -513,13 +855,21 @@ because that is how PDF and XPS like it. #Method SkScalar getScaleY() const -#Return incomplete ## +Returns scale factor multiplied by y input, contributing to y output. +With mapPoints, scales Points along the y-axis. + +#Return vertical scale factor ## #Example -// incomplete +SkMatrix matrix; +matrix.setScale(42, 24); +SkDebugf("matrix.getScaleY() %c= 24\n", matrix.getScaleY() == 24 ? '=' : '!'); +#StdOut +matrix.getScaleY() == 24 +## ## -#ToDo incomplete ## +#SeeAlso get getScaleX setScaleY setScale ## @@ -527,13 +877,22 @@ because that is how PDF and XPS like it. #Method SkScalar getSkewY() const -#Return incomplete ## +Returns scale factor multiplied by x input, contributing to y output. +With mapPoints, skews Points along the y-axis. +Skew x and y together can rotate Points. + +#Return vertical skew factor ## #Example -// incomplete +SkMatrix matrix; +matrix.setSkew(42, 24); +SkDebugf("matrix.getSkewY() %c= 24\n", matrix.getSkewY() == 24 ? '=' : '!'); +#StdOut +matrix.getSkewY() == 24 +## ## -#ToDo incomplete ## +#SeeAlso get getSkewX setSkewY setSkew ## @@ -541,13 +900,22 @@ because that is how PDF and XPS like it. #Method SkScalar getSkewX() const -#Return incomplete ## +Returns scale factor multiplied by y input, contributing to x output. +With mapPoints, skews Points along the x-axis. +Skew x and y together can rotate Points. + +#Return horizontal scale factor ## #Example -// incomplete +SkMatrix matrix; +matrix.setSkew(42, 24); +SkDebugf("matrix.getSkewX() %c= 42\n", matrix.getSkewX() == 42 ? '=' : '!'); +#StdOut +matrix.getSkewX() == 42 +## ## -#ToDo incomplete ## +#SeeAlso get getSkewY setSkewX setSkew ## @@ -555,13 +923,21 @@ because that is how PDF and XPS like it. #Method SkScalar getTranslateX() const -#Return incomplete ## +Returns translation contributing to x output. +With mapPoints, moves Points along the x-axis. + +#Return horizontal translation factor ## #Example -// incomplete +SkMatrix matrix; +matrix.setTranslate(42, 24); +SkDebugf("matrix.getTranslateX() %c= 42\n", matrix.getTranslateX() == 42 ? '=' : '!'); +#StdOut +matrix.getTranslateX() == 42 +## ## -#ToDo incomplete ## +#SeeAlso get getTranslateY setTranslateX setTranslate ## @@ -569,13 +945,21 @@ because that is how PDF and XPS like it. #Method SkScalar getTranslateY() const -#Return incomplete ## +Returns translation contributing to y output. +With mapPoints, moves Points along the y-axis. + +#Return vertical translation factor ## #Example -// incomplete +SkMatrix matrix; +matrix.setTranslate(42, 24); +SkDebugf("matrix.getTranslateY() %c= 24\n", matrix.getTranslateY() == 24 ? '=' : '!'); +#StdOut +matrix.getTranslateY() == 24 +## ## -#ToDo incomplete ## +#SeeAlso get getTranslateX setTranslateY setTranslate ## @@ -583,13 +967,29 @@ because that is how PDF and XPS like it. #Method SkScalar getPerspX() const -#Return incomplete ## +Returns factor scaling input x relative to input y. + +#Return input x perspective factor ## #Example -// incomplete + SkMatrix m; + m.setIdentity(); + m.set(SkMatrix::kMPersp0, -0.004f); + SkAutoCanvasRestore autoRestore(canvas, true); + canvas->translate(22, 144); + SkPaint black; + black.setAntiAlias(true); + black.setTextSize(24); + SkPaint gray = black; + gray.setColor(0xFF9f9f9f); + SkString string; + string.appendScalar(m.getPerspX()); + canvas->drawString(string, 0, -72, gray); + canvas->concat(m); + canvas->drawString(string, 0, 0, black); ## -#ToDo incomplete ## +#SeeAlso kMPersp0 getPerspY ## @@ -597,29 +997,69 @@ because that is how PDF and XPS like it. #Method SkScalar getPerspY() const -#Return incomplete ## + +Returns factor scaling input y relative to input x. + +#Return input y perspective factor ## #Example -// incomplete + SkMatrix m; + m.setIdentity(); + m.set(SkMatrix::kMPersp1, -0.004f); + SkAutoCanvasRestore autoRestore(canvas, true); + canvas->translate(22, 144); + SkPaint black; + black.setAntiAlias(true); + black.setTextSize(24); + SkPaint gray = black; + gray.setColor(0xFF9f9f9f); + SkString string; + string.appendScalar(m.getPerspY()); + canvas->drawString(string, 0, -72, gray); + canvas->concat(m); + canvas->drawString(string, 0, 0, black); ## -#ToDo incomplete ## +#SeeAlso kMPersp1 getPerspX ## # ------------------------------------------------------------------------------ -#Method SkScalar operator[](int index) +#Method SkScalar& operator[](int index) -#Param index incomplete ## +Returns writable Matrix value. Asserts if index is out of range and SK_DEBUG is +defined. Clears internal cache anticipating that caller will change Matrix value. -#Return incomplete ## +Next call to read Matrix state may recompute cache; subsequent writes to Matrix +value must be followed by dirtyMatrixTypeCache. + +#Param index one of: kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, + kMPersp0, kMPersp1, kMPersp2 +## + +#Return writable value corresponding to index ## #Example -// incomplete +SkMatrix matrix; +matrix.setIdentity(); +SkDebugf("with identity matrix: x = %g\n", matrix.mapXY(24, 42).fX); +SkScalar& skewRef = matrix[SkMatrix::kMSkewX]; +skewRef = 0; +SkDebugf("after skew x mod: x = %g\n", matrix.mapXY(24, 42).fX); +skewRef = 1; +SkDebugf("after 2nd skew x mod: x = %g\n", matrix.mapXY(24, 42).fX); +matrix.dirtyMatrixTypeCache(); +SkDebugf("after dirty cache: x = %g\n", matrix.mapXY(24, 42).fX); +#StdOut +with identity matrix: x = 24 +after skew x mod: x = 24 +after 2nd skew x mod: x = 24 +after dirty cache: x = 66 +## ## -#ToDo incomplete ## +#SeeAlso get dirtyMatrixTypeCache set ## @@ -627,128 +1067,236 @@ because that is how PDF and XPS like it. #Method void set(int index, SkScalar value) -#Param index incomplete ## -#Param value incomplete ## +Sets Matrix value. Asserts if index is out of range and SK_DEBUG is +defined. Safer than operator[]; internal cache is always maintained. + +#Param index one of: kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, + kMPersp0, kMPersp1, kMPersp2 +## +#Param value Scalar to store in Matrix ## #Example -// incomplete +SkMatrix matrix; +matrix.setIdentity(); +SkDebugf("with identity matrix: x = %g\n", matrix.mapXY(24, 42).fX); +matrix.set(SkMatrix::kMSkewX, 0); +SkDebugf("after skew x mod: x = %g\n", matrix.mapXY(24, 42).fX); +matrix.set(SkMatrix::kMSkewX, 1); +SkDebugf("after 2nd skew x mod: x = %g\n", matrix.mapXY(24, 42).fX); +#StdOut +with identity matrix: x = 24 +after skew x mod: x = 24 +after 2nd skew x mod: x = 66 +## ## -#ToDo incomplete ## +#SeeAlso operator[] get -## +#Method ## # ------------------------------------------------------------------------------ #Method void setScaleX(SkScalar v) -#Param v incomplete ## +Sets horizontal scale factor. + +#Param v horizontal scale factor to store ## #Example -// incomplete +#Height 64 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 12, 24, paint); +SkMatrix matrix; +matrix.setIdentity(); +matrix.setScaleX(3); +canvas->concat(matrix); +canvas->drawString("x scale", 0, 48, paint); ## -#ToDo incomplete ## +#SeeAlso set setScale setScaleY -## +#Method ## # ------------------------------------------------------------------------------ #Method void setScaleY(SkScalar v) -#Param v incomplete ## +Sets vertical scale factor. + +#Param v vertical scale factor to store ## #Example -// incomplete +#Height 192 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 12, 24, paint); +SkMatrix matrix; +matrix.setIdentity(); +matrix.setScaleY(3); +canvas->concat(matrix); +canvas->drawString("y scale", 12, 48, paint); ## -#ToDo incomplete ## +#SeeAlso set setScale setScaleX -## +#Method ## # ------------------------------------------------------------------------------ #Method void setSkewY(SkScalar v) -#Param v incomplete ## +Sets vertical skew factor. + +#Param v vertical skew factor to store ## #Example -// incomplete +#Height 96 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 12, 24, paint); +SkMatrix matrix; +matrix.setIdentity(); +matrix.setSkewY(.3f); +canvas->concat(matrix); +canvas->drawString("y skew", 12, 48, paint); ## -#ToDo incomplete ## +#SeeAlso set setSkew setSkewX -## +#Method ## # ------------------------------------------------------------------------------ #Method void setSkewX(SkScalar v) -#Param v incomplete ## +Sets horizontal skew factor. + +#Param v horizontal skew factor to store ## #Example -// incomplete +#Height 64 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 12, 24, paint); +SkMatrix matrix; +matrix.setIdentity(); +matrix.setSkewX(-.7f); +canvas->concat(matrix); +canvas->drawString("x skew", 36, 48, paint); ## -#ToDo incomplete ## +#SeeAlso set setSkew setSkewX -## +#Method ## # ------------------------------------------------------------------------------ #Method void setTranslateX(SkScalar v) -#Param v incomplete ## +Sets horizontal translation. + +#Param v horizontal translation to store ## #Example -// incomplete +#Height 48 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 8, 24, paint); +SkMatrix matrix; +matrix.setIdentity(); +matrix.setTranslateX(96); +canvas->concat(matrix); +canvas->drawString("x translate", 8, 24, paint); ## -#ToDo incomplete ## +#SeeAlso set setTranslate setTranslateY -## +#Method ## # ------------------------------------------------------------------------------ #Method void setTranslateY(SkScalar v) -#Param v incomplete ## +Sets vertical translation. + +#Param v vertical translation to store ## #Example -// incomplete +#Height 64 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 8, 24, paint); +SkMatrix matrix; +matrix.setIdentity(); +matrix.setTranslateY(24); +canvas->concat(matrix); +canvas->drawString("y translate", 8, 24, paint); ## -#ToDo incomplete ## +#SeeAlso set setTranslate setTranslateX -## +#Method ## # ------------------------------------------------------------------------------ #Method void setPerspX(SkScalar v) -#Param v incomplete ## +Sets input x perspective factor, which causes mapXY to vary input x inversely +proportional to input y. + +#Param v perspective factor ## #Example -// incomplete +#Image 4 +for (SkScalar perspX : { -.003f, 0.f, .003f, .012f } ) { + SkMatrix matrix; + matrix.setIdentity(); + matrix.setPerspX(perspX); + canvas->save(); + canvas->concat(matrix); + canvas->drawBitmap(source, 0, 0); + canvas->restore(); + canvas->translate(64, 64); +} ## -#ToDo incomplete ## +#SeeAlso getPerspX set setAll set9 -## +#Method ## # ------------------------------------------------------------------------------ #Method void setPerspY(SkScalar v) -#Param v incomplete ## +Sets input y perspective factor, which causes mapXY to vary input y inversely +proportional to input x. + +#Param v perspective factor ## #Example -// incomplete +#Image 4 +for (SkScalar perspX : { -.003f, 0.f, .003f, .012f } ) { + SkMatrix matrix; + matrix.setIdentity(); + matrix.setPerspY(perspX); + canvas->save(); + canvas->concat(matrix); + canvas->drawBitmap(source, 0, 0); + canvas->restore(); + canvas->translate(64, 64); +} ## -#ToDo incomplete ## +#SeeAlso getPerspY set setAll set9 -## +#Method ## # ------------------------------------------------------------------------------ @@ -756,528 +1304,1066 @@ because that is how PDF and XPS like it. SkScalar skewY, SkScalar scaleY, SkScalar transY, SkScalar persp0, SkScalar persp1, SkScalar persp2) -#Param scaleX incomplete ## -#Param skewX incomplete ## -#Param transX incomplete ## -#Param skewY incomplete ## -#Param scaleY incomplete ## -#Param transY incomplete ## -#Param persp0 incomplete ## -#Param persp1 incomplete ## -#Param persp2 incomplete ## +Sets all values from parameters. Sets matrix to: + +#Code +#Literal +| scaleX skewX transX | +| skewY scaleY transY | +| persp0 persp1 persp2 | +## + +#Param scaleX horizontal scale factor to store ## +#Param skewX horizontal skew factor to store ## +#Param transX horizontal translation to store ## +#Param skewY vertical skew factor to store ## +#Param scaleY vertical scale factor to store ## +#Param transY vertical translation to store ## +#Param persp0 input x perspective factor to store ## +#Param persp1 input y perspective factor to store ## +#Param persp2 perspective scale factor to store ## #Example -// incomplete + SkPaint p; + p.setAntiAlias(true); + p.setTextSize(64); + SkMatrix m; + for (SkScalar sx : { -1, 1 } ) { + for (SkScalar sy : { -1, 1 } ) { + SkAutoCanvasRestore autoRestore(canvas, true); + m.setAll(sx, 1, 128, 0, sy, 128, 0, 0, 1); + canvas->concat(m); + canvas->drawString("K", 0, 0, p); + } + } ## -#ToDo incomplete ## +#SeeAlso set9 -## +#Method ## # ------------------------------------------------------------------------------ #Method void get9(SkScalar buffer[9]) const -Copy the 9 scalars for this matrix into buffer, in member value ascending order: -kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, kMPersp0, kMPersp1, kMPersp2. +Copies nine Scalar values contained by Matrix into buffer, in member value +ascending order: kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, +kMPersp0, kMPersp1, kMPersp2. -#Param buffer incomplete ## +#Param buffer storage for nine Scalar values ## #Example -// incomplete +SkMatrix matrix = SkMatrix::MakeRectToRect({0, 0, 1, 1}, {3, 4, 7, 9}, + SkMatrix::kFill_ScaleToFit); +SkScalar b[9]; +matrix.get9(b); +SkDebugf("{%g, %g, %g},\n{%g, %g, %g},\n{%g, %g, %g}\n", b[0], b[1], b[2], + b[3], b[4], b[5], b[6], b[7], b[8]); +#StdOut +{4, 0, 3}, +{0, 5, 4}, +{0, 0, 1} +## ## -#ToDo incomplete ## +#SeeAlso set9 -## +#Method ## # ------------------------------------------------------------------------------ #Method void set9(const SkScalar buffer[9]) -Set this matrix to the 9 scalars from the buffer, in member value ascending order: -kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, kMPersp0, kMPersp1, kMPersp2. +Sets Matrix to nine Scalar values in buffer, in member value ascending order: +kMScaleX, kMSkewX, kMTransX, kMSkewY, kMScaleY, kMTransY, kMPersp0, kMPersp1, +kMPersp2. + +Sets matrix to: -Note: calling set9 followed by get9 may not return the exact same values. Since the matrix -is used to map non-homogeneous coordinates, it is free to scale the 9 values as needed. +#Code +#Literal +| buffer[0] buffer[1] buffer[2] | +| buffer[3] buffer[4] buffer[5] | +| buffer[6] buffer[7] buffer[8] | +## + +In the future, set9 followed by get9 may not return the same values. Since Matrix +maps non-homogeneous coordinates, scaling all nine values produces an equivalent +transformation, possibly improving precision. -#Param buffer incomplete ## +#Param buffer nine Scalar values ## #Example -// incomplete +#Image 4 +SkMatrix m; +SkScalar buffer[9] = {4, 0, 3, 0, 5, 4, 0, 0, 1}; +m.set9(buffer); +canvas->concat(m); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso setAll get9 -## +#Method ## # ------------------------------------------------------------------------------ #Method void reset() -Set the matrix to identity +Sets Matrix to identity; which has no effect on mapped Points. Sets Matrix to: -#Example -// incomplete +#Code +#Literal +| 1 0 0 | +| 0 1 0 | +| 0 0 1 | ## -#ToDo incomplete ## +Also called setIdentity(); use the one that provides better inline +documentation. +#Example +SkMatrix m; +m.reset(); +SkDebugf("m.isIdentity(): %s\n", m.isIdentity() ? "true" : "false"); +#StdOut +m.isIdentity(): true +## ## +#SeeAlso isIdentity setIdentity + +#Method ## + # ------------------------------------------------------------------------------ #Method void setIdentity() -alias for reset() +Sets Matrix to identity; which has no effect on mapped Points. Sets Matrix to: -#Example -// incomplete +#Code +#Literal +| 1 0 0 | +| 0 1 0 | +| 0 0 1 | ## -#ToDo incomplete ## +Also called reset(); use the one that provides better inline +documentation. +#Example +SkMatrix m; +m.setIdentity(); +SkDebugf("m.isIdentity(): %s\n", m.isIdentity() ? "true" : "false"); +#StdOut +m.isIdentity(): true +## ## +#SeeAlso isIdentity reset + +#Method ## + # ------------------------------------------------------------------------------ #Method void setTranslate(SkScalar dx, SkScalar dy) -Set the matrix to translate by (dx, dy). +Sets Matrix to translate by (dx, dy). -#Param dx incomplete ## -#Param dy incomplete ## +#Param dx horizontal translation ## +#Param dy vertical translation ## #Example -// incomplete +#Height 64 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 8, 24, paint); +SkMatrix matrix; +matrix.setTranslate(96, 24); +canvas->concat(matrix); +canvas->drawString("translate", 8, 24, paint); ## -#ToDo incomplete ## +#SeeAlso setTranslateX setTranslateY -## +#Method ## # ------------------------------------------------------------------------------ #Method void setTranslate(const SkVector& v) -#Param v incomplete ## +Sets Matrix to translate by (v.fX, v.fY). + +#Param v Vector containing horizontal and vertical translation ## #Example -// incomplete +#Height 64 +SkPaint paint; +paint.setAntiAlias(true); +paint.setTextSize(24); +canvas->drawString("normal", 8, 24, paint); +SkMatrix matrix; +matrix.setTranslate({96, 24}); +canvas->concat(matrix); +canvas->drawString("translate", 8, 24, paint); ## -#ToDo incomplete ## +#SeeAlso setTranslateX setTranslateY MakeTrans -## +#Method ## # ------------------------------------------------------------------------------ #Method void setScale(SkScalar sx, SkScalar sy, SkScalar px, SkScalar py) -Set the matrix to scale by sx and sy, with a pivot point at (px, py). -The pivot point is the coordinate that should remain unchanged by the -specified transformation. +Sets Matrix to scale by sx and sy, about a pivot point at (px, py). +The pivot point is unchanged when mapped with Matrix. -#Param sx incomplete ## -#Param sy incomplete ## -#Param px incomplete ## -#Param py incomplete ## +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete + SkPaint p; + p.setAntiAlias(true); + p.setTextSize(64); + SkMatrix m; + for (SkScalar sx : { -1, 1 } ) { + for (SkScalar sy : { -1, 1 } ) { + SkAutoCanvasRestore autoRestore(canvas, true); + m.setScale(sx, sy, 128, 128); + canvas->concat(m); + canvas->drawString("K", 128, 128, p); + } + } ## -#ToDo incomplete ## +#SeeAlso setScaleX setScaleY MakeScale preScale postScale -## +#Method ## # ------------------------------------------------------------------------------ #Method void setScale(SkScalar sx, SkScalar sy) -Set the matrix to scale by sx and sy. - -#Param sx incomplete ## -#Param sy incomplete ## - -#Example -// incomplete -## - -#ToDo incomplete ## - -## - -# ------------------------------------------------------------------------------ - -#Method bool setIDiv(int divx, int divy) - -Set the matrix to scale by 1/divx and 1/divy. Returns false and does not -touch the matrix if either divx or divy is zero. - -#Param divx incomplete ## -#Param divy incomplete ## +Sets Matrix to scale by sx and sy about at pivot point at (0, 0). -#Return incomplete ## +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## #Example -// incomplete + SkPaint p; + p.setAntiAlias(true); + p.setTextSize(64); + SkMatrix m; + for (SkScalar sx : { -1, 1 } ) { + for (SkScalar sy : { -1, 1 } ) { + SkAutoCanvasRestore autoRestore(canvas, true); + m.setScale(sx, sy); + m.postTranslate(128, 128); + canvas->concat(m); + canvas->drawString("K", 0, 0, p); + } + } ## -#ToDo incomplete ## +#SeeAlso setScaleX setScaleY MakeScale preScale postScale -## +#Method ## # ------------------------------------------------------------------------------ #Method void setRotate(SkScalar degrees, SkScalar px, SkScalar py) -Set the matrix to rotate by the specified number of degrees, with a -pivot point at (px, py). The pivot point is the coordinate that should -remain unchanged by the specified transformation. +Sets Matrix to rotate by degrees about a pivot point at (px, py). +The pivot point is unchanged when mapped with Matrix. + +Positive degrees rotates clockwise. -#Param degrees incomplete ## -#Param px incomplete ## -#Param py incomplete ## +#Param degrees angle of axes relative to upright axes ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete +#Height 128 + SkPaint paint; + paint.setColor(SK_ColorGRAY); + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + canvas->drawRect(rect, paint); + paint.setColor(SK_ColorRED); + SkMatrix matrix; + matrix.setRotate(25, rect.centerX(), rect.centerY()); + canvas->concat(matrix); + canvas->drawRect(rect, paint); ## -#ToDo incomplete ## +#SeeAlso setSinCos preRotate postRotate -## +#Method ## # ------------------------------------------------------------------------------ #Method void setRotate(SkScalar degrees) -Set the matrix to rotate about (0,0) by the specified number of degrees. +Sets Matrix to rotate by degrees about a pivot point at (0, 0). +Positive degrees rotates clockwise. -#Param degrees incomplete ## +#Param degrees angle of axes relative to upright axes ## #Example -// incomplete +#Height 128 + SkPaint paint; + paint.setColor(SK_ColorGRAY); + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + canvas->drawRect(rect, paint); + paint.setColor(SK_ColorRED); + SkMatrix matrix; + matrix.setRotate(25); + canvas->translate(rect.centerX(), rect.centerY()); + canvas->concat(matrix); + canvas->translate(-rect.centerX(), -rect.centerY()); + canvas->drawRect(rect, paint); ## -#ToDo incomplete ## +#SeeAlso setSinCos preRotate postRotate -## +#Method ## # ------------------------------------------------------------------------------ #Method void setSinCos(SkScalar sinValue, SkScalar cosValue, SkScalar px, SkScalar py) -Set the matrix to rotate by the specified sine and cosine values, with -a pivot point at (px, py). The pivot point is the coordinate that -should remain unchanged by the specified transformation. +Sets Matrix to rotate by sinValue and cosValue, about a pivot point at (px, py). +The pivot point is unchanged when mapped with Matrix. + +Vector (sinValue, cosValue) describes the angle of rotation relative to (0, 1). +Vector length specifies scale. -#Param sinValue incomplete ## -#Param cosValue incomplete ## -#Param px incomplete ## -#Param py incomplete ## +#Param sinValue rotation vector x component ## +#Param cosValue rotation vector y component ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete +#Height 128 + SkPaint paint; + paint.setColor(SK_ColorGRAY); + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + canvas->drawRect(rect, paint); + paint.setColor(SK_ColorRED); + SkMatrix matrix; + matrix.setSinCos(.25f, .85f, rect.centerX(), rect.centerY()); + canvas->concat(matrix); + canvas->drawRect(rect, paint); ## -#ToDo incomplete ## +#SeeAlso setRotate setScale setRSXform -## +#Method ## # ------------------------------------------------------------------------------ #Method void setSinCos(SkScalar sinValue, SkScalar cosValue) -Set the matrix to rotate by the specified sine and cosine values. +Sets Matrix to rotate by sinValue and cosValue, about a pivot point at (0, 0). + +Vector (sinValue, cosValue) describes the angle of rotation relative to (0, 1). +Vector length specifies scale. -#Param sinValue incomplete ## -#Param cosValue incomplete ## +#Param sinValue rotation vector x component ## +#Param cosValue rotation vector y component ## #Example -// incomplete +#Description +Canvas needs offset after applying Matrix to pivot about Rect center. +## +#Height 128 + SkPaint paint; + paint.setColor(SK_ColorGRAY); + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + canvas->drawRect(rect, paint); + paint.setColor(SK_ColorRED); + SkMatrix matrix; + matrix.setSinCos(.25f, .85f); + matrix.postTranslate(rect.centerX(), rect.centerY()); + canvas->concat(matrix); + canvas->translate(-rect.centerX(), -rect.centerY()); + canvas->drawRect(rect, paint); ## -#ToDo incomplete ## +#SeeAlso setRotate setScale setRSXform -## +#Method ## # ------------------------------------------------------------------------------ #Method SkMatrix& setRSXform(const SkRSXform& rsxForm) -#Param rsxForm incomplete ## +Sets Matrix to rotate, scale, and translate using a compressed matrix form. + +Vector (rsxForm.fSSin, rsxForm.fSCos) describes the angle of rotation relative +to (0, 1). Vector length specifies scale. Mapped point is rotated and scaled +by Vector, then translated by (rsxForm.fTx, rsxForm.fTy). -#Return incomplete ## +#Param rsxForm compressed RSXform matrix ## + +#Return reference to Matrix ## #Example -// incomplete +#Description +Canvas needs offset after applying Matrix to pivot about Rect center. +## +#Height 128 + SkPaint paint; + paint.setColor(SK_ColorGRAY); + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + canvas->drawRect(rect, paint); + paint.setColor(SK_ColorRED); + SkMatrix matrix; + matrix.setRSXform(SkRSXform::Make(.85f, .25f, rect.centerX(), rect.centerY())); + canvas->concat(matrix); + canvas->translate(-rect.centerX(), -rect.centerY()); + canvas->drawRect(rect, paint); ## -#ToDo incomplete ## +#SeeAlso setSinCos setScale setTranslate -## +#Method ## # ------------------------------------------------------------------------------ #Method void setSkew(SkScalar kx, SkScalar ky, SkScalar px, SkScalar py) -Set the matrix to skew by kx and ky, with a pivot point at (px, py). -The pivot point is the coordinate that should remain unchanged by the -specified transformation. +Sets Matrix to skew by kx and ky, about a pivot point at (px, py). +The pivot point is unchanged when mapped with Matrix. -#Param kx incomplete ## -#Param ky incomplete ## -#Param px incomplete ## -#Param py incomplete ## +#Param kx horizontal skew factor ## +#Param ky vertical skew factor ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete + SkPaint p; + p.setAntiAlias(true); + p.setTextSize(48); + SkMatrix m; + for (SkScalar sx : { -1, 0, 1 } ) { + for (SkScalar sy : { -1, 0, 1 } ) { + SkAutoCanvasRestore autoRestore(canvas, true); + m.setSkew(sx, sy, 96 + 64 * sx, 128 + 48 * sy); + canvas->concat(m); + canvas->drawString("K", 96 + 64 * sx, 128 + 48 * sy, p); + } + } ## -#ToDo incomplete ## +#SeeAlso setSkewX setSkewY preSkew postSkew -## +#Method ## # ------------------------------------------------------------------------------ #Method void setSkew(SkScalar kx, SkScalar ky) -Set the matrix to skew by kx and ky. +Sets Matrix to skew by kx and ky, about a pivot point at (0, 0). -#Param kx incomplete ## -#Param ky incomplete ## +#Param kx horizontal skew factor ## +#Param ky vertical skew factor ## #Example -// incomplete + SkPaint p; + p.setAntiAlias(true); + p.setTextSize(48); + SkMatrix m; + for (SkScalar sx : { -1, 0, 1 } ) { + for (SkScalar sy : { -1, 0, 1 } ) { + SkAutoCanvasRestore autoRestore(canvas, true); + m.setSkew(sx, sy); + m.postTranslate(96 + 64 * sx, 128 + 48 * sy); + canvas->concat(m); + canvas->drawString("K", 0, 0, p); + } + } ## -#ToDo incomplete ## +#SeeAlso setSkewX setSkewY preSkew postSkew -## +#Method ## # ------------------------------------------------------------------------------ #Method void setConcat(const SkMatrix& a, const SkMatrix& b) -Set the matrix to the concatenation of the two specified matrices. -Either of the two matrices may also be the target matrix. -this = a * b; +Sets Matrix to Matrix a multiplied by Matrix b. Either a or b may be this. -#Param a incomplete ## -#Param b incomplete ## +Given: -#Example -// incomplete +#Code +#Literal + | A B C | | J K L | +a = | D E F |, b = | M N O | + | G H I | | P Q R | ## -#ToDo incomplete ## +sets Matrix to: +#Code +#Literal + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +a * b = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR | ## +#Param a Matrix on left side of multiply expression ## +#Param b Matrix on right side of multiply expression ## + +#Example +#Image 3 +#Description +setPolyToPoly creates perspective matrices, one the inverse of the other. +Multiplying the matrix by its inverse turns into an identity matrix. +## +SkMatrix matrix, matrix2; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix2.setPolyToPoly(perspect, bitmapBounds, 4); +matrix.setConcat(matrix, matrix2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); +## + +#SeeAlso Concat preConcat postConcat SkCanvas::concat + +#Method ## + # ------------------------------------------------------------------------------ #Method void preTranslate(SkScalar dx, SkScalar dy) -Preconcats the matrix with the specified translation. -#Formula -M' = M * T(dx, dy) -## +Sets Matrix to Matrix multiplied by Matrix constructed from translation (dx, dy). +This can be thought of as moving the point to be mapped before applying Matrix. -#Param dx incomplete ## -#Param dy incomplete ## +Given: -#Example -// incomplete +#Code +#Literal + | A B C | | 1 0 dx | +Matrix = | D E F |, T(dx, dy) = | 0 1 dy | + | G H I | | 0 0 1 | ## -#ToDo incomplete ## +sets Matrix to: +#Code +#Literal + | A B C | | 1 0 dx | | A B A*dx+B*dy+C | +Matrix * T(dx, dy) = | D E F | | 0 1 dy | = | D E D*dx+E*dy+F | + | G H I | | 0 0 1 | | G H G*dx+H*dy+I | ## +#Param dx x translation before applying Matrix ## +#Param dy y translation before applying Matrix ## + +#Example +#Height 160 + SkPaint paint; + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + for (int i = 0; i < 2; ++i ) { + SkMatrix matrix; + i == 0 ? matrix.reset(): matrix.setRotate(25, rect.centerX(), 320); + { + SkAutoCanvasRestore acr(canvas, true); + canvas->concat(matrix); + paint.setColor(SK_ColorGRAY); + canvas->drawRect(rect, paint); + } + paint.setColor(SK_ColorRED); + for (int j = 0; j < 2; ++j ) { + SkAutoCanvasRestore acr(canvas, true); + matrix.preTranslate(40, 40); + canvas->concat(matrix); + canvas->drawCircle(0, 0, 3, paint); + } + } +## + +#SeeAlso postTranslate setTranslate MakeTrans + +#Method ## + # ------------------------------------------------------------------------------ #Method void preScale(SkScalar sx, SkScalar sy, SkScalar px, SkScalar py) -Preconcats the matrix with the specified scale. -#Formula -M' = M * S(sx, sy, px, py) +Sets Matrix to Matrix multiplied by Matrix constructed from scaling by (sx, sy) +about pivot point (px, py). +This can be thought of as scaling about a pivot point before applying Matrix. + +Given: + +#Code +#Literal + | A B C | | sx 0 dx | +Matrix = | D E F |, S(sx, sy, px, py) = | 0 sy dy | + | G H I | | 0 0 1 | ## -#Param sx incomplete ## -#Param sy incomplete ## -#Param px incomplete ## -#Param py incomplete ## +where -#Example -// incomplete +#Code +#Literal +dx = px - sx * px +dy = py - sy * py +## + +sets Matrix to: + +#Code +#Literal + | A B C | | sx 0 dx | | A*sx B*sy A*dx+B*dy+C | +Matrix * S(sx, sy, px, py) = | D E F | | 0 sy dy | = | D*sx E*sy D*dx+E*dy+F | + | G H I | | 0 0 1 | | G*sx H*sy G*dx+H*dy+I | ## -#ToDo incomplete ## +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## +#Param px pivot x ## +#Param py pivot y ## +#Example +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.preScale(.75f, 1.5f, source.width() / 2, source.height() / 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## +#SeeAlso postScale setScale MakeScale + +#Method ## + # ------------------------------------------------------------------------------ #Method void preScale(SkScalar sx, SkScalar sy) -Preconcats the matrix with the specified scale. -#Formula -M' = M * S(sx, sy) +Sets Matrix to Matrix multiplied by Matrix constructed from scaling by (sx, sy) +about pivot point (0, 0). +This can be thought of as scaling about the origin before applying Matrix. + +Given: + +#Code +#Literal + | A B C | | sx 0 0 | +Matrix = | D E F |, S(sx, sy) = | 0 sy 0 | + | G H I | | 0 0 1 | ## -#Param sx incomplete ## -#Param sy incomplete ## +sets Matrix to: -#Example -// incomplete +#Code +#Literal + | A B C | | sx 0 0 | | A*sx B*sy C | +Matrix * S(sx, sy) = | D E F | | 0 sy 0 | = | D*sx E*sy F | + | G H I | | 0 0 1 | | G*sx H*sy I | ## -#ToDo incomplete ## +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## +#Example +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.preScale(.75f, 1.5f); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## +#SeeAlso postScale setScale MakeScale + +#Method ## + # ------------------------------------------------------------------------------ #Method void preRotate(SkScalar degrees, SkScalar px, SkScalar py) -Preconcats the matrix with the specified rotation. -#Formula -M' = M * R(degrees, px, py) +Sets Matrix to Matrix multiplied by Matrix constructed from rotating by degrees +about pivot point (px, py). +This can be thought of as rotating about a pivot point before applying Matrix. + +Positive degrees rotates clockwise. + +Given: + +#Code +#Literal + | A B C | | c -s dx | +Matrix = | D E F |, R(degrees, px, py) = | s c dy | + | G H I | | 0 0 1 | ## -#Param degrees incomplete ## -#Param px incomplete ## -#Param py incomplete ## +where -#Example -// incomplete +#Code +#Literal +c = cos(degrees) +s = sin(degrees) +dx = s * py + (1 - c) * px +dy = -s * px + (1 - c) * py +## + +sets Matrix to: + +#Code +#Literal + | A B C | | c -s dx | | Ac+Bs -As+Bc A*dx+B*dy+C | +Matrix * R(degrees, px, py) = | D E F | | s c dy | = | Dc+Es -Ds+Ec D*dx+E*dy+F | + | G H I | | 0 0 1 | | Gc+Hs -Gs+Hc G*dx+H*dy+I | ## -#ToDo incomplete ## +#Param degrees angle of axes relative to upright axes ## +#Param px pivot x ## +#Param py pivot y ## +#Example +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.preRotate(45, source.width() / 2, source.height() / 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## +#SeeAlso postRotate setRotate + +#Method ## + # ------------------------------------------------------------------------------ #Method void preRotate(SkScalar degrees) -Preconcats the matrix with the specified rotation. -#Formula -M' = M * R(degrees) +Sets Matrix to Matrix multiplied by Matrix constructed from rotating by degrees +about pivot point (0, 0). +This can be thought of as rotating about the origin before applying Matrix. + +Positive degrees rotates clockwise. + +Given: + +#Code +#Literal + | A B C | | c -s 0 | +Matrix = | D E F |, R(degrees, px, py) = | s c 0 | + | G H I | | 0 0 1 | ## -#Param degrees incomplete ## +where -#Example -// incomplete +#Code +#Literal +c = cos(degrees) +s = sin(degrees) +## + +sets Matrix to: + +#Code +#Literal + | A B C | | c -s 0 | | Ac+Bs -As+Bc C | +Matrix * R(degrees, px, py) = | D E F | | s c 0 | = | Dc+Es -Ds+Ec F | + | G H I | | 0 0 1 | | Gc+Hs -Gs+Hc I | ## -#ToDo incomplete ## +#Param degrees angle of axes relative to upright axes ## +#Example +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.preRotate(45); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## +#SeeAlso postRotate setRotate + +#Method ## + # ------------------------------------------------------------------------------ #Method void preSkew(SkScalar kx, SkScalar ky, SkScalar px, SkScalar py) -Preconcats the matrix with the specified skew. -#Formula -M' = M * K(kx, ky, px, py) +Sets Matrix to Matrix multiplied by Matrix constructed from skewing by (kx, ky) +about pivot point (px, py). +This can be thought of as skewing about a pivot point before applying Matrix. + +Given: + +#Code +#Literal + | A B C | | 1 kx dx | +Matrix = | D E F |, K(kx, ky, px, py) = | ky 1 dy | + | G H I | | 0 0 1 | ## -#Param kx incomplete ## -#Param ky incomplete ## -#Param px incomplete ## -#Param py incomplete ## +where -#Example -// incomplete +#Code +#Literal +dx = -kx * py +dy = -ky * px ## -#ToDo incomplete ## +sets Matrix to: +#Code +#Literal + | A B C | | 1 kx dx | | A+B*ky A*kx+B A*dx+B*dy+C | +Matrix * K(kx, ky, px, py) = | D E F | | ky 1 dy | = | D+E*ky D*kx+E D*dx+E*dy+F | + | G H I | | 0 0 1 | | G+H*ky G*kx+H G*dx+H*dy+I | ## +#Param kx horizontal skew factor ## +#Param ky vertical skew factor ## +#Param px pivot x ## +#Param py pivot y ## + +#Example +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.preSkew(.5f, 0, source.width() / 2, source.height() / 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); +## + +#SeeAlso postSkew setSkew + +#Method ## + # ------------------------------------------------------------------------------ #Method void preSkew(SkScalar kx, SkScalar ky) -Preconcats the matrix with the specified skew. -#Formula -M' = M * K(kx, ky) +Sets Matrix to Matrix multiplied by Matrix constructed from skewing by (kx, ky) +about pivot point (0, 0). +This can be thought of as skewing about the origin before applying Matrix. + +Given: + +#Code +#Literal + | A B C | | 1 kx 0 | +Matrix = | D E F |, K(kx, ky) = | ky 1 0 | + | G H I | | 0 0 1 | ## -#Param kx incomplete ## -#Param ky incomplete ## +sets Matrix to: -#Example -// incomplete +#Code +#Literal + | A B C | | 1 kx 0 | | A+B*ky A*kx+B C | +Matrix * K(kx, ky) = | D E F | | ky 1 0 | = | D+E*ky D*kx+E F | + | G H I | | 0 0 1 | | G+H*ky G*kx+H I | ## -#ToDo incomplete ## +#Param kx horizontal skew factor ## +#Param ky vertical skew factor ## +#Example +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.preSkew(.5f, 0); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## +#SeeAlso postSkew setSkew + +#Method ## + # ------------------------------------------------------------------------------ #Method void preConcat(const SkMatrix& other) -Preconcats the matrix with the specified matrix. -#Formula -M' = M * other +Sets Matrix to Matrix multiplied by Matrix other. +This can be thought of mapping by other before applying Matrix. + +Given: + +#Code +#Literal + | A B C | | J K L | +Matrix = | D E F |, other = | M N O | + | G H I | | P Q R | ## -#Param other incomplete ## +sets Matrix to: -#Example -// incomplete +#Code +#Literal + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +Matrix * other = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR | ## -#ToDo incomplete ## +#Param other Matrix on right side of multiply expression ## +#Example +#Image 3 +#Description +setPolyToPoly creates perspective matrices, one the inverse of the other. +Multiplying the matrix by its inverse turns into an identity matrix. +## +SkMatrix matrix, matrix2; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix2.setPolyToPoly(perspect, bitmapBounds, 4); +matrix.preConcat(matrix2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## +#SeeAlso postConcat setConcat Concat + +#Method ## + # ------------------------------------------------------------------------------ #Method void postTranslate(SkScalar dx, SkScalar dy) -Postconcats the matrix with the specified translation. -#Formula -M' = T(dx, dy) * M -## +Sets Matrix to Matrix constructed from translation (dx, dy) multiplied by Matrix. +This can be thought of as moving the point to be mapped after applying Matrix. -#Param dx incomplete ## -#Param dy incomplete ## +Given: -#Example -// incomplete +#Code +#Literal + | J K L | | 1 0 dx | +Matrix = | M N O |, T(dx, dy) = | 0 1 dy | + | P Q R | | 0 0 1 | ## -#ToDo incomplete ## +sets Matrix to: +#Code +#Literal + | 1 0 dx | | J K L | | J+dx*P K+dx*Q L+dx*R | +T(dx, dy) * Matrix = | 0 1 dy | | M N O | = | M+dy*P N+dy*Q O+dy*R | + | 0 0 1 | | P Q R | | P Q R | ## +#Param dx x translation after applying Matrix ## +#Param dy y translation after applying Matrix ## + +#Example +#Height 160 +#Description +Compare with preTranslate example. +## + SkPaint paint; + paint.setAntiAlias(true); + SkRect rect = {20, 20, 100, 100}; + for (int i = 0; i < 2; ++i ) { + SkMatrix matrix; + i == 0 ? matrix.reset(): matrix.setRotate(25, rect.centerX(), 320); + { + SkAutoCanvasRestore acr(canvas, true); + canvas->concat(matrix); + paint.setColor(SK_ColorGRAY); + canvas->drawRect(rect, paint); + } + paint.setColor(SK_ColorRED); + for (int j = 0; j < 2; ++j ) { + SkAutoCanvasRestore acr(canvas, true); + matrix.postTranslate(40, 40); + canvas->concat(matrix); + canvas->drawCircle(0, 0, 3, paint); + } + } +## + +#SeeAlso preTranslate setTranslate MakeTrans + +#Method ## + # ------------------------------------------------------------------------------ #Method void postScale(SkScalar sx, SkScalar sy, SkScalar px, SkScalar py) -Postconcats the matrix with the specified scale. -#Formula -M' = S(sx, sy, px, py) * M +Sets Matrix to Matrix constructed from scaling by (sx, sy) about pivot point +(px, py), multiplied by Matrix. +This can be thought of as scaling about a pivot point after applying Matrix. + +Given: + +#Code +#Literal + | J K L | | sx 0 dx | +Matrix = | M N O |, S(sx, sy, px, py) = | 0 sy dy | + | P Q R | | 0 0 1 | ## -#Param sx incomplete ## -#Param sy incomplete ## -#Param px incomplete ## -#Param py incomplete ## +where + +#Code +#Literal +dx = px - sx * px +dy = py - sy * py +## + +sets Matrix to: + +#Code +#Literal + | sx 0 dx | | J K L | | sx*J+dx*P sx*K+dx*Q sx*L+dx+R | +S(sx, sy, px, py) * Matrix = | 0 sy dy | | M N O | = | sy*M+dy*P sy*N+dy*Q sy*O+dy*R | + | 0 0 1 | | P Q R | | P Q R | +## + +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postScale(.75f, 1.5f, source.width() / 2, source.height() / 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preScale setScale MakeScale ## @@ -1285,19 +2371,43 @@ M' = S(sx, sy, px, py) * M #Method void postScale(SkScalar sx, SkScalar sy) -Postconcats the matrix with the specified scale. -#Formula -M' = S(sx, sy) * M +Sets Matrix to Matrix constructed from scaling by (sx, sy) about pivot point +(0, 0), multiplied by Matrix. +This can be thought of as scaling about the origin after applying Matrix. + +Given: + +#Code +#Literal + | J K L | | sx 0 0 | +Matrix = | M N O |, S(sx, sy) = | 0 sy 0 | + | P Q R | | 0 0 1 | ## -#Param sx incomplete ## -#Param sy incomplete ## +sets Matrix to: + +#Code +#Literal + | sx 0 0 | | J K L | | sx*J sx*K sx*L | +S(sx, sy) * Matrix = | 0 sy 0 | | M N O | = | sy*M sy*N sy*O | + | 0 0 1 | | P Q R | | P Q R | +## + +#Param sx horizontal scale factor ## +#Param sy vertical scale factor ## #Example -// incomplete +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postScale(.75f, 1.5f); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preScale setScale MakeScale ## @@ -1305,21 +2415,57 @@ M' = S(sx, sy) * M #Method bool postIDiv(int divx, int divy) -Postconcats the matrix by dividing it by the specified integers. +Sets Matrix to Matrix constructed from scaling by #Formula -M' = S(1/divx, 1/divy, 0, 0) * M +(1/divx, 1/divy) ## +about pivot point (px, py), multiplied by Matrix. -#Param divx incomplete ## -#Param divy incomplete ## +Returns false if either divx or divy is zero. -#Return incomplete ## +Given: + +#Code +#Literal + | J K L | | sx 0 0 | +Matrix = | M N O |, I(divx, divy) = | 0 sy 0 | + | P Q R | | 0 0 1 | +## + +where + +#Code +#Literal +sx = 1 / divx +sy = 1 / divy +## + +sets Matrix to: + +#Code +#Literal + | sx 0 0 | | J K L | | sx*J sx*K sx*L | +I(divx, divy) * Matrix = | 0 sy 0 | | M N O | = | sy*M sy*N sy*O | + | 0 0 1 | | P Q R | | P Q R | +## + +#Param divx integer divisor for inverse scale in x ## +#Param divy integer divisor for inverse scale in y ## + +#Return true on successful scale ## #Example -// incomplete +#Image 3 +SkMatrix matrix, matrix2; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postIDiv(1, 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso postScale MakeScale ## @@ -1327,20 +2473,56 @@ M' = S(1/divx, 1/divy, 0, 0) * M #Method void postRotate(SkScalar degrees, SkScalar px, SkScalar py) -Postconcats the matrix with the specified rotation. -#Formula -M' = R(degrees, px, py) * M +Sets Matrix to Matrix constructed from rotating by degrees about pivot point +(px, py), multiplied by Matrix. +This can be thought of as rotating about a pivot point after applying Matrix. + +Positive degrees rotates clockwise. + +Given: + +#Code +#Literal + | J K L | | c -s dx | +Matrix = | M N O |, R(degrees, px, py) = | s c dy | + | P Q R | | 0 0 1 | ## -#Param degrees incomplete ## -#Param px incomplete ## -#Param py incomplete ## +where + +#Code +#Literal +c = cos(degrees) +s = sin(degrees) +dx = s * py + (1 - c) * px +dy = -s * px + (1 - c) * py +## + +sets Matrix to: + +#Code +#Literal + |c -s dx| |J K L| |cJ-sM+dx*P cK-sN+dx*Q cL-sO+dx+R| +R(degrees, px, py) * Matrix = |s c dy| |M N O| = |sJ+cM+dy*P sK+cN+dy*Q sL+cO+dy*R| + |0 0 1| |P Q R| | P Q R| +## + +#Param degrees angle of axes relative to upright axes ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postRotate(45, source.width() / 2, source.height() / 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preRotate setRotate ## @@ -1348,18 +2530,52 @@ M' = R(degrees, px, py) * M #Method void postRotate(SkScalar degrees) -Postconcats the matrix with the specified rotation. -#Formula -M' = R(degrees) * M +Sets Matrix to Matrix constructed from rotating by degrees about pivot point +(0, 0), multiplied by Matrix. +This can be thought of as rotating about the origin after applying Matrix. + +Positive degrees rotates clockwise. + +Given: + +#Code +#Literal + | J K L | | c -s 0 | +Matrix = | M N O |, R(degrees, px, py) = | s c 0 | + | P Q R | | 0 0 1 | +## + +where + +#Code +#Literal +c = cos(degrees) +s = sin(degrees) ## -#Param degrees incomplete ## +sets Matrix to: + +#Code +#Literal + | c -s dx | | J K L | | cJ-sM cK-sN cL-sO | +R(degrees, px, py) * Matrix = | s c dy | | M N O | = | sJ+cM sK+cN sL+cO | + | 0 0 1 | | P Q R | | P Q R | +## + +#Param degrees angle of axes relative to upright axes ## #Example -// incomplete +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postRotate(45); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preRotate setRotate ## @@ -1367,21 +2583,53 @@ M' = R(degrees) * M #Method void postSkew(SkScalar kx, SkScalar ky, SkScalar px, SkScalar py) -Postconcats the matrix with the specified skew. -#Formula -M' = K(kx, ky, px, py) * M +Sets Matrix to Matrix constructed from skewing by (kx, ky) about pivot point +(px, py), multiplied by Matrix. +This can be thought of as skewing about a pivot point after applying Matrix. + +Given: + +#Code +#Literal + | J K L | | 1 kx dx | +Matrix = | M N O |, K(kx, ky, px, py) = | ky 1 dy | + | P Q R | | 0 0 1 | +## + +where + +#Code +#Literal +dx = -kx * py +dy = -ky * px ## -#Param kx incomplete ## -#Param ky incomplete ## -#Param px incomplete ## -#Param py incomplete ## +sets Matrix to: + +#Code +#Literal + | 1 kx dx| |J K L| |J+kx*M+dx*P K+kx*N+dx*Q L+kx*O+dx+R| +K(kx, ky, px, py) * Matrix = |ky 1 dy| |M N O| = |ky*J+M+dy*P ky*K+N+dy*Q ky*L+O+dy*R| + | 0 0 1| |P Q R| | P Q R| +## + +#Param kx horizontal skew factor ## +#Param ky vertical skew factor ## +#Param px pivot x ## +#Param py pivot y ## #Example -// incomplete +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postSkew(.5f, 0, source.width() / 2, source.height() / 2); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preSkew setSkew ## @@ -1389,19 +2637,43 @@ M' = K(kx, ky, px, py) * M #Method void postSkew(SkScalar kx, SkScalar ky) -Postconcats the matrix with the specified skew. -#Formula -M' = K(kx, ky) * M +Sets Matrix to Matrix constructed from skewing by (kx, ky) about pivot point +(0, 0), multiplied by Matrix. +This can be thought of as skewing about the origin after applying Matrix. + +Given: + +#Code +#Literal + | J K L | | 1 kx 0 | +Matrix = | M N O |, K(kx, ky) = | ky 1 0 | + | P Q R | | 0 0 1 | ## -#Param kx incomplete ## -#Param ky incomplete ## +sets Matrix to: + +#Code +#Literal + | 1 kx 0 | | J K L | | J+kx*M K+kx*N L+kx*O | +K(kx, ky) * Matrix = | ky 1 0 | | M N O | = | ky*J+M ky*K+N ky*L+O | + | 0 0 1 | | P Q R | | P Q R | +## + +#Param kx horizontal skew factor ## +#Param ky vertical skew factor ## #Example -// incomplete +#Image 3 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postSkew(.5f, 0); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preSkew setSkew ## @@ -1409,18 +2681,42 @@ M' = K(kx, ky) * M #Method void postConcat(const SkMatrix& other) -Postconcats the matrix with the specified matrix. -#Formula -M' = other * M +Sets Matrix to Matrix other multiplied by Matrix. +This can be thought of mapping by other after applying Matrix. + +Given: + +#Code +#Literal + | J K L | | A B C | +Matrix = | M N O |, other = | D E F | + | P Q R | | G H I | ## -#Param other incomplete ## +sets Matrix to: + +#Code +#Literal + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +other * Matrix = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR | +## + +#Param other Matrix on left side of multiply expression ## #Example -// incomplete +#Image 3 +#Height 64 +SkMatrix matrix, matrix2; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix.postConcat(matrix); +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preConcat setConcat Concat ## @@ -1437,33 +2733,57 @@ M' = other * M }; ## -#Const kFill_ScaleToFit -Scale in X and Y independently, so that src matches dst exactly. -This may change the aspect ratio of the src. +ScaleToFit describes how Matrix is constructed to map one Rect to another. +ScaleToFit may allow Matrix to have unequal horizontal and vertical scaling, +or may restrict Matrix to square scaling. If restricted, ScaleToFit specifies +how Matrix maps to the side or center of the destination Rect. + +#Const kFill_ScaleToFit 0 + Computes Matrix that scales in x and y independently, so that source Rect is + mapped to completely fill destination Rect. The aspect ratio of source Rect + may change. ## -#Const kStart_ScaleToFit -Compute a scale that will maintain the original src aspect ratio, -but will also ensure that src fits entirely inside dst. At least one -axis (x or y) will fit exactly. Aligns the result to the -left and top edges of dst. +#Const kStart_ScaleToFit 1 + Computes Matrix that maintains source Rect aspect ratio, mapping source Rect + width or height to destination Rect. Aligns mapping to left and top edges + of destination Rect. ## -#Const kCenter_ScaleToFit -Compute a scale that will maintain the original src aspect ratio, -but will also ensure that src fits entirely inside dst. At least one -axis (x or y) will fit exactly. The result is centered inside dst. +#Const kCenter_ScaleToFit 2 + Computes Matrix that maintains source Rect aspect ratio, mapping source Rect + width or height to destination Rect. Aligns mapping to center of destination + Rect. ## -#Const kEnd_ScaleToFit -Compute a scale that will maintain the original src aspect ratio, -but will also ensure that src fits entirely inside dst. At least one -axis (x or y) will fit exactly. Aligns the result to the -right and bottom edges of dst. +#Const kEnd_ScaleToFit 3 + Computes Matrix that maintains source Rect aspect ratio, mapping source Rect + width or height to destination Rect. Aligns mapping to right and bottom + edges of destination Rect. ## #Example -// incomplete -## - -#ToDo incomplete ## + const char* labels[] = { "Fill", "Start", "Center", "End" }; + SkRect rects[] = {{5, 5, 59, 59}, {5, 74, 59, 108}, {10, 123, 44, 172}, {10, 187, 54, 231}}; + SkRect bounds; + source.getBounds(&bounds); + SkPaint paint; + paint.setAntiAlias(true); + for (auto fit : { SkMatrix::kFill_ScaleToFit, SkMatrix::kStart_ScaleToFit, + SkMatrix::kCenter_ScaleToFit, SkMatrix::kEnd_ScaleToFit } ) { + for (auto rect : rects ) { + canvas->drawRect(rect, paint); + SkMatrix matrix; + if (!matrix.setRectToRect(bounds, rect, fit)) { + continue; + } + SkAutoCanvasRestore acr(canvas, true); + canvas->concat(matrix); + canvas->drawBitmap(source, 0, 0); + } + canvas->drawString(labels[fit], 10, 255, paint); + canvas->translate(64, 0); + } +## + +#SeeAlso setRectToRect MakeRectToRect setPolyToPoly ## @@ -1471,25 +2791,53 @@ right and bottom edges of dst. #Method bool setRectToRect(const SkRect& src, const SkRect& dst, ScaleToFit stf) -Set the matrix to the scale and translate values that map the source -rectangle to the destination rectangle, returning true if the the result -can be represented. +Sets Matrix to scale and translate src Rect to dst Rect. stf selects whether +mapping completely fills dst or preserves the aspect ratio, and how to align +src within dst. Returns false if src is empty, and sets Matrix to identity. +Returns true if dst is empty, and sets Matrix to: -#Param src the source rectangle to map from -## -#Param dst the destination rectangle to map to -## -#Param stf the ScaleToFit option +#Code +#Literal +| 0 0 0 | +| 0 0 0 | +| 0 0 1 | ## -#Return true if the matrix can be represented by the rectangle mapping +#Param src Rect to map from ## +#Param dst Rect to map to ## +#Param stf one of: kFill_ScaleToFit, kStart_ScaleToFit, + kCenter_ScaleToFit, kEnd_ScaleToFit ## -#Example -// incomplete -## +#Return true if Matrix can represent Rect mapping ## -#ToDo incomplete ## +#Example + const SkRect srcs[] = { {0, 0, 0, 0}, {1, 2, 3, 4} }; + const SkRect dsts[] = { {0, 0, 0, 0}, {5, 6, 8, 9} }; + for (auto src : srcs) { + for (auto dst : dsts) { + SkMatrix matrix; + matrix.setAll(-1, -1, -1, -1, -1, -1, -1, -1, -1); + bool success = matrix.setRectToRect(src, dst, SkMatrix::kFill_ScaleToFit); + SkDebugf("src: %g, %g, %g, %g dst: %g, %g, %g, %g success: %s\n", + src.fLeft, src.fTop, src.fRight, src.fBottom, + dst.fLeft, dst.fTop, dst.fRight, dst.fBottom, success ? "true" : "false"); + matrix.dump(); + } + } +#StdOut +src: 0, 0, 0, 0 dst: 0, 0, 0, 0 success: false +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 0, 0, 0, 0 dst: 5, 6, 8, 9 success: false +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 0, 0, 0, 0 success: true +[ 0.0000 0.0000 0.0000][ 0.0000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 5, 6, 8, 9 success: true +[ 1.5000 0.0000 3.5000][ 0.0000 1.5000 3.0000][ 0.0000 0.0000 1.0000] +## +## + +#SeeAlso MakeRectToRect ScaleToFit setPolyToPoly SkRect::isEmpty ## @@ -1497,17 +2845,51 @@ can be represented. #Method static SkMatrix MakeRectToRect(const SkRect& src, const SkRect& dst, ScaleToFit stf) -#Param src incomplete ## -#Param dst incomplete ## -#Param stf incomplete ## +Returns Matrix set to scale and translate src Rect to dst Rect. stf selects +whether mapping completely fills dst or preserves the aspect ratio, and how to +align src within dst. Returns the identity Matrix if src is empty. If dst is +empty, returns Matrix set to: + +#Code +#Literal +| 0 0 0 | +| 0 0 0 | +| 0 0 1 | +## + +#Param src Rect to map from ## +#Param dst Rect to map to ## +#Param stf one of: kFill_ScaleToFit, kStart_ScaleToFit, + kCenter_ScaleToFit, kEnd_ScaleToFit +## -#Return incomplete ## +#Return Matrix mapping src to dst ## #Example -// incomplete + const SkRect srcs[] = { {0, 0, 0, 0}, {1, 2, 3, 4} }; + const SkRect dsts[] = { {0, 0, 0, 0}, {5, 6, 8, 9} }; + for (auto src : srcs) { + for (auto dst : dsts) { + SkMatrix matrix = SkMatrix::MakeRectToRect(src, dst, SkMatrix::kFill_ScaleToFit); + SkDebugf("src: %g, %g, %g, %g dst: %g, %g, %g, %g\n", + src.fLeft, src.fTop, src.fRight, src.fBottom, + dst.fLeft, dst.fTop, dst.fRight, dst.fBottom); + matrix.dump(); + } + } +#StdOut +src: 0, 0, 0, 0 dst: 0, 0, 0, 0 +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 0, 0, 0, 0 dst: 5, 6, 8, 9 +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 0, 0, 0, 0 +[ 0.0000 0.0000 0.0000][ 0.0000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 5, 6, 8, 9 +[ 1.5000 0.0000 3.5000][ 0.0000 1.5000 3.0000][ 0.0000 0.0000 1.0000] +## ## -#ToDo incomplete ## +#SeeAlso setRectToRect ScaleToFit setPolyToPoly SkRect::isEmpty ## @@ -1515,24 +2897,49 @@ can be represented. #Method bool setPolyToPoly(const SkPoint src[], const SkPoint dst[], int count) -Set the matrix such that the specified src points would map to the -specified dst points. count must be within [0..4]. +Sets Matrix to map src to dst. count must be zero or greater, and four or less. -#Param src array of src points -## -#Param dst array of dst points -## -#Param count number of points to use for the transformation -## +If count is zero, sets Matrix to identity and returns true. +If count is one, sets Matrix to translate and returns true. +If count is two or more, sets Matrix to map Points if possible; returns false +if Matrix cannot be constructed. If count is four, Matrix may include +perspective. -#Return true if the matrix was set to the specified transformation -## +#Param src Points to map from ## +#Param dst Points to map to ## +#Param count number of Points in src and dst ## -#Example -// incomplete +#Return true if Matrix was constructed successfully ## -#ToDo incomplete ## +#Example + const SkPoint src[] = { { 0, 0}, {30, 0}, {30, -30}, { 0, -30} }; + const SkPoint dst[] = { {50, 0}, {80, -10}, {90, -30}, {60, -40} }; + SkPaint blackPaint; + blackPaint.setAntiAlias(true); + blackPaint.setTextSize(42); + SkPaint redPaint = blackPaint; + redPaint.setColor(SK_ColorRED); + for (int count : { 1, 2, 3, 4 } ) { + canvas->translate(35, 55); + for (int index = 0; index < count; ++index) { + canvas->drawCircle(src[index], 3, blackPaint); + canvas->drawCircle(dst[index], 3, blackPaint); + if (index > 0) { + canvas->drawLine(src[index], src[index - 1], blackPaint); + canvas->drawLine(dst[index], dst[index - 1], blackPaint); + } + } + SkMatrix matrix; + matrix.setPolyToPoly(src, dst, count); + canvas->drawString("A", src[0].fX, src[0].fY, redPaint); + SkAutoCanvasRestore acr(canvas, true); + canvas->concat(matrix); + canvas->drawString("A", src[0].fX, src[0].fY, redPaint); + } +## + +#SeeAlso setRectToRect MakeRectToRect ## @@ -1540,19 +2947,35 @@ specified dst points. count must be within [0..4]. #Method bool SK_WARN_UNUSED_RESULT invert(SkMatrix* inverse) const -If this matrix can be inverted, return true and if inverse is not null, -set inverse to be the inverse of this matrix. If this matrix cannot be -inverted, ignore inverse and return false +Sets inverse to reciprocal matrix, returning true if Matrix can be inverted. +Geometrically, if Matrix maps from source to destination, inverse Matrix +maps from destination to source. If Matrix can not be inverted, inverse is +unchanged. -#Param inverse incomplete ## +#Param inverse storage for inverted Matrix; may be nullptr ## -#Return incomplete ## +#Return true if Matrix can be inverted ## #Example -// incomplete +#Height 128 + const SkPoint src[] = { { 10, 120}, {120, 120}, {120, 10}, { 10, 10} }; + const SkPoint dst[] = { {150, 120}, {200, 100}, {240, 30}, { 130, 40} }; + SkPaint paint; + paint.setAntiAlias(true); + SkMatrix matrix; + matrix.setPolyToPoly(src, dst, 4); + canvas->drawPoints(SkCanvas::kPolygon_PointMode, 4, src, paint); + canvas->drawPoints(SkCanvas::kPolygon_PointMode, 4, dst, paint); + paint.setColor(SK_ColorBLUE); + paint.setStrokeWidth(3); + paint.setStrokeCap(SkPaint::kRound_Cap); + canvas->drawPoints(SkCanvas::kPoints_PointMode, 4, dst, paint); + matrix.invert(&matrix); + canvas->concat(matrix); + canvas->drawPoints(SkCanvas::kPoints_PointMode, 4, dst, paint); ## -#ToDo incomplete ## +#SeeAlso Concat ## @@ -1560,19 +2983,33 @@ inverted, ignore inverse and return false #Method static void SetAffineIdentity(SkScalar affine[6]) -Fills the passed array with affine identity values -in column major order. +Fills affine with identity values in column major order. +Sets affine to: -#Param affine array to fill with affine identity values; must not be nullptr +#Code +#Literal +| 1 0 0 | +| 0 1 0 | ## -#Return incomplete ## +Affine 3x2 matrices in column major order are used by OpenGL and XPS. + +#Param affine storage for 3x2 affine matrix ## #Example -// incomplete + SkScalar affine[6]; + SkMatrix::SetAffineIdentity(affine); + const char* names[] = { "ScaleX", "SkewY", "SkewX", "ScaleY", "TransX", "TransY" }; + for (int i = 0; i < 6; ++i) { + SkDebugf("%s: %g ", names[i], affine[i]); + } + SkDebugf("\n"); +#StdOut +ScaleX: 1 SkewY: 0 SkewX: 0 ScaleY: 1 TransX: 0 TransY: 0 +## ## -#ToDo incomplete ## +#SeeAlso setAffine asAffine ## @@ -1580,20 +3017,36 @@ in column major order. #Method bool SK_WARN_UNUSED_RESULT asAffine(SkScalar affine[6]) const -Fills the passed array with the affine values in column major order. -If the matrix is a perspective transform, returns false -and does not change the passed array. +Fills affine in column major order. Sets affine to: -#Param affine array to fill with affine values; ignored if nullptr +#Code +#Literal +| scale-x skew-x translate-x | +| skew-y scale-y translate-y | ## -#Return incomplete ## +If Matrix contains perspective, returns false and leaves affine unchanged. + +#Param affine storage for 3x2 affine matrix; may be nullptr ## + +#Return true if Matrix does not contain perspective ## #Example -// incomplete +SkMatrix matrix; +matrix.setAll(2, 3, 4, 5, 6, 7, 0, 0, 1); +SkScalar affine[6]; +matrix.asAffine(affine); +const char* names[] = { "ScaleX", "SkewY", "SkewX", "ScaleY", "TransX", "TransY" }; +for (int i = 0; i < 6; ++i) { + SkDebugf("%s: %g ", names[i], affine[i]); +} +SkDebugf("\n"); +#StdOut +ScaleX: 2 SkewY: 5 SkewX: 3 ScaleY: 6 TransX: 4 TransY: 7 +## ## -#ToDo incomplete ## +#SeeAlso setAffine SetAffineIdentity ## @@ -1601,16 +3054,46 @@ and does not change the passed array. #Method void setAffine(const SkScalar affine[6]) -Set the matrix to the specified affine values. -Note: these are passed in column major order. +Sets Matrix to affine values, passed in column major order. Given affine, +column, then row, as: + +#Code +#Literal +| scale-x skew-x translate-x | +| skew-y scale-y translate-y | +## -#Param affine incomplete ## +Matrix is set, row, then column, to: + +#Code +#Literal +| scale-x skew-x translate-x | +| skew-y scale-y translate-y | +| 0 0 1 | +## + +#Param affine 3x2 affine matrix ## #Example -// incomplete +SkMatrix matrix; +matrix.setAll(2, 3, 4, 5, 6, 7, 0, 0, 1); +SkScalar affine[6]; +matrix.asAffine(affine); +const char* names[] = { "ScaleX", "SkewY", "SkewX", "ScaleY", "TransX", "TransY" }; +for (int i = 0; i < 6; ++i) { + SkDebugf("%s: %g ", names[i], affine[i]); +} +SkDebugf("\n"); +matrix.reset(); +matrix.setAffine(affine); +matrix.dump(); +#StdOut +ScaleX: 2 SkewY: 5 SkewX: 3 ScaleY: 6 TransX: 4 TransY: 7 +[ 2.0000 3.0000 4.0000][ 5.0000 6.0000 7.0000][ 0.0000 0.0000 1.0000] +## ## -#ToDo incomplete ## +#SeeAlso asAffine SetAffineIdentity ## @@ -1618,27 +3101,58 @@ Note: these are passed in column major order. #Method void mapPoints(SkPoint dst[], const SkPoint src[], int count) const -Apply this matrix to the array of points specified by src, and write -the transformed points into the array of points specified by dst. -#Formula -dst[] = M * src[] -## +Maps src Point array of length count to dst Point array of equal or greater +length. Points are mapped by multiplying each Point by Matrix. Given: -#Param dst storage for transformed coordinates; must - allow count entries +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 | ## -#Param src original coordinates that are to be transformed; - must allow count entries + +where + +#Code +#Literal +for (i = 0; i < count; ++i) { + x = src[i].fX + y = src[i].fY +} ## -#Param count number of points in src to read, and then transform - into dst + +each dst Point is computed as: + +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## +src and dst may point to the same storage. + +#Param dst storage for mapped Points ## +#Param src Points to transform ## +#Param count number of Points to transform ## + #Example -// incomplete + SkMatrix matrix; + matrix.reset(); + const int count = 4; + SkPoint src[count]; + matrix.mapRectToQuad(src, {40, 70, 180, 220} ); + SkPaint paint; + paint.setARGB(77, 23, 99, 154); + for (int i = 0; i < 5; ++i) { + SkPoint dst[count]; + matrix.mapPoints(dst, src, count); + canvas->drawPoints(SkCanvas::kPolygon_PointMode, count, dst, paint); + matrix.preRotate(35, 128, 128); + } ## -#ToDo incomplete ## +#SeeAlso mapPointsWithStride mapXY mapHomogeneousPoints mapVectors ## @@ -1646,22 +3160,53 @@ dst[] = M * src[] #Method void mapPoints(SkPoint pts[], int count) const -Apply this matrix to the array of points, overwriting it with the -transformed values. -#Formula -dst[] = M * pts[] +Maps pts Point array of length count in place. Points are mapped by multiplying +each Point by Matrix. Given: + +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 | ## -#Param pts storage for transformed points; must allow count entries +where + +#Code +#Literal +for (i = 0; i < count; ++i) { + x = pts[i].fX + y = pts[i].fY +} ## -#Param count number of points in pts + +each resulting pts Point is computed as: + +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## +#Param pts storage for mapped Points ## +#Param count number of Points to transform ## + #Example -// incomplete + SkMatrix matrix; + matrix.setRotate(35, 128, 128); + const int count = 4; + SkPoint pts[count]; + matrix.mapRectToQuad(pts, {40, 70, 180, 220} ); + SkPaint paint; + paint.setARGB(77, 23, 99, 154); + for (int i = 0; i < 5; ++i) { + canvas->drawPoints(SkCanvas::kPolygon_PointMode, count, pts, paint); + matrix.mapPoints(pts, count); + } ## -#ToDo incomplete ## +#SeeAlso mapPointsWithStride mapXY mapHomogeneousPoints mapVectors ## @@ -1669,507 +3214,862 @@ dst[] = M * pts[] #Method void mapPointsWithStride(SkPoint pts[], size_t stride, int count) const -Like mapPoints but with custom byte stride between the points. Stride -should be a multiple of -#Formula -sizeof(SkScalar) -## -. - -#Param pts incomplete ## -#Param stride incomplete ## -#Param count incomplete ## +Maps count pts, skipping stride bytes to advance from one Point to the next. +Points are mapped by multiplying each Point by Matrix. Given: -#Example -// incomplete +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 | ## -#ToDo incomplete ## +each resulting pts Point is computed as: +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## -# ------------------------------------------------------------------------------ - -#Method void mapPointsWithStride(SkPoint dst[], const SkPoint src[], size_t stride, int count) const - -Like mapPoints but with custom byte stride between the points. - -#Param dst incomplete ## -#Param src incomplete ## -#Param stride incomplete ## -#Param count incomplete ## +#Param pts storage for mapped Points ## +#Param stride size of record starting with Point, in bytes ## +#Param count number of Points to transform ## #Example -// incomplete + SkMatrix matrix; + matrix.reset(); + struct PointZ { + SkPoint fPt; + SkPoint fStationary; + } pts[] = {{{40, 70}, {40, 70}}, {{180, 70}, {180, 70}}, {{180, 220}, {180, 220}}, + {{40, 220}, {40, 220}}}; + constexpr int count = SK_ARRAY_COUNT(pts); + SkPaint paint; + paint.setARGB(77, 23, 99, 154); + for (int i = 0; i < 5; ++i) { + matrix.preRotate(10, 128, 128); + matrix.mapPointsWithStride(&pts[0].fPt, sizeof(PointZ), count); + canvas->drawPoints(SkCanvas::kPolygon_PointMode, count * 2, &pts[0].fPt, paint); + } ## -#ToDo incomplete ## +#SeeAlso mapPoints mapXY mapHomogeneousPoints mapVectors ## # ------------------------------------------------------------------------------ -#Method void mapHomogeneousPoints(SkScalar dst[], const SkScalar src[], int count) const +#Method void mapPointsWithStride(SkPoint dst[], const SkPoint src[], size_t stride, int count) const -Apply this matrix to the array of homogeneous points, specified by src, -where a homogeneous point is defined by 3 contiguous scalar values, -and write the transformed points into the array of scalars specified by dst. -#Formula -dst[] = M * src[] -## +Maps src Point array of length count to dst Point array, skipping stride bytes +to advance from one Point to the next. +Points are mapped by multiplying each Point by Matrix. Given: -#Param dst storage for transformed coordinates; must - allow 3 * count entries -## -#Param src original coordinates to be transformed; - must contain at least 3 * count entries +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, src = | y | + | G H I | | 1 | ## -#Param count number of triples (homogeneous points) in src to read, - and then transform into dst + +each resulting dst Point is computed as: + +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## +#Param dst storage for mapped Points ## +#Param src Points to transform ## +#Param stride size of record starting with Point, in bytes ## +#Param count number of Points to transform ## + #Example -// incomplete + struct PointZ { + SkPoint fPt; + const SkPoint fStationary; + }; + const PointZ src[] = {{{40, 70}, {40, 70}}, {{180, 70}, {180, 70}}, {{180, 220}, {180, 220}}, + {{40, 220}, {40, 220}}}; + PointZ dst[] = {{{0, 0}, {60, 80}}, {{0, 0}, {150, 40}}, {{0, 0}, {100, 240}}, + {{0, 0}, {10, 250}}}; + constexpr int count = SK_ARRAY_COUNT(src); + SkPaint paint; + paint.setARGB(77, 23, 99, 154); + for (int i = 0; i < 5; ++i) { + SkMatrix matrix; + matrix.setRotate(10 * i, 128, 128); + matrix.mapPointsWithStride(&dst[0].fPt, &src[0].fPt, sizeof(PointZ), count); + canvas->drawPoints(SkCanvas::kPolygon_PointMode, count * 2, &dst[0].fPt, paint); + } ## -#ToDo incomplete ## +#SeeAlso mapPoints mapXY mapHomogeneousPoints mapVectors ## # ------------------------------------------------------------------------------ -#Method void mapXY(SkScalar x, SkScalar y, SkPoint* result) const +#Method void mapHomogeneousPoints(SkPoint3 dst[], const SkPoint3 src[], int count) const -#Param x incomplete ## -#Param y incomplete ## -#Param result incomplete ## +Maps src Point3 array of length count to dst Point3 array, which must of length count or +greater. Point3 array is mapped by multiplying each Point3 by Matrix. Given: -#Example -// incomplete +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, src = | y | + | G H I | | z | ## -#ToDo incomplete ## +each resulting dst Point is computed as: +#Code +#Literal + |A B C| |x| +Matrix * src = |D E F| |y| = |Ax+By+Cz Dx+Ey+Fz Gx+Hy+Iz| + |G H I| |z| ## -# ------------------------------------------------------------------------------ - -#Method SkPoint mapXY(SkScalar x, SkScalar y) const - -#Param x incomplete ## -#Param y incomplete ## - -#Return incomplete ## +#Param dst storage for mapped Point3 array ## +#Param src Point3 array to transform ## +#Param count items in Point3 array to transform ## #Example -// incomplete + SkPoint3 src[] = {{3, 3, 1}, {8, 2, 2}, {5, 0, 4}, {0, 1, 3}, + {3, 7, 1}, {8, 6, 2}, {5, 4, 4}, {0, 5, 3}}; + int lines[] = { 0, 1, 1, 2, 2, 3, 3, 0, 4, 5, 5, 6, 6, 7, 7, 4, 0, 4, 1, 5, 2, 6, 3, 7 }; + constexpr int count = SK_ARRAY_COUNT(src); + auto debugster = [=](SkPoint3 src[]) -> void { + for (size_t i = 0; i < SK_ARRAY_COUNT(lines); i += 2) { + const SkPoint3& s = src[lines[i]]; + const SkPoint3& e = src[lines[i + 1]]; + SkPaint paint; + paint.setARGB(77, 23, 99, 154); + canvas->drawLine(s.fX / s.fZ, s.fY / s.fZ, e.fX / e.fZ, e.fY / e.fZ, paint); + } + }; + canvas->save(); + canvas->translate(5, 5); + canvas->scale(15, 15); + debugster(src); + canvas->restore(); + canvas->translate(128, 128); + SkMatrix matrix; + matrix.setAll(15, 0, 0, 0, 15, 0, -0.08, 0.04, 1); + matrix.mapHomogeneousPoints(&src[0].fX, &src[0].fX, count); + debugster(src); ## -#ToDo incomplete ## +#SeeAlso mapPoints mapXY mapPointsWithStride mapVectors ## # ------------------------------------------------------------------------------ -#Method void mapVectors(SkVector dst[], const SkVector src[], int count) const +#Method void mapXY(SkScalar x, SkScalar y, SkPoint* result) const -Apply this matrix to the array of vectors specified by src, and write -the transformed vectors into the array of vectors specified by dst. -This is similar to mapPoints, but ignores any translation in the matrix. +Maps Point (x, y) to result. Point is mapped by multiplying by Matrix. Given: -#Param dst storage for transformed coordinates; must - allow count entries -## -#Param src coordinates to be transformed; - must contain at least count entries +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 | ## -#Param count number of vectors in src to read and transform - into dst + +result is computed as: + +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## +#Param x x-coordinate of Point to map ## +#Param y y-coordinate of Point to map ## +#Param result storage for mapped Point ## + #Example -// incomplete + SkPaint paint; + paint.setAntiAlias(true); + SkMatrix matrix; + matrix.setRotate(60, 128, 128); + SkPoint lines[] = {{50, 50}, {150, 50}, {150, 150}}; + for (size_t i = 0; i < SK_ARRAY_COUNT(lines); ++i) { + SkPoint pt; + matrix.mapXY(lines[i].fX, lines[i].fY, &pt); + canvas->drawCircle(pt.fX, pt.fY, 3, paint); + } + canvas->concat(matrix); + canvas->drawPoints(SkCanvas::kPolygon_PointMode, SK_ARRAY_COUNT(lines), lines, paint); ## -#ToDo incomplete ## +#SeeAlso mapPoints mapPointsWithStride mapVectors ## # ------------------------------------------------------------------------------ -#Method void mapVectors(SkVector vecs[], int count) const +#Method SkPoint mapXY(SkScalar x, SkScalar y) const -Apply this matrix to count vectors in array vecs. -This is similar to mapPoints, but ignores any translation in the matrix. +Returns Point (x, y) multiplied by Matrix. Given: -#Param vecs vectors to transform; must contain at least - count entries +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 | ## -#Param count number of vectors in vecs + +result is computed as: + +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## +#Param x x-coordinate of Point to map ## +#Param y y-coordinate of Point to map ## + +#Return mapped Point ## + #Example -// incomplete +#Image 4 +SkMatrix matrix; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {30, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +SkPaint paint; +paint.setAntiAlias(true); +paint.setStrokeWidth(3); +for (int x : { 0, source.width() } ) { + for (int y : { 0, source.height() } ) { + canvas->drawPoint(matrix.mapXY(x, y), paint); + } +} +canvas->concat(matrix); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso mapPoints mapPointsWithStride mapVectors ## # ------------------------------------------------------------------------------ -#Method void mapVector(SkScalar dx, SkScalar dy, SkVector* result) const +#Method void mapVectors(SkVector dst[], const SkVector src[], int count) const -#Param dx incomplete ## -#Param dy incomplete ## -#Param result incomplete ## +Maps src Vector array of length count to Vector Point array of equal or greater +length. Vectors are mapped by multiplying each Vector by Matrix, treating +Matrix translation as zero. Given: -#Example -// incomplete +#Code +#Literal + | A B 0 | | x | +Matrix = | D E 0 |, src = | y | + | G H I | | 1 | ## -#ToDo incomplete ## +where +#Code +#Literal +for (i = 0; i < count; ++i) { + x = src[i].fX + y = src[i].fY +} ## -# ------------------------------------------------------------------------------ +each dst Vector is computed as: -#Method SkVector mapVector(SkScalar dx, SkScalar dy) const +#Code +#Literal + |A B 0| |x| Ax+By Dx+Ey +Matrix * src = |D E 0| |y| = |Ax+By Dx+Ey Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I +## -#Param dx incomplete ## -#Param dy incomplete ## +src and dst may point to the same storage. -#Return incomplete ## +#Param dst storage for mapped Vectors ## +#Param src Vectors to transform ## +#Param count number of Vectors to transform ## #Example -// incomplete + SkPaint paint; + paint.setAntiAlias(true); + paint.setStyle(SkPaint::kStroke_Style); + SkMatrix matrix; + matrix.reset(); + const SkVector radii[] = {{8, 4}, {9, 1}, {6, 2}, {7, 3}}; + for (int i = 0; i < 4; ++i) { + SkVector rScaled[4]; + matrix.preScale(1.5f, 2.f); + matrix.mapVectors(rScaled, radii, SK_ARRAY_COUNT(radii)); + SkRRect rrect; + rrect.setRectRadii({20, 20, 180, 70}, rScaled); + canvas->drawRRect(rrect, paint); + canvas->translate(0, 60); + } ## -#ToDo incomplete ## +#SeeAlso mapVector mapPoints mapPointsWithStride mapXY ## # ------------------------------------------------------------------------------ -#Method bool mapRect(SkRect* dst, const SkRect& src) const - -Apply this matrix to the src rectangle, and write the transformed -rectangle into dst. This is accomplished by transforming the 4 corners -of src, and then setting dst to the bounds of those points. - -#Param dst storage for transformed rectangle ## -#Param src rectangle to transform ## +#Method void mapVectors(SkVector vecs[], int count) const -#Return result of calling rectStaysRect -## +Maps vecs Vector array of length count in place, multiplying each Vector by +Matrix, treating Matrix translation as zero. Given: -#Example -// incomplete +#Code +#Literal + | A B 0 | | x | +Matrix = | D E 0 |, vec = | y | + | G H I | | 1 | ## -#ToDo incomplete ## +where +#Code +#Literal +for (i = 0; i < count; ++i) { + x = vecs[i].fX + y = vecs[i].fY +} ## -# ------------------------------------------------------------------------------ - -#Method bool mapRect(SkRect* rect) const - -Apply this matrix to the rectangle, and write the transformed rectangle -back into it. This is accomplished by transforming the 4 corners of -rect, and then setting it to the bounds of those points +each result Vector is computed as: -#Param rect rectangle to transform +#Code +#Literal + |A B 0| |x| Ax+By Dx+Ey +Matrix * vec = |D E 0| |y| = |Ax+By Dx+Ey Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I ## -#Return the result of calling rectStaysRect -## +#Param vecs Vectors to transform, and storage for mapped Vectors ## +#Param count number of Vectors to transform ## #Example -// incomplete + SkPaint paint; + paint.setAntiAlias(true); + paint.setStyle(SkPaint::kStroke_Style); + SkMatrix matrix; + matrix.setScale(2, 3); + SkVector radii[] = {{7, 7}, {3, 3}, {2, 2}, {4, 0}}; + for (int i = 0; i < 4; ++i) { + SkRRect rrect; + rrect.setRectRadii({20, 20, 180, 70}, radii); + canvas->drawRRect(rrect, paint); + canvas->translate(0, 60); + matrix.mapVectors(radii, SK_ARRAY_COUNT(radii)); + } ## -#ToDo incomplete ## +#SeeAlso mapVector mapPoints mapPointsWithStride mapXY ## # ------------------------------------------------------------------------------ -#Method void mapRectToQuad(SkPoint dst[4], const SkRect& rect) const +#Method void mapVector(SkScalar dx, SkScalar dy, SkVector* result) const -Applies Matrix to rect, and write the four transformed -points into dst. The points written to dst will be the original top-left, top-right, -bottom-right, and bottom-left points transformed by Matrix. +Maps Vector (x, y) to result. Vector is mapped by multiplying by Matrix, +treating Matrix translation as zero. Given: -#Param dst storage for transformed quad +#Code +#Literal + | A B 0 | | dx | +Matrix = | D E 0 |, vec = | dy | + | G H I | | 1 | ## -#Param rect rectangle to transform + +each result Vector is computed as: + +#Code +#Literal +#Outdent + |A B 0| |dx| A*dx+B*dy D*dx+E*dy +Matrix * vec = |D E 0| |dy| = |A*dx+B*dy D*dx+E*dy G*dx+H*dy+I| = ----------- , ----------- + |G H I| | 1| G*dx+H*dy+I G*dx+*dHy+I ## +#Param dx x-coordinate of Vector to map ## +#Param dy y-coordinate of Vector to map ## +#Param result storage for mapped Vector ## + #Example -// incomplete + SkPaint paint; + paint.setColor(SK_ColorGREEN); + paint.setAntiAlias(true); + paint.setTextSize(48); + SkMatrix matrix; + matrix.setRotate(90); + SkVector offset = { 7, 7 }; + for (int i = 0; i < 4; ++i) { + paint.setImageFilter(SkDropShadowImageFilter::Make(offset.fX, offset.fY, 3, 3, + SK_ColorBLUE, SkDropShadowImageFilter::kDrawShadowAndForeground_ShadowMode, nullptr)); + matrix.mapVector(offset.fX, offset.fY, &offset); + canvas->translate(0, 60); + canvas->drawString("Text", 50, 0, paint); + } ## -#ToDo incomplete ## +#SeeAlso mapVectors mapPoints mapPointsWithStride mapXY ## # ------------------------------------------------------------------------------ -#Method void mapRectScaleTranslate(SkRect* dst, const SkRect& src) const - -Maps a rectangle to another rectangle, asserting (in debug mode) that the matrix only contains -scale and translate elements. If it contains other elements, the results are undefined. +#Method SkVector mapVector(SkScalar dx, SkScalar dy) const -#Param dst incomplete ## -#Param src incomplete ## +Returns Vector (x, y) multiplied by Matrix, treating Matrix translation as zero. +Given: -#Example -// incomplete +#Code +#Literal + | A B 0 | | dx | +Matrix = | D E 0 |, vec = | dy | + | G H I | | 1 | ## -#ToDo incomplete ## +each result Vector is computed as: +#Code +#Literal +#Outdent + |A B 0| |dx| A*dx+B*dy D*dx+E*dy +Matrix * vec = |D E 0| |dy| = |A*dx+B*dy D*dx+E*dy G*dx+H*dy+I| = ----------- , ----------- + |G H I| | 1| G*dx+H*dy+I G*dx+*dHy+I ## -# ------------------------------------------------------------------------------ - -#Method SkScalar mapRadius(SkScalar radius) const +#Param dx x-coordinate of Vector to map ## +#Param dy y-coordinate of Vector to map ## -Return the mean radius of a circle after it has been mapped by -this matrix. NOTE: in perspective this value assumes the circle -has its center at the origin. - -#Param radius incomplete ## - -#Return incomplete ## +#Return mapped Vector ## #Example -// incomplete + SkPaint paint; + paint.setColor(SK_ColorGREEN); + paint.setAntiAlias(true); + paint.setTextSize(48); + SkMatrix matrix; + matrix.setRotate(90); + SkVector offset = { 7, 7 }; + for (int i = 0; i < 4; ++i) { + paint.setImageFilter(SkDropShadowImageFilter::Make(offset.fX, offset.fY, 3, 3, + SK_ColorBLUE, SkDropShadowImageFilter::kDrawShadowAndForeground_ShadowMode, nullptr)); + offset = matrix.mapVector(offset.fX, offset.fY); + canvas->translate(0, 60); + canvas->drawString("Text", 50, 0, paint); + } ## -#ToDo incomplete ## +#SeeAlso mapVectors mapPoints mapPointsWithStride mapXY ## # ------------------------------------------------------------------------------ -#Method static MapXYProc GetMapXYProc(TypeMask mask) +#Method bool mapRect(SkRect* dst, const SkRect& src) const + +Sets dst to bounds of src corners mapped by Matrix. +Returns true if mapped corners are dst corners. + +Returned value is the same as calling rectStaysRect. -#Param mask incomplete ## +#Param dst storage for bounds of mapped Points ## +#Param src Rect to map ## -#Return incomplete ## +#Return true if dst is equivalent to mapped src ## #Example -// incomplete + SkPaint paint; + paint.setAntiAlias(true); + SkMatrix matrix; + matrix.setRotate(45, 128, 128); + SkRect rotatedBounds, bounds = {40, 50, 190, 200}; + matrix.mapRect(&rotatedBounds, bounds ); + paint.setColor(SK_ColorGRAY); + canvas->drawRect(rotatedBounds, paint); + canvas->concat(matrix); + paint.setColor(SK_ColorRED); + canvas->drawRect(bounds, paint); ## -#ToDo incomplete ## +#SeeAlso mapPoints rectStaysRect ## # ------------------------------------------------------------------------------ -#Method MapXYProc getMapXYProc() const +#Method bool mapRect(SkRect* rect) const + +Sets rect to bounds of rect corners mapped by Matrix. +Returns true if mapped corners are computed rect corners. + +Returned value is the same as calling rectStaysRect. + +#Param rect rectangle to map, and storage for bounds of mapped corners ## -#Return incomplete ## +#Return true if result is equivalent to mapped src ## #Example -// incomplete + SkPaint paint; + paint.setAntiAlias(true); + SkMatrix matrix; + matrix.setRotate(45, 128, 128); + SkRect bounds = {40, 50, 190, 200}; + matrix.mapRect(&bounds); + paint.setColor(SK_ColorGRAY); + canvas->drawRect(bounds, paint); + canvas->concat(matrix); + paint.setColor(SK_ColorRED); + canvas->drawRect({40, 50, 190, 200}, paint); ## -#ToDo incomplete ## +#SeeAlso mapRectScaleTranslate mapPoints rectStaysRect ## # ------------------------------------------------------------------------------ -#Method static MapPtsProc GetMapPtsProc(TypeMask mask) +#Method void mapRectToQuad(SkPoint dst[4], const SkRect& rect) const -#Param mask incomplete ## +Maps four corners of rect to dst. Points are mapped by multiplying each +rect corner by Matrix. rect corner is processed in this order: +(rect.fLeft, rect.fTop), (rect.fRight, rect.fTop), (rect.fRight, rect.fBottom), +(rect.fLeft, rect.fBottom). -#Return incomplete ## +rect may be empty: rect.fLeft may be greater than or equal to rect.fRight; +rect.fTop may be greater than or equal to rect.fBottom. -#Example -// incomplete -## - -#ToDo incomplete ## +Given: +#Code +#Literal + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 | ## -# ------------------------------------------------------------------------------ +where pt is initialized from each of (rect.fLeft, rect.fTop), +(rect.fRight, rect.fTop), (rect.fRight, rect.fBottom), (rect.fLeft, rect.fBottom), +each dst Point is computed as: -#Method MapPtsProc getMapPtsProc() const +#Code +#Literal + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I +## -#Return incomplete ## +#Param dst storage for mapped corner Points ## +#Param rect Rect to map ## #Example -// incomplete + SkPaint paint; + paint.setAntiAlias(true); + SkMatrix matrix; + matrix.setRotate(60, 128, 128); + SkRect rect = {50, 50, 150, 150}; + SkPoint pts[4]; + matrix.mapRectToQuad(pts, rect); + for (int i = 0; i < 4; ++i) { + canvas->drawCircle(pts[i].fX, pts[i].fY, 3, paint); + } + canvas->concat(matrix); + paint.setStyle(SkPaint::kStroke_Style); + canvas->drawRect(rect, paint); ## -#ToDo incomplete ## +#SeeAlso mapRect mapRectScaleTranslate ## # ------------------------------------------------------------------------------ -#Method bool isFixedStepInX() const +#Method void mapRectScaleTranslate(SkRect* dst, const SkRect& src) const -Returns true if the matrix can be stepped in x (not complex -perspective). +Sets dst to bounds of src corners mapped by Matrix. If matrix contains +elements other than scale or translate: asserts if SK_DEBUG is defined; +otherwise, results are undefined. -#Return incomplete ## +#Param dst storage for bounds of mapped Points ## +#Param src Rect to map ## #Example -// incomplete + SkPaint paint; + SkMatrix matrix; + SkRect rect = {100, 50, 150, 180}; + matrix.setScale(2, .5f, rect.centerX(), rect.centerY()); + SkRect rotated; + matrix.mapRectScaleTranslate(&rotated, rect); + paint.setStyle(SkPaint::kStroke_Style); + canvas->drawRect(rect, paint); + paint.setColor(SK_ColorRED); + canvas->drawRect(rotated, paint); ## -#ToDo incomplete ## +#SeeAlso mapRect mapRectToQuad isScaleTranslate rectStaysRect ## # ------------------------------------------------------------------------------ -#Method SkVector fixedStepInX(SkScalar y) const +#Method SkScalar mapRadius(SkScalar radius) const -If the matrix can be stepped in x (not complex perspective) -then return the step value. -If it cannot, behavior is undefined. +Returns geometric mean radius of ellipse formed by constructing Circle of +size radius, and mapping constructed Circle with Matrix. The result squared is +equal to the major axis length times the minor axis length. +Result is not meaningful if Matrix contains perspective elements. -#Param y incomplete ## +#Param radius Circle size to map ## -#Return incomplete ## +#Return average mapped radius ## #Example -// incomplete -## - -#ToDo incomplete ## +#Description +The area enclosed by a square with sides equal to mappedRadius is the same as +the area enclosed by the ellipse major and minor axes. +## + SkPaint paint; + paint.setAntiAlias(true); + SkMatrix matrix; + const SkPoint center = {108, 93}; + matrix.setScale(2, .5f, center.fX, center.fY); + matrix.postRotate(45, center.fX, center.fY); + const SkScalar circleRadius = 50; + SkScalar mappedRadius = matrix.mapRadius(circleRadius); + SkVector minorAxis, majorAxis; + matrix.mapVector(0, circleRadius, &minorAxis); + matrix.mapVector(circleRadius, 0, &majorAxis); + SkString mappedArea; + mappedArea.printf("area = %g", mappedRadius * mappedRadius); + canvas->drawString(mappedArea, 145, 250, paint); + canvas->drawString("mappedRadius", center.fX + mappedRadius + 3, center.fY, paint); + paint.setColor(SK_ColorRED); + SkString axArea; + axArea.printf("area = %g", majorAxis.length() * minorAxis.length()); + paint.setStyle(SkPaint::kFill_Style); + canvas->drawString(axArea, 15, 250, paint); + paint.setStyle(SkPaint::kStroke_Style); + canvas->drawRect({10, 200, 10 + majorAxis.length(), 200 + minorAxis.length()}, paint); + paint.setColor(SK_ColorBLACK); + canvas->drawLine(center.fX, center.fY, center.fX + mappedRadius, center.fY, paint); + canvas->drawLine(center.fX, center.fY, center.fX, center.fY + mappedRadius, paint); + canvas->drawRect({140, 180, 140 + mappedRadius, 180 + mappedRadius}, paint); + canvas->concat(matrix); + canvas->drawCircle(center.fX, center.fY, circleRadius, paint); + paint.setColor(SK_ColorRED); + canvas->drawLine(center.fX, center.fY, center.fX + circleRadius, center.fY, paint); + canvas->drawLine(center.fX, center.fY, center.fX, center.fY + circleRadius, paint); +## + +#SeeAlso mapVector ## # ------------------------------------------------------------------------------ -#Method bool cheapEqualTo(const SkMatrix& m) const - -Returns true if Matrix equals m, using an efficient comparison. - -Return false when the sign of zero values is the different, that is, one -matrix has positive zero value and the other has negative zero value. +#Method bool isFixedStepInX() const -Normally, comparing NaN prevents the value from equaling any other value, -including itself. To improve performance, NaN values are treated as bit patterns -that are equal if their bit patterns are equal. +Returns true if a unit step in x at some y mapped through Matrix can be +represented by a constant Vector. Returns true if getType returns kIdentity_Mask, +or combinations of: kTranslate_Mask, kScale_Mask, and kAffine_Mask. -#Param m incomplete ## +May return true if getType returns kPerspective_Mask, but only when Matrix +does not include rotation or skewing along the y-axis. -#Return incomplete ## +#Return true if Matrix does not have complex perspective ## #Example -// incomplete -## - -#ToDo incomplete ## + SkMatrix matrix; + for (SkScalar px : { 0.0f, 0.1f } ) { + for (SkScalar py : { 0.0f, 0.1f } ) { + for (SkScalar sy : { 1, 2 } ) { + matrix.setAll(1, 0, 0, 0, sy, 0, px, py, 1); + matrix.dump(); + SkDebugf("isFixedStepInX: %s\n", matrix.isFixedStepInX() ? "true" : "false"); + } + } + } +#StdOut +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.0000 0.0000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.1000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.0000 0.1000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.1000 0.0000 1.0000] +isFixedStepInX: false +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.1000 0.0000 1.0000] +isFixedStepInX: false +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.1000 0.1000 1.0000] +isFixedStepInX: false +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.1000 0.1000 1.0000] +isFixedStepInX: false +## +## + +#SeeAlso fixedStepInX getType ## # ------------------------------------------------------------------------------ -#Method friend SK_API bool operator==(const SkMatrix& a, const SkMatrix& b) +#Method SkVector fixedStepInX(SkScalar y) const -mac chromium debug build requires SK_API to make operator== visible +Returns Vector representing a unit step in x at y mapped through Matrix. +If isFixedStepInX is false, returned value is undefined. -#Param a incomplete ## -#Param b incomplete ## +#Param y position of line parallel to x-axis ## -#Return incomplete ## +#Return Vector advance of mapped unit step in x ## #Example -// incomplete -## - -#ToDo incomplete ## +#Image 3 + SkMatrix matrix; + const SkPoint center = { 128, 128 }; + matrix.setScale(20, 25, center.fX, center.fY); + matrix.postRotate(75, center.fX, center.fY); + { + SkAutoCanvasRestore acr(canvas, true); + canvas->concat(matrix); + canvas->drawBitmap(source, 0, 0); + } + if (matrix.isFixedStepInX()) { + SkPaint paint; + paint.setAntiAlias(true); + SkVector step = matrix.fixedStepInX(128); + SkVector end = center + step; + canvas->drawLine(center, end, paint); + SkVector arrow = { step.fX + step.fY, step.fY - step.fX}; + arrow = arrow * .25f; + canvas->drawLine(end, end - arrow, paint); + canvas->drawLine(end, {end.fX + arrow.fY, end.fY - arrow.fX}, paint); + } +## + +#SeeAlso isFixedStepInX getType ## # ------------------------------------------------------------------------------ -#Method friend SK_API bool operator!=(const SkMatrix& a, const SkMatrix& b) - -#Param a incomplete ## -#Param b incomplete ## +#Method bool cheapEqualTo(const SkMatrix& m) const -#Return incomplete ## +Returns true if Matrix equals m, using an efficient comparison. -#Example -// incomplete -## +Returns false when the sign of zero values is the different; when one +matrix has positive zero value and the other has negative zero value. -#ToDo incomplete ## +Returns true even when both Matrices contain NaN. -## +NaN never equals any value, including itself. To improve performance, NaN values +are treated as bit patterns that are equal if their bit patterns are equal. -# ------------------------------------------------------------------------------ +#Param m Matrix to compare ## -#Enum _anonymous_3 +#Return true if m and Matrix are represented by identical bit patterns ## -#Code - enum { - kMaxFlattenSize = 9 * sizeof(SkScalar) + sizeof(uint32_t), +#Example + auto debugster = [](const char* prefix, const SkMatrix& a, const SkMatrix& b) -> void { + SkDebugf("%s: a %c= b a.cheapEqualTo(b): %s\n", prefix, + a == b ? '=' : '!', a.cheapEqualTo(b) ? "true" : "false"); }; + SkMatrix a, b; + a.setAll(1, 0, 0, 0, 1, 0, 0, 0, 1); + b.setIdentity(); + debugster("identity", a, b); + a.setAll(1, -0.0f, 0, 0, 1, 0, 0, 0, 1); + debugster("neg zero", a, b); + a.setAll(1, SK_ScalarNaN, 0, 0, 1, 0, 0, 0, 1); + debugster(" one NaN", a, b); + b.setAll(1, SK_ScalarNaN, 0, 0, 1, 0, 0, 0, 1); + debugster("both NaN", a, b); +#StdOut +identity: a == b a.cheapEqualTo(b): true +neg zero: a == b a.cheapEqualTo(b): false + one NaN: a != b a.cheapEqualTo(b): false +both NaN: a != b a.cheapEqualTo(b): true ## - -#Const kMaxFlattenSize = 9 * sizeof(SkScalar) + sizeof(uint32_t) - writeToMemory and readFromMemory will never return a value larger than this -## - -#Example -// incomplete ## -#ToDo incomplete ## +#SeeAlso operator==(const SkMatrix& a, const SkMatrix& b) ## # ------------------------------------------------------------------------------ -#Method size_t writeToMemory(void* buffer) const +#Method bool operator==(const SkMatrix& a, const SkMatrix& b) -return the number of bytes written, whether or not buffer is null +Compares a and b; returns true if a and b are numerically equal. Returns true +even if sign of zero values are different. Returns false if either Matrix +contains NaN, even if the other Matrix also contains NaN. -#Param buffer incomplete ## +#Param a Matrix to compare ## +#Param b Matrix to compare ## -#Return incomplete ## +#Return true if m and Matrix are numerically equal ## #Example -// incomplete + auto debugster = [](const char* prefix, const SkMatrix& a, const SkMatrix& b) -> void { + SkDebugf("%s: a %c= b a.cheapEqualTo(b): %s\n", prefix, + a == b ? '=' : '!', a.cheapEqualTo(b) ? "true" : "false"); + }; + SkMatrix a, b; + a.setAll(1, 0, 0, 0, 1, 0, 0, 0, 1); + b.setScale(2, 4); + b.postScale(0.5f, 0.25f); + debugster("identity", a, b); +#StdOut +identity: a == b a.cheapEqualTo(b): true +## ## -#ToDo incomplete ## +#SeeAlso cheapEqualTo operator!=(const SkMatrix& a, const SkMatrix& b) ## # ------------------------------------------------------------------------------ -#Method size_t readFromMemory(const void* buffer, size_t length) +#Method bool operator!=(const SkMatrix& a, const SkMatrix& b) -Reads data from the buffer parameter +Compares a and b; returns true if a and b are not numerically equal. Returns false +even if sign of zero values are different. Returns true if either Matrix +contains NaN, even if the other Matrix also contains NaN. -#Param buffer memory to read from -## -#Param length amount of memory available in the buffer -## +#Param a Matrix to compare ## +#Param b Matrix to compare ## -#Return number of bytes read (must be a multiple of 4) or - 0 if there was not enough memory available -## +#Return true if m and Matrix are numerically not equal ## #Example -// incomplete + auto debugster = [](const char* prefix, const SkMatrix& a, const SkMatrix& b) -> void { + SkDebugf("%s: a %c= b a.cheapEqualTo(b): %s\n", prefix, + a != b ? '!' : '=', a.cheapEqualTo(b) ? "true" : "false"); + }; + SkMatrix a, b; + a.setAll(1, 0, 0, 0, 1, 0, 1, 0, 1); + a.invert(&b); + debugster("identity", a, b); ## -#ToDo incomplete ## +#SeeAlso cheapEqualTo operator==(const SkMatrix& a, const SkMatrix& b) ## @@ -2177,11 +4077,26 @@ Reads data from the buffer parameter #Method void dump() const +Writes text representation of Matrix to standard output. Floating point values +are written with limited precision; it may not be possible to reconstruct +original Matrix from output. + #Example -// incomplete + SkMatrix matrix; + matrix.setRotate(45); + matrix.dump(); + SkMatrix nearlyEqual; + nearlyEqual.setAll(0.7071f, -0.7071f, 0, 0.7071f, 0.7071f, 0, 0, 0, 1); + nearlyEqual.dump(); + SkDebugf("matrix %c= nearlyEqual\n", matrix == nearlyEqual ? '=' : '!'); +#StdOut +[ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +[ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +matrix != nearlyEqual +## ## -#ToDo incomplete ## +#SeeAlso toString ## @@ -2189,13 +4104,31 @@ Reads data from the buffer parameter #Method void toString(SkString* str) const -#Param str incomplete ## +Creates string representation of Matrix. Floating point values +are written with limited precision; it may not be possible to reconstruct +original Matrix from output. + +#Param str storage for string representation of Matrix ## #Example -// incomplete + SkMatrix matrix; + matrix.setRotate(45); + SkString mStr, neStr; + matrix.toString(&mStr); + SkMatrix nearlyEqual; + nearlyEqual.setAll(0.7071f, -0.7071f, 0, 0.7071f, 0.7071f, 0, 0, 0, 1); + nearlyEqual.toString(&neStr); + SkDebugf("mStr %s\n", mStr.c_str()); + SkDebugf("neStr %s\n", neStr.c_str()); + SkDebugf("matrix %c= nearlyEqual\n", matrix == nearlyEqual ? '=' : '!'); +#StdOut +mStr [ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +neStr [ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +matrix != nearlyEqual +## ## -#ToDo incomplete ## +#SeeAlso dump ## @@ -2203,19 +4136,23 @@ Reads data from the buffer parameter #Method SkScalar getMinScale() const -Calculates the minimum scaling factor of the matrix as computed from the -singular value decomposition of the upper -left 2x2. If the max scale factor cannot be computed (for example overflow or perspective) --1 is returned. +Returns the minimum scaling factor of Matrix by decomposing the scaling and +skewing elements. +Returns -1 if scale factor overflows or Matrix contains perspective. #Return minimum scale factor ## #Example -// incomplete + SkMatrix matrix; + matrix.setScale(42, 24); + SkDebugf("matrix.getMinScale() %g\n", matrix.getMinScale()); +#StdOut +matrix.getMinScale() 24 +## ## -#ToDo incomplete ## +#SeeAlso getMaxScale getMinMaxScales ## @@ -2223,19 +4160,23 @@ left 2x2. If the max scale factor cannot be computed (for example overflow or pe #Method SkScalar getMaxScale() const -Calculates the maximum scaling factor of the matrix as computed from the -singular value decomposition of the upper -left 2x2. If the max scale factor cannot be computed (for example overflow or perspective) --1 is returned. +Returns the maximum scaling factor of Matrix by decomposing the scaling and +skewing elements. +Returns -1 if scale factor overflows or Matrix contains perspective. #Return maximum scale factor ## #Example -// incomplete + SkMatrix matrix; + matrix.setScale(42, 24); + SkDebugf("matrix.getMaxScale() %g\n", matrix.getMaxScale()); +#StdOut +matrix.getMaxScale() 42 +## ## -#ToDo incomplete ## +#SeeAlso getMinScale getMinMaxScales ## @@ -2243,19 +4184,30 @@ left 2x2. If the max scale factor cannot be computed (for example overflow or pe #Method bool SK_WARN_UNUSED_RESULT getMinMaxScales(SkScalar scaleFactors[2]) const -Gets both the min and max scale factors. The min scale factor is scaleFactors[0] and the max -is scaleFactors[1]. If the min/max scale factors cannot be computed false is returned and the -values of scaleFactors[] are undefined. +Sets scaleFactors[0] to the minimum scaling factor, and scaleFactors[1] to the +maximum scaling factor. Scaling factors are computed by decomposing +the Matrix scaling and skewing elements. + +Returns true if scaleFactors are found; otherwise, returns false and sets +scaleFactors to undefined values. -#Param scaleFactors incomplete ## +#Param scaleFactors storage for minimum and maximum scale factors ## -#Return incomplete ## +#Return true if scale factors were computed correctly ## #Example -// incomplete + SkMatrix matrix; + matrix.setAll(1, 0, 0, 0, 1, 0, 0, 0, 0); + matrix.invert(&matrix); + SkScalar factor[2] = {2, 2}; + bool result = matrix.getMinMaxScales(factor); + SkDebugf("matrix.getMinMaxScales() %s %g %g\n", result ? "true" : "false", factor[0], factor[1]); +#StdOut +matrix.getMinMaxScales() false 2 2 +## ## -#ToDo incomplete ## +#SeeAlso getMinScale getMaxScale ## @@ -2263,25 +4215,52 @@ values of scaleFactors[] are undefined. #Method bool decomposeScale(SkSize* scale, SkMatrix* remaining = nullptr) const -Attempt to decompose this matrix into a scale-only component and whatever remains, where -the scale component is to be applied first. +Decomposes Matrix into scale components and whatever remains. Returns false if +Matrix could not be decomposed. + +Sets scale to portion of Matrix that scales in x and y. Sets remaining to Matrix +with x and y scaling factored out. remaining may be passed as nullptr +to determine if Matrix can be decomposed without computing remainder. + +Returns true if scale components are found. scale and remaining are +unchanged if Matrix contains perspective; scale factors are not finite, or +are nearly zero. + +On success + #Formula -M -> Remaining * Scale +Matrix = scale * Remaining ## -On success, return true and assign the scale and remaining components (assuming their -respective parameters are not null). On failure return false and ignore the parameters. -Possible reasons to fail: perspective, one or more scale factors are zero. -#Param scale incomplete ## -#Param remaining incomplete ## +#Param scale x and y scaling factors; may be nullptr ## +#Param remaining Matrix without scaling; may be nullptr ## -#Return incomplete ## +#Return true if scale can be computed ## #Example -// incomplete + SkMatrix matrix; + matrix.setRotate(90 * SK_Scalar1); + matrix.postScale(1.f / 4, 1.f / 2); + matrix.dump(); + SkSize scale = {SK_ScalarNaN, SK_ScalarNaN}; + SkMatrix remaining; + remaining.reset(); + bool success = matrix.decomposeScale(&scale, &remaining); + SkDebugf("success: %s ", success ? "true" : "false"); + SkDebugf("scale: %g, %g\n", scale.width(), scale.height()); + remaining.dump(); + SkMatrix scaleMatrix = SkMatrix::MakeScale(scale.width(), scale.height()); + SkMatrix combined = SkMatrix::Concat(scaleMatrix, remaining); + combined.dump(); +#StdOut +[ 0.0000 -0.2500 0.0000][ 0.5000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +success: true scale: 0.5, 0.25 +[ 0.0000 -0.5000 0.0000][ 2.0000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +[ 0.0000 -0.2500 0.0000][ 0.5000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +## ## -#ToDo incomplete ## +#SeeAlso setScale MakeScale ## @@ -2289,15 +4268,31 @@ Possible reasons to fail: perspective, one or more scale factors are zero. #Method static const SkMatrix& I() -Return a reference to a const identity matrix +Returns reference to const identity Matrix. Returned Matrix is set to: -#Return incomplete ## +#Code +#Literal +| 1 0 0 | +| 0 1 0 | +| 0 0 1 | +## + +#Return const identity Matrix ## #Example -// incomplete + SkMatrix m1, m2, m3; + m1.reset(); + m2.setIdentity(); + m3 = SkMatrix::I(); + SkDebugf("m1 %c= m2\n", m1 == m2 ? '=' : '!'); + SkDebugf("m2 %c= m3\n", m1 == m2 ? '=' : '!'); +#StdOut +m1 == m2 +m2 == m3 +## ## -#ToDo incomplete ## +#SeeAlso reset() setIdentity ## @@ -2305,16 +4300,26 @@ Return a reference to a const identity matrix #Method static const SkMatrix& InvalidMatrix() -Return a reference to a const matrix that is "invalid", one that could -never be used. +Returns reference to a const Matrix with invalid values. Returned Matrix is set +to: + +#Code +#Literal +| SK_ScalarMax SK_ScalarMax SK_ScalarMax | +| SK_ScalarMax SK_ScalarMax SK_ScalarMax | +| SK_ScalarMax SK_ScalarMax SK_ScalarMax | +## -#Return incomplete ## +#Return const invalid Matrix ## #Example -// incomplete + SkDebugf("scaleX %g\n", SkMatrix::InvalidMatrix().getScaleX()); +#StdOut +scaleX 3.40282e+38 +## ## -#ToDo incomplete ## +#SeeAlso SeeAlso getType ## @@ -2322,18 +4327,49 @@ never be used. #Method static SkMatrix Concat(const SkMatrix& a, const SkMatrix& b) -Return the concatenation of two matrices, a * b. +Returns Matrix a multiplied by Matrix b. + +Given: + +#Code +#Literal + | A B C | | J K L | +a = | D E F |, b = | M N O | + | G H I | | P Q R | +## + +sets Matrix to: + +#Code +#Literal + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +a * b = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR | +## -#Param a incomplete ## -#Param b incomplete ## +#Param a Matrix on left side of multiply expression ## +#Param b Matrix on right side of multiply expression ## -#Return incomplete ## +#Return Matrix computed from a times b ## #Example -// incomplete +#Height 64 +#Image 4 +#Description +setPolyToPoly creates perspective matrices, one the inverse of the other. +Multiplying the matrix by its inverse turns into an identity matrix. +## +SkMatrix matrix, matrix2; +SkPoint bitmapBounds[4], perspect[4] = {{50, 10}, {180, 40}, {236, 176}, {10, 206}}; +SkRect::Make(source.bounds()).toQuad(bitmapBounds); +matrix.setPolyToPoly(bitmapBounds, perspect, 4); +matrix2.setPolyToPoly(perspect, bitmapBounds, 4); +SkMatrix concat = SkMatrix::Concat(matrix, matrix2); +canvas->concat(concat); +canvas->drawBitmap(source, 0, 0); ## -#ToDo incomplete ## +#SeeAlso preConcat postConcat ## @@ -2341,14 +4377,29 @@ Return the concatenation of two matrices, a * b. #Method void dirtyMatrixTypeCache() -Testing routine; the matrix type cache should never need to be -manually invalidated during normal use. +Sets internal cache to unknown state. Use to force update after repeated +modifications to Matrix element reference returned by operator[](int index). #Example -// incomplete +SkMatrix matrix; +matrix.setIdentity(); +SkDebugf("with identity matrix: x = %g\n", matrix.mapXY(24, 42).fX); +SkScalar& skewRef = matrix[SkMatrix::kMSkewX]; +skewRef = 0; +SkDebugf("after skew x mod: x = %g\n", matrix.mapXY(24, 42).fX); +skewRef = 1; +SkDebugf("after 2nd skew x mod: x = %g\n", matrix.mapXY(24, 42).fX); +matrix.dirtyMatrixTypeCache(); +SkDebugf("after dirty cache: x = %g\n", matrix.mapXY(24, 42).fX); +#StdOut +with identity matrix: x = 24 +after skew x mod: x = 24 +after 2nd skew x mod: x = 24 +after dirty cache: x = 66 +## ## -#ToDo incomplete ## +#SeeAlso operator[](int index) getType ## @@ -2356,18 +4407,30 @@ manually invalidated during normal use. #Method void setScaleTranslate(SkScalar sx, SkScalar sy, SkScalar tx, SkScalar ty) -Initialize the matrix to be scale + post-translate. +Initializes Matrix with scale and translate elements. -#Param sx incomplete ## -#Param sy incomplete ## -#Param tx incomplete ## -#Param ty incomplete ## +#Code +#Literal +| sx 0 tx | +| 0 sy ty | +| 0 0 1 | +## + +#Param sx horizontal scale factor to store ## +#Param sy vertical scale factor to store ## +#Param tx horizontal translation to store ## +#Param ty vertical translation to store ## #Example -// incomplete +SkMatrix matrix; +matrix.setScaleTranslate(1, 2, 3, 4); +matrix.dump(); +#StdOut +[ 1.0000 0.0000 3.0000][ 0.0000 2.0000 4.0000][ 0.0000 0.0000 1.0000] +## ## -#ToDo incomplete ## +#SeeAlso setScale preTranslate postTranslate ## @@ -2375,15 +4438,24 @@ Initialize the matrix to be scale + post-translate. #Method bool isFinite() const -Are all elements of the matrix finite? +Returns true if all elements of the matrix are finite. Returns false if any +element is infinity, or NaN. -#Return incomplete ## +#Return true if matrix has only finite elements ## #Example -// incomplete +SkMatrix matrix = SkMatrix::MakeTrans(SK_ScalarNaN, 0); +matrix.dump(); +SkDebugf("matrix is finite: %s\n", matrix.isFinite() ? "true" : "false"); +SkDebugf("matrix %c= matrix\n", matrix == matrix ? '=' : '!'); +#StdOut +[ 1.0000 0.0000 nan][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +matrix is finite: false +matrix != matrix +## ## -#ToDo incomplete ## +#SeeAlso operator== ## diff --git a/docs/SkPaint_Reference.bmh b/docs/SkPaint_Reference.bmh index 96822f950f..3369cd2861 100644 --- a/docs/SkPaint_Reference.bmh +++ b/docs/SkPaint_Reference.bmh @@ -4177,16 +4177,6 @@ void draw(SkCanvas* canvas) { #Struct FontMetrics - FontMetrics is filled out by getFontMetrics. FontMetrics contents reflect the values - computed by Font_Manager using Typeface. Values are set to zero if they are - not available. - - fUnderlineThickness and fUnderlinePosition have a bit set in fFlags if their values - are valid, since their value may be zero. - - fStrikeoutThickness and fStrikeoutPosition have a bit set in fFlags if their values - are valid, since their value may be zero. - #Code struct FontMetrics { enum FontMetricsFlags { @@ -4220,11 +4210,17 @@ void draw(SkCanvas* canvas) { }; ## - #Enum FontMetricsFlags + FontMetrics is filled out by getFontMetrics. FontMetrics contents reflect the values + computed by Font_Manager using Typeface. Values are set to zero if they are + not available. - FontMetricsFlags are set in fFlags when underline and strikeout metrics are valid; - the underline or strikeout metric may be valid and zero. - Fonts with embedded bitmaps may not have valid underline or strikeout metrics. + fUnderlineThickness and fUnderlinePosition have a bit set in fFlags if their values + are valid, since their value may be zero. + + fStrikeoutThickness and fStrikeoutPosition have a bit set in fFlags if their values + are valid, since their value may be zero. + + #Enum FontMetricsFlags #Code enum FontMetricsFlags { @@ -4235,6 +4231,10 @@ void draw(SkCanvas* canvas) { }; ## + FontMetricsFlags are set in fFlags when underline and strikeout metrics are valid; + the underline or strikeout metric may be valid and zero. + Fonts with embedded bitmaps may not have valid underline or strikeout metrics. + #Const kUnderlineThicknessIsValid_Flag 0x0001 Set if fUnderlineThickness is valid. ## diff --git a/docs/SkPath_Reference.bmh b/docs/SkPath_Reference.bmh index e38b30da77..9caad2d481 100644 --- a/docs/SkPath_Reference.bmh +++ b/docs/SkPath_Reference.bmh @@ -456,10 +456,10 @@ kCW_Direction travel clockwise; the same added with kCCW_Direction travel counterclockwise. #Const kCW_Direction 0 - Contour travels in a clockwise direction. + Contour travels in a clockwise direction ## #Const kCCW_Direction 1 - Contour travels in a counterclockwise direction. + Contour travels in a counterclockwise direction ## @@ -744,6 +744,7 @@ Point_Array, using the formula: #Formula (this->points * weight) + ending->points * (1 - weight) ## +. weight is most useful when between zero (ending Point_Array) and one (this Point_Array); will work with values outside of this @@ -3464,10 +3465,10 @@ Four Oval parts with radii (rx, ry) start at last Path Point and ends at (x, y). ArcSize and Direction select one of the four Oval parts. #Const kSmall_ArcSize 0 -Smaller of Arc pair. +smaller of Arc pair ## #Const kLarge_ArcSize 1 -Larger of Arc pair. +larger of Arc pair ## #Example @@ -3505,18 +3506,20 @@ void draw(SkCanvas* canvas) { #Method void arcTo(SkScalar rx, SkScalar ry, SkScalar xAxisRotate, ArcSize largeArc, Direction sweep, SkScalar x, SkScalar y) -Append Arc to Path. Arc is implemented by one or more Conics weighted to describe part of Oval -with radii (rx, ry) rotated by xAxisRotate degrees. Arc curves from last Path Point to (x, y), -choosing one of four possible routes: clockwise or counterclockwise, and smaller or larger. +Append Arc to Path. Arc is implemented by one or more Conics weighted to +describe part of Oval with radii (rx, ry) rotated by xAxisRotate degrees. Arc +curves from last Path Point to (x, y), choosing one of four possible routes: +clockwise or counterclockwise, and smaller or larger. -Arc sweep is always less than 360 degrees. arcTo appends Line to (x, y) if either radii are zero, -or if last Path Point equals (x, y). arcTo scales radii (rx, ry) to fit last Path Point and -(x, y) if both are greater than zero but too small. +Arc sweep is always less than 360 degrees. arcTo appends Line to (x, y) if +either radii are zero, or if last Path Point equals (x, y). arcTo scales radii +(rx, ry) to fit last Path Point and (x, y) if both are greater than zero but +too small. arcTo appends up to four Conic curves. -arcTo implements the functionality of SVG_Arc, although SVG "sweep-flag" value is -opposite the integer value of sweep; SVG "sweep-flag" uses 1 for clockwise, while kCW_Direction -cast to int is zero. +arcTo implements the functionality of SVG_Arc, although SVG "sweep-flag" value +is opposite the integer value of sweep; SVG "sweep-flag" uses 1 for clockwise, +while kCW_Direction cast to int is zero. #Param rx radius in x before x-axis rotation ## #Param ry radius in y before x-axis rotation ## @@ -3601,7 +3604,8 @@ void draw(SkCanvas* canvas) { Append Arc to Path, relative to last Path Point. Arc is implemented by one or more Conic, weighted to describe part of Oval with radii (rx, ry) rotated by -xAxisRotate degrees. Arc curves from last Path Point (x0, y0) to end Point +xAxisRotate degrees. Arc curves from last Path Point (x0, y0) to end Point: + #Formula (x0 + dx, y0 + dy) ## @@ -3812,8 +3816,9 @@ next Quad. Maximum pts storage size is given by: #Formula (1 + 2 * (1 << pow2)) * sizeof(SkPoint) ## +. -ConvertConicToQuads returns Quad count used the approximation, which may be smaller +Returns Quad count used the approximation, which may be smaller than the number requested. Conic_Weight determines the amount of influence Conic control point has on the curve. @@ -4200,12 +4205,12 @@ void draw(SkCanvas* canvas) { Direction dir = kCW_Direction) Add Circle centered at (x, y) of size radius to Path, appending kMove_Verb, -four kConic_Verb, and kClose_Verb. Circle begins at +four kConic_Verb, and kClose_Verb. Circle begins at: #Formula (x + radius, y) ## -, continuing clockwise if dir is kCW_Direction, and counterclockwise if dir is -kCCW_Direction. +, continuing +clockwise if dir is kCW_Direction, and counterclockwise if dir is kCCW_Direction. Has no effect if radius is zero or negative. @@ -5040,9 +5045,9 @@ for (int y = 2; y < 256; y += 9) { #Method void dump(SkWStream* stream, bool forceClose, bool dumpAsHex) const -Writes text representation of Path to stream. If stream is nullptr, dump() writes to -standard output. Set forceClose to true to get -edges used to fill Path. Set dumpAsHex true to generate exact binary representations +Writes text representation of Path to stream. If stream is nullptr, writes to +standard output. Set forceClose to true to get edges used to fill Path. +Set dumpAsHex true to generate exact binary representations of floating point numbers used in Point_Array and Conic_Weights. #Param stream writable Stream receiving Path text representation; may be nullptr ## diff --git a/docs/SkPixmap_Reference.bmh b/docs/SkPixmap_Reference.bmh index 837d3af153..9cec400b4b 100644 --- a/docs/SkPixmap_Reference.bmh +++ b/docs/SkPixmap_Reference.bmh @@ -55,13 +55,11 @@ to manage pixel memory; Pixel_Ref is safe across threads. # bounds() # Returns width and height as Rectangle. ## # colorSpace # Returns Image_Info Color_Space. ## # colorType # Returns Image_Info Color_Type. ## +# computeByteSize # Returns size required for pixels. ## # computeIsOpaque # Returns true if all pixels are opaque. ## # erase() # Writes Color to pixels. ## # extractSubset # Sets pointer to portion of original. ## # getColor # Returns one pixel as Unpremultiplied Color. ## -# getSafeSize # Returns minimum size required for pixels in 32 bits. ## -# getSafeSize64 # Returns minimum size required for pixels in 64 bits. ## -# getSize64 # Returns conservative size required for pixels. ## # height() # Returns pixel row count. ## # info() # Returns Image_Info. ## # isOpaque # Returns true if Image_Info describes opaque pixels. ## @@ -395,7 +393,7 @@ width: 384 height: 384 color: BGRA_8888 alpha: Opaque #Method size_t rowBytes() const Returns row bytes, the interval from one pixel row to the next. Row bytes -is at least as large as +is at least as large as: #Formula width() * info().bytesPerPixel() ## @@ -461,6 +459,7 @@ inset address: 0x7f2a440fb210 #Method int width() const Returns pixel count in each pixel row. Should be equal or less than: + #Formula rowBytes() / info().bytesPerPixel() ## @@ -622,11 +621,7 @@ isOpaque: true #Method SkIRect bounds() const -Returns IRect -#Formula -{ 0, 0, width(), height() } -## -. +Returns IRect { 0, 0, width(), height() }. #Return integral rectangle from origin to width() and height() ## @@ -718,66 +713,6 @@ color: kRGBA_F16_SkColorType bytesPerPixel: 8 shiftPerPixel: 3 # ------------------------------------------------------------------------------ -#Method uint64_t getSize64() const - -#Deprecated -## - -Returns conservative memory required for pixel storage. -Includes unused memory on last row when rowBytesAsPixels exceeds width(). - -#Return conservative pixel storage size ## - -#NoExample -## - -#SeeAlso getSafeSize64 getSafeSize height() rowBytes width() SkImageInfo::bytesPerPixel - -## - -# ------------------------------------------------------------------------------ - -#Method uint64_t getSafeSize64() const - -#Deprecated -## - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when rowBytesAsPixels exceeds width(). - -#Return exact pixel storage size ## - -#NoExample -## - -#SeeAlso getSize64 getSafeSize height() rowBytes width() SkImageInfo::bytesPerPixel - -## - -# ------------------------------------------------------------------------------ - -#Method size_t getSafeSize() const - -#Deprecated -## - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when rowBytesAsPixels exceeds width(). -Returns zero if value is does not fit in a signed 32-bit integer. -The largest value than can be returned is 2,147,483,647. - -#Return exact pixel storage size if size fits in signed 32 bits ## - -#NoExample -## - -#SeeAlso getSize64 getSafeSize64 height() rowBytes width() SkImageInfo::bytesPerPixel sk_64_isS32 - -## - - -# ------------------------------------------------------------------------------ - #Method size_t computeByteSize() const Returns minimum memory required for pixel storage. @@ -1574,11 +1509,8 @@ is drawn after overwriting bottom half float color with top half float color. #Method bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes, int srcX, int srcY, SkTransferFunctionBehavior behavior) const -Copies a Rect of pixels to dstPixels. Copy starts at (srcX, srcY), and does not exceed -#Formula -(this->width(), this->height()) -## -. +Copies a Rect of pixels to dstPixels. Copy starts at (srcX, srcY), and does not +exceed (this->width(), this->height()). dstInfo specifies width, height, Color_Type, Alpha_Type, and Color_Space of destination. dstRowBytes specifics the gap from one destination @@ -1593,7 +1525,8 @@ match. If this->colorSpace is nullptr, dstInfo.colorSpace must match. Returns false if pixel conversion is not possible. srcX and srcY may be negative to copy only top or left of source. Returns -false if width() or height() is zero or negative. Returns false if +false if width() or height() is zero or negative. Returns false if: + #Formula abs(srcX) >= this->width() ## @@ -1655,11 +1588,7 @@ void draw(SkCanvas* canvas) { #Method bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes) const Copies a Rect of pixels to dstPixels. Copy starts at (0, 0), and does not -exceed -#Formula -(this->width(), this->height()) -## -. +exceed (this->width(), this->height()). dstInfo specifies width, height, Color_Type, Alpha_Type, and Color_Space of destination. dstRowBytes specifics the gap from one destination @@ -1722,11 +1651,7 @@ creates visible banding. int srcY) const Copies a Rect of pixels to dstPixels. Copy starts at (srcX, srcY), and does not -exceed -#Formula -(this->width(), this->height()) -## -. +exceed (this->width(), this->height()). dstInfo specifies width, height, Color_Type, Alpha_Type, and Color_Space of destination. dstRowBytes specifics the gap from one destination @@ -1741,7 +1666,8 @@ match. If this->colorSpace is nullptr, dstInfo.colorSpace must match. Returns false if pixel conversion is not possible. srcX and srcY may be negative to copy only top or left of source. Returns -false if this->width() or this->height() is zero or negative. Returns false if +false if this->width() or this->height() is zero or negative. Returns false if: + #Formula abs(srcX) >= this->width() ## @@ -1803,7 +1729,8 @@ match. If this->colorSpace is nullptr, dst.info().colorSpace must match. Returns false if pixel conversion is not possible. srcX and srcY may be negative to copy only top or left of source. Returns -false this->width() or this->height() is zero or negative. Returns false if +false this->width() or this->height() is zero or negative. Returns false if: + #Formula abs(srcX) >= this->width() ## diff --git a/docs/SkRect_Reference.bmh b/docs/SkRect_Reference.bmh index 7dc1e3776a..1a28f1bd12 100644 --- a/docs/SkRect_Reference.bmh +++ b/docs/SkRect_Reference.bmh @@ -136,20 +136,20 @@ is a convenience, but does not designate a special empty rectangle. #Return bounds (0, 0, 0, 0) ## #Example - SkRect rect = SkRect::MakeEmpty();
- SkDebugf("MakeEmpty isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
- rect.offset(10, 10);
- SkDebugf("offset rect isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
- rect.inset(10, 10);
- SkDebugf("inset rect isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
- rect.outset(20, 20);
- SkDebugf("outset rect isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
-#StdOut
-MakeEmpty isEmpty: true
-offset rect isEmpty: true
-inset rect isEmpty: true
-outset rect isEmpty: false
-##
+ SkRect rect = SkRect::MakeEmpty(); + SkDebugf("MakeEmpty isEmpty: %s\n", rect.isEmpty() ? "true" : "false"); + rect.offset(10, 10); + SkDebugf("offset rect isEmpty: %s\n", rect.isEmpty() ? "true" : "false"); + rect.inset(10, 10); + SkDebugf("inset rect isEmpty: %s\n", rect.isEmpty() ? "true" : "false"); + rect.outset(20, 20); + SkDebugf("outset rect isEmpty: %s\n", rect.isEmpty() ? "true" : "false"); +#StdOut +MakeEmpty isEmpty: true +offset rect isEmpty: true +inset rect isEmpty: true +outset rect isEmpty: false +## ## #SeeAlso isEmpty setEmpty setLargestInverted SkIRect::MakeEmpty @@ -166,23 +166,23 @@ setting right and bottom to most positive finite value. #Return bounds (SK_ScalarMin, SK_ScalarMin, SK_ScalarMax, SK_ScalarMax) ## #Example - SkRect rect = SkRect::MakeLargest();
- SkDebugf("MakeLargest isLargest: %s\n", rect.isLargest() ? "true" : "false");
- SkDebugf("MakeLargest isFinite: %s\n", rect.isFinite() ? "true" : "false");
- rect.outset(1e31, 1e31);
- SkDebugf("outset a little isLargest: %s\n", rect.isLargest() ? "true" : "false");
- SkDebugf("outset a little isFinite: %s\n", rect.isFinite() ? "true" : "false");
- rect.outset(1e32, 1e32);
- SkDebugf("outset a little more isLargest: %s\n", rect.isLargest() ? "true" : "false");
- SkDebugf("outset a little more isFinite: %s\n", rect.isFinite() ? "true" : "false");
-#StdOut
-MakeLargest isLargest: true
-MakeLargest isFinite: true
-outset a little isLargest: true
-outset a little isFinite: true
-outset a little more isLargest: false
-outset a little more isFinite: false
-##
+ SkRect rect = SkRect::MakeLargest(); + SkDebugf("MakeLargest isLargest: %s\n", rect.isLargest() ? "true" : "false"); + SkDebugf("MakeLargest isFinite: %s\n", rect.isFinite() ? "true" : "false"); + rect.outset(1e31, 1e31); + SkDebugf("outset a little isLargest: %s\n", rect.isLargest() ? "true" : "false"); + SkDebugf("outset a little isFinite: %s\n", rect.isFinite() ? "true" : "false"); + rect.outset(1e32, 1e32); + SkDebugf("outset a little more isLargest: %s\n", rect.isLargest() ? "true" : "false"); + SkDebugf("outset a little more isFinite: %s\n", rect.isFinite() ? "true" : "false"); +#StdOut +MakeLargest isLargest: true +MakeLargest isFinite: true +outset a little isLargest: true +outset a little isFinite: true +outset a little more isLargest: false +outset a little more isFinite: false +## ## #SeeAlso MakeLargestS32 isLargest setLargest SkIRect::MakeLargest @@ -205,13 +205,13 @@ These are the largest values for which round() is well defined. ## #Example - SkRect f_rect = SkRect::MakeLargestS32();
- SkIRect i_rect = f_rect.round();
- SkRect r_rect = SkRect::Make(i_rect);
- SkDebugf("f_rect %c= r_rect\n", f_rect == r_rect ? '=' : '!');
-#StdOut
-f_rect == r_rect
-##
+ SkRect f_rect = SkRect::MakeLargestS32(); + SkIRect i_rect = f_rect.round(); + SkRect r_rect = SkRect::Make(i_rect); + SkDebugf("f_rect %c= r_rect\n", f_rect == r_rect ? '=' : '!'); +#StdOut +f_rect == r_rect +## ## #SeeAlso MakeLargest isLargest setLargest SkIRect::MakeLargest @@ -234,11 +234,11 @@ represent 32-bit integers exactly. Use SkIRect for an exact integer rectangle. #Return bounds (0, 0, w, h) ## #Example - SkRect rect1 = SkRect::MakeWH(25, 35);
- SkRect rect2 = SkRect::MakeIWH(25, 35);
- SkRect rect3 = SkRect::MakeXYWH(0, 0, 25, 35);
- SkRect rect4 = SkRect::MakeLTRB(0, 0, 25, 35);
- SkDebugf("all %s" "equal\n", rect1 == rect2 && rect2 == rect3 && rect3 == rect4 ?
+ SkRect rect1 = SkRect::MakeWH(25, 35); + SkRect rect2 = SkRect::MakeIWH(25, 35); + SkRect rect3 = SkRect::MakeXYWH(0, 0, 25, 35); + SkRect rect4 = SkRect::MakeLTRB(0, 0, 25, 35); + SkDebugf("all %s" "equal\n", rect1 == rect2 && rect2 == rect3 && rect3 == rect4 ? "" : "not "); #StdOut all equal @@ -265,14 +265,14 @@ Use SkIRect for an exact integer rectangle. #Return bounds (0, 0, w, h) ## #Example - SkIRect i_rect = SkIRect::MakeWH(25, 35);
- SkRect f_rect = SkRect::MakeIWH(25, 35);
- SkDebugf("i_rect width: %d f_rect width:%g\n", i_rect.width(), f_rect.width());
- i_rect = SkIRect::MakeWH(125000111, 0);
- f_rect = SkRect::MakeIWH(125000111, 0);
- SkDebugf("i_rect width: %d f_rect width:%.0f\n", i_rect.width(), f_rect.width());
+ SkIRect i_rect = SkIRect::MakeWH(25, 35); + SkRect f_rect = SkRect::MakeIWH(25, 35); + SkDebugf("i_rect width: %d f_rect width:%g\n", i_rect.width(), f_rect.width()); + i_rect = SkIRect::MakeWH(125000111, 0); + f_rect = SkRect::MakeIWH(125000111, 0); + SkDebugf("i_rect width: %d f_rect width:%.0f\n", i_rect.width(), f_rect.width()); #StdOut -i_rect width: 25 f_rect width:25
+i_rect width: 25 f_rect width:25 i_rect width: 125000111 f_rect width:125000112 ## ## @@ -293,14 +293,14 @@ validate input; size.width() or size.height() may be negative. #Return bounds (0, 0, size.width(), size.height()) ## #Example - SkSize size = {25.5f, 35.5f};
- SkRect rect = SkRect::MakeSize(size);
- SkDebugf("rect width: %g height: %g\n", rect.width(), rect.height());
- SkISize floor = size.toFloor();
- rect = SkRect::MakeSize(SkSize::Make(floor));
- SkDebugf("floor width: %g height: %g\n", rect.width(), rect.height());
+ SkSize size = {25.5f, 35.5f}; + SkRect rect = SkRect::MakeSize(size); + SkDebugf("rect width: %g height: %g\n", rect.width(), rect.height()); + SkISize floor = size.toFloor(); + rect = SkRect::MakeSize(SkSize::Make(floor)); + SkDebugf("floor width: %g height: %g\n", rect.width(), rect.height()); #StdOut -rect width: 25.5 height: 35.5
+rect width: 25.5 height: 35.5 floor width: 25 height: 35 ## ## @@ -325,14 +325,14 @@ result in fLeft greater than fRight, or fTop greater than fBottom. #Return bounds (l, t, r, b) ## #Example - SkRect rect = SkRect::MakeLTRB(5, 35, 15, 25);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect.sort();
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
+ SkRect rect = SkRect::MakeLTRB(5, 35, 15, 25); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect.sort(); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); #StdOut -rect: 5, 35, 15, 25 isEmpty: true
+rect: 5, 35, 15, 25 isEmpty: true rect: 5, 25, 15, 35 isEmpty: false ## ## @@ -360,14 +360,14 @@ w or h may be negative. #Return bounds at (x, y) with width w and height h ## #Example - SkRect rect = SkRect::MakeXYWH(5, 35, -15, 25);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect.sort();
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
+ SkRect rect = SkRect::MakeXYWH(5, 35, -15, 25); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect.sort(); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); #StdOut -rect: 5, 35, -10, 60 isEmpty: true
+rect: 5, 35, -10, 60 isEmpty: true rect: -10, 35, 5, 60 isEmpty: false ## ## @@ -408,9 +408,9 @@ Does not validate input; size.width() or size.height() may be negative. #Return bounds (0, 0, size.width(), size.height()) ## #Example - SkRect rect1 = SkRect::MakeSize({2, 35});
- SkRect rect2 = SkRect::MakeIWH(2, 35);
- SkDebugf("rect1 %c= rect2\n", rect1 == rect2 ? '=' : '!');
+ SkRect rect1 = SkRect::MakeSize({2, 35}); + SkRect rect2 = SkRect::MakeIWH(2, 35); + SkDebugf("rect1 %c= rect2\n", rect1 == rect2 ? '=' : '!'); #StdOut rect1 == rect2 ## @@ -433,12 +433,12 @@ than fBottom. #Return irect members converted to SkScalar ## #Example - SkIRect i_rect1 = {2, 35, 22, 53};
- SkRect f_rect = SkRect::Make(i_rect1);
- f_rect.offset(0.49f, 0.49f);
- SkIRect i_rect2;
- f_rect.round(&i_rect2);
- SkDebugf("i_rect1 %c= i_rect2\n", i_rect1 == i_rect2? '=' : '!');
+ SkIRect i_rect1 = {2, 35, 22, 53}; + SkRect f_rect = SkRect::Make(i_rect1); + f_rect.offset(0.49f, 0.49f); + SkIRect i_rect2; + f_rect.round(&i_rect2); + SkDebugf("i_rect1 %c= i_rect2\n", i_rect1 == i_rect2? '=' : '!'); ## #SeeAlso MakeLTRB @@ -456,20 +456,20 @@ width() or height(). #Return true if width() or height() are zero or negative ## #Example - SkRect tests[] = {{20, 40, 10, 50}, {20, 40, 20, 50}};
- for (auto rect : tests) {
- SkDebugf("rect: {%g, %g, %g, %g} is" "%s empty\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "" : " not");
- rect.sort();
- SkDebugf("sorted: {%g, %g, %g, %g} is" "%s empty\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "" : " not");
- }
-#StdOut
-rect: {20, 40, 10, 50} is empty
-sorted: {10, 40, 20, 50} is not empty
-rect: {20, 40, 20, 50} is empty
-sorted: {20, 40, 20, 50} is empty
-##
+ SkRect tests[] = {{20, 40, 10, 50}, {20, 40, 20, 50}}; + for (auto rect : tests) { + SkDebugf("rect: {%g, %g, %g, %g} is" "%s empty\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "" : " not"); + rect.sort(); + SkDebugf("sorted: {%g, %g, %g, %g} is" "%s empty\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "" : " not"); + } +#StdOut +rect: {20, 40, 10, 50} is empty +sorted: {10, 40, 20, 50} is not empty +rect: {20, 40, 20, 50} is empty +sorted: {20, 40, 20, 50} is empty +## ## #SeeAlso MakeEmpty sort SkIRect::isEmpty @@ -487,20 +487,20 @@ width() or height(). #Return true if width() or height() are zero or positive ## #Example - SkRect tests[] = {{20, 40, 10, 50}, {20, 40, 20, 50}};
- for (auto rect : tests) {
- SkDebugf("rect: {%g, %g, %g, %g} is" "%s sorted\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isSorted() ? "" : " not");
- rect.sort();
- SkDebugf("sorted: {%g, %g, %g, %g} is" "%s sorted\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isSorted() ? "" : " not");
- }
-#StdOut
-rect: {20, 40, 10, 50} is not sorted
-sorted: {10, 40, 20, 50} is sorted
-rect: {20, 40, 20, 50} is sorted
-sorted: {20, 40, 20, 50} is sorted
-##
+ SkRect tests[] = {{20, 40, 10, 50}, {20, 40, 20, 50}}; + for (auto rect : tests) { + SkDebugf("rect: {%g, %g, %g, %g} is" "%s sorted\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isSorted() ? "" : " not"); + rect.sort(); + SkDebugf("sorted: {%g, %g, %g, %g} is" "%s sorted\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isSorted() ? "" : " not"); + } +#StdOut +rect: {20, 40, 10, 50} is not sorted +sorted: {10, 40, 20, 50} is sorted +rect: {20, 40, 20, 50} is sorted +sorted: {20, 40, 20, 50} is sorted +## ## #SeeAlso sort makeSorted isEmpty @@ -519,16 +519,16 @@ Returns true if Rect encloses largest possible area. #Description Note that the width cannot be represented as a 32-bit finite value. ## - SkRect large = SkRect::MakeLargest();
- SkDebugf("large is largest: %s\n" ,large.isLargest() ? "true" : "false");
- SkDebugf("large width %g\n", large.width());
- SkDebugf("large is empty: %s\n", large.isEmpty() ? "true" : "false");
+ SkRect large = SkRect::MakeLargest(); + SkDebugf("large is largest: %s\n" ,large.isLargest() ? "true" : "false"); + SkDebugf("large width %g\n", large.width()); + SkDebugf("large is empty: %s\n", large.isEmpty() ? "true" : "false"); SkDebugf("large is sorted: %s\n", large.isSorted() ? "true" : "false"); - SkDebugf("large is finite: %s\n", large.isFinite() ? "true" : "false");
-#StdOut
-large is largest: true
-large width inf
-large is empty: false
+ SkDebugf("large is finite: %s\n", large.isFinite() ? "true" : "false"); +#StdOut +large is largest: true +large width inf +large is empty: false large is sorted: true large is finite: true ## @@ -548,14 +548,14 @@ and SK_ScalarMax or smaller. #Return true if no member is infinite or NaN ## #Example - SkRect largest = SkRect::MakeLargest();
- SkDebugf("largest is finite: %s\n", largest.isFinite() ? "true" : "false");
- SkDebugf("large width %g\n", largest.width());
- SkRect widest = SkRect::MakeWH(largest.width(), largest.height());
- SkDebugf("widest is finite: %s\n", widest.isFinite() ? "true" : "false");
-#StdOut
-largest is finite: true
-large width inf
+ SkRect largest = SkRect::MakeLargest(); + SkDebugf("largest is finite: %s\n", largest.isFinite() ? "true" : "false"); + SkDebugf("large width %g\n", largest.width()); + SkRect widest = SkRect::MakeWH(largest.width(), largest.height()); + SkDebugf("widest is finite: %s\n", widest.isFinite() ? "true" : "false"); +#StdOut +largest is finite: true +large width inf widest is finite: false ## ## @@ -574,12 +574,12 @@ Call sort() to reverse fLeft and fRight if needed. #Return fLeft ## #Example - SkRect unsorted = { 15, 5, 10, 25 };
- SkDebugf("unsorted.fLeft: %g unsorted.x(): %g\n", unsorted.fLeft, unsorted.x());
- SkRect sorted = unsorted.makeSorted();
- SkDebugf("sorted.fLeft: %g sorted.x(): %g\n", sorted.fLeft, sorted.x());
+ SkRect unsorted = { 15, 5, 10, 25 }; + SkDebugf("unsorted.fLeft: %g unsorted.x(): %g\n", unsorted.fLeft, unsorted.x()); + SkRect sorted = unsorted.makeSorted(); + SkDebugf("sorted.fLeft: %g sorted.x(): %g\n", sorted.fLeft, sorted.x()); #StdOut -unsorted.fLeft: 15 unsorted.x(): 15
+unsorted.fLeft: 15 unsorted.x(): 15 sorted.fLeft: 10 sorted.x(): 10 ## ## @@ -598,12 +598,12 @@ and sort() to reverse fTop and fBottom if needed. #Return fTop ## #Example - SkRect unsorted = { 15, 25, 10, 5 };
- SkDebugf("unsorted.fTop: %g unsorted.y(): %g\n", unsorted.fTop, unsorted.y());
- SkRect sorted = unsorted.makeSorted();
+ SkRect unsorted = { 15, 25, 10, 5 }; + SkDebugf("unsorted.fTop: %g unsorted.y(): %g\n", unsorted.fTop, unsorted.y()); + SkRect sorted = unsorted.makeSorted(); SkDebugf("sorted.fTop: %g sorted.y(): %g\n", sorted.fTop, sorted.y()); #StdOut -unsorted.fTop: 25 unsorted.y(): 25
+unsorted.fTop: 25 unsorted.y(): 25 sorted.fTop: 5 sorted.y(): 5 ## ## @@ -622,12 +622,12 @@ Call sort() to reverse fLeft and fRight if needed. #Return fLeft ## #Example - SkRect unsorted = { 15, 5, 10, 25 };
- SkDebugf("unsorted.fLeft: %g unsorted.left(): %g\n", unsorted.fLeft, unsorted.left());
- SkRect sorted = unsorted.makeSorted();
- SkDebugf("sorted.fLeft: %g sorted.left(): %g\n", sorted.fLeft, sorted.left());
+ SkRect unsorted = { 15, 5, 10, 25 }; + SkDebugf("unsorted.fLeft: %g unsorted.left(): %g\n", unsorted.fLeft, unsorted.left()); + SkRect sorted = unsorted.makeSorted(); + SkDebugf("sorted.fLeft: %g sorted.left(): %g\n", sorted.fLeft, sorted.left()); #StdOut -unsorted.fLeft: 15 unsorted.left(): 15
+unsorted.fLeft: 15 unsorted.left(): 15 sorted.fLeft: 10 sorted.left(): 10 ## ## @@ -646,12 +646,12 @@ and sort() to reverse fTop and fBottom if needed. #Return fTop ## #Example - SkRect unsorted = { 15, 25, 10, 5 };
- SkDebugf("unsorted.fTop: %g unsorted.top(): %g\n", unsorted.fTop, unsorted.top());
- SkRect sorted = unsorted.makeSorted();
+ SkRect unsorted = { 15, 25, 10, 5 }; + SkDebugf("unsorted.fTop: %g unsorted.top(): %g\n", unsorted.fTop, unsorted.top()); + SkRect sorted = unsorted.makeSorted(); SkDebugf("sorted.fTop: %g sorted.top(): %g\n", sorted.fTop, sorted.top()); #StdOut -unsorted.fTop: 25 unsorted.top(): 25
+unsorted.fTop: 25 unsorted.top(): 25 sorted.fTop: 5 sorted.top(): 5 ## ## @@ -670,12 +670,12 @@ Call sort() to reverse fLeft and fRight if needed. #Return fRight ## #Example - SkRect unsorted = { 15, 25, 10, 5 };
- SkDebugf("unsorted.fRight: %g unsorted.right(): %g\n", unsorted.fRight, unsorted.right());
- SkRect sorted = unsorted.makeSorted();
- SkDebugf("sorted.fRight: %g sorted.right(): %g\n", sorted.fRight, sorted.right());
+ SkRect unsorted = { 15, 25, 10, 5 }; + SkDebugf("unsorted.fRight: %g unsorted.right(): %g\n", unsorted.fRight, unsorted.right()); + SkRect sorted = unsorted.makeSorted(); + SkDebugf("sorted.fRight: %g sorted.right(): %g\n", sorted.fRight, sorted.right()); #StdOut -unsorted.fRight: 10 unsorted.right(): 10
+unsorted.fRight: 10 unsorted.right(): 10 sorted.fRight: 15 sorted.right(): 15 ## ## @@ -694,12 +694,12 @@ and sort() to reverse fTop and fBottom if needed. #Return fBottom ## #Example - SkRect unsorted = { 15, 25, 10, 5 };
- SkDebugf("unsorted.fBottom: %g unsorted.bottom(): %g\n", unsorted.fBottom, unsorted.bottom());
- SkRect sorted = unsorted.makeSorted();
- SkDebugf("sorted.fBottom: %g sorted.bottom(): %g\n", sorted.fBottom, sorted.bottom());
+ SkRect unsorted = { 15, 25, 10, 5 }; + SkDebugf("unsorted.fBottom: %g unsorted.bottom(): %g\n", unsorted.fBottom, unsorted.bottom()); + SkRect sorted = unsorted.makeSorted(); + SkDebugf("sorted.fBottom: %g sorted.bottom(): %g\n", sorted.fBottom, sorted.bottom()); #StdOut -unsorted.fBottom: 5 unsorted.bottom(): 5
+unsorted.fBottom: 5 unsorted.bottom(): 5 sorted.fBottom: 25 sorted.bottom(): 25 ## ## @@ -721,12 +721,12 @@ result fits in 32-bit float; result may be negative or infinity. #Description Compare with SkIRect::width() example. ## - SkRect unsorted = { 15, 25, 10, 5 };
- SkDebugf("unsorted width: %g\n", unsorted.width());
- SkRect large = { -2147483647.f, 1, 2147483644.f, 2 };
- SkDebugf("large width: %.0f\n", large.width());
+ SkRect unsorted = { 15, 25, 10, 5 }; + SkDebugf("unsorted width: %g\n", unsorted.width()); + SkRect large = { -2147483647.f, 1, 2147483644.f, 2 }; + SkDebugf("large width: %.0f\n", large.width()); #StdOut -unsorted width: -5
+unsorted width: -5 large width: 4294967296 ## ## @@ -748,12 +748,12 @@ result fits in 32-bit float; result may be negative or infinity. #Description Compare with SkIRect::height() example. ## - SkRect unsorted = { 15, 25, 10, 20 };
- SkDebugf("unsorted height: %g\n", unsorted.height());
- SkRect large = { 1, -2147483647.f, 2, 2147483644.f };
- SkDebugf("large height: %.0f\n", large.height());
+ SkRect unsorted = { 15, 25, 10, 20 }; + SkDebugf("unsorted height: %g\n", unsorted.height()); + SkRect large = { 1, -2147483647.f, 2, 2147483644.f }; + SkDebugf("large height: %.0f\n", large.height()); #StdOut -unsorted height: -5
+unsorted height: -5 large height: 4294967296 ## ## @@ -772,16 +772,16 @@ is sorted. Result may overflow to infinity if Rect is far from the origin. #Return midpoint in x ## #Example - SkRect tests[] = {{20, 30, 41, 51}, {-20, -30, -41, -51}};
- for (auto rect : tests) {
- SkDebugf("left: %3g right: %3g centerX: %3g\n", rect.left(), rect.right(), rect.centerX());
- rect.sort();
- SkDebugf("left: %3g right: %3g centerX: %3g\n", rect.left(), rect.right(), rect.centerX());
- }
+ SkRect tests[] = {{20, 30, 41, 51}, {-20, -30, -41, -51}}; + for (auto rect : tests) { + SkDebugf("left: %3g right: %3g centerX: %3g\n", rect.left(), rect.right(), rect.centerX()); + rect.sort(); + SkDebugf("left: %3g right: %3g centerX: %3g\n", rect.left(), rect.right(), rect.centerX()); + } #StdOut -left: 20 right: 41 centerX: 30.5
-left: 20 right: 41 centerX: 30.5
-left: -20 right: -41 centerX: -30.5
+left: 20 right: 41 centerX: 30.5 +left: 20 right: 41 centerX: 30.5 +left: -20 right: -41 centerX: -30.5 left: -41 right: -20 centerX: -30.5 ## ## @@ -800,9 +800,9 @@ is sorted. Result may overflow to infinity if Rect is far from the origin. #Return midpoint in y ## #Example - SkRect rect = { 2e+38, 2e+38, 3e+38, 3e+38 };
- SkDebugf("left: %g right: %g centerX: %g ", rect.left(), rect.right(), rect.centerX());
- SkDebugf("safe mid x: %g\n", rect.left() / 2 + rect.right() / 2);
+ SkRect rect = { 2e+38, 2e+38, 3e+38, 3e+38 }; + SkDebugf("left: %g right: %g centerX: %g ", rect.left(), rect.right(), rect.centerX()); + SkDebugf("safe mid x: %g\n", rect.left() / 2 + rect.right() / 2); #StdOut left: 2e+38 right: 3e+38 centerX: inf safe mid x: 2.5e+38 ## @@ -828,25 +828,25 @@ contain zeroes width different signs. #Return true if members are equal ## #Example - auto debugster = [](const SkRect& test) -> void {
- SkRect negZero = {-0.0f, -0.0f, 2, 2};
- SkDebugf("{%g, %g, %g, %g} %c= {%g, %g, %g, %g} %s numerically equal\n",
- test.fLeft, test.fTop, test.fRight, test.fBottom,
- negZero.fLeft, negZero.fTop, negZero.fRight, negZero.fBottom,
- test == negZero ? '=' : '!',
- test.fLeft == negZero.fLeft && test.fTop == negZero.fTop &&
- test.fRight == negZero.fRight && test.fBottom == negZero.fBottom ?
- "and are" : "yet are not");
- };
- SkRect tests[] = {{0, 0, 2, 2}, {-0, -0, 2, 2}, {0.0f, 0.0f, 2, 2}};
- SkDebugf("tests are %s" "equal\n", tests[0] == tests[1] && tests[1] == tests[2] ? "" : "not ");
- for (auto rect : tests) {
- debugster(rect);
+ auto debugster = [](const SkRect& test) -> void { + SkRect negZero = {-0.0f, -0.0f, 2, 2}; + SkDebugf("{%g, %g, %g, %g} %c= {%g, %g, %g, %g} %s numerically equal\n", + test.fLeft, test.fTop, test.fRight, test.fBottom, + negZero.fLeft, negZero.fTop, negZero.fRight, negZero.fBottom, + test == negZero ? '=' : '!', + test.fLeft == negZero.fLeft && test.fTop == negZero.fTop && + test.fRight == negZero.fRight && test.fBottom == negZero.fBottom ? + "and are" : "yet are not"); + }; + SkRect tests[] = {{0, 0, 2, 2}, {-0, -0, 2, 2}, {0.0f, 0.0f, 2, 2}}; + SkDebugf("tests are %s" "equal\n", tests[0] == tests[1] && tests[1] == tests[2] ? "" : "not "); + for (auto rect : tests) { + debugster(rect); } -#StdOut
-tests are equal
-{0, 0, 2, 2} == {-0, -0, 2, 2} and are numerically equal
-{0, 0, 2, 2} == {-0, -0, 2, 2} and are numerically equal
+#StdOut +tests are equal +{0, 0, 2, 2} == {-0, -0, 2, 2} and are numerically equal +{0, 0, 2, 2} == {-0, -0, 2, 2} and are numerically equal {0, 0, 2, 2} == {-0, -0, 2, 2} and are numerically equal ## ## @@ -871,9 +871,9 @@ contain zeroes width different signs. #Return true if members are not equal ## #Example - SkRect test = {0, 0, 2, SK_ScalarNaN};
- SkDebugf("test with NaN is %s" "equal to itself\n", test == test ? "" : "not ");
-#StdOut
+ SkRect test = {0, 0, 2, SK_ScalarNaN}; + SkDebugf("test with NaN is %s" "equal to itself\n", test == test ? "" : "not "); +#StdOut test with NaN is not equal to itself ## ## @@ -896,17 +896,17 @@ Consider adding param to control whether quad is CW or CCW. #Param quad storage for corners of Rect ## #Example - SkRect rect = {1, 2, 3, 4};
- SkPoint corners[4];
- rect.toQuad(corners);
- SkDebugf("rect: {%g, %g, %g, %g}\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- SkDebugf("corners:");
- for (auto corner : corners) {
- SkDebugf(" {%g, %g}", corner.fX, corner.fY);
- }
- SkDebugf("\n");
-#StdOut
-rect: {1, 2, 3, 4}
+ SkRect rect = {1, 2, 3, 4}; + SkPoint corners[4]; + rect.toQuad(corners); + SkDebugf("rect: {%g, %g, %g, %g}\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + SkDebugf("corners:"); + for (auto corner : corners) { + SkDebugf(" {%g, %g}", corner.fX, corner.fY); + } + SkDebugf("\n"); +#StdOut +rect: {1, 2, 3, 4} corners: {1, 2} {3, 2} {3, 4} {1, 4} ## ## @@ -926,16 +926,16 @@ or if top is equal to or greater than bottom. Setting all members to zero is a convenience, but does not designate a special empty rectangle. #Example - SkRect rect = {3, 4, 1, 2};
- for (int i = 0; i < 2; ++i) {
- SkDebugf("rect: {%g, %g, %g, %g} is %s" "empty\n", rect.fLeft, rect.fTop,
- rect.fRight, rect.fBottom, rect.isEmpty() ? "" : "not ");
- rect.setEmpty();
- }
-#StdOut
-rect: {3, 4, 1, 2} is empty
-rect: {0, 0, 0, 0} is empty
-##
+ SkRect rect = {3, 4, 1, 2}; + for (int i = 0; i < 2; ++i) { + SkDebugf("rect: {%g, %g, %g, %g} is %s" "empty\n", rect.fLeft, rect.fTop, + rect.fRight, rect.fBottom, rect.isEmpty() ? "" : "not "); + rect.setEmpty(); + } +#StdOut +rect: {3, 4, 1, 2} is empty +rect: {0, 0, 0, 0} is empty +## ## #SeeAlso MakeEmpty SkIRect::setEmpty @@ -952,15 +952,15 @@ Very large values in src may lose precision. #Param src integer Rect ## #Example - SkIRect i_rect = {3, 4, 1, 2};
- SkDebugf("i_rect: {%d, %d, %d, %d}\n", i_rect.fLeft, i_rect.fTop, i_rect.fRight, i_rect.fBottom);
- SkRect f_rect;
- f_rect.set(i_rect);
- SkDebugf("f_rect: {%g, %g, %g, %g}\n", f_rect.fLeft, f_rect.fTop, f_rect.fRight, f_rect.fBottom);
-#StdOut
-i_rect: {3, 4, 1, 2}
-f_rect: {3, 4, 1, 2}
-##
+ SkIRect i_rect = {3, 4, 1, 2}; + SkDebugf("i_rect: {%d, %d, %d, %d}\n", i_rect.fLeft, i_rect.fTop, i_rect.fRight, i_rect.fBottom); + SkRect f_rect; + f_rect.set(i_rect); + SkDebugf("f_rect: {%g, %g, %g, %g}\n", f_rect.fLeft, f_rect.fTop, f_rect.fRight, f_rect.fBottom); +#StdOut +i_rect: {3, 4, 1, 2} +f_rect: {3, 4, 1, 2} +## ## #SeeAlso setLTRB SkIntToScalar @@ -981,15 +981,15 @@ top and bottom are not sorted; top is not necessarily less than bottom. #Param bottom stored in fBottom ## #Example - SkRect rect1 = {3, 4, 1, 2};
- SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom);
- SkRect rect2;
- rect2.set(3, 4, 1, 2);
- SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom);
-#StdOut
-rect1: {3, 4, 1, 2}
-rect2: {3, 4, 1, 2}
-##
+ SkRect rect1 = {3, 4, 1, 2}; + SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom); + SkRect rect2; + rect2.set(3, 4, 1, 2); + SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom); +#StdOut +rect1: {3, 4, 1, 2} +rect2: {3, 4, 1, 2} +## ## #SeeAlso setLTRB setXYWH SkIRect::set @@ -1010,15 +1010,15 @@ top and bottom are not sorted; top is not necessarily less than bottom. #Param bottom stored in fBottom ## #Example - SkRect rect1 = {3, 4, 1, 2};
- SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom);
- SkRect rect2;
- rect2.setLTRB(3, 4, 1, 2);
- SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom);
-#StdOut
-rect1: {3, 4, 1, 2}
-rect2: {3, 4, 1, 2}
-##
+ SkRect rect1 = {3, 4, 1, 2}; + SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom); + SkRect rect2; + rect2.setLTRB(3, 4, 1, 2); + SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom); +#StdOut +rect1: {3, 4, 1, 2} +rect2: {3, 4, 1, 2} +## ## #SeeAlso set setXYWH SkIRect::set @@ -1040,15 +1040,15 @@ top and bottom are not sorted; top is not necessarily less than bottom. #Param bottom promoted to SkScalar and stored in fBottom ## #Example - SkRect rect1 = {3, 4, 1, 2};
- SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom);
- SkRect rect2;
- rect2.iset(3, 4, 1, 2);
- SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom);
-#StdOut
-rect1: {3, 4, 1, 2}
-rect2: {3, 4, 1, 2}
-##
+ SkRect rect1 = {3, 4, 1, 2}; + SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom); + SkRect rect2; + rect2.iset(3, 4, 1, 2); + SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom); +#StdOut +rect1: {3, 4, 1, 2} +rect2: {3, 4, 1, 2} +## ## #SeeAlso set setLTRB SkIRect::set SkIntToScalar @@ -1067,15 +1067,15 @@ integer to SkScalar, large values may lose precision. #Param height promoted to SkScalar and stored in fBottom ## #Example - SkRect rect1 = {0, 0, 1, 2};
- SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom);
- SkRect rect2;
- rect2.isetWH(1, 2);
+ SkRect rect1 = {0, 0, 1, 2}; + SkDebugf("rect1: {%g, %g, %g, %g}\n", rect1.fLeft, rect1.fTop, rect1.fRight, rect1.fBottom); + SkRect rect2; + rect2.isetWH(1, 2); SkDebugf("rect2: {%g, %g, %g, %g}\n", rect2.fLeft, rect2.fTop, rect2.fRight, rect2.fBottom); -#StdOut
-rect1: {0, 0, 1, 2}
-rect2: {0, 0, 1, 2}
-##
+#StdOut +rect1: {0, 0, 1, 2} +rect2: {0, 0, 1, 2} +## ## #SeeAlso MakeWH MakeXYWH iset() SkIRect:MakeWH @@ -1096,25 +1096,25 @@ fTop is less than or equal to fBottom. #Param count entries in array ## #Example - SkPoint points[] = {{3, 4}, {1, 2}, {5, 6}, {SK_ScalarNaN, 8}};
- for (int count = 0; count <= (int) SK_ARRAY_COUNT(points); ++count) {
- SkRect rect;
- rect.set(points, count);
- if (count > 0) {
- SkDebugf("added: %3g, %g ", points[count - 1].fX, points[count - 1].fY);
- } else {
- SkDebugf("%14s", " ");
- }
- SkDebugf("count: %d rect: %g, %g, %g, %g\n", count,
- rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- }
-#StdOut
- count: 0 rect: 0, 0, 0, 0
-added: 3, 4 count: 1 rect: 3, 4, 3, 4
-added: 1, 2 count: 2 rect: 1, 2, 3, 4
-added: 5, 6 count: 3 rect: 1, 2, 5, 6
-added: nan, 8 count: 4 rect: 0, 0, 0, 0
-##
+ SkPoint points[] = {{3, 4}, {1, 2}, {5, 6}, {SK_ScalarNaN, 8}}; + for (int count = 0; count <= (int) SK_ARRAY_COUNT(points); ++count) { + SkRect rect; + rect.set(points, count); + if (count > 0) { + SkDebugf("added: %3g, %g ", points[count - 1].fX, points[count - 1].fY); + } else { + SkDebugf("%14s", " "); + } + SkDebugf("count: %d rect: %g, %g, %g, %g\n", count, + rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + } +#StdOut + count: 0 rect: 0, 0, 0, 0 +added: 3, 4 count: 1 rect: 3, 4, 3, 4 +added: 1, 2 count: 2 rect: 1, 2, 3, 4 +added: 5, 6 count: 3 rect: 1, 2, 5, 6 +added: nan, 8 count: 4 rect: 0, 0, 0, 0 +## ## #SeeAlso setBounds setBoundsCheck SkPath::addPoly @@ -1135,25 +1135,25 @@ fTop is less than or equal to fBottom. #Param count entries in array ## #Example - SkPoint points[] = {{3, 4}, {1, 2}, {5, 6}, {SK_ScalarNaN, 8}};
- for (int count = 0; count <= (int) SK_ARRAY_COUNT(points); ++count) {
- SkRect rect;
- rect.setBounds(points, count);
- if (count > 0) {
- SkDebugf("added: %3g, %g ", points[count - 1].fX, points[count - 1].fY);
- } else {
- SkDebugf("%14s", " ");
- }
- SkDebugf("count: %d rect: %g, %g, %g, %g\n", count,
- rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- }
-#StdOut
- count: 0 rect: 0, 0, 0, 0
-added: 3, 4 count: 1 rect: 3, 4, 3, 4
-added: 1, 2 count: 2 rect: 1, 2, 3, 4
-added: 5, 6 count: 3 rect: 1, 2, 5, 6
-added: nan, 8 count: 4 rect: 0, 0, 0, 0
-##
+ SkPoint points[] = {{3, 4}, {1, 2}, {5, 6}, {SK_ScalarNaN, 8}}; + for (int count = 0; count <= (int) SK_ARRAY_COUNT(points); ++count) { + SkRect rect; + rect.setBounds(points, count); + if (count > 0) { + SkDebugf("added: %3g, %g ", points[count - 1].fX, points[count - 1].fY); + } else { + SkDebugf("%14s", " "); + } + SkDebugf("count: %d rect: %g, %g, %g, %g\n", count, + rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + } +#StdOut + count: 0 rect: 0, 0, 0, 0 +added: 3, 4 count: 1 rect: 3, 4, 3, 4 +added: 1, 2 count: 2 rect: 1, 2, 3, 4 +added: 5, 6 count: 3 rect: 1, 2, 5, 6 +added: nan, 8 count: 4 rect: 0, 0, 0, 0 +## ## #SeeAlso set setBoundsCheck SkPath::addPoly @@ -1177,25 +1177,25 @@ fTop is less than or equal to fBottom. #Return true if all Point values are finite ## #Example - SkPoint points[] = {{3, 4}, {1, 2}, {5, 6}, {SK_ScalarNaN, 8}};
- for (int count = 0; count <= (int) SK_ARRAY_COUNT(points); ++count) {
- SkRect rect;
- bool success = rect.setBoundsCheck(points, count);
- if (count > 0) {
- SkDebugf("added: %3g, %g ", points[count - 1].fX, points[count - 1].fY);
- } else {
- SkDebugf("%14s", " ");
- }
- SkDebugf("count: %d rect: %g, %g, %g, %g success: %s\n", count,
- rect.fLeft, rect.fTop, rect.fRight, rect.fBottom, success ? "true" : "false");
- }
-#StdOut
- count: 0 rect: 0, 0, 0, 0 success: true
-added: 3, 4 count: 1 rect: 3, 4, 3, 4 success: true
-added: 1, 2 count: 2 rect: 1, 2, 3, 4 success: true
-added: 5, 6 count: 3 rect: 1, 2, 5, 6 success: true
-added: nan, 8 count: 4 rect: 0, 0, 0, 0 success: false
-##
+ SkPoint points[] = {{3, 4}, {1, 2}, {5, 6}, {SK_ScalarNaN, 8}}; + for (int count = 0; count <= (int) SK_ARRAY_COUNT(points); ++count) { + SkRect rect; + bool success = rect.setBoundsCheck(points, count); + if (count > 0) { + SkDebugf("added: %3g, %g ", points[count - 1].fX, points[count - 1].fY); + } else { + SkDebugf("%14s", " "); + } + SkDebugf("count: %d rect: %g, %g, %g, %g success: %s\n", count, + rect.fLeft, rect.fTop, rect.fRight, rect.fBottom, success ? "true" : "false"); + } +#StdOut + count: 0 rect: 0, 0, 0, 0 success: true +added: 3, 4 count: 1 rect: 3, 4, 3, 4 success: true +added: 1, 2 count: 2 rect: 1, 2, 3, 4 success: true +added: 5, 6 count: 3 rect: 1, 2, 5, 6 success: true +added: nan, 8 count: 4 rect: 0, 0, 0, 0 success: false +## ## #SeeAlso set setBounds SkPath::addPoly @@ -1216,13 +1216,13 @@ sorted and may be empty. Does not check to see if values are finite. #Description p0 and p1 may be swapped and have the same effect unless one contains NaN. ## - SkPoint point1 = {SK_ScalarNaN, 8};
- SkPoint point2 = {3, 4};
- SkRect rect;
- rect.set(point1, point2);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- rect.set(point2, point1);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
+ SkPoint point1 = {SK_ScalarNaN, 8}; + SkPoint point2 = {3, 4}; + SkRect rect; + rect.set(point1, point2); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + rect.set(point2, point1); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); ## #SeeAlso setBounds setBoundsCheck @@ -1246,15 +1246,15 @@ width or height may be negative. #Param height added to y and stored in fBottom ## #Example - SkRect rect;
- rect.setXYWH(5, 35, -15, 25);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect.sort();
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
+ SkRect rect; + rect.setXYWH(5, 35, -15, 25); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect.sort(); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); #StdOut -rect: 5, 35, -10, 60 isEmpty: true
+rect: 5, 35, -10, 60 isEmpty: true rect: -10, 35, 5, 60 isEmpty: false ## ## @@ -1274,15 +1274,15 @@ width or height may be negative. #Param height stored in fBottom ## #Example - SkRect rect;
- rect.setWH(-15, 25);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect.sort();
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
+ SkRect rect; + rect.setWH(-15, 25); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect.sort(); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); #StdOut -rect: 0, 0, -15, 25 isEmpty: true
+rect: 0, 0, -15, 25 isEmpty: true rect: -15, 0, 0, 25 isEmpty: false ## ## @@ -1299,24 +1299,24 @@ Sets rectangle left and top to most negative finite value, and sets right and bottom to most positive finite value. #Example - SkRect rect;
- rect.setLargest();
- SkDebugf("MakeLargest isLargest: %s\n", rect.isLargest() ? "true" : "false");
- SkDebugf("MakeLargest isFinite: %s\n", rect.isFinite() ? "true" : "false");
- rect.outset(1e31, 1e31);
- SkDebugf("outset a little isLargest: %s\n", rect.isLargest() ? "true" : "false");
- SkDebugf("outset a little isFinite: %s\n", rect.isFinite() ? "true" : "false");
- rect.outset(1e32, 1e32);
- SkDebugf("outset a little more isLargest: %s\n", rect.isLargest() ? "true" : "false");
- SkDebugf("outset a little more isFinite: %s\n", rect.isFinite() ? "true" : "false");
-#StdOut
-MakeLargest isLargest: true
-MakeLargest isFinite: true
-outset a little isLargest: true
-outset a little isFinite: true
-outset a little more isLargest: false
-outset a little more isFinite: false
-##
+ SkRect rect; + rect.setLargest(); + SkDebugf("MakeLargest isLargest: %s\n", rect.isLargest() ? "true" : "false"); + SkDebugf("MakeLargest isFinite: %s\n", rect.isFinite() ? "true" : "false"); + rect.outset(1e31, 1e31); + SkDebugf("outset a little isLargest: %s\n", rect.isLargest() ? "true" : "false"); + SkDebugf("outset a little isFinite: %s\n", rect.isFinite() ? "true" : "false"); + rect.outset(1e32, 1e32); + SkDebugf("outset a little more isLargest: %s\n", rect.isLargest() ? "true" : "false"); + SkDebugf("outset a little more isFinite: %s\n", rect.isFinite() ? "true" : "false"); +#StdOut +MakeLargest isLargest: true +MakeLargest isFinite: true +outset a little isLargest: true +outset a little isFinite: true +outset a little more isLargest: false +outset a little more isFinite: false +## ## #SeeAlso MakeLargest isLargest setLargestInverted SK_ScalarMin SK_ScalarMax @@ -1333,20 +1333,20 @@ right and bottom to most negative finite value. Use to initial Rect before one or more calls to growToInclude. #Example - auto debugster = [](const char* prefix, const SkRect& rect) -> void {
- SkDebugf("%s ", prefix);
- SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom());
- SkDebugf("isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
- };
- SkRect ptBounds;
- ptBounds.setLargestInverted();
- debugster("original", ptBounds);
- ptBounds.growToInclude( { 42, 24 } );
+ auto debugster = [](const char* prefix, const SkRect& rect) -> void { + SkDebugf("%s ", prefix); + SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom()); + SkDebugf("isEmpty: %s\n", rect.isEmpty() ? "true" : "false"); + }; + SkRect ptBounds; + ptBounds.setLargestInverted(); + debugster("original", ptBounds); + ptBounds.growToInclude( { 42, 24 } ); debugster("grown", ptBounds); -#StdOut
-original rect: 3.40282e+38, 3.40282e+38, -3.40282e+38, -3.40282e+38 isEmpty: true
-grown rect: 42, 24, 42, 24 isEmpty: true
-##
+#StdOut +original rect: 3.40282e+38, 3.40282e+38, -3.40282e+38, -3.40282e+38 isEmpty: true +grown rect: 42, 24, 42, 24 isEmpty: true +## ## #SeeAlso growToInclude setEmpty setLargest @@ -1370,16 +1370,16 @@ If dy is positive, Rect returned is moved downward. #Return Rect offset in x or y, with original width and height ## #Example - SkRect rect = { 10, 50, 20, 60 };
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect = rect.makeOffset(15, 32);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
-#StdOut
-rect: 10, 50, 20, 60 isEmpty: false
-rect: 25, 82, 35, 92 isEmpty: false
-##
+ SkRect rect = { 10, 50, 20, 60 }; + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect = rect.makeOffset(15, 32); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); +#StdOut +rect: 10, 50, 20, 60 isEmpty: false +rect: 25, 82, 35, 92 isEmpty: false +## ## #SeeAlso offset() makeInset makeOutset SkIRect::makeOffset @@ -1403,16 +1403,16 @@ If dy is positive, Rect returned is shorter. #Return Rect inset symmetrically left and right, top and bottom ## #Example - SkRect rect = { 10, 50, 20, 60 };
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect = rect.makeInset(15, 32);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
-#StdOut
-rect: 10, 50, 20, 60 isEmpty: false
-rect: 25, 82, 5, 28 isEmpty: true
-##
+ SkRect rect = { 10, 50, 20, 60 }; + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect = rect.makeInset(15, 32); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); +#StdOut +rect: 10, 50, 20, 60 isEmpty: false +rect: 25, 82, 5, 28 isEmpty: true +## ## #SeeAlso inset() makeOffset makeOutset SkIRect::makeInset @@ -1436,16 +1436,16 @@ If dy is positive, Rect returned is taller. #Return Rect outset symmetrically left and right, top and bottom ## #Example - SkRect rect = { 10, 50, 20, 60 };
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
- rect = rect.makeOutset(15, 32);
- SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(),
- rect.bottom(), rect.isEmpty() ? "true" : "false");
-#StdOut
-rect: 10, 50, 20, 60 isEmpty: false
-rect: -5, 18, 35, 92 isEmpty: false
-##
+ SkRect rect = { 10, 50, 20, 60 }; + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); + rect = rect.makeOutset(15, 32); + SkDebugf("rect: %g, %g, %g, %g isEmpty: %s\n", rect.left(), rect.top(), rect.right(), + rect.bottom(), rect.isEmpty() ? "true" : "false"); +#StdOut +rect: 10, 50, 20, 60 isEmpty: false +rect: -5, 18, 35, 92 isEmpty: false +## ## #SeeAlso outset() makeOffset makeInset SkIRect::makeOutset @@ -1467,12 +1467,12 @@ If dy is positive, moves Rect downward. #Param dy offset added to fTop and fBottom ## #Example - SkRect rect = { 10, 14, 50, 73 };
- rect.offset(5, 13);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut
-rect: 15, 27, 55, 86
-##
+ SkRect rect = { 10, 14, 50, 73 }; + rect.offset(5, 13); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); +#StdOut +rect: 15, 27, 55, 86 +## ## #SeeAlso offsetTo makeOffset SkIRect::offset @@ -1494,12 +1494,12 @@ If delta.fY is positive, moves Rect downward. #Param delta added to Rect ## #Example - SkRect rect = { 10, 14, 50, 73 };
- rect.offset({5, 13});
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut
-rect: 15, 27, 55, 86
-##
+ SkRect rect = { 10, 14, 50, 73 }; + rect.offset({5, 13}); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); +#StdOut +rect: 15, 27, 55, 86 +## ## #SeeAlso offsetTo makeOffset SkIRect::offset @@ -1517,12 +1517,12 @@ are unchanged. #Param newY stored in fTop, preserving height() ## #Example - SkRect rect = { 10, 14, 50, 73 };
- rect.offsetTo(15, 27);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut
-rect: 15, 27, 55, 86
-##
+ SkRect rect = { 10, 14, 50, 73 }; + rect.offsetTo(15, 27); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); +#StdOut +rect: 15, 27, 55, 86 +## ## #SeeAlso offset makeOffset setXYWH SkIRect::offsetTo @@ -1544,12 +1544,12 @@ If dy is negative, makes Rect taller. #Param dy added to fTop and subtracted from fBottom ## #Example - SkRect rect = { 10, 14, 50, 73 };
- rect.inset(5, 13);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut
-rect: 15, 27, 45, 60
-##
+ SkRect rect = { 10, 14, 50, 73 }; + rect.inset(5, 13); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); +#StdOut +rect: 15, 27, 45, 60 +## ## #SeeAlso outset makeInset SkIRect::inset @@ -1571,12 +1571,12 @@ If dy is negative, makes Rect shorter. #Param dy subtracted to fTop and added from fBottom ## #Example - SkRect rect = { 10, 14, 50, 73 };
- rect.outset(5, 13);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
-#StdOut
-rect: 5, 1, 55, 86
-##
+ SkRect rect = { 10, 14, 50, 73 }; + rect.outset(5, 13); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); +#StdOut +rect: 5, 1, 55, 86 +## ## #SeeAlso inset makeOutset SkIRect::outset @@ -1587,11 +1587,14 @@ rect: 5, 1, 55, 86 Rects intersect when they enclose a common area. To intersect, each of the pair must describe area; fLeft is less than fRight, and fTop is less than fBottom; -empty() returns false. The intersection of Rect a and Rect b can be described by: +empty() returns false. The intersection of Rect pair can be described by: + #Formula (max(a.fLeft, b.fLeft), max(a.fTop, b.fTop), min(a.fRight, b.fRight), min(a.fBottom, b.fBottom)) ## +. + The intersection is only meaningful if the resulting Rect is not empty and describes an area: fLeft is less than fRight, and fTop is less than fBottom. @@ -1614,10 +1617,10 @@ Two SkDebugf calls are required. If the calls are combined, their arguments may not be evaluated in left to right order: the printed intersection may be before or after the call to intersect. ## - SkRect leftRect = { 10, 40, 50, 80 };
- SkRect rightRect = { 30, 60, 70, 90 };
- SkDebugf("%s intersection: ", leftRect.intersect(rightRect) ? "" : "no ");
- SkDebugf("%g, %g, %g, %g\n", leftRect.left(), leftRect.top(),
+ SkRect leftRect = { 10, 40, 50, 80 }; + SkRect rightRect = { 30, 60, 70, 90 }; + SkDebugf("%s intersection: ", leftRect.intersect(rightRect) ? "" : "no "); + SkDebugf("%g, %g, %g, %g\n", leftRect.left(), leftRect.top(), leftRect.right(), leftRect.bottom()); #StdOut intersection: 30, 60, 50, 80 @@ -1653,9 +1656,9 @@ Two SkDebugf calls are required. If the calls are combined, their arguments may not be evaluated in left to right order: the printed intersection may be before or after the call to intersect. ## - SkRect leftRect = { 10, 40, 50, 80 };
- SkDebugf("%s intersection: ", leftRect.intersect(30, 60, 70, 90) ? "" : "no ");
- SkDebugf("%g, %g, %g, %g\n", leftRect.left(), leftRect.top(),
+ SkRect leftRect = { 10, 40, 50, 80 }; + SkDebugf("%s intersection: ", leftRect.intersect(30, 60, 70, 90) ? "" : "no "); + SkDebugf("%g, %g, %g, %g\n", leftRect.left(), leftRect.top(), leftRect.right(), leftRect.bottom()); #StdOut intersection: 30, 60, 50, 80 @@ -1681,10 +1684,10 @@ Returns false if either a or b is empty, leaving Rect unchanged. #Return true if a and b have area in common ## #Example - SkRect result;
- bool intersected = result.intersect({ 10, 40, 50, 80 }, { 30, 60, 70, 90 });
- SkDebugf("%s intersection: %g, %g, %g, %g\n", intersected ? "" : "no ",
- result.left(), result.top(), result.right(), result.bottom());
+ SkRect result; + bool intersected = result.intersect({ 10, 40, 50, 80 }, { 30, 60, 70, 90 }); + SkDebugf("%s intersection: %g, %g, %g, %g\n", intersected ? "" : "no ", + result.left(), result.top(), result.right(), result.bottom()); #StdOut intersection: 30, 60, 50, 80 ## @@ -1712,8 +1715,8 @@ Returns false if either construction or Rect is empty, or do not intersect. #Return true if construction and Rect have area in common ## #Example - SkRect rect = { 10, 40, 50, 80 };
- SkDebugf("%s intersection", rect.intersects(30, 60, 70, 90) ? "" : "no ");
+ SkRect rect = { 10, 40, 50, 80 }; + SkDebugf("%s intersection", rect.intersects(30, 60, 70, 90) ? "" : "no "); #StdOut intersection ## @@ -1735,8 +1738,8 @@ Returns false if either r or Rect is empty, or do not intersect. #Return true if r and Rect have area in common ## #Example - SkRect rect = { 10, 40, 50, 80 };
- SkDebugf("%s intersection", rect.intersects({30, 60, 70, 90}) ? "" : "no ");
+ SkRect rect = { 10, 40, 50, 80 }; + SkDebugf("%s intersection", rect.intersects({30, 60, 70, 90}) ? "" : "no "); #StdOut intersection ## @@ -1759,7 +1762,7 @@ Returns false if either a or b is empty, or do not intersect. #Return true if a and b have area in common ## #Example - SkDebugf("%s intersection", SkRect::Intersects({10, 40, 50, 80}, {30, 60, 70, 90}) ? "" : "no ");
+ SkDebugf("%s intersection", SkRect::Intersects({10, 40, 50, 80}, {30, 60, 70, 90}) ? "" : "no "); #StdOut intersection ## @@ -1790,9 +1793,9 @@ Rect to construction. #Param bottom y maximum of constructed Rect ## #Example - SkRect rect = { 10, 20, 15, 25};
- rect.join(50, 60, 55, 65);
- SkDebugf("join: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
+ SkRect rect = { 10, 20, 15, 25}; + rect.join(50, 60, 55, 65); + SkDebugf("join: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); #StdOut join: 10, 20, 55, 65 ## @@ -1814,9 +1817,9 @@ Rect to r. #Param r expansion Rect ## #Example - SkRect rect = { 10, 20, 15, 25};
- rect.join({50, 60, 55, 65});
- SkDebugf("join: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
+ SkRect rect = { 10, 20, 15, 25}; + rect.join({50, 60, 55, 65}); + SkDebugf("join: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); #StdOut join: 10, 20, 55, 65 ## @@ -1843,15 +1846,15 @@ May produce incorrect results if r is empty. #Description Since Rect is not sorted, first result is copy of toJoin. ## - SkRect rect = { 10, 100, 15, 0};
- SkRect sorted = rect.makeSorted();
- SkRect toJoin = { 50, 60, 55, 65 };
- rect.joinNonEmptyArg(toJoin);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- sorted.joinNonEmptyArg(toJoin);
+ SkRect rect = { 10, 100, 15, 0}; + SkRect sorted = rect.makeSorted(); + SkRect toJoin = { 50, 60, 55, 65 }; + rect.joinNonEmptyArg(toJoin); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + sorted.joinNonEmptyArg(toJoin); SkDebugf("sorted: %g, %g, %g, %g\n", sorted.fLeft, sorted.fTop, sorted.fRight, sorted.fBottom); #StdOut -rect: 50, 60, 55, 65
+rect: 50, 60, 55, 65 sorted: 10, 0, 55, 100 ## ## @@ -1874,15 +1877,15 @@ May produce incorrect results if Rect or r is empty. #Description Since Rect is not sorted, first result is not useful. ## - SkRect rect = { 10, 100, 15, 0};
- SkRect sorted = rect.makeSorted();
- SkRect toJoin = { 50, 60, 55, 65 };
- rect.joinPossiblyEmptyRect(toJoin);
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- sorted.joinPossiblyEmptyRect(toJoin);
- SkDebugf("sorted: %g, %g, %g, %g\n", sorted.fLeft, sorted.fTop, sorted.fRight, sorted.fBottom);
+ SkRect rect = { 10, 100, 15, 0}; + SkRect sorted = rect.makeSorted(); + SkRect toJoin = { 50, 60, 55, 65 }; + rect.joinPossiblyEmptyRect(toJoin); + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + sorted.joinPossiblyEmptyRect(toJoin); + SkDebugf("sorted: %g, %g, %g, %g\n", sorted.fLeft, sorted.fTop, sorted.fRight, sorted.fBottom); #StdOut -rect: 10, 60, 55, 65
+rect: 10, 60, 55, 65 sorted: 10, 0, 55, 100 ## ## @@ -1896,6 +1899,7 @@ sorted: 10, 0, 55, 100 #Method void growToInclude(SkPoint pt) Grows Rect to include (pt.fX, pt.fY), modifying it so that: + #Formula fLeft <= pt.fX <= fRight && fTop <= pt.fY <= fBottom ## @@ -1907,11 +1911,11 @@ Points after one or more calls. In this case, Rect is empty after first call. #Param pt Point to include ## #Example - SkRect rect;
- rect.setLargestInverted();
- rect.growToInclude( { 42, 24 } );
- SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom());
- SkDebugf("isEmpty: %s\n", rect.isEmpty() ? "true" : "false");
+ SkRect rect; + rect.setLargestInverted(); + rect.growToInclude( { 42, 24 } ); + SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom()); + SkDebugf("isEmpty: %s\n", rect.isEmpty() ? "true" : "false"); #StdOut rect: 42, 24, 42, 24 isEmpty: true ## @@ -1939,11 +1943,11 @@ Points after one or more calls. In this case, Rect is empty after first call. #Param count number of points in array ## #Example - SkPoint pts[] = { { 30, 50 }, { 40, 50 }, { 30, 60 } };
- SkRect rect = { pts[0].fX, pts[0].fY, pts[0].fX, pts[0].fY };
- rect.growToInclude( pts[1] );
- rect.growToInclude( pts[2] );
- SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom());
+ SkPoint pts[] = { { 30, 50 }, { 40, 50 }, { 30, 60 } }; + SkRect rect = { pts[0].fX, pts[0].fY, pts[0].fX, pts[0].fY }; + rect.growToInclude( pts[1] ); + rect.growToInclude( pts[2] ); + SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom()); #StdOut rect: 30, 50, 40, 60 ## @@ -1962,8 +1966,10 @@ it so that: #Formula fLeft <= pt.fX <= fRight && fTop <= pt.fY <= fBottom ## -. Point may be followed with other data in each array element. stride is number - of bytes in element; the interval to skip to advance from one Point to +. + +Point may be followed with other data in each array element. stride is number +of bytes in element; the interval to skip to advance from one Point to the next. If Rect is initialized with setLargestInverted, then Rect will contain bounds of @@ -1975,11 +1981,11 @@ Points after one or more calls. In this case, Rect is empty after first call. #Bug 7142 ## #Example - SkPoint3 pts[] = { { 30, 50, -1 }, { 40, 50, -1 }, { 30, 60, -1 } };
- SkRect rect;
- rect.setLargestInverted();
- rect.growToInclude((SkPoint* ) &pts[0].fX, sizeof(SkPoint3), SK_ARRAY_COUNT(pts));
- SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom());
+ SkPoint3 pts[] = { { 30, 50, -1 }, { 40, 50, -1 }, { 30, 60, -1 } }; + SkRect rect; + rect.setLargestInverted(); + rect.growToInclude((SkPoint* ) &pts[0].fX, sizeof(SkPoint3), SK_ARRAY_COUNT(pts)); + SkDebugf("rect: %g, %g, %g, %g ", rect.left(), rect.top(), rect.right(), rect.bottom()); #StdOut #Volatile rect: 30, 50, 40, 60 @@ -2004,19 +2010,19 @@ Rect contains r when Rect area completely includes r area. #Return true if all sides of Rect are outside r ## #Example - SkRect rect = { 30, 50, 40, 60 };
- SkRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
- for (auto contained : tests) {
- SkDebugf("rect: (%g, %g, %g, %g) %s (%g, %g, %g, %g)\n",
- rect.left(), rect.top(), rect.right(), rect.bottom(),
- rect.contains(contained) ? "contains" : "does not contain",
- contained.left(), contained.top(), contained.right(), contained.bottom());
- }
-#StdOut
-rect: (30, 50, 40, 60) contains (30, 50, 31, 51)
-rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
-rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
-##
+ SkRect rect = { 30, 50, 40, 60 }; + SkRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} }; + for (auto contained : tests) { + SkDebugf("rect: (%g, %g, %g, %g) %s (%g, %g, %g, %g)\n", + rect.left(), rect.top(), rect.right(), rect.bottom(), + rect.contains(contained) ? "contains" : "does not contain", + contained.left(), contained.top(), contained.right(), contained.bottom()); + } +#StdOut +rect: (30, 50, 40, 60) contains (30, 50, 31, 51) +rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50) +rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60) +## ## #SeeAlso SkIRect::contains @@ -2037,19 +2043,19 @@ Rect contains r when Rect area completely includes r area. #Return true if all sides of Rect are outside r ## #Example - SkRect rect = { 30, 50, 40, 60 };
- SkIRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} };
- for (auto contained : tests) {
- SkDebugf("rect: (%g, %g, %g, %g) %s (%d, %d, %d, %d)\n",
- rect.left(), rect.top(), rect.right(), rect.bottom(),
- rect.contains(contained) ? "contains" : "does not contain",
- contained.left(), contained.top(), contained.right(), contained.bottom());
- }
-#StdOut
-rect: (30, 50, 40, 60) contains (30, 50, 31, 51)
-rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50)
-rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60)
-##
+ SkRect rect = { 30, 50, 40, 60 }; + SkIRect tests[] = { { 30, 50, 31, 51}, { 39, 49, 40, 50}, { 29, 59, 30, 60} }; + for (auto contained : tests) { + SkDebugf("rect: (%g, %g, %g, %g) %s (%d, %d, %d, %d)\n", + rect.left(), rect.top(), rect.right(), rect.bottom(), + rect.contains(contained) ? "contains" : "does not contain", + contained.left(), contained.top(), contained.right(), contained.bottom()); + } +#StdOut +rect: (30, 50, 40, 60) contains (30, 50, 31, 51) +rect: (30, 50, 40, 60) does not contain (39, 49, 40, 50) +rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60) +## ## #SeeAlso SkIRect::contains @@ -2073,10 +2079,10 @@ members, using #Param dst storage for IRect ## #Example - SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f };
- SkIRect round;
- rect.round(&round);
- SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f }; + SkIRect round; + rect.round(&round); + SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom); #StdOut round: 31, 51, 41, 61 ## @@ -2101,10 +2107,10 @@ rounding up fRight and FBottom, using #Param dst storage for IRect ## #Example - SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f };
- SkIRect round;
- rect.roundOut(&round);
- SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f }; + SkIRect round; + rect.roundOut(&round); + SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom); #StdOut round: 30, 50, 41, 61 ## @@ -2129,10 +2135,10 @@ rounding up fRight and FBottom, using #Param dst storage for Rect ## #Example - SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f };
- SkRect round;
- rect.roundOut(&round);
- SkDebugf("round: %g, %g, %g, %g\n", round.fLeft, round.fTop, round.fRight, round.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f }; + SkRect round; + rect.roundOut(&round); + SkDebugf("round: %g, %g, %g, %g\n", round.fLeft, round.fTop, round.fRight, round.fBottom); #StdOut round: 30, 50, 41, 61 ## @@ -2148,6 +2154,7 @@ round: 30, 50, 41, 61 Sets Rect by rounding up fLeft and fTop; and discarding the fractional portion of fRight and FBottom, using + #Formula (SkScalarCeilToInt(fLeft), SkScalarCeilToInt(fTop), SkScalarFloorToInt(fRight), SkScalarFloorToInt(fBottom)) @@ -2157,12 +2164,12 @@ discarding the fractional portion of fRight and FBottom, using #Param dst storage for IRect ## #Example - SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f };
- SkIRect round;
- rect.roundIn(&round);
- SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f }; + SkIRect round; + rect.roundIn(&round); + SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom); #StdOut -round: 31, 51, 40, 60
+round: 31, 51, 40, 60 ## ## @@ -2185,11 +2192,11 @@ members, using #Return rounded IRect ## #Example - SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f };
- SkIRect round = rect.round();
- SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f }; + SkIRect round = rect.round(); + SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom); #StdOut -round: 31, 51, 41, 61
+round: 31, 51, 41, 61 ## ## @@ -2212,11 +2219,11 @@ rounding up fRight and FBottom, using #Return rounded IRect ## #Example - SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f };
- SkIRect round = rect.roundOut();
- SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 40.5f, 60.5f }; + SkIRect round = rect.roundOut(); + SkDebugf("round: %d, %d, %d, %d\n", round.fLeft, round.fTop, round.fRight, round.fBottom); #StdOut -round: 30, 50, 41, 61
+round: 30, 50, 41, 61 ## ## @@ -2235,12 +2242,12 @@ fTop and fBottom if fTop is greater than fBottom. Result may be empty; and width() and height() will be zero or positive. #Example - SkRect rect = { 30.5f, 50.5f, 20.5f, 10.5f };
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- rect.sort();
- SkDebugf("sorted: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 20.5f, 10.5f }; + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + rect.sort(); + SkDebugf("sorted: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); #StdOut -rect: 30.5, 50.5, 20.5, 10.5
+rect: 30.5, 50.5, 20.5, 10.5 sorted: 20.5, 10.5, 30.5, 50.5 ## ## @@ -2260,12 +2267,12 @@ and width() and height() will be zero or positive. #Return sorted Rect ## #Example - SkRect rect = { 30.5f, 50.5f, 20.5f, 10.5f };
- SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom);
- SkRect sort = rect.makeSorted();
- SkDebugf("sorted: %g, %g, %g, %g\n", sort.fLeft, sort.fTop, sort.fRight, sort.fBottom);
+ SkRect rect = { 30.5f, 50.5f, 20.5f, 10.5f }; + SkDebugf("rect: %g, %g, %g, %g\n", rect.fLeft, rect.fTop, rect.fRight, rect.fBottom); + SkRect sort = rect.makeSorted(); + SkDebugf("sorted: %g, %g, %g, %g\n", sort.fLeft, sort.fTop, sort.fRight, sort.fBottom); #StdOut -rect: 30.5, 50.5, 20.5, 10.5
+rect: 30.5, 50.5, 20.5, 10.5 sorted: 20.5, 10.5, 30.5, 50.5 ## ## @@ -2284,11 +2291,11 @@ entries. #Return pointer to fLeft ## #Example - SkRect rect = {7, 11, 13, 17};
-SkDebugf("rect.asScalars() %c= &rect.fLeft\n", rect.asScalars() == &rect.fLeft? '=' : '!');
-#StdOut
-rect.asScalars() == &rect.fLeft
-##
+ SkRect rect = {7, 11, 13, 17}; +SkDebugf("rect.asScalars() %c= &rect.fLeft\n", rect.asScalars() == &rect.fLeft? '=' : '!'); +#StdOut +rect.asScalars() == &rect.fLeft +## ## #SeeAlso toQuad @@ -2311,12 +2318,12 @@ generate exact binary representations of floating point numbers. SkDebugf("\n"); } #StdOut -SkRect::MakeLTRB(20, 30, 40, 50);
-
-SkRect::MakeLTRB(SkBits2Float(0x41a00000), /* 20.000000 */
- SkBits2Float(0x41f00000), /* 30.000000 */
- SkBits2Float(0x42200000), /* 40.000000 */
- SkBits2Float(0x42480000) /* 50.000000 */);
+SkRect::MakeLTRB(20, 30, 40, 50); + +SkRect::MakeLTRB(SkBits2Float(0x41a00000), /* 20.000000 */ + SkBits2Float(0x41f00000), /* 30.000000 */ + SkBits2Float(0x42200000), /* 40.000000 */ + SkBits2Float(0x42480000) /* 50.000000 */); ## ## @@ -2334,12 +2341,12 @@ with limited precision; it may not be possible to reconstruct original Rect from output. #Example -SkRect rect = {6.f / 7, 2.f / 3, 26.f / 10, 42.f / 6};
-rect.dump();
-SkRect copy = SkRect::MakeLTRB(0.857143f, 0.666667f, 2.6f, 7);
-SkDebugf("rect is " "%s" "equal to copy\n", rect == copy ? "" : "not ");
+SkRect rect = {6.f / 7, 2.f / 3, 26.f / 10, 42.f / 6}; +rect.dump(); +SkRect copy = SkRect::MakeLTRB(0.857143f, 0.666667f, 2.6f, 7); +SkDebugf("rect is " "%s" "equal to copy\n", rect == copy ? "" : "not "); #StdOut -SkRect::MakeLTRB(0.857143f, 0.666667f, 2.6f, 7);
+SkRect::MakeLTRB(0.857143f, 0.666667f, 2.6f, 7); rect is not equal to copy ## ## @@ -2362,18 +2369,18 @@ Use instead of dump() when submitting . #Example - SkRect rect = {6.f / 7, 2.f / 3, 26.f / 10, 42.f / 6};
-rect.dumpHex();
-SkRect copy = SkRect::MakeLTRB(SkBits2Float(0x3f5b6db7), /* 0.857143 */
- SkBits2Float(0x3f2aaaab), /* 0.666667 */
- SkBits2Float(0x40266666), /* 2.600000 */
- SkBits2Float(0x40e00000) /* 7.000000 */);
+ SkRect rect = {6.f / 7, 2.f / 3, 26.f / 10, 42.f / 6}; +rect.dumpHex(); +SkRect copy = SkRect::MakeLTRB(SkBits2Float(0x3f5b6db7), /* 0.857143 */ + SkBits2Float(0x3f2aaaab), /* 0.666667 */ + SkBits2Float(0x40266666), /* 2.600000 */ + SkBits2Float(0x40e00000) /* 7.000000 */); SkDebugf("rect is " "%s" "equal to copy\n", rect == copy ? "" : "not "); #StdOut -SkRect::MakeLTRB(SkBits2Float(0x3f5b6db7), /* 0.857143 */
- SkBits2Float(0x3f2aaaab), /* 0.666667 */
- SkBits2Float(0x40266666), /* 2.600000 */
- SkBits2Float(0x40e00000) /* 7.000000 */);
+SkRect::MakeLTRB(SkBits2Float(0x3f5b6db7), /* 0.857143 */ + SkBits2Float(0x3f2aaaab), /* 0.666667 */ + SkBits2Float(0x40266666), /* 2.600000 */ + SkBits2Float(0x40e00000) /* 7.000000 */); rect is equal to copy ## ## diff --git a/docs/undocumented.bmh b/docs/undocumented.bmh index 0239034eec..8a57459607 100644 --- a/docs/undocumented.bmh +++ b/docs/undocumented.bmh @@ -11,7 +11,7 @@ PDF XPS RFC NaN NaNs - Bezier Coons Cartesian + Bezier Coons Cartesian Euclidean C C++ Destructor Subclasses SaveLayerFlags # not external; need to add typedef support SkUserConfig # not external, but still thinking about how markup refers to this @@ -336,6 +336,8 @@ FT_Load_Glyph ## #Method size_t computeByteSize(size_t rowBytes) const ## + #Method void validate() const + ## ## #Subtopic ## #Class SkImage @@ -362,6 +364,11 @@ FT_Load_Glyph #Topic Image_Scaling ## +#Topic ISize +#Struct SkISize +## +## + #Topic Left_Side_Bearing ## @@ -559,6 +566,11 @@ FT_Load_Glyph #Subtopic ## #Topic ## +#Topic Point3 +#Struct SkPoint3 +## +#Topic ## + #Topic PostScript #Substitute PostScript #Subtopic Arct @@ -637,7 +649,8 @@ FT_Load_Glyph #Topic ## #Topic Size -#Alias ISize +#Struct SkSize +## ## #Topic Sprite @@ -645,7 +658,7 @@ FT_Load_Glyph #Topic ## #Topic Stream -#Class SkFlattenable +#Class SkStream #Class ## #Topic ## @@ -702,6 +715,7 @@ FT_Load_Glyph ## #Topic Vector +#Alias Vectors #Struct SkVector ## ## diff --git a/site/user/api/SkBitmap_Reference.md b/site/user/api/SkBitmap_Reference.md index abff9ffbb1..4182c50733 100644 --- a/site/user/api/SkBitmap_Reference.md +++ b/site/user/api/SkBitmap_Reference.md @@ -74,8 +74,7 @@ is useful to position one or more <a href="#Bitmap">Bitmaps</a> within a shared | <a href="#SkBitmap_bytesPerPixel">bytesPerPixel</a> | Returns number of bytes in pixel based on <a href="undocumented#Color_Type">Color Type</a>. | | <a href="#SkBitmap_colorSpace">colorSpace</a> | Returns <a href="#Info">Image Info</a> <a href="undocumented#Color_Space">Color Space</a>. | | <a href="#SkBitmap_colorType">colorType</a> | Returns <a href="#Info">Image Info</a> <a href="undocumented#Color_Type">Color Type</a>. | -| <a href="#SkBitmap_computeSafeSize64">computeSafeSize64</a> | Returns minimum size required for pixels in 64 bits. | -| <a href="#SkBitmap_computeSize64">computeSize64</a> | Returns conservative size required for pixels. | +| <a href="#SkBitmap_computeByteSize">computeByteSize</a> | Returns size required for pixels. | | <a href="#SkBitmap_dimensions">dimensions</a> | Returns <a href="#SkBitmap_width">width</a> and <a href="#SkBitmap_height">height</a>. | | <a href="#SkBitmap_drawsNothing">drawsNothing</a> | Returns true if no <a href="#SkBitmap_width">width</a>, no <a href="#SkBitmap_height">height</a>, or no <a href="undocumented#Pixel_Ref">Pixel Ref</a>. | | <a href="#SkBitmap_empty">empty</a> | Returns true if <a href="#Info">Image Info</a> has zero <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a>. | @@ -83,7 +82,7 @@ is useful to position one or more <a href="#Bitmap">Bitmaps</a> within a shared | <a href="#SkBitmap_eraseARGB">eraseARGB</a> | Writes <a href="undocumented#Color">Color</a> to pixels. | | <a href="#SkBitmap_eraseArea">eraseArea</a> | Deprecated | | <a href="#SkBitmap_eraseColor">eraseColor</a> | Writes <a href="undocumented#Color">Color</a> to pixels. | -| <a href="#SkBitmap_eraseRGB">eraseRGB</a> | Writes opaque <a href="undocumented#Color">Color</a> to pixels. | +| <a href="#SkBitmap_eraseRGB">eraseRGB</a> | Deprecated | | <a href="#SkBitmap_extractAlpha">extractAlpha</a> | Creates <a href="#Bitmap">Bitmap</a> containing <a href="#Alpha">Alpha</a> of pixels. | | <a href="#SkBitmap_extractSubset">extractSubset</a> | Creates <a href="#Bitmap">Bitmap</a>, sharing pixels if possible. | | <a href="#SkBitmap_getAddr">getAddr</a> | Returns readable pixel address as void pointer. | @@ -94,8 +93,6 @@ is useful to position one or more <a href="#Bitmap">Bitmaps</a> within a shared | <a href="#SkBitmap_getColor">getColor</a> | Returns one pixel as <a href="#Unpremultiply">Unpremultiplied</a> <a href="undocumented#Color">Color</a>. | | <a href="#SkBitmap_getGenerationID">getGenerationID</a> | Returns unique ID. | | <a href="#SkBitmap_getPixels">getPixels</a> | Returns address of pixels. | -| <a href="#SkBitmap_getSafeSize">getSafeSize</a> | Returns minimum size required for pixels in 32 bits. | -| <a href="#SkBitmap_getSize">getSize</a> | Returns conservative size required for pixels in 32 bits. | | <a href="#SkBitmap_getSubset">getSubset</a> | Returns <a href="#SkBitmap_bounds">bounds</a> offset by origin. | | <a href="#SkBitmap_hasHardwareMipMap">hasHardwareMipMap</a> | Returns <a href="undocumented#Mip_Map">Mip Map</a> support present; <a href="undocumented#Android">Android</a> only. | | <a href="#SkBitmap_height">height</a> | Returns pixel row count. | @@ -129,12 +126,13 @@ is useful to position one or more <a href="#Bitmap">Bitmaps</a> within a shared | <a href="#SkBitmap_tryAllocN32Pixels">tryAllocN32Pixels</a> | Allocates compatible <a href="#ARGB">Color ARGB</a> pixels if possible. | | <a href="#SkBitmap_tryAllocPixels">tryAllocPixels</a> | Allocates pixels from <a href="#Info">Image Info</a> if possible. | | <a href="#SkBitmap_tryAllocPixelsFlags">tryAllocPixelsFlags</a> | Allocates pixels from <a href="#Info">Image Info</a> with options if possible. | +| <a href="#SkBitmap_validate">validate</a> | Asserts if <a href="#Bitmap">Bitmap</a> is invalid (debug only). | | <a href="#SkBitmap_width">width</a> | Returns pixel column count. | | <a href="#SkBitmap_writePixels">writePixels</a> | Copies and converts pixels. | # <a name="SkBitmap::Allocator"></a> Class SkBitmap::Allocator -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> class <a href="#SkBitmap_Allocator">Allocator</a> : public <a href="undocumented#SkRefCnt">SkRefCnt</a> { public: virtual bool <a href="#SkBitmap_Allocator_allocPixelRef">allocPixelRef(SkBitmap* bitmap)</a> = 0; @@ -172,7 +170,7 @@ true if <a href="undocumented#Pixel_Ref">Pixel Ref</a> was allocated # <a name="SkBitmap::HeapAllocator"></a> Class SkBitmap::HeapAllocator -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> class <a href="#SkBitmap_HeapAllocator">HeapAllocator</a> : public <a href="#SkBitmap_Allocator">Allocator</a> { public: bool <a href="#SkBitmap_HeapAllocator_allocPixelRef">allocPixelRef(SkBitmap* bitmap)</a> override; @@ -516,6 +514,7 @@ int width() const </pre> Returns pixel count in each pixel row. Should be equal or less than: + <a href="#SkBitmap_rowBytes">rowBytes</a> / <a href="#SkBitmap_info">info</a>.<a href="#SkBitmap_bytesPerPixel">bytesPerPixel</a>. Maybe be less than <a href="#SkBitmap_pixelRef">pixelRef</a>.<a href="#SkBitmap_width">width</a>. Will not exceed <a href="#SkBitmap_pixelRef">pixelRef</a>.<a href="#SkBitmap_width">width</a> less @@ -1096,175 +1095,6 @@ width: 1000000 height: 1000000 computeByteSize: 4999999000000 --- -<a name="SkBitmap_getSize"></a> -## getSize - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -size_t getSize() const -</pre> - -Returns conservative memory required for pixel storage. -Includes unused memory on last row when <a href="#SkBitmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkBitmap_width">width</a>. - -Does not check to see if result fits in 32 bits. Use getSize64() if the -result may exceed 32 bits. - -### Return Value - -<a href="#SkBitmap_height">height</a> times <a href="#SkBitmap_rowBytes">rowBytes</a> - -### Example - -<div><fiddle-embed name="798d5f259dbd1ead4f3b1eac955c2cde"><div><a href="#SkBitmap_getSize">getSize</a> results are not useful when <a href="#SkBitmap_width">width</a> and <a href="#SkBitmap_height">height</a> are large.</div> - -#### Example Output - -~~~~ -width: 1 height: 1 getSize: 5 -width: 1 height: 1000 getSize: 5000 -width: 1 height: 1000000 getSize: 5000000 -width: 1000 height: 1 getSize: 5000 -width: 1000 height: 1000 getSize: 5000000 -width: 1000 height: 1000000 getSize: 705032704 -width: 1000000 height: 1 getSize: 5000000 -width: 1000000 height: 1000 getSize: 705032704 -width: 1000000 height: 1000000 getSize: 658067456 -~~~~ - -</fiddle-embed></div> - -### See Also - -<a href="#SkBitmap_getSafeSize">getSafeSize</a> <a href="#SkBitmap_computeSize64">computeSize64</a> <a href="#SkBitmap_rowBytes">rowBytes</a> <a href="#SkBitmap_width">width</a> - ---- - -<a name="SkBitmap_getSafeSize"></a> -## getSafeSize - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -size_t getSafeSize() const -</pre> - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when <a href="#SkBitmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkBitmap_width">width</a>. - -Returns zero if size does not fit in 32 bits. Use <a href="#SkBitmap_computeSafeSize64">computeSafeSize64</a> if the -result may exceed 32 bits. - -The pixel storage visible may be a subset of the <a href="undocumented#Pixel_Ref">Pixel Ref</a>. Accessing memory -beyond the result may generate an exception. - -### Return Value - -exact pixel storage size - -### Example - -<div><fiddle-embed name="47a93c44326c86371dbf42d2544e76be"><div><a href="#SkBitmap_getSafeSize">getSafeSize</a> results are not useful when <a href="#SkBitmap_width">width</a> and <a href="#SkBitmap_height">height</a> are large.</div> - -#### Example Output - -~~~~ -width: 1 height: 1 getSafeSize: 4 -width: 1 height: 1000 getSafeSize: 4999 -width: 1 height: 1000000 getSafeSize: 4999999 -width: 1000 height: 1 getSafeSize: 4000 -width: 1000 height: 1000 getSafeSize: 4999000 -width: 1000 height: 1000000 getSafeSize: 0 -width: 1000000 height: 1 getSafeSize: 4000000 -width: 1000000 height: 1000 getSafeSize: 0 -width: 1000000 height: 1000000 getSafeSize: 0 -~~~~ - -</fiddle-embed></div> - -### See Also - -<a href="#SkBitmap_getSize">getSize</a> <a href="#SkBitmap_computeSafeSize64">computeSafeSize64</a> <a href="#SkBitmap_rowBytes">rowBytes</a> <a href="#SkBitmap_width">width</a> - ---- - -<a name="SkBitmap_computeSize64"></a> -## computeSize64 - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -int64_t computeSize64() const -</pre> - -Returns conservative memory required for pixel storage. -Includes unused memory on last row when <a href="#SkBitmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkBitmap_width">width</a>. - -### Return Value - -conservative pixel storage size - -### Example - -<div><fiddle-embed name="e7deb420416751aa68c1bd7956596833"> - -#### Example Output - -~~~~ -width: 1 height: 1 computeSize64: 5 -width: 1 height: 1000 computeSize64: 5000 -width: 1 height: 1000000 computeSize64: 5000000 -width: 1000 height: 1 computeSize64: 5000 -width: 1000 height: 1000 computeSize64: 5000000 -width: 1000 height: 1000000 computeSize64: 5000000000 -width: 1000000 height: 1 computeSize64: 5000000 -width: 1000000 height: 1000 computeSize64: 5000000000 -width: 1000000 height: 1000000 computeSize64: 5000000000000 -~~~~ - -</fiddle-embed></div> - -### See Also - -<a href="#SkBitmap_getSize">getSize</a> <a href="#SkBitmap_computeSafeSize64">computeSafeSize64</a> <a href="#SkBitmap_rowBytes">rowBytes</a> <a href="#SkBitmap_width">width</a> - ---- - -<a name="SkBitmap_computeSafeSize64"></a> -## computeSafeSize64 - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -int64_t computeSafeSize64() const -</pre> - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when <a href="#SkBitmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkBitmap_width">width</a>. - -### Return Value - -exact pixel storage size - -### Example - -<div><fiddle-embed name="ff12ff8354c1add9ea00797412f6342c"> - -#### Example Output - -~~~~ -width: 1 height: 1 computeSafeSize64: 4 -width: 1 height: 1000 computeSafeSize64: 4999 -width: 1 height: 1000000 computeSafeSize64: 4999999 -width: 1000 height: 1 computeSafeSize64: 4000 -width: 1000 height: 1000 computeSafeSize64: 4999000 -width: 1000 height: 1000000 computeSafeSize64: 4999999000 -width: 1000000 height: 1 computeSafeSize64: 4000000 -width: 1000000 height: 1000 computeSafeSize64: 4999000000 -width: 1000000 height: 1000000 computeSafeSize64: 4999999000000 -~~~~ - -</fiddle-embed></div> - -### See Also - -<a href="#SkBitmap_getSafeSize">getSafeSize</a> <a href="#SkBitmap_computeSize64">computeSize64</a> <a href="#SkBitmap_rowBytes">rowBytes</a> <a href="#SkBitmap_width">width</a> - ---- - <a name="SkBitmap_isImmutable"></a> ## isImmutable @@ -1306,9 +1136,9 @@ copy is immutable void setImmutable() </pre> -Once set, pixels can not change. Any other bitmap sharing the same <a href="undocumented#Pixel_Ref">Pixel Ref</a> -are also marked as immutable. Once <a href="undocumented#Pixel_Ref">Pixel Ref</a> is marked immutable, the setting -cannot be cleared. +Sets internal flag to mark <a href="#Bitmap">Bitmap</a> as immutable. Once set, pixels can not change. +Any other bitmap sharing the same <a href="undocumented#Pixel_Ref">Pixel Ref</a> are also marked as immutable. +Once <a href="undocumented#Pixel_Ref">Pixel Ref</a> is marked immutable, the setting cannot be cleared. Writing to immutable <a href="#Bitmap">Bitmap</a> pixels triggers an assert on debug builds. @@ -1591,7 +1421,7 @@ integral rectangle from origin to <a href="#SkBitmap_width">width</a> and <a hre SkISize dimensions() const </pre> -Returns <a href="#Size">ISize</a> { <a href="#SkBitmap_width">width</a>, <a href="#SkBitmap_height">height</a> }. +Returns <a href="undocumented#ISize">ISize</a> { <a href="#SkBitmap_width">width</a>, <a href="#SkBitmap_height">height</a> }. ### Return Value @@ -1699,7 +1529,7 @@ true if <a href="#Info">Image Info</a> set successfully ## <a name="SkBitmap_AllocFlags"></a> Enum SkBitmap::AllocFlags -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkBitmap_AllocFlags">AllocFlags</a> { <a href="#SkBitmap_kZeroPixels_AllocFlag">kZeroPixels AllocFlag</a> = 1 << 0, };</pre> @@ -2577,7 +2407,7 @@ then <a href="#RGB">Color RGB</a> is ignored. ### See Also -<a href="#SkBitmap_eraseARGB">eraseARGB</a> <a href="#SkBitmap_eraseRGB">eraseRGB</a> <a href="#SkBitmap_erase">erase</a> +<a href="#SkBitmap_eraseARGB">eraseARGB</a> <a href="#SkBitmap_erase">erase</a> --- @@ -2613,7 +2443,7 @@ amount of <a href="#RGB_Blue">Color RGB Blue</a>, from no blue (0) to full blue ### See Also -<a href="#SkBitmap_eraseColor">eraseColor</a> <a href="#SkBitmap_eraseRGB">eraseRGB</a> <a href="#SkBitmap_erase">erase</a> +<a href="#SkBitmap_eraseColor">eraseColor</a> <a href="#SkBitmap_erase">erase</a> --- @@ -2624,25 +2454,19 @@ amount of <a href="#RGB_Blue">Color RGB Blue</a>, from no blue (0) to full blue void eraseRGB(U8CPU r, U8CPU g, U8CPU b) const </pre> -Replaces pixel values with <a href="undocumented#Color">Color</a> built from <a href="#SkBitmap_eraseRGB_r">r</a>, <a href="#SkBitmap_eraseRGB_g">g</a>, and <a href="#SkBitmap_eraseRGB_b">b</a> with <a href="#Alpha">Color Alpha</a> set -to 255. All pixels contained by <a href="#SkBitmap_bounds">bounds</a> are affected. -If <a href="#SkBitmap_colorType">colorType</a> is <a href="undocumented#SkColorType">kAlpha 8 SkColorType</a>, all pixels are set to 255. +Deprecated. Use <a href="#SkBitmap_eraseARGB">eraseARGB</a> or <a href="#SkBitmap_eraseColor">eraseColor</a>. ### Parameters <table> <tr> <td><a name="SkBitmap_eraseRGB_r"> <code><strong>r </strong></code> </a></td> <td> -amount of <a href="#RGB_Red">Color RGB Red</a>, from no red (0) to full red (255)</td> +amount of red</td> </tr> <tr> <td><a name="SkBitmap_eraseRGB_g"> <code><strong>g </strong></code> </a></td> <td> -amount of <a href="#RGB_Green">Color RGB Green</a>, from no green (0) to full green (255)</td> +amount of green</td> </tr> <tr> <td><a name="SkBitmap_eraseRGB_b"> <code><strong>b </strong></code> </a></td> <td> -amount of <a href="#RGB_Blue">Color RGB Blue</a>, from no blue (0) to full blue (255)</td> +amount of blue</td> </tr> </table> -### Example - -<div><fiddle-embed name="3088f4d6cf8a01644ffd41bfddad5e03"></fiddle-embed></div> - ### See Also <a href="#SkBitmap_eraseColor">eraseColor</a> <a href="#SkBitmap_eraseARGB">eraseARGB</a> <a href="#SkBitmap_erase">erase</a> @@ -3041,7 +2865,8 @@ If this-><a href="#SkBitmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkBitmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkBitmap_readPixels_dstInfo">dstInfo</a>.<a href="#SkBitmap_colorSpace">colorSpace</a> must match. Returns false if pixel conversion is not possible. <a href="#SkBitmap_readPixels_srcX">srcX</a> and <a href="#SkBitmap_readPixels_srcY">srcY</a> may be negative to copy only top or left of source. Returns -false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. Returns false ifabs(srcX) >= this-><a href="#SkBitmap_width">width</a>, +false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. +Returns false ifabs(srcX) >= this-><a href="#SkBitmap_width">width</a>, or ifabs(srcY) >= this-><a href="#SkBitmap_height">height</a>. If <a href="#SkBitmap_readPixels_behavior">behavior</a> is <a href="#SkTransferFunctionBehavior_kRespect">SkTransferFunctionBehavior::kRespect</a>: converts source @@ -3106,7 +2931,8 @@ If this-><a href="#SkBitmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkBitmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkBitmap_readPixels_2_dstInfo">dstInfo</a>.<a href="#SkBitmap_colorSpace">colorSpace</a> must match. Returns false if pixel conversion is not possible. <a href="#SkBitmap_readPixels_2_srcX">srcX</a> and <a href="#SkBitmap_readPixels_2_srcY">srcY</a> may be negative to copy only top or left of source. Returns -false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. Returns false ifabs(srcX) >= this-><a href="#SkBitmap_width">width</a>, +false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. +Returns false ifabs(srcX) >= this-><a href="#SkBitmap_width">width</a>, or ifabs(srcY) >= this-><a href="#SkBitmap_height">height</a>. ### Parameters @@ -3163,7 +2989,8 @@ If this-><a href="#SkBitmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkBitmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkBitmap_readPixels_3_dst">dst</a> <a href="undocumented#Color_Space">Color Space</a> must match. Returns false if pixel conversion is not possible. <a href="#SkBitmap_readPixels_3_srcX">srcX</a> and <a href="#SkBitmap_readPixels_3_srcY">srcY</a> may be negative to copy only top or left of source. Returns -false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. Returns false ifabs(srcX) >= this-><a href="#SkBitmap_width">width</a>, +false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. +Returns false ifabs(srcX) >= this-><a href="#SkBitmap_width">width</a>, or ifabs(srcY) >= this-><a href="#SkBitmap_height">height</a>. ### Parameters @@ -3263,7 +3090,8 @@ If this-><a href="#SkBitmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkBitmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkBitmap_writePixels_src">src</a> <a href="undocumented#Color_Space">Color Space</a> must match. Returns false if pixel conversion is not possible. <a href="#SkBitmap_writePixels_dstX">dstX</a> and <a href="#SkBitmap_writePixels_dstY">dstY</a> may be negative to copy only top or left of source. Returns -false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. Returns false ifabs(dstX) >= this-><a href="#SkBitmap_width">width</a>, +false if <a href="#SkBitmap_width">width</a> or <a href="#SkBitmap_height">height</a> is zero or negative. +Returns false ifabs(dstX) >= this-><a href="#SkBitmap_width">width</a>, or ifabs(dstY) >= this-><a href="#SkBitmap_height">height</a>. ### Parameters @@ -3550,11 +3378,11 @@ true if <a href="#Alpha">Alpha</a> layer was constructed in <a href="#SkBitmap_e bool peekPixels(SkPixmap* pixmap) const </pre> -If the pixels are available from this bitmap return true, and fill out the -specified <a href="#SkBitmap_peekPixels_pixmap">pixmap</a> (if not null). If there are no pixels, return false and -ignore the <a href="#SkBitmap_peekPixels_pixmap">pixmap</a> parameter. -Note: if this returns true, the results (in the <a href="#SkBitmap_peekPixels_pixmap">pixmap</a>) are only valid until the bitmap -is changed in any way, in which case the results are invalid. +Copies <a href="#Bitmap">Bitmap</a> pixel address, row bytes, and <a href="#Info">Image Info</a> to <a href="#SkBitmap_peekPixels_pixmap">pixmap</a>, if address +is available, and returns true. If pixel address is not available, return +false and leave <a href="#SkBitmap_peekPixels_pixmap">pixmap</a> unchanged. + +<a href="#SkBitmap_peekPixels_pixmap">pixmap</a> contents become invalid on any future change to <a href="#Bitmap">Bitmap</a>. ### Parameters @@ -3595,6 +3423,22 @@ true if <a href="#Bitmap">Bitmap</a> has direct access to pixels --- +<a name="SkBitmap_validate"></a> +## validate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void validate() const; +</pre> + +Asserts if internal values are illegal or inconsistent. Only available if +<a href="undocumented#SK_DEBUG">SK DEBUG</a> is defined at compile time. + +### See Also + +<a href="#SkImageInfo_validate">SkImageInfo::validate()</a> + +--- + <a name="SkBitmap_toString"></a> ## toString diff --git a/site/user/api/SkCanvas_Reference.md b/site/user/api/SkCanvas_Reference.md index 8d39ac47ed..5d59fd4dd4 100644 --- a/site/user/api/SkCanvas_Reference.md +++ b/site/user/api/SkCanvas_Reference.md @@ -430,7 +430,7 @@ storage of <a href="undocumented#Raster_Surface">Raster Surface</a></td> ## <a name="SkCanvas_ColorBehavior"></a> Enum SkCanvas::ColorBehavior -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum class <a href="#SkCanvas_ColorBehavior">ColorBehavior</a> { <a href="#SkCanvas_ColorBehavior_kLegacy">kLegacy</a>, };</pre> @@ -875,10 +875,11 @@ bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes, int srcX, int srcY) </pre> -Copies rectangle of pixels from <a href="#Canvas">Canvas</a> into <a href="#SkCanvas_readPixels_dstPixels">dstPixels</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are -ignored. Source rectangle corners are (<a href="#SkCanvas_readPixels_srcX">srcX</a>, <a href="#SkCanvas_readPixels_srcY">srcY</a>) and(this-><a href="#SkCanvas_imageInfo">imageInfo</a>.width(), this-><a href="#SkCanvas_imageInfo">imageInfo</a>.height()). +Copies <a href="SkRect_Reference#Rect">Rect</a> of pixels from <a href="#Canvas">Canvas</a> into <a href="#SkCanvas_readPixels_dstPixels">dstPixels</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are +ignored. Source <a href="SkRect_Reference#Rect">Rect</a> corners are (<a href="#SkCanvas_readPixels_srcX">srcX</a>, <a href="#SkCanvas_readPixels_srcY">srcY</a>) and +(<a href="#SkCanvas_imageInfo">imageInfo</a>.width(), <a href="#SkCanvas_imageInfo">imageInfo</a>.height()). -Destination rectangle corners are (0, 0) and (bitmap.width(), bitmap.height()). +Destination <a href="SkRect_Reference#Rect">Rect</a> corners are (0, 0) and (bitmap.width(), bitmap.height()). Copies each readable pixel intersecting both rectangles, without scaling, converting to <a href="#SkCanvas_readPixels_dstInfo">dstInfo</a>.colorType() and <a href="#SkCanvas_readPixels_dstInfo">dstInfo</a>.alphaType() if required. @@ -891,7 +892,7 @@ The destination pixel storage must be allocated by the caller. <a href="undocumented#Pixel">Pixel</a> values are converted only if <a href="#Color_Type">Image Color Type</a> and <a href="#Alpha_Type">Image Alpha Type</a> do not match. Only pixels within both source and destination rectangles -are copied. <a href="#SkCanvas_readPixels_dstPixels">dstPixels</a> contents outside the rectangle intersection are unchanged. +are copied. <a href="#SkCanvas_readPixels_dstPixels">dstPixels</a> contents outside <a href="SkRect_Reference#Rect">Rect</a> intersection are unchanged. Pass negative values for <a href="#SkCanvas_readPixels_srcX">srcX</a> or <a href="#SkCanvas_readPixels_srcY">srcY</a> to offset pixels across or down destination. @@ -956,10 +957,11 @@ pixel = 8056a9ff bool readPixels(const SkPixmap& pixmap, int srcX, int srcY) </pre> -Copies rectangle of pixels from <a href="#Canvas">Canvas</a> into <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are -ignored. Source rectangle corners are (<a href="#SkCanvas_readPixels_2_srcX">srcX</a>, <a href="#SkCanvas_readPixels_2_srcY">srcY</a>) and(this-><a href="#SkCanvas_imageInfo">imageInfo</a>.width(), this-><a href="#SkCanvas_imageInfo">imageInfo</a>.height()). +Copies <a href="SkRect_Reference#Rect">Rect</a> of pixels from <a href="#Canvas">Canvas</a> into <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are +ignored. Source <a href="SkRect_Reference#Rect">Rect</a> corners are (<a href="#SkCanvas_readPixels_2_srcX">srcX</a>, <a href="#SkCanvas_readPixels_2_srcY">srcY</a>) and +(<a href="#SkCanvas_imageInfo">imageInfo</a>.width(), <a href="#SkCanvas_imageInfo">imageInfo</a>.height()). -Destination rectangle corners are (0, 0) and (bitmap.width(), bitmap.height()). +Destination <a href="SkRect_Reference#Rect">Rect</a> corners are (0, 0) and (bitmap.width(), bitmap.height()). Copies each readable pixel intersecting both rectangles, without scaling, converting to <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a>.colorType() and <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a>.alphaType() if required. @@ -971,8 +973,8 @@ class like <a href="undocumented#SkDumpCanvas">SkDumpCanvas</a>. Caller must allocate pixel storage in <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a> if needed. <a href="undocumented#Pixel">Pixel</a> values are converted only if <a href="#Color_Type">Image Color Type</a> and <a href="#Alpha_Type">Image Alpha Type</a> -do not match. Only pixels within both source and destination rectangles -are copied. <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a> pixels contents outside the rectangle intersection are unchanged. +do not match. Only pixels within both source and destination <a href="#Rect">Rects</a> +are copied. <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a> pixels contents outside <a href="SkRect_Reference#Rect">Rect</a> intersection are unchanged. Pass negative values for <a href="#SkCanvas_readPixels_2_srcX">srcX</a> or <a href="#SkCanvas_readPixels_2_srcY">srcY</a> to offset pixels across or down <a href="#SkCanvas_readPixels_2_pixmap">pixmap</a>. @@ -1025,10 +1027,11 @@ pixel = 802b5580 bool readPixels(const SkBitmap& bitmap, int srcX, int srcY) </pre> -Copies rectangle of pixels from <a href="#Canvas">Canvas</a> into <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are -ignored. Source rectangle corners are (<a href="#SkCanvas_readPixels_3_srcX">srcX</a>, <a href="#SkCanvas_readPixels_3_srcY">srcY</a>) and(this-><a href="#SkCanvas_imageInfo">imageInfo</a>.width(), this-><a href="#SkCanvas_imageInfo">imageInfo</a>.height()). +Copies <a href="SkRect_Reference#Rect">Rect</a> of pixels from <a href="#Canvas">Canvas</a> into <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are +ignored. Source <a href="SkRect_Reference#Rect">Rect</a> corners are (<a href="#SkCanvas_readPixels_3_srcX">srcX</a>, <a href="#SkCanvas_readPixels_3_srcY">srcY</a>) and +(<a href="#SkCanvas_imageInfo">imageInfo</a>.width(), <a href="#SkCanvas_imageInfo">imageInfo</a>.height()). -Destination rectangle corners are (0, 0) and (<a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>.width(), <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>.height()). +Destination <a href="SkRect_Reference#Rect">Rect</a> corners are (0, 0) and (<a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>.width(), <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>.height()). Copies each readable pixel intersecting both rectangles, without scaling, converting to <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>.colorType() and <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>.alphaType() if required. @@ -1041,7 +1044,7 @@ Caller must allocate pixel storage in <a href="#SkCanvas_readPixels_3_bitmap">bi <a href="SkBitmap_Reference#Bitmap">Bitmap</a> values are converted only if <a href="#Color_Type">Image Color Type</a> and <a href="#Alpha_Type">Image Alpha Type</a> do not match. Only pixels within both source and destination rectangles -are copied. <a href="SkBitmap_Reference#Bitmap">Bitmap</a> pixels outside the rectangle intersection are unchanged. +are copied. <a href="SkBitmap_Reference#Bitmap">Bitmap</a> pixels outside <a href="SkRect_Reference#Rect">Rect</a> intersection are unchanged. Pass negative values for <a href="#SkCanvas_readPixels_3_srcX">srcX</a> or <a href="#SkCanvas_readPixels_3_srcY">srcY</a> to offset pixels across or down <a href="#SkCanvas_readPixels_3_bitmap">bitmap</a>. @@ -1098,12 +1101,13 @@ bool writePixels(const SkImageInfo& info, const void* pixels, size_t rowBytes, int x, int y) </pre> -Copies rectangle from <a href="#SkCanvas_writePixels_pixels">pixels</a> to <a href="#Canvas">Canvas</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are ignored. -Source rectangle corners are (0, 0) and (<a href="#SkCanvas_writePixels_info">info</a>.width(), <a href="#SkCanvas_writePixels_info">info</a>.height()). -Destination rectangle corners are (<a href="#SkCanvas_writePixels_x">x</a>, <a href="#SkCanvas_writePixels_y">y</a>) and(this-><a href="#SkCanvas_imageInfo">imageInfo</a>.width(), this-><a href="#SkCanvas_imageInfo">imageInfo</a>.height()). +Copies <a href="SkRect_Reference#Rect">Rect</a> from <a href="#SkCanvas_writePixels_pixels">pixels</a> to <a href="#Canvas">Canvas</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are ignored. +Source <a href="SkRect_Reference#Rect">Rect</a> corners are (0, 0) and (<a href="#SkCanvas_writePixels_info">info</a>.width(), <a href="#SkCanvas_writePixels_info">info</a>.height()). +Destination <a href="SkRect_Reference#Rect">Rect</a> corners are (<a href="#SkCanvas_writePixels_x">x</a>, <a href="#SkCanvas_writePixels_y">y</a>) and +(<a href="#SkCanvas_imageInfo">imageInfo</a>.width(), <a href="#SkCanvas_imageInfo">imageInfo</a>.height()). Copies each readable pixel intersecting both rectangles, without scaling, -converting tothis-><a href="#SkCanvas_imageInfo">imageInfo</a>.colorType()andthis-><a href="#SkCanvas_imageInfo">imageInfo</a>.alphaType()if required. +converting to <a href="#SkCanvas_imageInfo">imageInfo</a>.colorType() and <a href="#SkCanvas_imageInfo">imageInfo</a>.alphaType() if required. Pixels are writable when <a href="undocumented#Device">Device</a> is raster, or backed by a <a href="undocumented#GPU">GPU</a>. Pixels are not writable when <a href="#SkCanvas">SkCanvas</a> is returned by <a href="#SkDocument_beginPage">SkDocument::beginPage</a>, @@ -1112,7 +1116,7 @@ class like <a href="undocumented#SkDumpCanvas">SkDumpCanvas</a>. <a href="undocumented#Pixel">Pixel</a> values are converted only if <a href="#Color_Type">Image Color Type</a> and <a href="#Alpha_Type">Image Alpha Type</a> do not match. Only <a href="#SkCanvas_writePixels_pixels">pixels</a> within both source and destination rectangles -are copied. <a href="#Canvas">Canvas</a> <a href="#SkCanvas_writePixels_pixels">pixels</a> outside the rectangle intersection are unchanged. +are copied. <a href="#Canvas">Canvas</a> <a href="#SkCanvas_writePixels_pixels">pixels</a> outside <a href="SkRect_Reference#Rect">Rect</a> intersection are unchanged. Pass negative values for <a href="#SkCanvas_writePixels_x">x</a> or <a href="#SkCanvas_writePixels_y">y</a> to offset <a href="#SkCanvas_writePixels_pixels">pixels</a> to the left or above <a href="#Canvas">Canvas</a> <a href="#SkCanvas_writePixels_pixels">pixels</a>. @@ -1160,13 +1164,14 @@ true if <a href="#SkCanvas_writePixels_pixels">pixels</a> were written to <a hre bool writePixels(const SkBitmap& bitmap, int x, int y) </pre> -Copies rectangle from pixels to <a href="#Canvas">Canvas</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are ignored. -Source rectangle corners are (0, 0) and (<a href="#SkCanvas_writePixels_2_bitmap">bitmap</a>.width(), <a href="#SkCanvas_writePixels_2_bitmap">bitmap</a>.height()). +Copies <a href="SkRect_Reference#Rect">Rect</a> from pixels to <a href="#Canvas">Canvas</a>. <a href="#Matrix">Matrix</a> and <a href="#Clip">Clip</a> are ignored. +Source <a href="SkRect_Reference#Rect">Rect</a> corners are (0, 0) and (<a href="#SkCanvas_writePixels_2_bitmap">bitmap</a>.width(), <a href="#SkCanvas_writePixels_2_bitmap">bitmap</a>.height()). -Destination rectangle corners are (<a href="#SkCanvas_writePixels_2_x">x</a>, <a href="#SkCanvas_writePixels_2_y">y</a>) and(this-><a href="#SkCanvas_imageInfo">imageInfo</a>.width(), this-><a href="#SkCanvas_imageInfo">imageInfo</a>.height()). +Destination <a href="SkRect_Reference#Rect">Rect</a> corners are (<a href="#SkCanvas_writePixels_2_x">x</a>, <a href="#SkCanvas_writePixels_2_y">y</a>) and +(<a href="#SkCanvas_imageInfo">imageInfo</a>.width(), <a href="#SkCanvas_imageInfo">imageInfo</a>.height()). Copies each readable pixel intersecting both rectangles, without scaling, -converting tothis-><a href="#SkCanvas_imageInfo">imageInfo</a>.colorType()andthis-><a href="#SkCanvas_imageInfo">imageInfo</a>.alphaType()if required. +converting to <a href="#SkCanvas_imageInfo">imageInfo</a>.colorType() and <a href="#SkCanvas_imageInfo">imageInfo</a>.alphaType() if required. Pixels are writable when <a href="undocumented#Device">Device</a> is raster, or backed by a <a href="undocumented#GPU">GPU</a>. Pixels are not writable when <a href="#SkCanvas">SkCanvas</a> is returned by <a href="#SkDocument_beginPage">SkDocument::beginPage</a>, @@ -1175,7 +1180,7 @@ class like <a href="undocumented#SkDumpCanvas">SkDumpCanvas</a>. <a href="undocumented#Pixel">Pixel</a> values are converted only if <a href="#Color_Type">Image Color Type</a> and <a href="#Alpha_Type">Image Alpha Type</a> do not match. Only pixels within both source and destination rectangles -are copied. <a href="#Canvas">Canvas</a> pixels outside the rectangle intersection are unchanged. +are copied. <a href="#Canvas">Canvas</a> pixels outside <a href="SkRect_Reference#Rect">Rect</a> intersection are unchanged. Pass negative values for <a href="#SkCanvas_writePixels_2_x">x</a> or <a href="#SkCanvas_writePixels_2_y">y</a> to offset pixels to the left or above <a href="#Canvas">Canvas</a> pixels. @@ -1554,7 +1559,7 @@ depth of saved stack ## <a name="SkCanvas__anonymous"></a> Enum SkCanvas::_anonymous -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum { <a href="#SkCanvas_kIsOpaque_SaveLayerFlag">kIsOpaque SaveLayerFlag</a> = 1 << 0, <a href="#SkCanvas_kPreserveLCDText_SaveLayerFlag">kPreserveLCDText SaveLayerFlag</a> = 1 << 1, @@ -1596,7 +1601,7 @@ scalePaint blends <a href="#Layer">Layer</a> back with transparency.</div></fidd # <a name="SkCanvas_SaveLayerRec"></a> Struct SkCanvas::SaveLayerRec -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> struct <a href="#SkCanvas_SaveLayerRec_SaveLayerRec">SaveLayerRec</a> { <a href="#SkCanvas_SaveLayerRec_SaveLayerRec">SaveLayerRec</a>*(... @@ -2732,7 +2737,7 @@ graphics state used to fill <a href="#Canvas">Canvas</a></td> ## <a name="SkCanvas_PointMode"></a> Enum SkCanvas::PointMode -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkCanvas_PointMode">PointMode</a> { <a href="#SkCanvas_kPoints_PointMode">kPoints PointMode</a>, <a href="#SkCanvas_kLines_PointMode">kLines PointMode</a>, @@ -3389,7 +3394,7 @@ and so on; or nullptr</td> ## <a name="SkCanvas_SrcRectConstraint"></a> Enum SkCanvas::SrcRectConstraint -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkCanvas_SrcRectConstraint">SrcRectConstraint</a> { <a href="#SkCanvas_kStrict_SrcRectConstraint">kStrict SrcRectConstraint</a>, <a href="#SkCanvas_kFast_SrcRectConstraint">kFast SrcRectConstraint</a>, @@ -4007,15 +4012,8 @@ and below <a href="#SkCanvas_drawBitmapNine_center">center</a> to fill the remai --- # <a name="SkCanvas_Lattice"></a> Struct SkCanvas::Lattice -<a href="#SkCanvas_Lattice">Lattice</a> divides <a href="SkBitmap_Reference#Bitmap">Bitmap</a> or <a href="undocumented#Image">Image</a> into a rectangular grid. -Grid entries on even columns and even rows are fixed; these entries are -always drawn at their original size if the destination is large enough. -If the destination side is too small to hold the fixed entries, all fixed -entries are proportionately scaled down to fit. -The grid entries not on even columns and rows are scaled to fit the -remaining space, if any. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> struct <a href="#SkCanvas_Lattice">Lattice</a> { enum <a href="#SkCanvas_Lattice_Flags">Flags</a> {... @@ -4027,9 +4025,17 @@ int <a href="#SkCanvas_Lattice_fYCount">fYCount</a>; const <a href="SkIRect_Reference#SkIRect">SkIRect</a>* <a href="#SkCanvas_Lattice_fBounds">fBounds</a>; };</pre> +<a href="#SkCanvas_Lattice">Lattice</a> divides <a href="SkBitmap_Reference#Bitmap">Bitmap</a> or <a href="undocumented#Image">Image</a> into a rectangular grid. +Grid entries on even columns and even rows are fixed; these entries are +always drawn at their original size if the destination is large enough. +If the destination side is too small to hold the fixed entries, all fixed +entries are proportionately scaled down to fit. +The grid entries not on even columns and rows are scaled to fit the +remaining space, if any. + ## <a name="SkCanvas_Lattice_Flags"></a> Enum SkCanvas::Lattice::Flags -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkCanvas_Lattice_Flags">Flags</a> : uint8_t { <a href="#SkCanvas_Lattice_kTransparent_Flags">kTransparent Flags</a> = 1 << 0, };</pre> @@ -5306,8 +5312,8 @@ Restores <a href="#Canvas">Canvas</a> to saved state. void restore() </pre> -Restores <a href="#Canvas">Canvas</a> to saved state immediately. Subsequent calls and class -destructor have no effect. +Restores <a href="#Canvas">Canvas</a> to saved state immediately. Subsequent calls and +<a href="#SkAutoCanvasRestore_destructor">~SkAutoCanvasRestore</a> have no effect. ### Example diff --git a/site/user/api/SkIRect_Reference.md b/site/user/api/SkIRect_Reference.md index 1982c5094d..7022cc6aec 100644 --- a/site/user/api/SkIRect_Reference.md +++ b/site/user/api/SkIRect_Reference.md @@ -34,7 +34,7 @@ its <a href="#SkIRect_top">top</a>, it is considered empty. | <a href="#SkIRect_MakeEmpty">MakeEmpty</a> | Returns bounds of (0, 0, 0, 0). | | <a href="#SkIRect_MakeLTRB">MakeLTRB</a> | Constructs from int <a href="#SkIRect_left">left</a>, <a href="#SkIRect_top">top</a>, <a href="#SkIRect_right">right</a>, <a href="#SkIRect_bottom">bottom</a>. | | <a href="#SkIRect_MakeLargest">MakeLargest</a> | Constructs from (<a href="undocumented#SK_MinS32">SK MinS32</a>, <a href="undocumented#SK_MinS32">SK MinS32</a>, <a href="undocumented#SK_MaxS32">SK MaxS32</a>, <a href="undocumented#SK_MaxS32">SK MaxS32</a>). | -| <a href="#SkIRect_MakeSize">MakeSize</a> | Constructs from <a href="#Size">ISize</a> returning (0, 0, <a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | +| <a href="#SkIRect_MakeSize">MakeSize</a> | Constructs from <a href="undocumented#ISize">ISize</a> returning (0, 0, <a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | | <a href="#SkIRect_MakeWH">MakeWH</a> | Constructs from int input returning (0, 0, <a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | | <a href="#SkIRect_MakeXYWH">MakeXYWH</a> | Constructs from int input returning (<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | | <a href="#SkIRect_bottom">bottom</a> | Returns larger bounds in <a href="#SkIRect_y">y</a>, if sorted. | @@ -66,7 +66,7 @@ its <a href="#SkIRect_top">top</a>, it is considered empty. | <a href="#SkIRect_setLargest">setLargest</a> | Sets to (<a href="undocumented#SK_MinS32">SK MinS32</a>, <a href="undocumented#SK_MinS32">SK MinS32</a>, <a href="undocumented#SK_MaxS32">SK MaxS32</a>, <a href="undocumented#SK_MaxS32">SK MaxS32</a>). | | <a href="#SkIRect_setLargestInverted">setLargestInverted</a> | Sets to (<a href="undocumented#SK_MaxS32">SK MaxS32</a>, <a href="undocumented#SK_MaxS32">SK MaxS32</a>, <a href="undocumented#SK_MinS32">SK MinS32</a>, <a href="undocumented#SK_MinS32">SK MinS32</a>). | | <a href="#SkIRect_setXYWH">setXYWH</a> | Sets to (<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | -| <a href="#SkIRect_size">size</a> | Returns <a href="#Size">ISize</a> (<a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | +| <a href="#SkIRect_size">size</a> | Returns <a href="undocumented#ISize">ISize</a> (<a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>). | | <a href="#SkIRect_sort">sort</a> | Orders sides from smaller to larger. | | <a href="#SkIRect_top">top</a> | Returns smaller bounds in <a href="#SkIRect_y">y</a>, if sorted. | | <a href="#SkIRect_width">width</a> | Returns span in <a href="#SkIRect_x">x</a>. | @@ -301,7 +301,8 @@ static constexpr SkIRect SK_WARN_UNUSED_RESULT MakeXYWH(int32_t x, int32_t y, int32_t w, int32_t h) </pre> -Returns constructed <a href="#IRect">IRect</a> <a href="#SkIRect_set">set</a> to(<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_x">x</a> + <a href="#SkIRect_MakeXYWH_w">w</a>, <a href="#SkIRect_y">y</a> + <a href="#SkIRect_MakeXYWH_h">h</a>). +Returns constructed <a href="#IRect">IRect</a> <a href="#SkIRect_set">set</a> to: +(<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_x">x</a> + <a href="#SkIRect_MakeXYWH_w">w</a>, <a href="#SkIRect_y">y</a> + <a href="#SkIRect_MakeXYWH_h">h</a>). Does not validate input; <a href="#SkIRect_MakeXYWH_w">w</a> or <a href="#SkIRect_MakeXYWH_h">h</a> may be negative. @@ -617,7 +618,7 @@ or if result fits in 32-bit signed integer; result may be negative. ### Return Value -<a href="#Size">ISize</a> (<a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>) +<a href="undocumented#ISize">ISize</a> (<a href="#SkIRect_width">width</a>, <a href="#SkIRect_height">height</a>) ### Example @@ -1019,7 +1020,8 @@ rect2: {3, 4, 1, 2} void setXYWH(int32_t x, int32_t y, int32_t width, int32_t height) </pre> -Sets <a href="#IRect">IRect</a> to(<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_x">x</a> + <a href="#SkIRect_width">width</a>, <a href="#SkIRect_y">y</a> + <a href="#SkIRect_height">height</a>). +Sets <a href="#IRect">IRect</a> to: +(<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_x">x</a> + <a href="#SkIRect_width">width</a>, <a href="#SkIRect_y">y</a> + <a href="#SkIRect_height">height</a>). Does not validate input; <a href="#SkIRect_width">width</a> or <a href="#SkIRect_height">height</a> may be negative. @@ -1495,11 +1497,13 @@ rect (7, 11, 13, 17) test(12, 16, 14, 18) quickReject false; intersects true bool contains(int32_t x, int32_t y) const </pre> -Returns true if<a href="#SkIRect_fLeft">fLeft</a> <= <a href="#SkIRect_x">x</a> < <a href="#SkIRect_fRight">fRight</a> && <a href="#SkIRect_fTop">fTop</a> <= <a href="#SkIRect_y">y</a> < <a href="#SkIRect_fBottom">fBottom</a>. +Returns true if: +<a href="#SkIRect_fLeft">fLeft</a> <= <a href="#SkIRect_x">x</a> < <a href="#SkIRect_fRight">fRight</a> && <a href="#SkIRect_fTop">fTop</a> <= <a href="#SkIRect_y">y</a> < <a href="#SkIRect_fBottom">fBottom</a>. Returns false if <a href="SkRect_Reference#Rect">Rect</a> is empty. -Considers input to describe constructed <a href="#IRect">IRect</a> (<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_x">x</a> + 1, <a href="#SkIRect_y">y</a> + 1) and +Considers input to describe constructed <a href="#IRect">IRect</a>: +(<a href="#SkIRect_x">x</a>, <a href="#SkIRect_y">y</a>, <a href="#SkIRect_x">x</a> + 1, <a href="#SkIRect_y">y</a> + 1)and returns true if constructed area is completely enclosed by <a href="#IRect">IRect</a> area. ### Parameters @@ -1758,7 +1762,7 @@ rect: (30, 50, 40, 60) does not contain (29, 59, 30, 60) # <a name="Intersection"></a> Intersection IRects <a href="#SkIRect_intersect">intersect</a> when they enclose a common area. To <a href="#SkIRect_intersect">intersect</a>, each of the pair must describe area; <a href="#SkIRect_fLeft">fLeft</a> is less than <a href="#SkIRect_fRight">fRight</a>, and <a href="#SkIRect_fTop">fTop</a> is less than <a href="#SkIRect_fBottom">fBottom</a>; -empty() returns false. The intersection of <a href="#IRect">IRect</a> a and <a href="#IRect">IRect</a> b can be described by: +empty() returns false. The intersection of <a href="#IRect">IRect</a> pair can be described by: (max(a.fLeft, b.fLeft), max(a.fTop, b.fTop), min(a.fRight, b.fRight), min(a.fBottom, b.fBottom))The intersection is only meaningful if the resulting <a href="#IRect">IRect</a> is not empty and describes an area: <a href="#SkIRect_fLeft">fLeft</a> is less than <a href="#SkIRect_fRight">fRight</a>, and <a href="#SkIRect_fTop">fTop</a> is less than <a href="#SkIRect_fBottom">fBottom</a>. diff --git a/site/user/api/SkMatrix_Reference.md b/site/user/api/SkMatrix_Reference.md new file mode 100644 index 0000000000..46cca59545 --- /dev/null +++ b/site/user/api/SkMatrix_Reference.md @@ -0,0 +1,4459 @@ +SkMatrix Reference +=== + +# <a name="Matrix"></a> Matrix + +# <a name="SkMatrix"></a> Class SkMatrix +<a href="#Matrix">Matrix</a> holds a 3x3 matrix for transforming coordinates. This allows mapping +<a href="#Point">Points</a> and <a href="#Vector">Vectors</a> with translation, scaling, skewing, rotation, and +perspective. + +<a href="#Matrix">Matrix</a> elements are in row major order. <a href="#Matrix">Matrix</a> does not have a constructor, +so it must be explicitly initialized. <a href="#SkMatrix_setIdentity">setIdentity</a> initializes <a href="#Matrix">Matrix</a> +so it has no effect. <a href="#SkMatrix_setTranslate">setTranslate</a>, <a href="#SkMatrix_setScale">setScale</a>, <a href="#SkMatrix_setSkew">setSkew</a>, <a href="#SkMatrix_setRotate">setRotate</a>, <a href="#SkMatrix_set9">set9</a> and <a href="#SkMatrix_setAll">setAll</a> +initializes all <a href="#Matrix">Matrix</a> elements with the corresponding mapping. + +<a href="#Matrix">Matrix</a> includes a hidden variable that classifies the type of matrix to +improve performance. <a href="#Matrix">Matrix</a> is not thread safe unless <a href="#SkMatrix_getType">getType</a> is called first. + +# <a name="Overview"></a> Overview + +## <a name="Subtopics"></a> Subtopics + +| topics | description | +| --- | --- | + +## <a name="Operators"></a> Operators + +| function | description | +| --- | --- | +| <a href="#SkMatrix_not_equal_operator">operator!=(const SkMatrix& a, const SkMatrix& b)</a> | Returns true if members are unequal. | +| <a href="#SkMatrix_equal_operator">operator==(const SkMatrix& a, const SkMatrix& b)</a> | Returns true if members are equal. | +| <a href="#SkMatrix_subscript_operator_const">operator[](int index)</a> const | Returns <a href="#Matrix">Matrix</a> value. | +| <a href="#SkMatrix_subscript_operator_const">operator[](int index)</a> | Returns writable reference to <a href="#Matrix">Matrix</a> value. | + +## <a name="Member_Functions"></a> Member Functions + +| function | description | +| --- | --- | +| <a href="#SkMatrix_Concat">Concat</a> | Returns the concatenation of <a href="#Matrix">Matrix</a> pair. | +| <a href="#SkMatrix_I">I</a> | Returns a reference to a const identity <a href="#Matrix">Matrix</a>. | +| <a href="#SkMatrix_InvalidMatrix">InvalidMatrix</a> | Returns a reference to a const invalid <a href="#Matrix">Matrix</a>. | +| <a href="#SkMatrix_MakeRectToRect">MakeRectToRect</a> | Constructs from source <a href="SkRect_Reference#Rect">Rect</a> to destination <a href="SkRect_Reference#Rect">Rect</a>. | +| <a href="#SkMatrix_MakeScale">MakeScale</a> | Constructs from scale in x and y. | +| <a href="#SkMatrix_MakeTrans">MakeTrans</a> | Constructs from translate in x and y. | +| <a href="#SkMatrix_SetAffineIdentity">SetAffineIdentity</a> | Sets 3x2 array to identity. | +| <a href="#SkMatrix_asAffine">asAffine</a> | Copies to 3x2 array. | +| <a href="#SkMatrix_cheapEqualTo">cheapEqualTo</a> | Compares <a href="#Matrix">Matrix</a> pair using memcmp(). | +| <a href="#SkMatrix_decomposeScale">decomposeScale</a> | Separates scale if possible. | +| <a href="#SkMatrix_dirtyMatrixTypeCache">dirtyMatrixTypeCache</a> | Sets internal cache to unknown state. | +| <a href="#SkMatrix_dump">dump</a> | Sends text representation using floats to standard output. | +| <a href="#SkMatrix_fixedStepInX">fixedStepInX</a> | Returns step in x for a position in y. | +| <a href="#SkMatrix_get">get</a> | Returns one of nine <a href="#Matrix">Matrix</a> values. | +| <a href="#SkMatrix_get9">get9</a> | Returns all nine <a href="#Matrix">Matrix</a> values. | +| <a href="#SkMatrix_getMaxScale">getMaxScale</a> | Returns maximum scaling, if possible. | +| <a href="#SkMatrix_getMinMaxScales">getMinMaxScales</a> | Returns minimum and maximum scaling, if possible. | +| <a href="#SkMatrix_getMinScale">getMinScale</a> | Returns minimum scaling, if possible. | +| <a href="#SkMatrix_getPerspX">getPerspX</a> | Returns input x perspective factor. | +| <a href="#SkMatrix_getPerspY">getPerspY</a> | Returns input y perspective factor. | +| <a href="#SkMatrix_getScaleX">getScaleX</a> | Returns horizontal scale factor. | +| <a href="#SkMatrix_getScaleY">getScaleY</a> | Returns vertical scale factor. | +| <a href="#SkMatrix_getSkewX">getSkewX</a> | Returns horizontal skew factor. | +| <a href="#SkMatrix_getSkewY">getSkewY</a> | Returns vertical skew factor. | +| <a href="#SkMatrix_getTranslateX">getTranslateX</a> | Returns horizontal translation. | +| <a href="#SkMatrix_getTranslateY">getTranslateY</a> | Returns vertical translation. | +| <a href="#SkMatrix_getType">getType</a> | Returns transform complexity. | +| <a href="#SkMatrix_hasPerspective">hasPerspective</a> | Returns if transform includes perspective. | +| <a href="#SkMatrix_invert">invert</a> | Returns inverse, if possible. | +| <a href="#SkMatrix_isFinite">isFinite</a> | Returns if all <a href="#Matrix">Matrix</a> values are not infinity, <a href="undocumented#NaN">NaN</a>. | +| <a href="#SkMatrix_isFixedStepInX">isFixedStepInX</a> | Returns if transformation supports fixed step in x. | +| <a href="#SkMatrix_isIdentity">isIdentity</a> | Returns if matrix equals the identity <a href="#Matrix">Matrix</a> . | +| <a href="#SkMatrix_isScaleTranslate">isScaleTranslate</a> | Returns if transform is limited to scale and translate. | +| <a href="#SkMatrix_isSimilarity">isSimilarity</a> | Returns if transform is limited to square scale and rotation. | +| <a href="#SkMatrix_isTranslate">isTranslate</a> | Returns if transform is limited to translate. | +| <a href="#SkMatrix_mapHomogeneousPoints">mapHomogeneousPoints</a> | Maps <a href="undocumented#Point3">Point3</a> array. | +| <a href="#SkMatrix_mapPoints">mapPoints</a> | Maps <a href="undocumented#Point">Point</a> array. | +| <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> | Maps <a href="undocumented#Point">Point</a> array with padding. | +| <a href="#SkMatrix_mapRadius">mapRadius</a> | Returns mean radius of mapped <a href="undocumented#Circle">Circle</a>. | +| <a href="#SkMatrix_mapRect">mapRect</a> | Returns bounds of mapped <a href="SkRect_Reference#Rect">Rect</a>. | +| <a href="#SkMatrix_mapRectScaleTranslate">mapRectScaleTranslate</a> | Returns bounds of mapped <a href="SkRect_Reference#Rect">Rect</a>. | +| <a href="#SkMatrix_mapRectToQuad">mapRectToQuad</a> | Maps <a href="SkRect_Reference#Rect">Rect</a> to <a href="undocumented#Point">Point</a> array. | +| <a href="#SkMatrix_mapVector">mapVector</a> | Maps <a href="undocumented#Vector">Vector</a>. | +| <a href="#SkMatrix_mapVectors">mapVectors</a> | Maps <a href="undocumented#Vector">Vector</a> array. | +| <a href="#SkMatrix_mapXY">mapXY</a> | Maps <a href="undocumented#Point">Point</a>. | +| <a href="#SkMatrix_postConcat">postConcat</a> | Post-multiplies <a href="#Matrix">Matrix</a> by <a href="#Matrix">Matrix</a> parameter. | +| <a href="#SkMatrix_postIDiv">postIDiv</a> | Post-multiplies <a href="#Matrix">Matrix</a> by inverse scale. | +| <a href="#SkMatrix_postRotate">postRotate</a> | Post-multiplies <a href="#Matrix">Matrix</a> by rotation. | +| <a href="#SkMatrix_postScale">postScale</a> | Post-multiplies <a href="#Matrix">Matrix</a> by scale. | +| <a href="#SkMatrix_postSkew">postSkew</a> | Post-multiplies <a href="#Matrix">Matrix</a> by skew. | +| <a href="#SkMatrix_postTranslate">postTranslate</a> | Post-multiplies <a href="#Matrix">Matrix</a> by translation. | +| <a href="#SkMatrix_preConcat">preConcat</a> | Pre-multiplies <a href="#Matrix">Matrix</a> by <a href="#Matrix">Matrix</a> parameter. | +| <a href="#SkMatrix_preRotate">preRotate</a> | Pre-multiplies <a href="#Matrix">Matrix</a> by rotation. | +| <a href="#SkMatrix_preScale">preScale</a> | Pre-multiplies <a href="#Matrix">Matrix</a> by scale. | +| <a href="#SkMatrix_preSkew">preSkew</a> | Pre-multiplies <a href="#Matrix">Matrix</a> by skew. | +| <a href="#SkMatrix_preTranslate">preTranslate</a> | Pre-multiplies <a href="#Matrix">Matrix</a> by translation. | +| <a href="#SkMatrix_preservesAxisAlignment">preservesAxisAlignment</a> | Returns if mapping restricts to 90 degree multiples and mirroring. | +| <a href="#SkMatrix_preservesRightAngles">preservesRightAngles</a> | Returns if mapped 90 angle remains 90 degrees. | +| <a href="#SkMatrix_rectStaysRect">rectStaysRect</a> | Returns if mapped <a href="SkRect_Reference#Rect">Rect</a> can be represented by another <a href="SkRect_Reference#Rect">Rect</a>. | +| <a href="#SkMatrix_reset">reset</a> | Sets <a href="#Matrix">Matrix</a> to identity. | +| <a href="#SkMatrix_set">set</a> | Sets one value. | +| <a href="#SkMatrix_set9">set9</a> | Sets all values from <a href="#Scalar">Scalar</a> array. | +| <a href="#SkMatrix_setAffine">setAffine</a> | Sets left two columns. | +| <a href="#SkMatrix_setAll">setAll</a> | Sets all values from parameters. | +| <a href="#SkMatrix_setConcat">setConcat</a> | Sets to <a href="#Matrix">Matrix</a> parameter multiplied by <a href="#Matrix">Matrix</a> parameter. | +| <a href="#SkMatrix_setIdentity">setIdentity</a> | Sets <a href="#Matrix">Matrix</a> to identity. | +| <a href="#SkMatrix_setPerspX">setPerspX</a> | Sets input x perspective factor. | +| <a href="#SkMatrix_setPerspY">setPerspY</a> | Sets input y perspective factor. | +| <a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> | Sets to map one to four points to an equal array of points. | +| <a href="#SkMatrix_setRSXform">setRSXform</a> | Sets to rotate, scale, and translate. | +| <a href="#SkMatrix_setRectToRect">setRectToRect</a> | Sets to map one <a href="SkRect_Reference#Rect">Rect</a> to another. | +| <a href="#SkMatrix_setRotate">setRotate</a> | Sets to rotate about a point. | +| <a href="#SkMatrix_setScale">setScale</a> | Sets to scale about a point. | +| <a href="#SkMatrix_setScaleTranslate">setScaleTranslate</a> | Sets to scale and translate. | +| <a href="#SkMatrix_setScaleX">setScaleX</a> | Sets horizontal scale factor. | +| <a href="#SkMatrix_setScaleY">setScaleY</a> | Sets vertical scale factor | +| <a href="#SkMatrix_setSinCos">setSinCos</a> | Sets to rotate and scale about a point. | +| <a href="#SkMatrix_setSkew">setSkew</a> | Sets to skew about a point. | +| <a href="#SkMatrix_setSkewX">setSkewX</a> | Sets horizontal skew factor. | +| <a href="#SkMatrix_setSkewY">setSkewY</a> | Sets vertical skew factor. | +| <a href="#SkMatrix_setTranslate">setTranslate</a> | Sets to translate in x and y. | +| <a href="#SkMatrix_setTranslateX">setTranslateX</a> | Sets horizontal translation. | +| <a href="#SkMatrix_setTranslateY">setTranslateY</a> | Sets vertical translation. | +| <a href="#SkMatrix_toString">toString</a> | Converts <a href="#Matrix">Matrix</a> to machine readable form. | + +<a name="SkMatrix_MakeScale"></a> +## MakeScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static SkMatrix SK_WARN_UNUSED_RESULT MakeScale(SkScalar sx, SkScalar sy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to scale by (<a href="#SkMatrix_MakeScale_sx">sx</a>, <a href="#SkMatrix_MakeScale_sy">sy</a>). Returned matrix is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| sx 0 0 | +| 0 sy 0 | +| 0 0 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_MakeScale_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_MakeScale_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> +</table> + +### Return Value + +<a href="#Matrix">Matrix</a> with scale + +### Example + +<div><fiddle-embed name="7ff17718111df6d6f95381d8a8f1b389"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_postScale">postScale</a> <a href="#SkMatrix_preScale">preScale</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static SkMatrix SK_WARN_UNUSED_RESULT MakeScale(SkScalar scale) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#SkMatrix_MakeScale_2_scale">scale</a> by (<a href="#SkMatrix_MakeScale_2_scale">scale</a>, <a href="#SkMatrix_MakeScale_2_scale">scale</a>). Returned matrix is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale 0 0 | +| 0 scale 0 | +| 0 0 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_MakeScale_2_scale"> <code><strong>scale </strong></code> </a></td> <td> +horizontal and vertical <a href="#SkMatrix_MakeScale_2_scale">scale</a> factor</td> + </tr> +</table> + +### Return Value + +<a href="#Matrix">Matrix</a> with <a href="#SkMatrix_MakeScale_2_scale">scale</a> + +### Example + +<div><fiddle-embed name="2956aeb50fa862cdb13995e1e56a4bc8"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_postScale">postScale</a> <a href="#SkMatrix_preScale">preScale</a> + +--- + +<a name="SkMatrix_MakeTrans"></a> +## MakeTrans + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static SkMatrix SK_WARN_UNUSED_RESULT MakeTrans(SkScalar dx, SkScalar dy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to translate by (<a href="#SkMatrix_MakeTrans_dx">dx</a>, <a href="#SkMatrix_MakeTrans_dy">dy</a>). Returned matrix is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 0 | +| 0 1 0 | +| dx dy 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_MakeTrans_dx"> <code><strong>dx </strong></code> </a></td> <td> +horizontal translation</td> + </tr> <tr> <td><a name="SkMatrix_MakeTrans_dy"> <code><strong>dy </strong></code> </a></td> <td> +vertical translation</td> + </tr> +</table> + +### Return Value + +<a href="#Matrix">Matrix</a> with translation + +### Example + +<div><fiddle-embed name="b2479df0d9cf296ff64ac31e36684557"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_postTranslate">postTranslate</a> <a href="#SkMatrix_preTranslate">preTranslate</a> + +--- + +## <a name="SkMatrix_TypeMask"></a> Enum SkMatrix::TypeMask + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +enum <a href="#SkMatrix_TypeMask">TypeMask</a> { +<a href="#SkMatrix_kIdentity_Mask">kIdentity Mask</a> = 0, +<a href="#SkMatrix_kTranslate_Mask">kTranslate Mask</a> = 0x01, +<a href="#SkMatrix_kScale_Mask">kScale Mask</a> = 0x02, +<a href="#SkMatrix_kAffine_Mask">kAffine Mask</a> = 0x04, +<a href="#SkMatrix_kPerspective_Mask">kPerspective Mask</a> = 0x08, +};</pre> + +Enum of bit fields for mask returned by <a href="#SkMatrix_getType">getType</a>. +Used to identify the complexity of <a href="#Matrix">Matrix</a>, to optimize performance. + +### Constants + +<table> + <tr> + <td><a name="SkMatrix_kIdentity_Mask"> <code><strong>SkMatrix::kIdentity_Mask </strong></code> </a></td><td>0</td><td>all bits clear if <a href="#Matrix">Matrix</a> is identity</td> + </tr> + <tr> + <td><a name="SkMatrix_kTranslate_Mask"> <code><strong>SkMatrix::kTranslate_Mask </strong></code> </a></td><td>1</td><td><a href="#SkMatrix_set">set</a> if <a href="#Matrix">Matrix</a> has translation</td> + </tr> + <tr> + <td><a name="SkMatrix_kScale_Mask"> <code><strong>SkMatrix::kScale_Mask </strong></code> </a></td><td>2</td><td><a href="#SkMatrix_set">set</a> if <a href="#Matrix">Matrix</a> has x or y scale</td> + </tr> + <tr> + <td><a name="SkMatrix_kAffine_Mask"> <code><strong>SkMatrix::kAffine_Mask </strong></code> </a></td><td>4</td><td><a href="#SkMatrix_set">set</a> if <a href="#Matrix">Matrix</a> skews or rotates</td> + </tr> + <tr> + <td><a name="SkMatrix_kPerspective_Mask"> <code><strong>SkMatrix::kPerspective_Mask </strong></code> </a></td><td>8</td><td><a href="#SkMatrix_set">set</a> if <a href="#Matrix">Matrix</a> has perspective</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="ba19b36df8cd78586f3dff54e2d4c093"> + +#### Example Output + +~~~~ +after reset: kIdentity_Mask +after postTranslate: kTranslate_Mask +after postScale: kTranslate_Mask kScale_Mask +after postScale: kTranslate_Mask kScale_Mask kAffine_Mask +after setPolyToPoly: kTranslate_Mask kScale_Mask kAffine_Mask kPerspective_Mask +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_getType">getType</a> + + + +<a name="SkMatrix_getType"></a> +## getType + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +TypeMask getType() const +</pre> + +Returns a bit field describing the transformations the matrix may +perform. The bit field is computed conservatively, so it may include +false positives. For example, when <a href="#SkMatrix_kPerspective_Mask">kPerspective Mask</a> is <a href="#SkMatrix_set">set</a>, all +other bits are <a href="#SkMatrix_set">set</a>. + +### Return Value + +<a href="#SkMatrix_kIdentity_Mask">kIdentity Mask</a>, or combinations of: <a href="#SkMatrix_kTranslate_Mask">kTranslate Mask</a>, <a href="#SkMatrix_kScale_Mask">kScale Mask</a>, +<a href="#SkMatrix_kAffine_Mask">kAffine Mask</a>, <a href="#SkMatrix_kPerspective_Mask">kPerspective Mask</a> + +### Example + +<div><fiddle-embed name="8e45fe2dd52731bb2d4318686257e1d7"> + +#### Example Output + +~~~~ +identity flags hex: 0 decimal: 0 +set all flags hex: f decimal: 15 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_TypeMask">TypeMask</a> + +--- + +<a name="SkMatrix_isIdentity"></a> +## isIdentity + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool isIdentity() const +</pre> + +Returns true if <a href="#Matrix">Matrix</a> is identity. Identity matrix is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 0 | +| 0 1 0 | +| 0 0 1 |</pre> + +### Return Value + +true if <a href="#Matrix">Matrix</a> has no effect + +### Example + +<div><fiddle-embed name="780ab376325b3cfa889ea26c0769ec11"> + +#### Example Output + +~~~~ +is identity: true +is identity: false +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_reset">reset</a> <a href="#SkMatrix_setIdentity">setIdentity</a> <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_isScaleTranslate"></a> +## isScaleTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool isScaleTranslate() const +</pre> + +Returns true if <a href="#Matrix">Matrix</a> at most scales and translates. <a href="#Matrix">Matrix</a> may be identity, +contain only scale elements, only translate elements, or both. <a href="#Matrix">Matrix</a> form is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale-x 0 translate-x | +| 0 scale-y translate-y | +| 0 0 1 |</pre> + +### Return Value + +true if <a href="#Matrix">Matrix</a> is identity; or scales, translates, or both + +### Example + +<div><fiddle-embed name="6287e29674a487eb94174992d45b9a34"> + +#### Example Output + +~~~~ +is scale-translate: true +is scale-translate: true +is scale-translate: true +is scale-translate: true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_isTranslate">isTranslate</a> <a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_isTranslate"></a> +## isTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool isTranslate() const +</pre> + +Returns true if <a href="#Matrix">Matrix</a> is identity, or translates. <a href="#Matrix">Matrix</a> form is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 translate-x | +| 0 1 translate-y | +| 0 0 1 |</pre> + +### Return Value + +true if <a href="#Matrix">Matrix</a> is identity, or translates + +### Example + +<div><fiddle-embed name="73ac71a8a30841873577c11c6c9b38ee"> + +#### Example Output + +~~~~ +is translate: true +is translate: true +is translate: false +is translate: false +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_rectStaysRect"></a> +## rectStaysRect + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool rectStaysRect() const +</pre> + +Returns true <a href="#Matrix">Matrix</a> maps <a href="SkRect_Reference#Rect">Rect</a> to another <a href="SkRect_Reference#Rect">Rect</a>. If true, <a href="#Matrix">Matrix</a> is identity, +or scales, or rotates a multiple of 90 degrees, or mirrors in x or y. In all +cases, <a href="#Matrix">Matrix</a> may also have translation. <a href="#Matrix">Matrix</a> form is either: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale-x 0 translate-x | +| 0 scale-y translate-y | +| 0 0 1 |</pre> + +or + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 0 rotate-x translate-x | +| rotate-y 0 translate-y | +| 0 0 1 |</pre> + +for non-zero values of scale-x, scale-y, rotate-x, and rotate-y. + +Also called <a href="#SkMatrix_preservesAxisAlignment">preservesAxisAlignment</a>; use the one that provides better inline +documentation. + +### Return Value + +true if <a href="#Matrix">Matrix</a> maps one <a href="SkRect_Reference#Rect">Rect</a> into another + +### Example + +<div><fiddle-embed name="ce5319c036c9b5086da8a0009fe409f8"> + +#### Example Output + +~~~~ +rectStaysRect: true +rectStaysRect: true +rectStaysRect: true +rectStaysRect: true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preservesAxisAlignment">preservesAxisAlignment</a> <a href="#SkMatrix_preservesRightAngles">preservesRightAngles</a> + +--- + +<a name="SkMatrix_preservesAxisAlignment"></a> +## preservesAxisAlignment + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool preservesAxisAlignment() const +</pre> + +Returns true <a href="#Matrix">Matrix</a> maps <a href="SkRect_Reference#Rect">Rect</a> to another <a href="SkRect_Reference#Rect">Rect</a>. If true, <a href="#Matrix">Matrix</a> is identity, +or scales, or rotates a multiple of 90 degrees, or mirrors in x or y. In all +cases, <a href="#Matrix">Matrix</a> may also have translation. <a href="#Matrix">Matrix</a> form is either: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale-x 0 translate-x | +| 0 scale-y translate-y | +| 0 0 1 |</pre> + +or + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 0 rotate-x translate-x | +| rotate-y 0 translate-y | +| 0 0 1 |</pre> + +for non-zero values of scale-x, scale-y, rotate-x, and rotate-y. + +Also called <a href="#SkMatrix_rectStaysRect">rectStaysRect</a>; use the one that provides better inline +documentation. + +### Return Value + +true if <a href="#Matrix">Matrix</a> maps one <a href="SkRect_Reference#Rect">Rect</a> into another + +### Example + +<div><fiddle-embed name="7a234c96608fb7cb8135b9940b0b15f7"> + +#### Example Output + +~~~~ +preservesAxisAlignment: true +preservesAxisAlignment: true +preservesAxisAlignment: true +preservesAxisAlignment: true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_rectStaysRect">rectStaysRect</a> <a href="#SkMatrix_preservesRightAngles">preservesRightAngles</a> + +--- + +<a name="SkMatrix_hasPerspective"></a> +## hasPerspective + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool hasPerspective() const +</pre> + +Returns true if the matrix contains perspective elements. <a href="#Matrix">Matrix</a> form is: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| -- -- -- | +| -- -- -- | +| perspective-x perspective-y perspective-scale |</pre> + +where perspective-x or perspective-y is non-zero, or perspective-scale is +not one. All other elements may have any value. + +### Return Value + +true if <a href="#Matrix">Matrix</a> is in most general form + +### Example + +<div><fiddle-embed name="688123908c733169bbbfaf11f41ecff6"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setAll">setAll</a> <a href="#SkMatrix_set9">set9</a> + +--- + +<a name="SkMatrix_isSimilarity"></a> +## isSimilarity + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool isSimilarity(SkScalar tol = SK_ScalarNearlyZero) const +</pre> + +Returns true if <a href="#Matrix">Matrix</a> contains only translation, rotation, reflection, and +uniform scale. +Returns false if <a href="#Matrix">Matrix</a> contains different scales, skewing, perspective, or +degenerate forms that collapse to a line or point. + +Describes that the <a href="#Matrix">Matrix</a> makes rendering with and without the matrix are +visually alike; a transformed circle remains a circle. Mathematically, this is +referred to as similarity of a <a href="undocumented#Euclidean">Euclidean</a> space, or a similarity transformation. + +Preserves right angles, keeping the arms of the angle equal lengths. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_isSimilarity_tol"> <code><strong>tol </strong></code> </a></td> <td> +to be deprecated</td> + </tr> +</table> + +### Return Value + +true if <a href="#Matrix">Matrix</a> only rotates, uniformly scales, translates + +### Example + +<div><fiddle-embed name="98d60230ad633ae74d851de3a65d72d6"><div><a href="undocumented#String">String</a> is drawn four times through but only two are visible. Drawing the pair +with <a href="#SkMatrix_isSimilarity">isSimilarity</a> false reveals the pair not visible through the matrix.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_isScaleTranslate">isScaleTranslate</a> <a href="#SkMatrix_preservesRightAngles">preservesRightAngles</a> <a href="#SkMatrix_rectStaysRect">rectStaysRect</a> <a href="#SkMatrix_isFixedStepInX">isFixedStepInX</a> + +--- + +<a name="SkMatrix_preservesRightAngles"></a> +## preservesRightAngles + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool preservesRightAngles(SkScalar tol = SK_ScalarNearlyZero) const +</pre> + +Returns true if <a href="#Matrix">Matrix</a> contains only translation, rotation, reflection, and +scale. Scale may differ along rotated axes. +Returns false if <a href="#Matrix">Matrix</a> skewing, perspective, or degenerate forms that collapse +to a line or point. + +Preserves right angles, but not requiring that the arms of the angle +retain equal lengths. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preservesRightAngles_tol"> <code><strong>tol </strong></code> </a></td> <td> +to be deprecated</td> + </tr> +</table> + +### Return Value + +true if <a href="#Matrix">Matrix</a> only rotates, scales, translates + +### Example + +<div><fiddle-embed name="a3d5bfebc1c3423fb983d30aaf4ac5f4"><div>Equal scale is both similar and preserves right angles. +Unequal scale is not similar but preserves right angles. +Skews are not similar and do not preserve right angles.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_isScaleTranslate">isScaleTranslate</a> <a href="#SkMatrix_isSimilarity">isSimilarity</a> <a href="#SkMatrix_rectStaysRect">rectStaysRect</a> <a href="#SkMatrix_isFixedStepInX">isFixedStepInX</a> + +--- + +## <a name="SkMatrix__anonymous"></a> Enum SkMatrix::_anonymous + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +enum { +<a href="#SkMatrix_kMScaleX">kMScaleX</a>, +<a href="#SkMatrix_kMSkewX">kMSkewX</a>, +<a href="#SkMatrix_kMTransX">kMTransX</a>, +<a href="#SkMatrix_kMSkewY">kMSkewY</a>, +<a href="#SkMatrix_kMScaleY">kMScaleY</a>, +<a href="#SkMatrix_kMTransY">kMTransY</a>, +<a href="#SkMatrix_kMPersp0">kMPersp0</a>, +<a href="#SkMatrix_kMPersp1">kMPersp1</a>, +<a href="#SkMatrix_kMPersp2">kMPersp2</a>, +};</pre> + +<a href="#Matrix">Matrix</a> organizes its values in row order. These members correspond to +each value in <a href="#Matrix">Matrix</a>. + +### Constants + +<table> + <tr> + <td><a name="SkMatrix_kMScaleX"> <code><strong>SkMatrix::kMScaleX </strong></code> </a></td><td>0</td><td>horizontal scale factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kMSkewX"> <code><strong>SkMatrix::kMSkewX </strong></code> </a></td><td>1</td><td>horizontal skew factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kMTransX"> <code><strong>SkMatrix::kMTransX </strong></code> </a></td><td>2</td><td>horizontal translation</td> + </tr> + <tr> + <td><a name="SkMatrix_kMSkewY"> <code><strong>SkMatrix::kMSkewY </strong></code> </a></td><td>3</td><td>vertical skew factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kMScaleY"> <code><strong>SkMatrix::kMScaleY </strong></code> </a></td><td>4</td><td>vertical scale factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kMTransY"> <code><strong>SkMatrix::kMTransY </strong></code> </a></td><td>5</td><td>vertical translation</td> + </tr> + <tr> + <td><a name="SkMatrix_kMPersp0"> <code><strong>SkMatrix::kMPersp0 </strong></code> </a></td><td>6</td><td>input x perspective factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kMPersp1"> <code><strong>SkMatrix::kMPersp1 </strong></code> </a></td><td>7</td><td>input y perspective factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kMPersp2"> <code><strong>SkMatrix::kMPersp2 </strong></code> </a></td><td>8</td><td>perspective bias</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="3bbf75f4748420810aa2586e3c8548d9"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_set">set</a> + + + +## <a name="SkMatrix__anonymous_2"></a> Enum SkMatrix::_anonymous_2 + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +enum { +<a href="#SkMatrix_kAScaleX">kAScaleX</a>, +<a href="#SkMatrix_kASkewY">kASkewY</a>, +<a href="#SkMatrix_kASkewX">kASkewX</a>, +<a href="#SkMatrix_kAScaleY">kAScaleY</a>, +<a href="#SkMatrix_kATransX">kATransX</a>, +<a href="#SkMatrix_kATransY">kATransY</a>, +};</pre> + +Affine arrays are in column major order to match the matrix used by +<a href="undocumented#PDF">PDF</a> and <a href="undocumented#XPS">XPS</a>. + +### Constants + +<table> + <tr> + <td><a name="SkMatrix_kAScaleX"> <code><strong>SkMatrix::kAScaleX </strong></code> </a></td><td>0</td><td>horizontal scale factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kASkewY"> <code><strong>SkMatrix::kASkewY </strong></code> </a></td><td>1</td><td>vertical skew factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kASkewX"> <code><strong>SkMatrix::kASkewX </strong></code> </a></td><td>2</td><td>horizontal skew factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kAScaleY"> <code><strong>SkMatrix::kAScaleY </strong></code> </a></td><td>3</td><td>vertical scale factor</td> + </tr> + <tr> + <td><a name="SkMatrix_kATransX"> <code><strong>SkMatrix::kATransX </strong></code> </a></td><td>4</td><td>horizontal translation</td> + </tr> + <tr> + <td><a name="SkMatrix_kATransY"> <code><strong>SkMatrix::kATransY </strong></code> </a></td><td>5</td><td>vertical translation</td> + </tr> +</table> + +### See Also + +<a href="#SkMatrix_SetAffineIdentity">SetAffineIdentity</a> <a href="#SkMatrix_asAffine">asAffine</a> <a href="#SkMatrix_setAffine">setAffine</a> + + + +<a name="SkMatrix_subscript_operator_const"></a> +## operator[] + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar operator[](int index) const +</pre> + +Returns one matrix value. Asserts if <a href="#SkMatrix_subscript_operator_const_index">index</a> is out of range and <a href="undocumented#SK_DEBUG">SK DEBUG</a> is +defined. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_subscript_operator_const_index"> <code><strong>index </strong></code> </a></td> <td> +one of: <a href="#SkMatrix_kMScaleX">kMScaleX</a>, <a href="#SkMatrix_kMSkewX">kMSkewX</a>, <a href="#SkMatrix_kMTransX">kMTransX</a>, <a href="#SkMatrix_kMSkewY">kMSkewY</a>, <a href="#SkMatrix_kMScaleY">kMScaleY</a>, <a href="#SkMatrix_kMTransY">kMTransY</a>, +<a href="#SkMatrix_kMPersp0">kMPersp0</a>, <a href="#SkMatrix_kMPersp1">kMPersp1</a>, <a href="#SkMatrix_kMPersp2">kMPersp2</a></td> + </tr> +</table> + +### Return Value + +value corresponding to <a href="#SkMatrix_subscript_operator_const_index">index</a> + +### Example + +<div><fiddle-embed name="e8740493abdf0c6341762db9cee56b89"> + +#### Example Output + +~~~~ +matrix[SkMatrix::kMScaleX] == 42 +matrix[SkMatrix::kMScaleY] == 24 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_set">set</a> + +--- + +<a name="SkMatrix_get"></a> +## get + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar get(int index) const +</pre> + +Returns one matrix value. Asserts if <a href="#SkMatrix_get_index">index</a> is out of range and <a href="undocumented#SK_DEBUG">SK DEBUG</a> is +defined. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_get_index"> <code><strong>index </strong></code> </a></td> <td> +one of: <a href="#SkMatrix_kMScaleX">kMScaleX</a>, <a href="#SkMatrix_kMSkewX">kMSkewX</a>, <a href="#SkMatrix_kMTransX">kMTransX</a>, <a href="#SkMatrix_kMSkewY">kMSkewY</a>, <a href="#SkMatrix_kMScaleY">kMScaleY</a>, <a href="#SkMatrix_kMTransY">kMTransY</a>, +<a href="#SkMatrix_kMPersp0">kMPersp0</a>, <a href="#SkMatrix_kMPersp1">kMPersp1</a>, <a href="#SkMatrix_kMPersp2">kMPersp2</a></td> + </tr> +</table> + +### Return Value + +value corresponding to <a href="#SkMatrix_get_index">index</a> + +### Example + +<div><fiddle-embed name="f5ed382bd04fa7d50b2398cce2fca23a"> + +#### Example Output + +~~~~ +matrix.get(SkMatrix::kMSkewX) == 42 +matrix.get(SkMatrix::kMSkewY) == 24 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_subscript_operator_const">operator[](int index)</a> <a href="#SkMatrix_set">set</a> + +--- + +<a name="SkMatrix_getScaleX"></a> +## getScaleX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getScaleX() const +</pre> + +Returns scale factor multiplied by x input, contributing to x output. +With <a href="#SkMatrix_mapPoints">mapPoints</a>, scales <a href="#Point">Points</a> along the x-axis. + +### Return Value + +horizontal scale factor + +### Example + +<div><fiddle-embed name="ab746d9be63975041ae8e50cba84dc3d"> + +#### Example Output + +~~~~ +matrix.getScaleX() == 42 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_getScaleY">getScaleY</a> <a href="#SkMatrix_setScaleX">setScaleX</a> <a href="#SkMatrix_setScale">setScale</a> + +--- + +<a name="SkMatrix_getScaleY"></a> +## getScaleY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getScaleY() const +</pre> + +Returns scale factor multiplied by y input, contributing to y output. +With <a href="#SkMatrix_mapPoints">mapPoints</a>, scales <a href="#Point">Points</a> along the y-axis. + +### Return Value + +vertical scale factor + +### Example + +<div><fiddle-embed name="708b1a548a2f8661b2ab570782fbc751"> + +#### Example Output + +~~~~ +matrix.getScaleY() == 24 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_getScaleX">getScaleX</a> <a href="#SkMatrix_setScaleY">setScaleY</a> <a href="#SkMatrix_setScale">setScale</a> + +--- + +<a name="SkMatrix_getSkewY"></a> +## getSkewY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getSkewY() const +</pre> + +Returns scale factor multiplied by x input, contributing to y output. +With <a href="#SkMatrix_mapPoints">mapPoints</a>, skews <a href="#Point">Points</a> along the y-axis. +Skew x and y together can rotate <a href="#Point">Points</a>. + +### Return Value + +vertical skew factor + +### Example + +<div><fiddle-embed name="6be5704506d029ffc91ba03b1d3e674b"> + +#### Example Output + +~~~~ +matrix.getSkewY() == 24 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_getSkewX">getSkewX</a> <a href="#SkMatrix_setSkewY">setSkewY</a> <a href="#SkMatrix_setSkew">setSkew</a> + +--- + +<a name="SkMatrix_getSkewX"></a> +## getSkewX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getSkewX() const +</pre> + +Returns scale factor multiplied by y input, contributing to x output. +With <a href="#SkMatrix_mapPoints">mapPoints</a>, skews <a href="#Point">Points</a> along the x-axis. +Skew x and y together can rotate <a href="#Point">Points</a>. + +### Return Value + +horizontal scale factor + +### Example + +<div><fiddle-embed name="df3a5d3c688e7597eae1e4e07bf91ae6"> + +#### Example Output + +~~~~ +matrix.getSkewX() == 42 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_getSkewY">getSkewY</a> <a href="#SkMatrix_setSkewX">setSkewX</a> <a href="#SkMatrix_setSkew">setSkew</a> + +--- + +<a name="SkMatrix_getTranslateX"></a> +## getTranslateX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getTranslateX() const +</pre> + +Returns translation contributing to x output. +With <a href="#SkMatrix_mapPoints">mapPoints</a>, moves <a href="#Point">Points</a> along the x-axis. + +### Return Value + +horizontal translation factor + +### Example + +<div><fiddle-embed name="6236f7f2b91aff977a66ba2ee2558ca4"> + +#### Example Output + +~~~~ +matrix.getTranslateX() == 42 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_getTranslateY">getTranslateY</a> <a href="#SkMatrix_setTranslateX">setTranslateX</a> <a href="#SkMatrix_setTranslate">setTranslate</a> + +--- + +<a name="SkMatrix_getTranslateY"></a> +## getTranslateY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getTranslateY() const +</pre> + +Returns translation contributing to y output. +With <a href="#SkMatrix_mapPoints">mapPoints</a>, moves <a href="#Point">Points</a> along the y-axis. + +### Return Value + +vertical translation factor + +### Example + +<div><fiddle-embed name="08464e32d22421d2b254c71a84545ef5"> + +#### Example Output + +~~~~ +matrix.getTranslateY() == 24 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_getTranslateX">getTranslateX</a> <a href="#SkMatrix_setTranslateY">setTranslateY</a> <a href="#SkMatrix_setTranslate">setTranslate</a> + +--- + +<a name="SkMatrix_getPerspX"></a> +## getPerspX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getPerspX() const +</pre> + +Returns factor scaling input x relative to input y. + +### Return Value + +input x perspective factor + +### Example + +<div><fiddle-embed name="a0f5bf4b55e8c33bfda29bf67e34306f"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_kMPersp0">kMPersp0</a> <a href="#SkMatrix_getPerspY">getPerspY</a> + +--- + +<a name="SkMatrix_getPerspY"></a> +## getPerspY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getPerspY() const +</pre> + +Returns factor scaling input y relative to input x. + +### Return Value + +input y perspective factor + +### Example + +<div><fiddle-embed name="424a00a73675dbd99ad20feb0267442b"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_kMPersp1">kMPersp1</a> <a href="#SkMatrix_getPerspX">getPerspX</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar& operator[](int index) +</pre> + +Returns writable <a href="#Matrix">Matrix</a> value. Asserts if <a href="#SkMatrix_subscript_operator_index">index</a> is out of range and <a href="undocumented#SK_DEBUG">SK DEBUG</a> is +defined. Clears internal cache anticipating that caller will change <a href="#Matrix">Matrix</a> value. + +Next call to read <a href="#Matrix">Matrix</a> state may recompute cache; subsequent writes to <a href="#Matrix">Matrix</a> +value must be followed by <a href="#SkMatrix_dirtyMatrixTypeCache">dirtyMatrixTypeCache</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_subscript_operator_index"> <code><strong>index </strong></code> </a></td> <td> +one of: <a href="#SkMatrix_kMScaleX">kMScaleX</a>, <a href="#SkMatrix_kMSkewX">kMSkewX</a>, <a href="#SkMatrix_kMTransX">kMTransX</a>, <a href="#SkMatrix_kMSkewY">kMSkewY</a>, <a href="#SkMatrix_kMScaleY">kMScaleY</a>, <a href="#SkMatrix_kMTransY">kMTransY</a>, +<a href="#SkMatrix_kMPersp0">kMPersp0</a>, <a href="#SkMatrix_kMPersp1">kMPersp1</a>, <a href="#SkMatrix_kMPersp2">kMPersp2</a></td> + </tr> +</table> + +### Return Value + +writable value corresponding to <a href="#SkMatrix_subscript_operator_index">index</a> + +### Example + +<div><fiddle-embed name="f4365ef332f51f7fd25040e0771ba9a2"> + +#### Example Output + +~~~~ +with identity matrix: x = 24 +after skew x mod: x = 24 +after 2nd skew x mod: x = 24 +after dirty cache: x = 66 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_get">get</a> <a href="#SkMatrix_dirtyMatrixTypeCache">dirtyMatrixTypeCache</a> <a href="#SkMatrix_set">set</a> + +--- + +<a name="SkMatrix_set"></a> +## set + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void set(int index, SkScalar value) +</pre> + +Sets <a href="#Matrix">Matrix</a> <a href="#SkMatrix_set_value">value</a>. Asserts if <a href="#SkMatrix_set_index">index</a> is out of range and <a href="undocumented#SK_DEBUG">SK DEBUG</a> is +defined. Safer than operator[]; internal cache is always maintained. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_set_index"> <code><strong>index </strong></code> </a></td> <td> +one of: <a href="#SkMatrix_kMScaleX">kMScaleX</a>, <a href="#SkMatrix_kMSkewX">kMSkewX</a>, <a href="#SkMatrix_kMTransX">kMTransX</a>, <a href="#SkMatrix_kMSkewY">kMSkewY</a>, <a href="#SkMatrix_kMScaleY">kMScaleY</a>, <a href="#SkMatrix_kMTransY">kMTransY</a>, +<a href="#SkMatrix_kMPersp0">kMPersp0</a>, <a href="#SkMatrix_kMPersp1">kMPersp1</a>, <a href="#SkMatrix_kMPersp2">kMPersp2</a></td> + </tr> <tr> <td><a name="SkMatrix_set_value"> <code><strong>value </strong></code> </a></td> <td> +<a href="#Scalar">Scalar</a> to store in <a href="#Matrix">Matrix</a></td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="1d400a92ca826cc89bcb88ea051f28c8"> + +#### Example Output + +~~~~ +with identity matrix: x = 24 +after skew x mod: x = 24 +after 2nd skew x mod: x = 66 +~~~~ + +</fiddle-embed></div> + +### See Also + +operator[] <a href="#SkMatrix_get">get</a> + +--- + +<a name="SkMatrix_setScaleX"></a> +## setScaleX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setScaleX(SkScalar v) +</pre> + +Sets horizontal scale factor. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setScaleX_v"> <code><strong>v </strong></code> </a></td> <td> +horizontal scale factor to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="a39dfed98c3c3c3a56be9ad59fe4e21e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_setScaleY">setScaleY</a> + +--- + +<a name="SkMatrix_setScaleY"></a> +## setScaleY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setScaleY(SkScalar v) +</pre> + +Sets vertical scale factor. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setScaleY_v"> <code><strong>v </strong></code> </a></td> <td> +vertical scale factor to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="f040c6dd85a02e94eaca00d5c2832604"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_setScaleX">setScaleX</a> + +--- + +<a name="SkMatrix_setSkewY"></a> +## setSkewY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setSkewY(SkScalar v) +</pre> + +Sets vertical skew factor. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setSkewY_v"> <code><strong>v </strong></code> </a></td> <td> +vertical skew factor to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="b418d15df9829aefcc6aca93a37428bb"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setSkew">setSkew</a> <a href="#SkMatrix_setSkewX">setSkewX</a> + +--- + +<a name="SkMatrix_setSkewX"></a> +## setSkewX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setSkewX(SkScalar v) +</pre> + +Sets horizontal skew factor. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setSkewX_v"> <code><strong>v </strong></code> </a></td> <td> +horizontal skew factor to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="c7177a6fbc1545be95a5ebca87e0cd0d"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setSkew">setSkew</a> <a href="#SkMatrix_setSkewX">setSkewX</a> + +--- + +<a name="SkMatrix_setTranslateX"></a> +## setTranslateX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setTranslateX(SkScalar v) +</pre> + +Sets horizontal translation. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setTranslateX_v"> <code><strong>v </strong></code> </a></td> <td> +horizontal translation to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="a18bc2e3607ac3a8e438bcb61fb13130"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_setTranslateY">setTranslateY</a> + +--- + +<a name="SkMatrix_setTranslateY"></a> +## setTranslateY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setTranslateY(SkScalar v) +</pre> + +Sets vertical translation. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setTranslateY_v"> <code><strong>v </strong></code> </a></td> <td> +vertical translation to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="34e3c70a72b836abf7f4858d35eecc98"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_setTranslateX">setTranslateX</a> + +--- + +<a name="SkMatrix_setPerspX"></a> +## setPerspX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setPerspX(SkScalar v) +</pre> + +Sets input x perspective factor, which causes <a href="#SkMatrix_mapXY">mapXY</a> to vary input x inversely +proportional to input y. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setPerspX_v"> <code><strong>v </strong></code> </a></td> <td> +perspective factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="830a9e4e4bb93d25afd83b2fea63929e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_getPerspX">getPerspX</a> <a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setAll">setAll</a> <a href="#SkMatrix_set9">set9</a> + +--- + +<a name="SkMatrix_setPerspY"></a> +## setPerspY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setPerspY(SkScalar v) +</pre> + +Sets input y perspective factor, which causes <a href="#SkMatrix_mapXY">mapXY</a> to vary input y inversely +proportional to input x. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setPerspY_v"> <code><strong>v </strong></code> </a></td> <td> +perspective factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="aeb258b7922c1a11b698b00f562182ec"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_getPerspY">getPerspY</a> <a href="#SkMatrix_set">set</a> <a href="#SkMatrix_setAll">setAll</a> <a href="#SkMatrix_set9">set9</a> + +--- + +<a name="SkMatrix_setAll"></a> +## setAll + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setAll(SkScalar scaleX, SkScalar skewX, SkScalar transX, SkScalar skewY, + SkScalar scaleY, SkScalar transY, SkScalar persp0, SkScalar persp1, + SkScalar persp2) +</pre> + +Sets all values from parameters. Sets matrix to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scaleX skewX transX | +| skewY scaleY transY | +| persp0 persp1 persp2 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setAll_scaleX"> <code><strong>scaleX </strong></code> </a></td> <td> +horizontal scale factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_skewX"> <code><strong>skewX </strong></code> </a></td> <td> +horizontal skew factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_transX"> <code><strong>transX </strong></code> </a></td> <td> +horizontal translation to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_skewY"> <code><strong>skewY </strong></code> </a></td> <td> +vertical skew factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_scaleY"> <code><strong>scaleY </strong></code> </a></td> <td> +vertical scale factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_transY"> <code><strong>transY </strong></code> </a></td> <td> +vertical translation to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_persp0"> <code><strong>persp0 </strong></code> </a></td> <td> +input x perspective factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_persp1"> <code><strong>persp1 </strong></code> </a></td> <td> +input y perspective factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setAll_persp2"> <code><strong>persp2 </strong></code> </a></td> <td> +perspective scale factor to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="c51d81b637b58da30fb9ae2d68877167"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set9">set9</a> + +--- + +<a name="SkMatrix_get9"></a> +## get9 + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void get9(SkScalar buffer[9]) const +</pre> + +Copies nine <a href="#Scalar">Scalar</a> values contained by <a href="#Matrix">Matrix</a> into <a href="#SkMatrix_get9_buffer">buffer</a>, in member value +ascending order: <a href="#SkMatrix_kMScaleX">kMScaleX</a>, <a href="#SkMatrix_kMSkewX">kMSkewX</a>, <a href="#SkMatrix_kMTransX">kMTransX</a>, <a href="#SkMatrix_kMSkewY">kMSkewY</a>, <a href="#SkMatrix_kMScaleY">kMScaleY</a>, <a href="#SkMatrix_kMTransY">kMTransY</a>, +<a href="#SkMatrix_kMPersp0">kMPersp0</a>, <a href="#SkMatrix_kMPersp1">kMPersp1</a>, <a href="#SkMatrix_kMPersp2">kMPersp2</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_get9_buffer"> <code><strong>buffer </strong></code> </a></td> <td> +storage for nine <a href="#Scalar">Scalar</a> values</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="df509d73b47cb98b0475e4465db7b246"> + +#### Example Output + +~~~~ +{4, 0, 3}, +{0, 5, 4}, +{0, 0, 1} +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_set9">set9</a> + +--- + +<a name="SkMatrix_set9"></a> +## set9 + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void set9(const SkScalar buffer[9]) +</pre> + +Sets <a href="#Matrix">Matrix</a> to nine <a href="#Scalar">Scalar</a> values in <a href="#SkMatrix_set9_buffer">buffer</a>, in member value ascending order: +<a href="#SkMatrix_kMScaleX">kMScaleX</a>, <a href="#SkMatrix_kMSkewX">kMSkewX</a>, <a href="#SkMatrix_kMTransX">kMTransX</a>, <a href="#SkMatrix_kMSkewY">kMSkewY</a>, <a href="#SkMatrix_kMScaleY">kMScaleY</a>, <a href="#SkMatrix_kMTransY">kMTransY</a>, <a href="#SkMatrix_kMPersp0">kMPersp0</a>, <a href="#SkMatrix_kMPersp1">kMPersp1</a>, +<a href="#SkMatrix_kMPersp2">kMPersp2</a>. + +Sets matrix to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| buffer[0] buffer[1] buffer[2] | +| buffer[3] buffer[4] buffer[5] | +| buffer[6] buffer[7] buffer[8] |</pre> + +In the future, <a href="#SkMatrix_set9">set9</a> followed by <a href="#SkMatrix_get9">get9</a> may not return the same values. Since <a href="#Matrix">Matrix</a> +maps non-homogeneous coordinates, scaling all nine values produces an equivalent +transformation, possibly improving precision. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_set9_buffer"> <code><strong>buffer </strong></code> </a></td> <td> +nine <a href="#Scalar">Scalar</a> values</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="ec5de0d23e5fe28ba7628625d1402e85"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setAll">setAll</a> <a href="#SkMatrix_get9">get9</a> + +--- + +<a name="SkMatrix_reset"></a> +## reset + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void reset() +</pre> + +Sets <a href="#Matrix">Matrix</a> to identity; which has no effect on mapped <a href="#Point">Points</a>. Sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 0 | +| 0 1 0 | +| 0 0 1 |</pre> + +Also called <a href="#SkMatrix_setIdentity">setIdentity</a>; use the one that provides better inline +documentation. + +### Example + +<div><fiddle-embed name="ca94f7922bc37ef03bbc51ad70536fcf"> + +#### Example Output + +~~~~ +m.isIdentity(): true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_isIdentity">isIdentity</a> <a href="#SkMatrix_setIdentity">setIdentity</a> + +--- + +<a name="SkMatrix_setIdentity"></a> +## setIdentity + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setIdentity() +</pre> + +Sets <a href="#Matrix">Matrix</a> to identity; which has no effect on mapped <a href="#Point">Points</a>. Sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 0 | +| 0 1 0 | +| 0 0 1 |</pre> + +Also called <a href="#SkMatrix_reset">reset</a>; use the one that provides better inline +documentation. + +### Example + +<div><fiddle-embed name="3979c865bb482e6ef1fafc71e56bbb91"> + +#### Example Output + +~~~~ +m.isIdentity(): true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_isIdentity">isIdentity</a> <a href="#SkMatrix_reset">reset</a> + +--- + +<a name="SkMatrix_setTranslate"></a> +## setTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setTranslate(SkScalar dx, SkScalar dy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to translate by (<a href="#SkMatrix_setTranslate_dx">dx</a>, <a href="#SkMatrix_setTranslate_dy">dy</a>). + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setTranslate_dx"> <code><strong>dx </strong></code> </a></td> <td> +horizontal translation</td> + </tr> <tr> <td><a name="SkMatrix_setTranslate_dy"> <code><strong>dy </strong></code> </a></td> <td> +vertical translation</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="63ca62985741b1bccb5e8b9cf734874e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setTranslateX">setTranslateX</a> <a href="#SkMatrix_setTranslateY">setTranslateY</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setTranslate(const SkVector& v) +</pre> + +Sets <a href="#Matrix">Matrix</a> to translate by (<a href="#SkMatrix_setTranslate_2_v">v</a>.fX, <a href="#SkMatrix_setTranslate_2_v">v</a>.fY). + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setTranslate_2_v"> <code><strong>v </strong></code> </a></td> <td> +<a href="undocumented#Vector">Vector</a> containing horizontal and vertical translation</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="ccfc734aff2ddea0b097c83f5621de5e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setTranslateX">setTranslateX</a> <a href="#SkMatrix_setTranslateY">setTranslateY</a> <a href="#SkMatrix_MakeTrans">MakeTrans</a> + +--- + +<a name="SkMatrix_setScale"></a> +## setScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setScale(SkScalar sx, SkScalar sy, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to scale by <a href="#SkMatrix_setScale_sx">sx</a> and <a href="#SkMatrix_setScale_sy">sy</a>, about a pivot point at (<a href="#SkMatrix_setScale_px">px</a>, <a href="#SkMatrix_setScale_py">py</a>). +The pivot point is unchanged when mapped with <a href="#Matrix">Matrix</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setScale_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_setScale_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> <tr> <td><a name="SkMatrix_setScale_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_setScale_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="397db8da89bc92e7c576ad013d64ed24"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScaleX">setScaleX</a> <a href="#SkMatrix_setScaleY">setScaleY</a> <a href="#SkMatrix_MakeScale">MakeScale</a> <a href="#SkMatrix_preScale">preScale</a> <a href="#SkMatrix_postScale">postScale</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setScale(SkScalar sx, SkScalar sy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to scale by <a href="#SkMatrix_setScale_2_sx">sx</a> and <a href="#SkMatrix_setScale_2_sy">sy</a> about at pivot point at (0, 0). + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setScale_2_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_setScale_2_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="94a9ec11b994580dca14aa2159a796a9"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScaleX">setScaleX</a> <a href="#SkMatrix_setScaleY">setScaleY</a> <a href="#SkMatrix_MakeScale">MakeScale</a> <a href="#SkMatrix_preScale">preScale</a> <a href="#SkMatrix_postScale">postScale</a> + +--- + +<a name="SkMatrix_setRotate"></a> +## setRotate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setRotate(SkScalar degrees, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to rotate by <a href="#SkMatrix_setRotate_degrees">degrees</a> about a pivot point at (<a href="#SkMatrix_setRotate_px">px</a>, <a href="#SkMatrix_setRotate_py">py</a>). +The pivot point is unchanged when mapped with <a href="#Matrix">Matrix</a>. + +Positive <a href="#SkMatrix_setRotate_degrees">degrees</a> rotates clockwise. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setRotate_degrees"> <code><strong>degrees </strong></code> </a></td> <td> +angle of axes relative to upright axes</td> + </tr> <tr> <td><a name="SkMatrix_setRotate_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_setRotate_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="8c28db3add9cd0177225088f6df6bbb5"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setSinCos">setSinCos</a> <a href="#SkMatrix_preRotate">preRotate</a> <a href="#SkMatrix_postRotate">postRotate</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setRotate(SkScalar degrees) +</pre> + +Sets <a href="#Matrix">Matrix</a> to rotate by <a href="#SkMatrix_setRotate_2_degrees">degrees</a> about a pivot point at (0, 0). +Positive <a href="#SkMatrix_setRotate_2_degrees">degrees</a> rotates clockwise. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setRotate_2_degrees"> <code><strong>degrees </strong></code> </a></td> <td> +angle of axes relative to upright axes</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="93efb9d191bf1b9710c173513e014d6c"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setSinCos">setSinCos</a> <a href="#SkMatrix_preRotate">preRotate</a> <a href="#SkMatrix_postRotate">postRotate</a> + +--- + +<a name="SkMatrix_setSinCos"></a> +## setSinCos + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setSinCos(SkScalar sinValue, SkScalar cosValue, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to rotate by <a href="#SkMatrix_setSinCos_sinValue">sinValue</a> and <a href="#SkMatrix_setSinCos_cosValue">cosValue</a>, about a pivot point at (<a href="#SkMatrix_setSinCos_px">px</a>, <a href="#SkMatrix_setSinCos_py">py</a>). +The pivot point is unchanged when mapped with <a href="#Matrix">Matrix</a>. + +<a href="undocumented#Vector">Vector</a> (<a href="#SkMatrix_setSinCos_sinValue">sinValue</a>, <a href="#SkMatrix_setSinCos_cosValue">cosValue</a>) describes the angle of rotation relative to (0, 1). +<a href="undocumented#Vector">Vector</a> length specifies scale. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setSinCos_sinValue"> <code><strong>sinValue </strong></code> </a></td> <td> +rotation vector x component</td> + </tr> <tr> <td><a name="SkMatrix_setSinCos_cosValue"> <code><strong>cosValue </strong></code> </a></td> <td> +rotation vector y component</td> + </tr> <tr> <td><a name="SkMatrix_setSinCos_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_setSinCos_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="187e1d9228e2e4341ef820bd77b6fda9"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setRotate">setRotate</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_setRSXform">setRSXform</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setSinCos(SkScalar sinValue, SkScalar cosValue) +</pre> + +Sets <a href="#Matrix">Matrix</a> to rotate by <a href="#SkMatrix_setSinCos_2_sinValue">sinValue</a> and <a href="#SkMatrix_setSinCos_2_cosValue">cosValue</a>, about a pivot point at (0, 0). + +<a href="undocumented#Vector">Vector</a> (<a href="#SkMatrix_setSinCos_2_sinValue">sinValue</a>, <a href="#SkMatrix_setSinCos_2_cosValue">cosValue</a>) describes the angle of rotation relative to (0, 1). +<a href="undocumented#Vector">Vector</a> length specifies scale. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setSinCos_2_sinValue"> <code><strong>sinValue </strong></code> </a></td> <td> +rotation vector x component</td> + </tr> <tr> <td><a name="SkMatrix_setSinCos_2_cosValue"> <code><strong>cosValue </strong></code> </a></td> <td> +rotation vector y component</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="e37a94a53c959951b059fcd624639ef6"><div><a href="SkCanvas_Reference#Canvas">Canvas</a> needs offset after applying <a href="#Matrix">Matrix</a> to pivot about <a href="SkRect_Reference#Rect">Rect</a> center.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setRotate">setRotate</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_setRSXform">setRSXform</a> + +--- + +<a name="SkMatrix_setRSXform"></a> +## setRSXform + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkMatrix& setRSXform(const SkRSXform& rsxForm) +</pre> + +Sets <a href="#Matrix">Matrix</a> to rotate, scale, and translate using a compressed matrix form. + +<a href="undocumented#Vector">Vector</a> (<a href="#SkMatrix_setRSXform_rsxForm">rsxForm</a>.fSSin, <a href="#SkMatrix_setRSXform_rsxForm">rsxForm</a>.fSCos) describes the angle of rotation relative +to (0, 1). <a href="undocumented#Vector">Vector</a> length specifies scale. Mapped point is rotated and scaled +by <a href="undocumented#Vector">Vector</a>, then translated by (<a href="#SkMatrix_setRSXform_rsxForm">rsxForm</a>.fTx, <a href="#SkMatrix_setRSXform_rsxForm">rsxForm</a>.fTy). + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setRSXform_rsxForm"> <code><strong>rsxForm </strong></code> </a></td> <td> +compressed <a href="undocumented#RSXform">RSXform</a> matrix</td> + </tr> +</table> + +### Return Value + +reference to <a href="#Matrix">Matrix</a> + +### Example + +<div><fiddle-embed name="c3f5faddca466f78278b32b88fd5f5eb"><div><a href="SkCanvas_Reference#Canvas">Canvas</a> needs offset after applying <a href="#Matrix">Matrix</a> to pivot about <a href="SkRect_Reference#Rect">Rect</a> center.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setSinCos">setSinCos</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_setTranslate">setTranslate</a> + +--- + +<a name="SkMatrix_setSkew"></a> +## setSkew + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setSkew(SkScalar kx, SkScalar ky, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to skew by <a href="#SkMatrix_setSkew_kx">kx</a> and <a href="#SkMatrix_setSkew_ky">ky</a>, about a pivot point at (<a href="#SkMatrix_setSkew_px">px</a>, <a href="#SkMatrix_setSkew_py">py</a>). +The pivot point is unchanged when mapped with <a href="#Matrix">Matrix</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setSkew_kx"> <code><strong>kx </strong></code> </a></td> <td> +horizontal skew factor</td> + </tr> <tr> <td><a name="SkMatrix_setSkew_ky"> <code><strong>ky </strong></code> </a></td> <td> +vertical skew factor</td> + </tr> <tr> <td><a name="SkMatrix_setSkew_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_setSkew_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="55e0431adc6c5b1987ebb8123cc10342"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setSkewX">setSkewX</a> <a href="#SkMatrix_setSkewY">setSkewY</a> <a href="#SkMatrix_preSkew">preSkew</a> <a href="#SkMatrix_postSkew">postSkew</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setSkew(SkScalar kx, SkScalar ky) +</pre> + +Sets <a href="#Matrix">Matrix</a> to skew by <a href="#SkMatrix_setSkew_2_kx">kx</a> and <a href="#SkMatrix_setSkew_2_ky">ky</a>, about a pivot point at (0, 0). + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setSkew_2_kx"> <code><strong>kx </strong></code> </a></td> <td> +horizontal skew factor</td> + </tr> <tr> <td><a name="SkMatrix_setSkew_2_ky"> <code><strong>ky </strong></code> </a></td> <td> +vertical skew factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="05be7844e9afdd7b9bfc31c5423a70a2"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setSkewX">setSkewX</a> <a href="#SkMatrix_setSkewY">setSkewY</a> <a href="#SkMatrix_preSkew">preSkew</a> <a href="#SkMatrix_postSkew">postSkew</a> + +--- + +<a name="SkMatrix_setConcat"></a> +## setConcat + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setConcat(const SkMatrix& a, const SkMatrix& b) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> <a href="#SkMatrix_setConcat_a">a</a> multiplied by <a href="#Matrix">Matrix</a> <a href="#SkMatrix_setConcat_b">b</a>. Either <a href="#SkMatrix_setConcat_a">a</a> or <a href="#SkMatrix_setConcat_b">b</a> may be this. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | +a = | D E F |, b = | M N O | + | G H I | | P Q R |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +a * b = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setConcat_a"> <code><strong>a </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> on left side of multiply expression</td> + </tr> <tr> <td><a name="SkMatrix_setConcat_b"> <code><strong>b </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> on right side of multiply expression</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="0381a10ac69bdefdf9d15b47cbb9fefe"><div><a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> creates perspective matrices, one the inverse of the other. +Multiplying the matrix by its inverse turns into an identity matrix.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_Concat">Concat</a> <a href="#SkMatrix_preConcat">preConcat</a> <a href="#SkMatrix_postConcat">postConcat</a> <a href="#SkCanvas_concat">SkCanvas::concat</a> + +--- + +<a name="SkMatrix_preTranslate"></a> +## preTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preTranslate(SkScalar dx, SkScalar dy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from translation (<a href="#SkMatrix_preTranslate_dx">dx</a>, <a href="#SkMatrix_preTranslate_dy">dy</a>). +This can be thought of as moving the point to be mapped before applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | 1 0 dx | +Matrix = | D E F |, T(dx, dy) = | 0 1 dy | + | G H I | | 0 0 1 |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | 1 0 dx | | A B A*dx+B*dy+C | +Matrix * T(dx, dy) = | D E F | | 0 1 dy | = | D E D*dx+E*dy+F | + | G H I | | 0 0 1 | | G H G*dx+H*dy+I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preTranslate_dx"> <code><strong>dx </strong></code> </a></td> <td> +x translation before applying <a href="#Matrix">Matrix</a></td> + </tr> <tr> <td><a name="SkMatrix_preTranslate_dy"> <code><strong>dy </strong></code> </a></td> <td> +y translation before applying <a href="#Matrix">Matrix</a></td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="08f6749933f4ce541073077ab506fd9b"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postTranslate">postTranslate</a> <a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_MakeTrans">MakeTrans</a> + +--- + +<a name="SkMatrix_preScale"></a> +## preScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preScale(SkScalar sx, SkScalar sy, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from scaling by (<a href="#SkMatrix_preScale_sx">sx</a>, <a href="#SkMatrix_preScale_sy">sy</a>) +about pivot point (<a href="#SkMatrix_preScale_px">px</a>, <a href="#SkMatrix_preScale_py">py</a>). +This can be thought of as scaling about a pivot point before applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | sx 0 dx | +Matrix = | D E F |, S(sx, sy, px, py) = | 0 sy dy | + | G H I | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +dx = px - sx * px +dy = py - sy * py</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | sx 0 dx | | A*sx B*sy A*dx+B*dy+C | +Matrix * S(sx, sy, px, py) = | D E F | | 0 sy dy | = | D*sx E*sy D*dx+E*dy+F | + | G H I | | 0 0 1 | | G*sx H*sy G*dx+H*dy+I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preScale_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_preScale_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> <tr> <td><a name="SkMatrix_preScale_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_preScale_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="2531f8d1e05d7b6dc22f3efcd2fb84e4"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postScale">postScale</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_MakeScale">MakeScale</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preScale(SkScalar sx, SkScalar sy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from scaling by (<a href="#SkMatrix_preScale_2_sx">sx</a>, <a href="#SkMatrix_preScale_2_sy">sy</a>) +about pivot point (0, 0). +This can be thought of as scaling about the origin before applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | sx 0 0 | +Matrix = | D E F |, S(sx, sy) = | 0 sy 0 | + | G H I | | 0 0 1 |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | sx 0 0 | | A*sx B*sy C | +Matrix * S(sx, sy) = | D E F | | 0 sy 0 | = | D*sx E*sy F | + | G H I | | 0 0 1 | | G*sx H*sy I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preScale_2_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_preScale_2_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="3edbdea8e43d06086abf33ec4a9b415b"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postScale">postScale</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_MakeScale">MakeScale</a> + +--- + +<a name="SkMatrix_preRotate"></a> +## preRotate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preRotate(SkScalar degrees, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from rotating by <a href="#SkMatrix_preRotate_degrees">degrees</a> +about pivot point (<a href="#SkMatrix_preRotate_px">px</a>, <a href="#SkMatrix_preRotate_py">py</a>). +This can be thought of as rotating about a pivot point before applying <a href="#Matrix">Matrix</a>. + +Positive <a href="#SkMatrix_preRotate_degrees">degrees</a> rotates clockwise. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | c -s dx | +Matrix = | D E F |, R(degrees, px, py) = | s c dy | + | G H I | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +c = cos(degrees) +s = sin(degrees) +dx = s * py + (1 - c) * px +dy = -s * px + (1 - c) * py</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | c -s dx | | Ac+Bs -As+Bc A*dx+B*dy+C | +Matrix * R(degrees, px, py) = | D E F | | s c dy | = | Dc+Es -Ds+Ec D*dx+E*dy+F | + | G H I | | 0 0 1 | | Gc+Hs -Gs+Hc G*dx+H*dy+I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preRotate_degrees"> <code><strong>degrees </strong></code> </a></td> <td> +angle of axes relative to upright axes</td> + </tr> <tr> <td><a name="SkMatrix_preRotate_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_preRotate_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="a70bb18d67c06a20ab514e7a47924e5a"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postRotate">postRotate</a> <a href="#SkMatrix_setRotate">setRotate</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preRotate(SkScalar degrees) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from rotating by <a href="#SkMatrix_preRotate_2_degrees">degrees</a> +about pivot point (0, 0). +This can be thought of as rotating about the origin before applying <a href="#Matrix">Matrix</a>. + +Positive <a href="#SkMatrix_preRotate_2_degrees">degrees</a> rotates clockwise. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | c -s 0 | +Matrix = | D E F |, R(degrees, px, py) = | s c 0 | + | G H I | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +c = cos(degrees) +s = sin(degrees)</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | c -s 0 | | Ac+Bs -As+Bc C | +Matrix * R(degrees, px, py) = | D E F | | s c 0 | = | Dc+Es -Ds+Ec F | + | G H I | | 0 0 1 | | Gc+Hs -Gs+Hc I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preRotate_2_degrees"> <code><strong>degrees </strong></code> </a></td> <td> +angle of axes relative to upright axes</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="5acd49bd931c79a808dd6c7cc0e92f72"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postRotate">postRotate</a> <a href="#SkMatrix_setRotate">setRotate</a> + +--- + +<a name="SkMatrix_preSkew"></a> +## preSkew + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preSkew(SkScalar kx, SkScalar ky, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from skewing by (<a href="#SkMatrix_preSkew_kx">kx</a>, <a href="#SkMatrix_preSkew_ky">ky</a>) +about pivot point (<a href="#SkMatrix_preSkew_px">px</a>, <a href="#SkMatrix_preSkew_py">py</a>). +This can be thought of as skewing about a pivot point before applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | 1 kx dx | +Matrix = | D E F |, K(kx, ky, px, py) = | ky 1 dy | + | G H I | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +dx = -kx * py +dy = -ky * px</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | 1 kx dx | | A+B*ky A*kx+B A*dx+B*dy+C | +Matrix * K(kx, ky, px, py) = | D E F | | ky 1 dy | = | D+E*ky D*kx+E D*dx+E*dy+F | + | G H I | | 0 0 1 | | G+H*ky G*kx+H G*dx+H*dy+I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preSkew_kx"> <code><strong>kx </strong></code> </a></td> <td> +horizontal skew factor</td> + </tr> <tr> <td><a name="SkMatrix_preSkew_ky"> <code><strong>ky </strong></code> </a></td> <td> +vertical skew factor</td> + </tr> <tr> <td><a name="SkMatrix_preSkew_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_preSkew_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="199a18ad61d702664ce6df1d7037aa48"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postSkew">postSkew</a> <a href="#SkMatrix_setSkew">setSkew</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preSkew(SkScalar kx, SkScalar ky) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> constructed from skewing by (<a href="#SkMatrix_preSkew_2_kx">kx</a>, <a href="#SkMatrix_preSkew_2_ky">ky</a>) +about pivot point (0, 0). +This can be thought of as skewing about the origin before applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | 1 kx 0 | +Matrix = | D E F |, K(kx, ky) = | ky 1 0 | + | G H I | | 0 0 1 |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | 1 kx 0 | | A+B*ky A*kx+B C | +Matrix * K(kx, ky) = | D E F | | ky 1 0 | = | D+E*ky D*kx+E F | + | G H I | | 0 0 1 | | G+H*ky G*kx+H I |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preSkew_2_kx"> <code><strong>kx </strong></code> </a></td> <td> +horizontal skew factor</td> + </tr> <tr> <td><a name="SkMatrix_preSkew_2_ky"> <code><strong>ky </strong></code> </a></td> <td> +vertical skew factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="e100c543869fe8fd516ba69de79444ba"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postSkew">postSkew</a> <a href="#SkMatrix_setSkew">setSkew</a> + +--- + +<a name="SkMatrix_preConcat"></a> +## preConcat + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void preConcat(const SkMatrix& other) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> multiplied by <a href="#Matrix">Matrix</a> <a href="#SkMatrix_preConcat_other">other</a>. +This can be thought of mapping by <a href="#SkMatrix_preConcat_other">other</a> before applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | +Matrix = | D E F |, other = | M N O | + | G H I | | P Q R |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +Matrix * other = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_preConcat_other"> <code><strong>other </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> on right side of multiply expression</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="b07e62298e7b0ab5683db199faffceb2"><div><a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> creates perspective matrices, one the inverse of the <a href="#SkMatrix_preConcat_other">other</a>. +Multiplying the matrix by its inverse turns into an identity matrix.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postConcat">postConcat</a> <a href="#SkMatrix_setConcat">setConcat</a> <a href="#SkMatrix_Concat">Concat</a> + +--- + +<a name="SkMatrix_postTranslate"></a> +## postTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postTranslate(SkScalar dx, SkScalar dy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from translation (<a href="#SkMatrix_postTranslate_dx">dx</a>, <a href="#SkMatrix_postTranslate_dy">dy</a>) multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as moving the point to be mapped after applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | 1 0 dx | +Matrix = | M N O |, T(dx, dy) = | 0 1 dy | + | P Q R | | 0 0 1 |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | 1 0 dx | | J K L | | J+dx*P K+dx*Q L+dx*R | +T(dx, dy) * Matrix = | 0 1 dy | | M N O | = | M+dy*P N+dy*Q O+dy*R | + | 0 0 1 | | P Q R | | P Q R |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postTranslate_dx"> <code><strong>dx </strong></code> </a></td> <td> +x translation after applying <a href="#Matrix">Matrix</a></td> + </tr> <tr> <td><a name="SkMatrix_postTranslate_dy"> <code><strong>dy </strong></code> </a></td> <td> +y translation after applying <a href="#Matrix">Matrix</a></td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="57e4cff302c0d754ac6c66050d741772"><div>Compare with <a href="#SkMatrix_preTranslate">preTranslate</a> example.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preTranslate">preTranslate</a> <a href="#SkMatrix_setTranslate">setTranslate</a> <a href="#SkMatrix_MakeTrans">MakeTrans</a> + +--- + +<a name="SkMatrix_postScale"></a> +## postScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postScale(SkScalar sx, SkScalar sy, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from scaling by (<a href="#SkMatrix_postScale_sx">sx</a>, <a href="#SkMatrix_postScale_sy">sy</a>) about pivot point +(<a href="#SkMatrix_postScale_px">px</a>, <a href="#SkMatrix_postScale_py">py</a>), multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as scaling about a pivot point after applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | sx 0 dx | +Matrix = | M N O |, S(sx, sy, px, py) = | 0 sy dy | + | P Q R | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +dx = px - sx * px +dy = py - sy * py</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | sx 0 dx | | J K L | | sx*J+dx*P sx*K+dx*Q sx*L+dx+R | +S(sx, sy, px, py) * Matrix = | 0 sy dy | | M N O | = | sy*M+dy*P sy*N+dy*Q sy*O+dy*R | + | 0 0 1 | | P Q R | | P Q R |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postScale_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_postScale_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> <tr> <td><a name="SkMatrix_postScale_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_postScale_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="ed3aa18ba0ea95c85cc49aa3829fe384"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preScale">preScale</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_MakeScale">MakeScale</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postScale(SkScalar sx, SkScalar sy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from scaling by (<a href="#SkMatrix_postScale_2_sx">sx</a>, <a href="#SkMatrix_postScale_2_sy">sy</a>) about pivot point +(0, 0), multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as scaling about the origin after applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | sx 0 0 | +Matrix = | M N O |, S(sx, sy) = | 0 sy 0 | + | P Q R | | 0 0 1 |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | sx 0 0 | | J K L | | sx*J sx*K sx*L | +S(sx, sy) * Matrix = | 0 sy 0 | | M N O | = | sy*M sy*N sy*O | + | 0 0 1 | | P Q R | | P Q R |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postScale_2_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor</td> + </tr> <tr> <td><a name="SkMatrix_postScale_2_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="1931017698766a67d3a26423453b8095"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preScale">preScale</a> <a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_MakeScale">MakeScale</a> + +--- + +<a name="SkMatrix_postIDiv"></a> +## postIDiv + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool postIDiv(int divx, int divy) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from scaling by(1/<a href="#SkMatrix_postIDiv_divx">divx</a>, 1/<a href="#SkMatrix_postIDiv_divy">divy</a>)about pivot point (px, py), multiplied by <a href="#Matrix">Matrix</a>. + +Returns false if either <a href="#SkMatrix_postIDiv_divx">divx</a> or <a href="#SkMatrix_postIDiv_divy">divy</a> is zero. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | sx 0 0 | +Matrix = | M N O |, I(divx, divy) = | 0 sy 0 | + | P Q R | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +sx = 1 / divx +sy = 1 / divy</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | sx 0 0 | | J K L | | sx*J sx*K sx*L | +I(divx, divy) * Matrix = | 0 sy 0 | | M N O | = | sy*M sy*N sy*O | + | 0 0 1 | | P Q R | | P Q R |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postIDiv_divx"> <code><strong>divx </strong></code> </a></td> <td> +integer divisor for inverse scale in x</td> + </tr> <tr> <td><a name="SkMatrix_postIDiv_divy"> <code><strong>divy </strong></code> </a></td> <td> +integer divisor for inverse scale in y</td> + </tr> +</table> + +### Return Value + +true on successful scale + +### Example + +<div><fiddle-embed name="58c844b8f0c36acdbc8211e8c929c253"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_postScale">postScale</a> <a href="#SkMatrix_MakeScale">MakeScale</a> + +--- + +<a name="SkMatrix_postRotate"></a> +## postRotate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postRotate(SkScalar degrees, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from rotating by <a href="#SkMatrix_postRotate_degrees">degrees</a> about pivot point +(<a href="#SkMatrix_postRotate_px">px</a>, <a href="#SkMatrix_postRotate_py">py</a>), multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as rotating about a pivot point after applying <a href="#Matrix">Matrix</a>. + +Positive <a href="#SkMatrix_postRotate_degrees">degrees</a> rotates clockwise. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | c -s dx | +Matrix = | M N O |, R(degrees, px, py) = | s c dy | + | P Q R | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +c = cos(degrees) +s = sin(degrees) +dx = s * py + (1 - c) * px +dy = -s * px + (1 - c) * py</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |c -s dx| |J K L| |cJ-sM+dx*P cK-sN+dx*Q cL-sO+dx+R| +R(degrees, px, py) * Matrix = |s c dy| |M N O| = |sJ+cM+dy*P sK+cN+dy*Q sL+cO+dy*R| + |0 0 1| |P Q R| | P Q R|</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postRotate_degrees"> <code><strong>degrees </strong></code> </a></td> <td> +angle of axes relative to upright axes</td> + </tr> <tr> <td><a name="SkMatrix_postRotate_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_postRotate_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="e09194ee48a81e7b375ade473d340f0d"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preRotate">preRotate</a> <a href="#SkMatrix_setRotate">setRotate</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postRotate(SkScalar degrees) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from rotating by <a href="#SkMatrix_postRotate_2_degrees">degrees</a> about pivot point +(0, 0), multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as rotating about the origin after applying <a href="#Matrix">Matrix</a>. + +Positive <a href="#SkMatrix_postRotate_2_degrees">degrees</a> rotates clockwise. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | c -s 0 | +Matrix = | M N O |, R(degrees, px, py) = | s c 0 | + | P Q R | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +c = cos(degrees) +s = sin(degrees)</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | c -s dx | | J K L | | cJ-sM cK-sN cL-sO | +R(degrees, px, py) * Matrix = | s c dy | | M N O | = | sJ+cM sK+cN sL+cO | + | 0 0 1 | | P Q R | | P Q R |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postRotate_2_degrees"> <code><strong>degrees </strong></code> </a></td> <td> +angle of axes relative to upright axes</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="52e4c53e26971af5576b30de60fa70c2"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preRotate">preRotate</a> <a href="#SkMatrix_setRotate">setRotate</a> + +--- + +<a name="SkMatrix_postSkew"></a> +## postSkew + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postSkew(SkScalar kx, SkScalar ky, SkScalar px, SkScalar py) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from skewing by (<a href="#SkMatrix_postSkew_kx">kx</a>, <a href="#SkMatrix_postSkew_ky">ky</a>) about pivot point +(<a href="#SkMatrix_postSkew_px">px</a>, <a href="#SkMatrix_postSkew_py">py</a>), multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as skewing about a pivot point after applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | 1 kx dx | +Matrix = | M N O |, K(kx, ky, px, py) = | ky 1 dy | + | P Q R | | 0 0 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +dx = -kx * py +dy = -ky * px</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | 1 kx dx| |J K L| |J+kx*M+dx*P K+kx*N+dx*Q L+kx*O+dx+R| +K(kx, ky, px, py) * Matrix = |ky 1 dy| |M N O| = |ky*J+M+dy*P ky*K+N+dy*Q ky*L+O+dy*R| + | 0 0 1| |P Q R| | P Q R|</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postSkew_kx"> <code><strong>kx </strong></code> </a></td> <td> +horizontal skew factor</td> + </tr> <tr> <td><a name="SkMatrix_postSkew_ky"> <code><strong>ky </strong></code> </a></td> <td> +vertical skew factor</td> + </tr> <tr> <td><a name="SkMatrix_postSkew_px"> <code><strong>px </strong></code> </a></td> <td> +pivot x</td> + </tr> <tr> <td><a name="SkMatrix_postSkew_py"> <code><strong>py </strong></code> </a></td> <td> +pivot y</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="8c34ae3a2b7e2742bb969819737365ec"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preSkew">preSkew</a> <a href="#SkMatrix_setSkew">setSkew</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postSkew(SkScalar kx, SkScalar ky) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> constructed from skewing by (<a href="#SkMatrix_postSkew_2_kx">kx</a>, <a href="#SkMatrix_postSkew_2_ky">ky</a>) about pivot point +(0, 0), multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of as skewing about the origin after applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | 1 kx 0 | +Matrix = | M N O |, K(kx, ky) = | ky 1 0 | + | P Q R | | 0 0 1 |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | 1 kx 0 | | J K L | | J+kx*M K+kx*N L+kx*O | +K(kx, ky) * Matrix = | ky 1 0 | | M N O | = | ky*J+M ky*K+N ky*L+O | + | 0 0 1 | | P Q R | | P Q R |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postSkew_2_kx"> <code><strong>kx </strong></code> </a></td> <td> +horizontal skew factor</td> + </tr> <tr> <td><a name="SkMatrix_postSkew_2_ky"> <code><strong>ky </strong></code> </a></td> <td> +vertical skew factor</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="3aa2603225dff72ac53dd359f897f494"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preSkew">preSkew</a> <a href="#SkMatrix_setSkew">setSkew</a> + +--- + +<a name="SkMatrix_postConcat"></a> +## postConcat + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void postConcat(const SkMatrix& other) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#Matrix">Matrix</a> <a href="#SkMatrix_postConcat_other">other</a> multiplied by <a href="#Matrix">Matrix</a>. +This can be thought of mapping by <a href="#SkMatrix_postConcat_other">other</a> after applying <a href="#Matrix">Matrix</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | J K L | | A B C | +Matrix = | M N O |, other = | D E F | + | P Q R | | G H I |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +other * Matrix = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_postConcat_other"> <code><strong>other </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> on left side of multiply expression</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="0a4214289249c77f48d59227c4ac4d9e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preConcat">preConcat</a> <a href="#SkMatrix_setConcat">setConcat</a> <a href="#SkMatrix_Concat">Concat</a> + +--- + +## <a name="SkMatrix_ScaleToFit"></a> Enum SkMatrix::ScaleToFit + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +enum <a href="#SkMatrix_ScaleToFit">ScaleToFit</a> { +<a href="#SkMatrix_kFill_ScaleToFit">kFill ScaleToFit</a>, +<a href="#SkMatrix_kStart_ScaleToFit">kStart ScaleToFit</a>, +<a href="#SkMatrix_kCenter_ScaleToFit">kCenter ScaleToFit</a>, +<a href="#SkMatrix_kEnd_ScaleToFit">kEnd ScaleToFit</a>, +};</pre> + +<a href="#SkMatrix_ScaleToFit">ScaleToFit</a> describes how <a href="#Matrix">Matrix</a> is constructed to map one <a href="SkRect_Reference#Rect">Rect</a> to another. +<a href="#SkMatrix_ScaleToFit">ScaleToFit</a> may allow <a href="#Matrix">Matrix</a> to have unequal horizontal and vertical scaling, +or may restrict <a href="#Matrix">Matrix</a> to square scaling. If restricted, <a href="#SkMatrix_ScaleToFit">ScaleToFit</a> specifies +how <a href="#Matrix">Matrix</a> maps to the side or center of the destination <a href="SkRect_Reference#Rect">Rect</a>. + +### Constants + +<table> + <tr> + <td><a name="SkMatrix_kFill_ScaleToFit"> <code><strong>SkMatrix::kFill_ScaleToFit </strong></code> </a></td><td>0</td><td>Computes <a href="#Matrix">Matrix</a> that scales in x and y independently, so that source <a href="SkRect_Reference#Rect">Rect</a> is +mapped to completely fill destination <a href="SkRect_Reference#Rect">Rect</a>. The aspect ratio of source <a href="SkRect_Reference#Rect">Rect</a> +may change.</td> + </tr> + <tr> + <td><a name="SkMatrix_kStart_ScaleToFit"> <code><strong>SkMatrix::kStart_ScaleToFit </strong></code> </a></td><td>1</td><td>Computes <a href="#Matrix">Matrix</a> that maintains source <a href="SkRect_Reference#Rect">Rect</a> aspect ratio, mapping source <a href="SkRect_Reference#Rect">Rect</a> +width or height to destination <a href="SkRect_Reference#Rect">Rect</a>. Aligns mapping to left and top edges +of destination <a href="SkRect_Reference#Rect">Rect</a>.</td> + </tr> + <tr> + <td><a name="SkMatrix_kCenter_ScaleToFit"> <code><strong>SkMatrix::kCenter_ScaleToFit </strong></code> </a></td><td>2</td><td>Computes <a href="#Matrix">Matrix</a> that maintains source <a href="SkRect_Reference#Rect">Rect</a> aspect ratio, mapping source <a href="SkRect_Reference#Rect">Rect</a> +width or height to destination <a href="SkRect_Reference#Rect">Rect</a>. Aligns mapping to center of destination +<a href="SkRect_Reference#Rect">Rect</a>.</td> + </tr> + <tr> + <td><a name="SkMatrix_kEnd_ScaleToFit"> <code><strong>SkMatrix::kEnd_ScaleToFit </strong></code> </a></td><td>3</td><td>Computes <a href="#Matrix">Matrix</a> that maintains source <a href="SkRect_Reference#Rect">Rect</a> aspect ratio, mapping source <a href="SkRect_Reference#Rect">Rect</a> +width or height to destination <a href="SkRect_Reference#Rect">Rect</a>. Aligns mapping to right and bottom +edges of destination <a href="SkRect_Reference#Rect">Rect</a>.</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="17c3070b31b700ea8f52e48af9a66b6e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setRectToRect">setRectToRect</a> <a href="#SkMatrix_MakeRectToRect">MakeRectToRect</a> <a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> + + + +<a name="SkMatrix_setRectToRect"></a> +## setRectToRect + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool setRectToRect(const SkRect& src, const SkRect& dst, ScaleToFit stf) +</pre> + +Sets <a href="#Matrix">Matrix</a> to scale and translate <a href="#SkMatrix_setRectToRect_src">src</a> <a href="SkRect_Reference#Rect">Rect</a> to <a href="#SkMatrix_setRectToRect_dst">dst</a> <a href="SkRect_Reference#Rect">Rect</a>. <a href="#SkMatrix_setRectToRect_stf">stf</a> selects whether +mapping completely fills <a href="#SkMatrix_setRectToRect_dst">dst</a> or preserves the aspect ratio, and how to align +<a href="#SkMatrix_setRectToRect_src">src</a> within <a href="#SkMatrix_setRectToRect_dst">dst</a>. Returns false if <a href="#SkMatrix_setRectToRect_src">src</a> is empty, and sets <a href="#Matrix">Matrix</a> to identity. +Returns true if <a href="#SkMatrix_setRectToRect_dst">dst</a> is empty, and sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 0 0 0 | +| 0 0 0 | +| 0 0 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setRectToRect_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map from</td> + </tr> <tr> <td><a name="SkMatrix_setRectToRect_dst"> <code><strong>dst </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map to</td> + </tr> <tr> <td><a name="SkMatrix_setRectToRect_stf"> <code><strong>stf </strong></code> </a></td> <td> +one of: <a href="#SkMatrix_kFill_ScaleToFit">kFill ScaleToFit</a>, <a href="#SkMatrix_kStart_ScaleToFit">kStart ScaleToFit</a>, +<a href="#SkMatrix_kCenter_ScaleToFit">kCenter ScaleToFit</a>, <a href="#SkMatrix_kEnd_ScaleToFit">kEnd ScaleToFit</a></td> + </tr> +</table> + +### Return Value + +true if <a href="#Matrix">Matrix</a> can represent <a href="SkRect_Reference#Rect">Rect</a> mapping + +### Example + +<div><fiddle-embed name="69cdea599dcaaec35efcb24403f4287b"> + +#### Example Output + +~~~~ +src: 0, 0, 0, 0 dst: 0, 0, 0, 0 success: false +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 0, 0, 0, 0 dst: 5, 6, 8, 9 success: false +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 0, 0, 0, 0 success: true +[ 0.0000 0.0000 0.0000][ 0.0000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 5, 6, 8, 9 success: true +[ 1.5000 0.0000 3.5000][ 0.0000 1.5000 3.0000][ 0.0000 0.0000 1.0000] +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_MakeRectToRect">MakeRectToRect</a> <a href="#SkMatrix_ScaleToFit">ScaleToFit</a> <a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> <a href="#SkRect_isEmpty">SkRect::isEmpty</a> + +--- + +<a name="SkMatrix_MakeRectToRect"></a> +## MakeRectToRect + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static SkMatrix MakeRectToRect(const SkRect& src, const SkRect& dst, + ScaleToFit stf) +</pre> + +Returns <a href="#Matrix">Matrix</a> <a href="#SkMatrix_set">set</a> to scale and translate <a href="#SkMatrix_MakeRectToRect_src">src</a> <a href="SkRect_Reference#Rect">Rect</a> to <a href="#SkMatrix_MakeRectToRect_dst">dst</a> <a href="SkRect_Reference#Rect">Rect</a>. <a href="#SkMatrix_MakeRectToRect_stf">stf</a> selects +whether mapping completely fills <a href="#SkMatrix_MakeRectToRect_dst">dst</a> or preserves the aspect ratio, and how to +align <a href="#SkMatrix_MakeRectToRect_src">src</a> within <a href="#SkMatrix_MakeRectToRect_dst">dst</a>. Returns the identity <a href="#Matrix">Matrix</a> if <a href="#SkMatrix_MakeRectToRect_src">src</a> is empty. If <a href="#SkMatrix_MakeRectToRect_dst">dst</a> is +empty, returns <a href="#Matrix">Matrix</a> <a href="#SkMatrix_set">set</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 0 0 0 | +| 0 0 0 | +| 0 0 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_MakeRectToRect_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map from</td> + </tr> <tr> <td><a name="SkMatrix_MakeRectToRect_dst"> <code><strong>dst </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map to</td> + </tr> <tr> <td><a name="SkMatrix_MakeRectToRect_stf"> <code><strong>stf </strong></code> </a></td> <td> +one of: <a href="#SkMatrix_kFill_ScaleToFit">kFill ScaleToFit</a>, <a href="#SkMatrix_kStart_ScaleToFit">kStart ScaleToFit</a>, +<a href="#SkMatrix_kCenter_ScaleToFit">kCenter ScaleToFit</a>, <a href="#SkMatrix_kEnd_ScaleToFit">kEnd ScaleToFit</a></td> + </tr> +</table> + +### Return Value + +<a href="#Matrix">Matrix</a> mapping <a href="#SkMatrix_MakeRectToRect_src">src</a> to <a href="#SkMatrix_MakeRectToRect_dst">dst</a> + +### Example + +<div><fiddle-embed name="a1d6a6721b39350f81021f71a1b93208"> + +#### Example Output + +~~~~ +src: 0, 0, 0, 0 dst: 0, 0, 0, 0 +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 0, 0, 0, 0 dst: 5, 6, 8, 9 +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 0, 0, 0, 0 +[ 0.0000 0.0000 0.0000][ 0.0000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +src: 1, 2, 3, 4 dst: 5, 6, 8, 9 +[ 1.5000 0.0000 3.5000][ 0.0000 1.5000 3.0000][ 0.0000 0.0000 1.0000] +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setRectToRect">setRectToRect</a> <a href="#SkMatrix_ScaleToFit">ScaleToFit</a> <a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> <a href="#SkRect_isEmpty">SkRect::isEmpty</a> + +--- + +<a name="SkMatrix_setPolyToPoly"></a> +## setPolyToPoly + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool setPolyToPoly(const SkPoint src[], const SkPoint dst[], int count) +</pre> + +Sets <a href="#Matrix">Matrix</a> to map <a href="#SkMatrix_setPolyToPoly_src">src</a> to <a href="#SkMatrix_setPolyToPoly_dst">dst</a>. <a href="#SkMatrix_setPolyToPoly_count">count</a> must be zero or greater, and four or less. + +If <a href="#SkMatrix_setPolyToPoly_count">count</a> is zero, sets <a href="#Matrix">Matrix</a> to identity and returns true. +If <a href="#SkMatrix_setPolyToPoly_count">count</a> is one, sets <a href="#Matrix">Matrix</a> to translate and returns true. +If <a href="#SkMatrix_setPolyToPoly_count">count</a> is two or more, sets <a href="#Matrix">Matrix</a> to map <a href="#Point">Points</a> if possible; returns false +if <a href="#Matrix">Matrix</a> cannot be constructed. If <a href="#SkMatrix_setPolyToPoly_count">count</a> is four, <a href="#Matrix">Matrix</a> may include +perspective. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setPolyToPoly_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="#Point">Points</a> to map from</td> + </tr> <tr> <td><a name="SkMatrix_setPolyToPoly_dst"> <code><strong>dst </strong></code> </a></td> <td> +<a href="#Point">Points</a> to map to</td> + </tr> <tr> <td><a name="SkMatrix_setPolyToPoly_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Point">Points</a> in <a href="#SkMatrix_setPolyToPoly_src">src</a> and <a href="#SkMatrix_setPolyToPoly_dst">dst</a></td> + </tr> +</table> + +### Return Value + +true if <a href="#Matrix">Matrix</a> was constructed successfully + +### Example + +<div><fiddle-embed name="c851d1313e8909aaea4f0591699fdb7b"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setRectToRect">setRectToRect</a> <a href="#SkMatrix_MakeRectToRect">MakeRectToRect</a> + +--- + +<a name="SkMatrix_invert"></a> +## invert + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool SK_WARN_UNUSED_RESULT invert(SkMatrix* inverse) const +</pre> + +Sets <a href="#SkMatrix_invert_inverse">inverse</a> to reciprocal matrix, returning true if <a href="#Matrix">Matrix</a> can be inverted. +Geometrically, if <a href="#Matrix">Matrix</a> maps from source to destination, <a href="#SkMatrix_invert_inverse">inverse</a> <a href="#Matrix">Matrix</a> +maps from destination to source. If <a href="#Matrix">Matrix</a> can not be inverted, <a href="#SkMatrix_invert_inverse">inverse</a> is +unchanged. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_invert_inverse"> <code><strong>inverse </strong></code> </a></td> <td> +storage for inverted <a href="#Matrix">Matrix</a>; may be nullptr</td> + </tr> +</table> + +### Return Value + +true if <a href="#Matrix">Matrix</a> can be inverted + +### Example + +<div><fiddle-embed name="10a10c5bf2ac7ec88e84204441fc83b6"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_Concat">Concat</a> + +--- + +<a name="SkMatrix_SetAffineIdentity"></a> +## SetAffineIdentity + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static void SetAffineIdentity(SkScalar affine[6]) +</pre> + +Fills <a href="#SkMatrix_SetAffineIdentity_affine">affine</a> with identity values in column major order. +Sets <a href="#SkMatrix_SetAffineIdentity_affine">affine</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 0 | +| 0 1 0 |</pre> + +Affine 3x2 matrices in column major order are used by <a href="undocumented#OpenGL">OpenGL</a> and <a href="undocumented#XPS">XPS</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_SetAffineIdentity_affine"> <code><strong>affine </strong></code> </a></td> <td> +storage for 3x2 <a href="#SkMatrix_SetAffineIdentity_affine">affine</a> matrix</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="e10adbd0bcc940c5d4d872db0e78e892"> + +#### Example Output + +~~~~ +ScaleX: 1 SkewY: 0 SkewX: 0 ScaleY: 1 TransX: 0 TransY: 0 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setAffine">setAffine</a> <a href="#SkMatrix_asAffine">asAffine</a> + +--- + +<a name="SkMatrix_asAffine"></a> +## asAffine + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool SK_WARN_UNUSED_RESULT asAffine(SkScalar affine[6]) const +</pre> + +Fills <a href="#SkMatrix_asAffine_affine">affine</a> in column major order. Sets <a href="#SkMatrix_asAffine_affine">affine</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale-x skew-x translate-x | +| skew-y scale-y translate-y |</pre> + +If <a href="#Matrix">Matrix</a> contains perspective, returns false and leaves <a href="#SkMatrix_asAffine_affine">affine</a> unchanged. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_asAffine_affine"> <code><strong>affine </strong></code> </a></td> <td> +storage for 3x2 <a href="#SkMatrix_asAffine_affine">affine</a> matrix; may be nullptr</td> + </tr> +</table> + +### Return Value + +true if <a href="#Matrix">Matrix</a> does not contain perspective + +### Example + +<div><fiddle-embed name="752e4a48ed1dae05765a2499c390f277"> + +#### Example Output + +~~~~ +ScaleX: 2 SkewY: 5 SkewX: 3 ScaleY: 6 TransX: 4 TransY: 7 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setAffine">setAffine</a> <a href="#SkMatrix_SetAffineIdentity">SetAffineIdentity</a> + +--- + +<a name="SkMatrix_setAffine"></a> +## setAffine + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setAffine(const SkScalar affine[6]) +</pre> + +Sets <a href="#Matrix">Matrix</a> to <a href="#SkMatrix_setAffine_affine">affine</a> values, passed in column major order. Given <a href="#SkMatrix_setAffine_affine">affine</a>, +column, then row, as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale-x skew-x translate-x | +| skew-y scale-y translate-y |</pre> + +<a href="#Matrix">Matrix</a> is <a href="#SkMatrix_set">set</a>, row, then column, to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| scale-x skew-x translate-x | +| skew-y scale-y translate-y | +| 0 0 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setAffine_affine"> <code><strong>affine </strong></code> </a></td> <td> +3x2 <a href="#SkMatrix_setAffine_affine">affine</a> matrix</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="403370bd53526f59020a7141955d70b0"> + +#### Example Output + +~~~~ +ScaleX: 2 SkewY: 5 SkewX: 3 ScaleY: 6 TransX: 4 TransY: 7 +[ 2.0000 3.0000 4.0000][ 5.0000 6.0000 7.0000][ 0.0000 0.0000 1.0000] +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_asAffine">asAffine</a> <a href="#SkMatrix_SetAffineIdentity">SetAffineIdentity</a> + +--- + +<a name="SkMatrix_mapPoints"></a> +## mapPoints + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapPoints(SkPoint dst[], const SkPoint src[], int count) const +</pre> + +Maps <a href="#SkMatrix_mapPoints_src">src</a> <a href="undocumented#Point">Point</a> array of length <a href="#SkMatrix_mapPoints_count">count</a> to <a href="#SkMatrix_mapPoints_dst">dst</a> <a href="undocumented#Point">Point</a> array of equal or greater +length. <a href="#Point">Points</a> are mapped by multiplying each <a href="undocumented#Point">Point</a> by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +for (i = 0; i < count; ++i) { + x = src[i].fX + y = src[i].fY +}</pre> + +each <a href="#SkMatrix_mapPoints_dst">dst</a> <a href="undocumented#Point">Point</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +<a href="#SkMatrix_mapPoints_src">src</a> and <a href="#SkMatrix_mapPoints_dst">dst</a> may point to the same storage. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapPoints_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for mapped <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapPoints_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="#Point">Points</a> to transform</td> + </tr> <tr> <td><a name="SkMatrix_mapPoints_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Point">Points</a> to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="f99dcb00296d0c56b6c0e178e94b3534"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapXY">mapXY</a> <a href="#SkMatrix_mapHomogeneousPoints">mapHomogeneousPoints</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapPoints(SkPoint pts[], int count) const +</pre> + +Maps <a href="#SkMatrix_mapPoints_2_pts">pts</a> <a href="undocumented#Point">Point</a> array of length <a href="#SkMatrix_mapPoints_2_count">count</a> in place. <a href="#Point">Points</a> are mapped by multiplying +each <a href="undocumented#Point">Point</a> by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +for (i = 0; i < count; ++i) { + x = pts[i].fX + y = pts[i].fY +}</pre> + +each resulting <a href="#SkMatrix_mapPoints_2_pts">pts</a> <a href="undocumented#Point">Point</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapPoints_2_pts"> <code><strong>pts </strong></code> </a></td> <td> +storage for mapped <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapPoints_2_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Point">Points</a> to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="428ca171ae3bd0d3f992458ac598b97b"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapXY">mapXY</a> <a href="#SkMatrix_mapHomogeneousPoints">mapHomogeneousPoints</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<a name="SkMatrix_mapPointsWithStride"></a> +## mapPointsWithStride + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapPointsWithStride(SkPoint pts[], size_t stride, int count) const +</pre> + +Maps <a href="#SkMatrix_mapPointsWithStride_count">count</a> <a href="#SkMatrix_mapPointsWithStride_pts">pts</a>, skipping <a href="#SkMatrix_mapPointsWithStride_stride">stride</a> bytes to advance from one <a href="undocumented#Point">Point</a> to the next. +<a href="#Point">Points</a> are mapped by multiplying each <a href="undocumented#Point">Point</a> by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 |</pre> + +each resulting <a href="#SkMatrix_mapPointsWithStride_pts">pts</a> <a href="undocumented#Point">Point</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapPointsWithStride_pts"> <code><strong>pts </strong></code> </a></td> <td> +storage for mapped <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapPointsWithStride_stride"> <code><strong>stride </strong></code> </a></td> <td> +size of record starting with <a href="undocumented#Point">Point</a>, in bytes</td> + </tr> <tr> <td><a name="SkMatrix_mapPointsWithStride_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Point">Points</a> to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="02c50c7bb5d5dd1fe7e54b0d3bf64c2a"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapXY">mapXY</a> <a href="#SkMatrix_mapHomogeneousPoints">mapHomogeneousPoints</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapPointsWithStride(SkPoint dst[], const SkPoint src[], size_t stride, + int count) const +</pre> + +Maps <a href="#SkMatrix_mapPointsWithStride_2_src">src</a> <a href="undocumented#Point">Point</a> array of length <a href="#SkMatrix_mapPointsWithStride_2_count">count</a> to <a href="#SkMatrix_mapPointsWithStride_2_dst">dst</a> <a href="undocumented#Point">Point</a> array, skipping <a href="#SkMatrix_mapPointsWithStride_2_stride">stride</a> bytes +to advance from one <a href="undocumented#Point">Point</a> to the next. +<a href="#Point">Points</a> are mapped by multiplying each <a href="undocumented#Point">Point</a> by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, src = | y | + | G H I | | 1 |</pre> + +each resulting <a href="#SkMatrix_mapPointsWithStride_2_dst">dst</a> <a href="undocumented#Point">Point</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapPointsWithStride_2_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for mapped <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapPointsWithStride_2_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="#Point">Points</a> to transform</td> + </tr> <tr> <td><a name="SkMatrix_mapPointsWithStride_2_stride"> <code><strong>stride </strong></code> </a></td> <td> +size of record starting with <a href="undocumented#Point">Point</a>, in bytes</td> + </tr> <tr> <td><a name="SkMatrix_mapPointsWithStride_2_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Point">Points</a> to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="08e32de52131e6859db16729b2e56e4e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapXY">mapXY</a> <a href="#SkMatrix_mapHomogeneousPoints">mapHomogeneousPoints</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<a name="SkMatrix_mapHomogeneousPoints"></a> +## mapHomogeneousPoints + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapHomogeneousPoints(SkPoint3 dst[], const SkPoint3 src[], int count) const +</pre> + +Maps <a href="#SkMatrix_mapHomogeneousPoints_src">src</a> <a href="undocumented#Point3">Point3</a> array of length <a href="#SkMatrix_mapHomogeneousPoints_count">count</a> to <a href="#SkMatrix_mapHomogeneousPoints_dst">dst</a> <a href="undocumented#Point3">Point3</a> array, which must of length <a href="#SkMatrix_mapHomogeneousPoints_count">count</a> or +greater. <a href="undocumented#Point3">Point3</a> array is mapped by multiplying each <a href="undocumented#Point3">Point3</a> by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, src = | y | + | G H I | | z |</pre> + +each resulting <a href="#SkMatrix_mapHomogeneousPoints_dst">dst</a> <a href="undocumented#Point">Point</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| +Matrix * src = |D E F| |y| = |Ax+By+Cz Dx+Ey+Fz Gx+Hy+Iz| + |G H I| |z|</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapHomogeneousPoints_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for mapped <a href="undocumented#Point3">Point3</a> array</td> + </tr> <tr> <td><a name="SkMatrix_mapHomogeneousPoints_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="undocumented#Point3">Point3</a> array to transform</td> + </tr> <tr> <td><a name="SkMatrix_mapHomogeneousPoints_count"> <code><strong>count </strong></code> </a></td> <td> +items in <a href="undocumented#Point3">Point3</a> array to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="0d8c7aa7249048f2b83d32cf13f88560"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapXY">mapXY</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<a name="SkMatrix_mapXY"></a> +## mapXY + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapXY(SkScalar x, SkScalar y, SkPoint* result) const +</pre> + +Maps <a href="undocumented#Point">Point</a> (<a href="#SkMatrix_mapXY_x">x</a>, <a href="#SkMatrix_mapXY_y">y</a>) to <a href="#SkMatrix_mapXY_result">result</a>. <a href="undocumented#Point">Point</a> is mapped by multiplying by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 |</pre> + +<a href="#SkMatrix_mapXY_result">result</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapXY_x"> <code><strong>x </strong></code> </a></td> <td> +x-coordinate of <a href="undocumented#Point">Point</a> to map</td> + </tr> <tr> <td><a name="SkMatrix_mapXY_y"> <code><strong>y </strong></code> </a></td> <td> +y-coordinate of <a href="undocumented#Point">Point</a> to map</td> + </tr> <tr> <td><a name="SkMatrix_mapXY_result"> <code><strong>result </strong></code> </a></td> <td> +storage for mapped <a href="undocumented#Point">Point</a></td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="9e50185d502dc6903783679a84106089"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkPoint mapXY(SkScalar x, SkScalar y) const +</pre> + +Returns <a href="undocumented#Point">Point</a> (<a href="#SkMatrix_mapXY_2_x">x</a>, <a href="#SkMatrix_mapXY_2_y">y</a>) multiplied by <a href="#Matrix">Matrix</a>. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 |</pre> + +result is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapXY_2_x"> <code><strong>x </strong></code> </a></td> <td> +x-coordinate of <a href="undocumented#Point">Point</a> to map</td> + </tr> <tr> <td><a name="SkMatrix_mapXY_2_y"> <code><strong>y </strong></code> </a></td> <td> +y-coordinate of <a href="undocumented#Point">Point</a> to map</td> + </tr> +</table> + +### Return Value + +mapped <a href="undocumented#Point">Point</a> + +### Example + +<div><fiddle-embed name="b1ead09c67a177ab8eace12b061610a7"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapVectors">mapVectors</a> + +--- + +<a name="SkMatrix_mapVectors"></a> +## mapVectors + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapVectors(SkVector dst[], const SkVector src[], int count) const +</pre> + +Maps <a href="#SkMatrix_mapVectors_src">src</a> <a href="undocumented#Vector">Vector</a> array of length <a href="#SkMatrix_mapVectors_count">count</a> to <a href="undocumented#Vector">Vector</a> <a href="undocumented#Point">Point</a> array of equal or greater +length. <a href="#Vector">Vectors</a> are mapped by multiplying each <a href="undocumented#Vector">Vector</a> by <a href="#Matrix">Matrix</a>, treating +<a href="#Matrix">Matrix</a> translation as zero. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B 0 | | x | +Matrix = | D E 0 |, src = | y | + | G H I | | 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +for (i = 0; i < count; ++i) { + x = src[i].fX + y = src[i].fY +}</pre> + +each <a href="#SkMatrix_mapVectors_dst">dst</a> <a href="undocumented#Vector">Vector</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B 0| |x| Ax+By Dx+Ey +Matrix * src = |D E 0| |y| = |Ax+By Dx+Ey Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +<a href="#SkMatrix_mapVectors_src">src</a> and <a href="#SkMatrix_mapVectors_dst">dst</a> may point to the same storage. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapVectors_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for mapped <a href="#Vector">Vectors</a></td> + </tr> <tr> <td><a name="SkMatrix_mapVectors_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="#Vector">Vectors</a> to transform</td> + </tr> <tr> <td><a name="SkMatrix_mapVectors_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Vector">Vectors</a> to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="918a9778c3d7d5cb306692784399f6dc"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapVector">mapVector</a> <a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapXY">mapXY</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapVectors(SkVector vecs[], int count) const +</pre> + +Maps <a href="#SkMatrix_mapVectors_2_vecs">vecs</a> <a href="undocumented#Vector">Vector</a> array of length <a href="#SkMatrix_mapVectors_2_count">count</a> in place, multiplying each <a href="undocumented#Vector">Vector</a> by +<a href="#Matrix">Matrix</a>, treating <a href="#Matrix">Matrix</a> translation as zero. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B 0 | | x | +Matrix = | D E 0 |, vec = | y | + | G H I | | 1 |</pre> + +where + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +for (i = 0; i < count; ++i) { + x = vecs[i].fX + y = vecs[i].fY +}</pre> + +each result <a href="undocumented#Vector">Vector</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B 0| |x| Ax+By Dx+Ey +Matrix * vec = |D E 0| |y| = |Ax+By Dx+Ey Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapVectors_2_vecs"> <code><strong>vecs </strong></code> </a></td> <td> +<a href="#Vector">Vectors</a> to transform, and storage for mapped <a href="#Vector">Vectors</a></td> + </tr> <tr> <td><a name="SkMatrix_mapVectors_2_count"> <code><strong>count </strong></code> </a></td> <td> +number of <a href="#Vector">Vectors</a> to transform</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="5754501a00a1323e76353fb53153e939"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapVector">mapVector</a> <a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapXY">mapXY</a> + +--- + +<a name="SkMatrix_mapVector"></a> +## mapVector + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapVector(SkScalar dx, SkScalar dy, SkVector* result) const +</pre> + +Maps <a href="undocumented#Vector">Vector</a> (x, y) to <a href="#SkMatrix_mapVector_result">result</a>. <a href="undocumented#Vector">Vector</a> is mapped by multiplying by <a href="#Matrix">Matrix</a>, +treating <a href="#Matrix">Matrix</a> translation as zero. Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B 0 | | dx | +Matrix = | D E 0 |, vec = | dy | + | G H I | | 1 |</pre> + +each <a href="#SkMatrix_mapVector_result">result</a> <a href="undocumented#Vector">Vector</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B 0| |dx| A*dx+B*dy D*dx+E*dy +Matrix * vec = |D E 0| |dy| = |A*dx+B*dy D*dx+E*dy G*dx+H*dy+I| = ----------- , ----------- + |G H I| | 1| G*dx+H*dy+I G*dx+*dHy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapVector_dx"> <code><strong>dx </strong></code> </a></td> <td> +x-coordinate of <a href="undocumented#Vector">Vector</a> to map</td> + </tr> <tr> <td><a name="SkMatrix_mapVector_dy"> <code><strong>dy </strong></code> </a></td> <td> +y-coordinate of <a href="undocumented#Vector">Vector</a> to map</td> + </tr> <tr> <td><a name="SkMatrix_mapVector_result"> <code><strong>result </strong></code> </a></td> <td> +storage for mapped <a href="undocumented#Vector">Vector</a></td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="aed143fc6cd0bce4ed029b98d1e61f2d"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapVectors">mapVectors</a> <a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapXY">mapXY</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkVector mapVector(SkScalar dx, SkScalar dy) const +</pre> + +Returns <a href="undocumented#Vector">Vector</a> (x, y) multiplied by <a href="#Matrix">Matrix</a>, treating <a href="#Matrix">Matrix</a> translation as zero. +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B 0 | | dx | +Matrix = | D E 0 |, vec = | dy | + | G H I | | 1 |</pre> + +each result <a href="undocumented#Vector">Vector</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B 0| |dx| A*dx+B*dy D*dx+E*dy +Matrix * vec = |D E 0| |dy| = |A*dx+B*dy D*dx+E*dy G*dx+H*dy+I| = ----------- , ----------- + |G H I| | 1| G*dx+H*dy+I G*dx+*dHy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapVector_2_dx"> <code><strong>dx </strong></code> </a></td> <td> +x-coordinate of <a href="undocumented#Vector">Vector</a> to map</td> + </tr> <tr> <td><a name="SkMatrix_mapVector_2_dy"> <code><strong>dy </strong></code> </a></td> <td> +y-coordinate of <a href="undocumented#Vector">Vector</a> to map</td> + </tr> +</table> + +### Return Value + +mapped <a href="undocumented#Vector">Vector</a> + +### Example + +<div><fiddle-embed name="8bf1518db3f369696cd3065b541a8bd7"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapVectors">mapVectors</a> <a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_mapPointsWithStride">mapPointsWithStride</a> <a href="#SkMatrix_mapXY">mapXY</a> + +--- + +<a name="SkMatrix_mapRect"></a> +## mapRect + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool mapRect(SkRect* dst, const SkRect& src) const +</pre> + +Sets <a href="#SkMatrix_mapRect_dst">dst</a> to bounds of <a href="#SkMatrix_mapRect_src">src</a> corners mapped by <a href="#Matrix">Matrix</a>. +Returns true if mapped corners are <a href="#SkMatrix_mapRect_dst">dst</a> corners. + +Returned value is the same as calling <a href="#SkMatrix_rectStaysRect">rectStaysRect</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapRect_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for bounds of mapped <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapRect_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map</td> + </tr> +</table> + +### Return Value + +true if <a href="#SkMatrix_mapRect_dst">dst</a> is equivalent to mapped <a href="#SkMatrix_mapRect_src">src</a> + +### Example + +<div><fiddle-embed name="dbcf928b035a31ca69c99392e2e2cca9"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_rectStaysRect">rectStaysRect</a> + +--- + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool mapRect(SkRect* rect) const +</pre> + +Sets <a href="#SkMatrix_mapRect_2_rect">rect</a> to bounds of <a href="#SkMatrix_mapRect_2_rect">rect</a> corners mapped by <a href="#Matrix">Matrix</a>. +Returns true if mapped corners are computed <a href="#SkMatrix_mapRect_2_rect">rect</a> corners. + +Returned value is the same as calling <a href="#SkMatrix_rectStaysRect">rectStaysRect</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapRect_2_rect"> <code><strong>rect </strong></code> </a></td> <td> +rectangle to map, and storage for bounds of mapped corners</td> + </tr> +</table> + +### Return Value + +true if result is equivalent to mapped src + +### Example + +<div><fiddle-embed name="5fafd0bd23d1ed37425b970b4a3c6cc9"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapRectScaleTranslate">mapRectScaleTranslate</a> <a href="#SkMatrix_mapPoints">mapPoints</a> <a href="#SkMatrix_rectStaysRect">rectStaysRect</a> + +--- + +<a name="SkMatrix_mapRectToQuad"></a> +## mapRectToQuad + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapRectToQuad(SkPoint dst[4], const SkRect& rect) const +</pre> + +Maps four corners of <a href="#SkMatrix_mapRectToQuad_rect">rect</a> to <a href="#SkMatrix_mapRectToQuad_dst">dst</a>. <a href="#Point">Points</a> are mapped by multiplying each +<a href="#SkMatrix_mapRectToQuad_rect">rect</a> corner by <a href="#Matrix">Matrix</a>. <a href="#SkMatrix_mapRectToQuad_rect">rect</a> corner is processed in this order: +(<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fLeft, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fTop), (<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fRight, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fTop), (<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fRight, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fBottom), +(<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fLeft, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fBottom). + +<a href="#SkMatrix_mapRectToQuad_rect">rect</a> may be empty: <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fLeft may be greater than or equal to <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fRight; +<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fTop may be greater than or equal to <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fBottom. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | x | +Matrix = | D E F |, pt = | y | + | G H I | | 1 |</pre> + +where pt is initialized from each of (<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fLeft, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fTop), +(<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fRight, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fTop), (<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fRight, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fBottom), (<a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fLeft, <a href="#SkMatrix_mapRectToQuad_rect">rect</a>.fBottom), +each <a href="#SkMatrix_mapRectToQuad_dst">dst</a> <a href="undocumented#Point">Point</a> is computed as: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + |A B C| |x| Ax+By+C Dx+Ey+F +Matrix * pt = |D E F| |y| = |Ax+By+C Dx+Ey+F Gx+Hy+I| = ------- , ------- + |G H I| |1| Gx+Hy+I Gx+Hy+I</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapRectToQuad_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for mapped corner <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapRectToQuad_rect"> <code><strong>rect </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="3bf9404624735d7cf34b47b9c7b27bcc"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapRect">mapRect</a> <a href="#SkMatrix_mapRectScaleTranslate">mapRectScaleTranslate</a> + +--- + +<a name="SkMatrix_mapRectScaleTranslate"></a> +## mapRectScaleTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void mapRectScaleTranslate(SkRect* dst, const SkRect& src) const +</pre> + +Sets <a href="#SkMatrix_mapRectScaleTranslate_dst">dst</a> to bounds of <a href="#SkMatrix_mapRectScaleTranslate_src">src</a> corners mapped by <a href="#Matrix">Matrix</a>. If matrix contains +elements other than scale or translate: asserts if <a href="undocumented#SK_DEBUG">SK DEBUG</a> is defined; +otherwise, results are undefined. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapRectScaleTranslate_dst"> <code><strong>dst </strong></code> </a></td> <td> +storage for bounds of mapped <a href="#Point">Points</a></td> + </tr> <tr> <td><a name="SkMatrix_mapRectScaleTranslate_src"> <code><strong>src </strong></code> </a></td> <td> +<a href="SkRect_Reference#Rect">Rect</a> to map</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="62bc26989c2b4c2a54d516596a71dd97"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapRect">mapRect</a> <a href="#SkMatrix_mapRectToQuad">mapRectToQuad</a> <a href="#SkMatrix_isScaleTranslate">isScaleTranslate</a> <a href="#SkMatrix_rectStaysRect">rectStaysRect</a> + +--- + +<a name="SkMatrix_mapRadius"></a> +## mapRadius + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar mapRadius(SkScalar radius) const +</pre> + +Returns geometric mean <a href="#SkMatrix_mapRadius_radius">radius</a> of ellipse formed by constructing <a href="undocumented#Circle">Circle</a> of +size <a href="#SkMatrix_mapRadius_radius">radius</a>, and mapping constructed <a href="undocumented#Circle">Circle</a> with <a href="#Matrix">Matrix</a>. The result squared is +equal to the major axis length times the minor axis length. +Result is not meaningful if <a href="#Matrix">Matrix</a> contains perspective elements. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_mapRadius_radius"> <code><strong>radius </strong></code> </a></td> <td> +<a href="undocumented#Circle">Circle</a> size to map</td> + </tr> +</table> + +### Return Value + +average mapped <a href="#SkMatrix_mapRadius_radius">radius</a> + +### Example + +<div><fiddle-embed name="6d6f2082fcf59d9f02bfb1758b87db69"><div>The area enclosed by a square with sides equal to mappedRadius is the same as +the area enclosed by the ellipse major and minor axes.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_mapVector">mapVector</a> + +--- + +<a name="SkMatrix_isFixedStepInX"></a> +## isFixedStepInX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool isFixedStepInX() const +</pre> + +Returns true if a unit step in x at some y mapped through <a href="#Matrix">Matrix</a> can be +represented by a constant <a href="undocumented#Vector">Vector</a>. Returns true if <a href="#SkMatrix_getType">getType</a> returns <a href="#SkMatrix_kIdentity_Mask">kIdentity Mask</a>, +or combinations of: <a href="#SkMatrix_kTranslate_Mask">kTranslate Mask</a>, <a href="#SkMatrix_kScale_Mask">kScale Mask</a>, and <a href="#SkMatrix_kAffine_Mask">kAffine Mask</a>. + +May return true if <a href="#SkMatrix_getType">getType</a> returns <a href="#SkMatrix_kPerspective_Mask">kPerspective Mask</a>, but only when <a href="#Matrix">Matrix</a> +does not include rotation or skewing along the y-axis. + +### Return Value + +true if <a href="#Matrix">Matrix</a> does not have complex perspective + +### Example + +<div><fiddle-embed name="ab57b232acef69f26de9cb23d23c8a1a"> + +#### Example Output + +~~~~ +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.0000 0.0000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.0000 0.1000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.0000 0.1000 1.0000] +isFixedStepInX: true +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.1000 0.0000 1.0000] +isFixedStepInX: false +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.1000 0.0000 1.0000] +isFixedStepInX: false +[ 1.0000 0.0000 0.0000][ 0.0000 1.0000 0.0000][ 0.1000 0.1000 1.0000] +isFixedStepInX: false +[ 1.0000 0.0000 0.0000][ 0.0000 2.0000 0.0000][ 0.1000 0.1000 1.0000] +isFixedStepInX: false +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_fixedStepInX">fixedStepInX</a> <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_fixedStepInX"></a> +## fixedStepInX + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkVector fixedStepInX(SkScalar y) const +</pre> + +Returns <a href="undocumented#Vector">Vector</a> representing a unit step in x at <a href="#SkMatrix_fixedStepInX_y">y</a> mapped through <a href="#Matrix">Matrix</a>. +If <a href="#SkMatrix_isFixedStepInX">isFixedStepInX</a> is false, returned value is undefined. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_fixedStepInX_y"> <code><strong>y </strong></code> </a></td> <td> +position of line parallel to x-axis</td> + </tr> +</table> + +### Return Value + +<a href="undocumented#Vector">Vector</a> advance of mapped unit step in x + +### Example + +<div><fiddle-embed name="fad6b92b21b1e1deeae61978cec2d232"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_isFixedStepInX">isFixedStepInX</a> <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_cheapEqualTo"></a> +## cheapEqualTo + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool cheapEqualTo(const SkMatrix& m) const +</pre> + +Returns true if <a href="#Matrix">Matrix</a> equals <a href="#SkMatrix_cheapEqualTo_m">m</a>, using an efficient comparison. + +Returns false when the sign of zero values is the different; when one +matrix has positive zero value and the other has negative zero value. + +Returns true even when both <a href="#Matrix">Matrices</a> contain <a href="undocumented#NaN">NaN</a>. + +<a href="undocumented#NaN">NaN</a> never equals any value, including itself. To improve performance, <a href="undocumented#NaN">NaN</a> values +are treated as bit patterns that are equal if their bit patterns are equal. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_cheapEqualTo_m"> <code><strong>m </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> to compare</td> + </tr> +</table> + +### Return Value + +true if <a href="#SkMatrix_cheapEqualTo_m">m</a> and <a href="#Matrix">Matrix</a> are represented by identical bit patterns + +### Example + +<div><fiddle-embed name="39016b3cfc6bbabb09348a53822ce508"> + +#### Example Output + +~~~~ +identity: a == b a.cheapEqualTo(b): true +neg zero: a == b a.cheapEqualTo(b): false +one NaN: a != b a.cheapEqualTo(b): false +both NaN: a != b a.cheapEqualTo(b): true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_equal_operator">operator==(const SkMatrix& a, const SkMatrix& b)</a> + +--- + +<a name="SkMatrix_equal_operator"></a> +## operator== + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool operator==(const SkMatrix& a, const SkMatrix& b) +</pre> + +Compares <a href="#SkMatrix_equal_operator_a">a</a> and <a href="#SkMatrix_equal_operator_b">b</a>; returns true if <a href="#SkMatrix_equal_operator_a">a</a> and <a href="#SkMatrix_equal_operator_b">b</a> are numerically equal. Returns true +even if sign of zero values are different. Returns false if either <a href="#Matrix">Matrix</a> +contains <a href="undocumented#NaN">NaN</a>, even if the other <a href="#Matrix">Matrix</a> also contains <a href="undocumented#NaN">NaN</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_equal_operator_a"> <code><strong>a </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> to compare</td> + </tr> <tr> <td><a name="SkMatrix_equal_operator_b"> <code><strong>b </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> to compare</td> + </tr> +</table> + +### Return Value + +true if m and <a href="#Matrix">Matrix</a> are numerically equal + +### Example + +<div><fiddle-embed name="3902859150b0f0c4aeb1f25d00434baa"> + +#### Example Output + +~~~~ +identity: a == b a.cheapEqualTo(b): true +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_cheapEqualTo">cheapEqualTo</a> <a href="#SkMatrix_not_equal_operator">operator!=(const SkMatrix& a, const SkMatrix& b)</a> + +--- + +<a name="SkMatrix_not_equal_operator"></a> +## operator!= + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool operator!=(const SkMatrix& a, const SkMatrix& b) +</pre> + +Compares <a href="#SkMatrix_not_equal_operator_a">a</a> and <a href="#SkMatrix_not_equal_operator_b">b</a>; returns true if <a href="#SkMatrix_not_equal_operator_a">a</a> and <a href="#SkMatrix_not_equal_operator_b">b</a> are not numerically equal. Returns false +even if sign of zero values are different. Returns true if either <a href="#Matrix">Matrix</a> +contains <a href="undocumented#NaN">NaN</a>, even if the other <a href="#Matrix">Matrix</a> also contains <a href="undocumented#NaN">NaN</a>. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_not_equal_operator_a"> <code><strong>a </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> to compare</td> + </tr> <tr> <td><a name="SkMatrix_not_equal_operator_b"> <code><strong>b </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> to compare</td> + </tr> +</table> + +### Return Value + +true if m and <a href="#Matrix">Matrix</a> are numerically not equal + +### Example + +<div><fiddle-embed name="8a8fadf5fd294daa4ee152833cc0dc0e"></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_cheapEqualTo">cheapEqualTo</a> <a href="#SkMatrix_equal_operator">operator==(const SkMatrix& a, const SkMatrix& b)</a> + +--- + +<a name="SkMatrix_dump"></a> +## dump + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void dump() const +</pre> + +Writes text representation of <a href="#Matrix">Matrix</a> to standard output. Floating point values +are written with limited precision; it may not be possible to reconstruct +original <a href="#Matrix">Matrix</a> from output. + +### Example + +<div><fiddle-embed name="8d72a4818e5a9188348f6c08ab5d8a40"> + +#### Example Output + +~~~~ +[ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +[ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +matrix != nearlyEqual +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_toString">toString</a> + +--- + +<a name="SkMatrix_toString"></a> +## toString + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void toString(SkString* str) const +</pre> + +Creates string representation of <a href="#Matrix">Matrix</a>. Floating point values +are written with limited precision; it may not be possible to reconstruct +original <a href="#Matrix">Matrix</a> from output. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_toString_str"> <code><strong>str </strong></code> </a></td> <td> +storage for string representation of <a href="#Matrix">Matrix</a></td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="1d86e43958e42b8eaaa9b16df1baa4c8"> + +#### Example Output + +~~~~ +mStr [ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +neStr [ 0.7071 -0.7071 0.0000][ 0.7071 0.7071 0.0000][ 0.0000 0.0000 1.0000] +matrix != nearlyEqual +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_dump">dump</a> + +--- + +<a name="SkMatrix_getMinScale"></a> +## getMinScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getMinScale() const +</pre> + +Returns the minimum scaling factor of <a href="#Matrix">Matrix</a> by decomposing the scaling and +skewing elements. +Returns -1 if scale factor overflows or <a href="#Matrix">Matrix</a> contains perspective. + +### Return Value + +minimum scale factor + +### Example + +<div><fiddle-embed name="1d6f67904c88a806c3731879e9af4ae5"> + +#### Example Output + +~~~~ +matrix.getMinScale() 24 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_getMaxScale">getMaxScale</a> <a href="#SkMatrix_getMinMaxScales">getMinMaxScales</a> + +--- + +<a name="SkMatrix_getMaxScale"></a> +## getMaxScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +SkScalar getMaxScale() const +</pre> + +Returns the maximum scaling factor of <a href="#Matrix">Matrix</a> by decomposing the scaling and +skewing elements. +Returns -1 if scale factor overflows or <a href="#Matrix">Matrix</a> contains perspective. + +### Return Value + +maximum scale factor + +### Example + +<div><fiddle-embed name="3fee4364929899649cf9efc37897e964"> + +#### Example Output + +~~~~ +matrix.getMaxScale() 42 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_getMinScale">getMinScale</a> <a href="#SkMatrix_getMinMaxScales">getMinMaxScales</a> + +--- + +<a name="SkMatrix_getMinMaxScales"></a> +## getMinMaxScales + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool SK_WARN_UNUSED_RESULT getMinMaxScales(SkScalar scaleFactors[2]) const +</pre> + +Sets <a href="#SkMatrix_getMinMaxScales_scaleFactors">scaleFactors</a>[0] to the minimum scaling factor, and <a href="#SkMatrix_getMinMaxScales_scaleFactors">scaleFactors</a>[1] to the +maximum scaling factor. Scaling factors are computed by decomposing +the <a href="#Matrix">Matrix</a> scaling and skewing elements. + +Returns true if <a href="#SkMatrix_getMinMaxScales_scaleFactors">scaleFactors</a> are found; otherwise, returns false and sets +<a href="#SkMatrix_getMinMaxScales_scaleFactors">scaleFactors</a> to undefined values. + +### Parameters + +<table> <tr> <td><a name="SkMatrix_getMinMaxScales_scaleFactors"> <code><strong>scaleFactors </strong></code> </a></td> <td> +storage for minimum and maximum scale factors</td> + </tr> +</table> + +### Return Value + +true if scale factors were computed correctly + +### Example + +<div><fiddle-embed name="cd4dc63d3e04226f0b5861ba8925e223"> + +#### Example Output + +~~~~ +matrix.getMinMaxScales() false 2 2 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_getMinScale">getMinScale</a> <a href="#SkMatrix_getMaxScale">getMaxScale</a> + +--- + +<a name="SkMatrix_decomposeScale"></a> +## decomposeScale + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool decomposeScale(SkSize* scale, SkMatrix* remaining = nullptr) const +</pre> + +Decomposes <a href="#Matrix">Matrix</a> into <a href="#SkMatrix_decomposeScale_scale">scale</a> components and whatever remains. Returns false if +<a href="#Matrix">Matrix</a> could not be decomposed. + +Sets <a href="#SkMatrix_decomposeScale_scale">scale</a> to portion of <a href="#Matrix">Matrix</a> that scales in x and y. Sets <a href="#SkMatrix_decomposeScale_remaining">remaining</a> to <a href="#Matrix">Matrix</a> +with x and y scaling factored out. <a href="#SkMatrix_decomposeScale_remaining">remaining</a> may be passed as nullptr +to determine if <a href="#Matrix">Matrix</a> can be decomposed without computing remainder. + +Returns true if <a href="#SkMatrix_decomposeScale_scale">scale</a> components are found. <a href="#SkMatrix_decomposeScale_scale">scale</a> and <a href="#SkMatrix_decomposeScale_remaining">remaining</a> are +unchanged if <a href="#Matrix">Matrix</a> contains perspective; <a href="#SkMatrix_decomposeScale_scale">scale</a> factors are not finite, or +are nearly zero. + +On success<a href="#Matrix">Matrix</a> = <a href="#SkMatrix_decomposeScale_scale">scale</a> * Remaining + +### Parameters + +<table> <tr> <td><a name="SkMatrix_decomposeScale_scale"> <code><strong>scale </strong></code> </a></td> <td> +x and y scaling factors; may be nullptr</td> + </tr> <tr> <td><a name="SkMatrix_decomposeScale_remaining"> <code><strong>remaining </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> without scaling; may be nullptr</td> + </tr> +</table> + +### Return Value + +true if <a href="#SkMatrix_decomposeScale_scale">scale</a> can be computed + +### Example + +<div><fiddle-embed name="139b874da0a3ede1f3df88119085c0aa"> + +#### Example Output + +~~~~ +[ 0.0000 -0.2500 0.0000][ 0.5000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +success: true scale: 0.5, 0.25 +[ 0.0000 -0.5000 0.0000][ 2.0000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +[ 0.0000 -0.2500 0.0000][ 0.5000 0.0000 0.0000][ 0.0000 0.0000 1.0000] +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_MakeScale">MakeScale</a> + +--- + +<a name="SkMatrix_I"></a> +## I + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static const SkMatrix& I() +</pre> + +Returns reference to const identity <a href="#Matrix">Matrix</a>. Returned <a href="#Matrix">Matrix</a> is <a href="#SkMatrix_set">set</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| 1 0 0 | +| 0 1 0 | +| 0 0 1 |</pre> + +### Return Value + +const identity <a href="#Matrix">Matrix</a> + +### Example + +<div><fiddle-embed name="d961d91020f19037204a8c3fd8cb1060"> + +#### Example Output + +~~~~ +m1 == m2 +m2 == m3 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_reset">reset</a> <a href="#SkMatrix_setIdentity">setIdentity</a> + +--- + +<a name="SkMatrix_InvalidMatrix"></a> +## InvalidMatrix + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static const SkMatrix& InvalidMatrix() +</pre> + +Returns reference to a const <a href="#Matrix">Matrix</a> with invalid values. Returned <a href="#Matrix">Matrix</a> is <a href="#SkMatrix_set">set</a> +to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| SK_ScalarMax SK_ScalarMax SK_ScalarMax | +| SK_ScalarMax SK_ScalarMax SK_ScalarMax | +| SK_ScalarMax SK_ScalarMax SK_ScalarMax |</pre> + +### Return Value + +const invalid <a href="#Matrix">Matrix</a> + +### Example + +<div><fiddle-embed name="af0b72360c1c7a25b4754bfa47011dd5"> + +#### Example Output + +~~~~ +scaleX 3.40282e+38 +~~~~ + +</fiddle-embed></div> + +### See Also + +SeeAlso <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_Concat"></a> +## Concat + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +static SkMatrix Concat(const SkMatrix& a, const SkMatrix& b) +</pre> + +Returns <a href="#Matrix">Matrix</a> <a href="#SkMatrix_Concat_a">a</a> multiplied by <a href="#Matrix">Matrix</a> <a href="#SkMatrix_Concat_b">b</a>. + +Given: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | +a = | D E F |, b = | M N O | + | G H I | | P Q R |</pre> + +sets <a href="#Matrix">Matrix</a> to: + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> + | A B C | | J K L | | AJ+BM+CP AK+BN+CQ AL+BO+CR | +a * b = | D E F | * | M N O | = | DJ+EM+FP DK+EN+FQ DL+EO+FR | + | G H I | | P Q R | | GJ+HM+IP GK+HN+IQ GL+HO+IR |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_Concat_a"> <code><strong>a </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> on left side of multiply expression</td> + </tr> <tr> <td><a name="SkMatrix_Concat_b"> <code><strong>b </strong></code> </a></td> <td> +<a href="#Matrix">Matrix</a> on right side of multiply expression</td> + </tr> +</table> + +### Return Value + +<a href="#Matrix">Matrix</a> computed from <a href="#SkMatrix_Concat_a">a</a> times <a href="#SkMatrix_Concat_b">b</a> + +### Example + +<div><fiddle-embed name="6b4562c7052da94f3d5b2412dca41946"><div><a href="#SkMatrix_setPolyToPoly">setPolyToPoly</a> creates perspective matrices, one the inverse of the other. +Multiplying the matrix by its inverse turns into an identity matrix.</div></fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_preConcat">preConcat</a> <a href="#SkMatrix_postConcat">postConcat</a> + +--- + +<a name="SkMatrix_dirtyMatrixTypeCache"></a> +## dirtyMatrixTypeCache + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void dirtyMatrixTypeCache() +</pre> + +Sets internal cache to unknown state. Use to force update after repeated +modifications to <a href="#Matrix">Matrix</a> element reference returned by <a href="#SkMatrix_subscript_operator_const">operator[](int index)</a>. + +### Example + +<div><fiddle-embed name="f4365ef332f51f7fd25040e0771ba9a2"> + +#### Example Output + +~~~~ +with identity matrix: x = 24 +after skew x mod: x = 24 +after 2nd skew x mod: x = 24 +after dirty cache: x = 66 +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_subscript_operator_const">operator[](int index)</a> <a href="#SkMatrix_getType">getType</a> + +--- + +<a name="SkMatrix_setScaleTranslate"></a> +## setScaleTranslate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void setScaleTranslate(SkScalar sx, SkScalar sy, SkScalar tx, SkScalar ty) +</pre> + +Initializes <a href="#Matrix">Matrix</a> with scale and translate elements. + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +| sx 0 tx | +| 0 sy ty | +| 0 0 1 |</pre> + +### Parameters + +<table> <tr> <td><a name="SkMatrix_setScaleTranslate_sx"> <code><strong>sx </strong></code> </a></td> <td> +horizontal scale factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setScaleTranslate_sy"> <code><strong>sy </strong></code> </a></td> <td> +vertical scale factor to store</td> + </tr> <tr> <td><a name="SkMatrix_setScaleTranslate_tx"> <code><strong>tx </strong></code> </a></td> <td> +horizontal translation to store</td> + </tr> <tr> <td><a name="SkMatrix_setScaleTranslate_ty"> <code><strong>ty </strong></code> </a></td> <td> +vertical translation to store</td> + </tr> +</table> + +### Example + +<div><fiddle-embed name="fed43797f13796529cb6731385d6f8f3"> + +#### Example Output + +~~~~ +[ 1.0000 0.0000 3.0000][ 0.0000 2.0000 4.0000][ 0.0000 0.0000 1.0000] +~~~~ + +</fiddle-embed></div> + +### See Also + +<a href="#SkMatrix_setScale">setScale</a> <a href="#SkMatrix_preTranslate">preTranslate</a> <a href="#SkMatrix_postTranslate">postTranslate</a> + +--- + +<a name="SkMatrix_isFinite"></a> +## isFinite + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +bool isFinite() const +</pre> + +Returns true if all elements of the matrix are finite. Returns false if any +element is infinity, or <a href="undocumented#NaN">NaN</a>. + +### Return Value + +true if matrix has only finite elements + +### Example + +<div><fiddle-embed name="bc6c6f6a5df770287120d87f81b922eb"> + +#### Example Output + +~~~~ +[ 1.0000 0.0000 nan][ 0.0000 1.0000 0.0000][ 0.0000 0.0000 1.0000] +matrix is finite: false +matrix != matrix +~~~~ + +</fiddle-embed></div> + +### See Also + +operator== + +--- + diff --git a/site/user/api/SkPaint_Reference.md b/site/user/api/SkPaint_Reference.md index e539b3a628..ffab03e288 100644 --- a/site/user/api/SkPaint_Reference.md +++ b/site/user/api/SkPaint_Reference.md @@ -653,7 +653,7 @@ serialized data describing <a href="#Paint">Paint</a> content</td> ## <a name="SkPaint_Hinting"></a> Enum SkPaint::Hinting -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#Hinting">Hinting</a> { <a href="#SkPaint_kNo_Hinting">kNo Hinting</a> = 0, <a href="#SkPaint_kSlight_Hinting">kSlight Hinting</a> = 1, @@ -776,7 +776,7 @@ paint1 == paint2 ## <a name="SkPaint_Flags"></a> Enum SkPaint::Flags -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#Flags">Flags</a> { <a href="#SkPaint_kAntiAlias_Flag">kAntiAlias Flag</a> = 0x01, <a href="#SkPaint_kDither_Flag">kDither Flag</a> = 0x04, @@ -845,7 +845,7 @@ multiple settings at once. ## <a name="SkPaint_ReserveFlags"></a> Enum SkPaint::ReserveFlags -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_ReserveFlags">ReserveFlags</a> { <a href="#SkPaint_kUnderlineText_ReserveFlag">kUnderlineText ReserveFlag</a> = 0x08, <a href="#SkPaint_kStrikeThruText_ReserveFlag">kStrikeThruText ReserveFlag</a> = 0x10, @@ -1356,7 +1356,7 @@ the outline glyph if <a href="#SkPaint_kEmbeddedBitmapText_Flag">kEmbeddedBitmap ### Example -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> <div>The "" <a href="undocumented#TrueType">TrueType</a> font in the <a href="undocumented#Skia">Skia</a> resources/fonts directory includes an embedded bitmap <a href="undocumented#Glyph">Glyph</a> at odd font sizes. This example works on platforms that use <a href="undocumented#FreeType">FreeType</a> as their <a href="#Engine">Font Engine</a>. @@ -2066,7 +2066,7 @@ while stroking. ## <a name="SkPaint_Style"></a> Enum SkPaint::Style -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_Style">Style</a> { <a href="#SkPaint_kFill_Style">kFill Style</a>, <a href="#SkPaint_kStroke_Style">kStroke Style</a>, @@ -2110,7 +2110,7 @@ and the set <a href="#Fill_Type">Path Fill Type</a> is ignored.</td> ## <a name="SkPaint__anonymous"></a> Enum SkPaint::_anonymous -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum { <a href="#SkPaint_kStyleCount">kStyleCount</a> = <a href="#SkPaint_kStrokeAndFill_Style">kStrokeAndFill Style</a> + 1, };</pre> @@ -2375,7 +2375,7 @@ default miter limit == 8 ## <a name="SkPaint_Cap"></a> Enum SkPaint::Cap -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_Cap">Cap</a> { <a href="#SkPaint_kButt_Cap">kButt Cap</a>, <a href="#SkPaint_kRound_Cap">kRound Cap</a>, @@ -2520,7 +2520,7 @@ the following curve, the pair of curves meet at <a href="#Stroke_Join">Stroke Jo ## <a name="SkPaint_Join"></a> Enum SkPaint::Join -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_Join">Join</a> { <a href="#SkPaint_kMiter_Join">kMiter Join</a>, <a href="#SkPaint_kRound_Join">kRound Join</a>, @@ -3663,7 +3663,7 @@ sets <a href="undocumented#Draw_Looper">Draw Looper</a> to <a href="#SkPaint_set ## <a name="SkPaint_Align"></a> Enum SkPaint::Align -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_Align">Align</a> { <a href="#SkPaint_kLeft_Align">kLeft Align</a>, <a href="#SkPaint_kCenter_Align">kCenter Align</a>, @@ -3706,7 +3706,7 @@ and by its height if <a href="#SkPaint_Flags">Flags</a> has <a href="#SkPaint_kV ## <a name="SkPaint__anonymous_2"></a> Enum SkPaint::_anonymous_2 -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum { <a href="#SkPaint_kAlignCount">kAlignCount</a> = 3, };</pre> @@ -3944,7 +3944,7 @@ additional shear in x-axis relative to y-axis</td> ## <a name="SkPaint_TextEncoding"></a> Enum SkPaint::TextEncoding -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_TextEncoding">TextEncoding</a> { <a href="#SkPaint_kUTF8_TextEncoding">kUTF8 TextEncoding</a>, <a href="#SkPaint_kUTF16_TextEncoding">kUTF16 TextEncoding</a>, @@ -4075,16 +4075,8 @@ Y-axis values above the baseline are negative, and below the baseline are positi <div><fiddle-embed name="b5b76e0a15da0c3530071186a9006498"></fiddle-embed></div> # <a name="SkPaint_FontMetrics"></a> Struct SkPaint::FontMetrics -<a href="#SkPaint_FontMetrics">FontMetrics</a> is filled out by <a href="#SkPaint_getFontMetrics">getFontMetrics</a>. <a href="#SkPaint_FontMetrics">FontMetrics</a> contents reflect the values -computed by <a href="undocumented#Font_Manager">Font Manager</a> using <a href="undocumented#Typeface">Typeface</a>. Values are set to zero if they are -not available. - -<a href="#SkPaint_FontMetrics_fUnderlineThickness">fUnderlineThickness</a> and <a href="#SkPaint_FontMetrics_fUnderlinePosition">fUnderlinePosition</a> have a bit set in <a href="#SkPaint_FontMetrics_fFlags">fFlags</a> if their values -are valid, since their value may be zero. -<a href="#SkPaint_FontMetrics_fStrikeoutThickness">fStrikeoutThickness</a> and <a href="#SkPaint_FontMetrics_fStrikeoutPosition">fStrikeoutPosition</a> have a bit set in <a href="#SkPaint_FontMetrics_fFlags">fFlags</a> if their values -are valid, since their value may be zero. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> struct <a href="#SkPaint_FontMetrics">FontMetrics</a> { enum <a href="#SkPaint_FontMetrics_FontMetricsFlags">FontMetricsFlags</a> { <a href="#SkPaint_FontMetrics_kUnderlineThicknessIsValid_Flag">kUnderlineThicknessIsValid Flag</a> = 1 << 0, @@ -4116,13 +4108,18 @@ bool <a href="#SkPaint_FontMetrics_hasStrikeoutThickness">hasStrikeoutThickness( bool <a href="#SkPaint_FontMetrics_hasStrikeoutPosition">hasStrikeoutPosition(SkScalar* position)</a> const; };</pre> -## <a name="SkPaint_FontMetrics_FontMetricsFlags"></a> Enum SkPaint::FontMetrics::FontMetricsFlags +<a href="#SkPaint_FontMetrics">FontMetrics</a> is filled out by <a href="#SkPaint_getFontMetrics">getFontMetrics</a>. <a href="#SkPaint_FontMetrics">FontMetrics</a> contents reflect the values +computed by <a href="undocumented#Font_Manager">Font Manager</a> using <a href="undocumented#Typeface">Typeface</a>. Values are set to zero if they are +not available. -<a href="#SkPaint_FontMetrics_FontMetricsFlags">FontMetricsFlags</a> are set in <a href="#SkPaint_FontMetrics_fFlags">fFlags</a> when underline and strikeout metrics are valid; -the underline or strikeout metric may be valid and zero. -Fonts with embedded bitmaps may not have valid underline or strikeout metrics. +<a href="#SkPaint_FontMetrics_fUnderlineThickness">fUnderlineThickness</a> and <a href="#SkPaint_FontMetrics_fUnderlinePosition">fUnderlinePosition</a> have a bit set in <a href="#SkPaint_FontMetrics_fFlags">fFlags</a> if their values +are valid, since their value may be zero. +<a href="#SkPaint_FontMetrics_fStrikeoutThickness">fStrikeoutThickness</a> and <a href="#SkPaint_FontMetrics_fStrikeoutPosition">fStrikeoutPosition</a> have a bit set in <a href="#SkPaint_FontMetrics_fFlags">fFlags</a> if their values +are valid, since their value may be zero. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +## <a name="SkPaint_FontMetrics_FontMetricsFlags"></a> Enum SkPaint::FontMetrics::FontMetricsFlags + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPaint_FontMetrics_FontMetricsFlags">FontMetricsFlags</a> { <a href="#SkPaint_FontMetrics_kUnderlineThicknessIsValid_Flag">kUnderlineThicknessIsValid Flag</a> = 1 << 0, <a href="#SkPaint_FontMetrics_kUnderlinePositionIsValid_Flag">kUnderlinePositionIsValid Flag</a> = 1 << 1, @@ -4130,6 +4127,10 @@ enum <a href="#SkPaint_FontMetrics_FontMetricsFlags">FontMetricsFlags</a> { <a href="#SkPaint_FontMetrics_kStrikeoutPositionIsValid_Flag">kStrikeoutPositionIsValid Flag</a> = 1 << 3, };</pre> +<a href="#SkPaint_FontMetrics_FontMetricsFlags">FontMetricsFlags</a> are set in <a href="#SkPaint_FontMetrics_fFlags">fFlags</a> when underline and strikeout metrics are valid; +the underline or strikeout metric may be valid and zero. +Fonts with embedded bitmaps may not have valid underline or strikeout metrics. + ### Constants <table> diff --git a/site/user/api/SkPath_Reference.md b/site/user/api/SkPath_Reference.md index bb3634e373..154b66b27d 100644 --- a/site/user/api/SkPath_Reference.md +++ b/site/user/api/SkPath_Reference.md @@ -216,7 +216,7 @@ Internally, <a href="#Path">Path</a> lazily computes metrics likes bounds and co ## <a name="SkPath_Verb"></a> Enum SkPath::Verb -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#Verb">Verb</a> { <a href="#SkPath_kMove_Verb">kMove Verb</a>, <a href="#SkPath_kLine_Verb">kLine Verb</a>, @@ -298,7 +298,7 @@ verbs: kMove_Verb kLine_Verb kQuad_Verb kClose_Verb kMove_Verb kCubic_Verb kConi ## <a name="SkPath_Direction"></a> Enum SkPath::Direction -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#Direction">Direction</a> { <a href="#SkPath_kCW_Direction">kCW Direction</a>, <a href="#SkPath_kCCW_Direction">kCCW Direction</a>, @@ -320,10 +320,10 @@ travel counterclockwise. <table> <tr> - <td><a name="SkPath_kCW_Direction"> <code><strong>SkPath::kCW_Direction </strong></code> </a></td><td>0</td><td><a href="#Contour">Contour</a> travels in a clockwise direction.</td> + <td><a name="SkPath_kCW_Direction"> <code><strong>SkPath::kCW_Direction </strong></code> </a></td><td>0</td><td><a href="#Contour">Contour</a> travels in a clockwise direction</td> </tr> <tr> - <td><a name="SkPath_kCCW_Direction"> <code><strong>SkPath::kCCW_Direction </strong></code> </a></td><td>1</td><td><a href="#Contour">Contour</a> travels in a counterclockwise direction.</td> + <td><a name="SkPath_kCCW_Direction"> <code><strong>SkPath::kCCW_Direction </strong></code> </a></td><td>1</td><td><a href="#Contour">Contour</a> travels in a counterclockwise direction</td> </tr> </table> @@ -617,7 +617,9 @@ Interpolate between <a href="#Path">Paths</a> with equal sized <a href="SkPath_R Copy <a href="#Verb_Array">Verb Array</a> and <a href="#Weight">Weights</a> to <a href="#SkPath_interpolate_out">out</a>, and set <a href="#SkPath_interpolate_out">out</a> <a href="#Point_Array">Point Array</a> to a weighted average of this <a href="#Point_Array">Point Array</a> and <a href="#SkPath_interpolate_ending">ending</a> <a href="#Point_Array">Point Array</a>, using the formula: -(this->points * <a href="#SkPath_interpolate_weight">weight</a>) + ending->points * (1 - <a href="#SkPath_interpolate_weight">weight</a>)<a href="#SkPath_interpolate_weight">weight</a> is most useful when between zero (<a href="#SkPath_interpolate_ending">ending</a> <a href="#Point_Array">Point Array</a>) and +(this->points * <a href="#SkPath_interpolate_weight">weight</a>) + ending->points * (1 - <a href="#SkPath_interpolate_weight">weight</a>). + +<a href="#SkPath_interpolate_weight">weight</a> is most useful when between zero (<a href="#SkPath_interpolate_ending">ending</a> <a href="#Point_Array">Point Array</a>) and one (this <a href="#Point_Array">Point Array</a>); will work with values outside of this range. @@ -668,7 +670,7 @@ true if <a href="#Path">Path</a> has one owner ## <a name="SkPath_FillType"></a> Enum SkPath::FillType -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPath_FillType">FillType</a> { <a href="#SkPath_kWinding_FillType">kWinding FillType</a>, <a href="#SkPath_kEvenOdd_FillType">kEvenOdd FillType</a>, @@ -842,7 +844,7 @@ unmodified by the original <a href="#SkPath_FillType">FillType</a>. ## <a name="SkPath_Convexity"></a> Enum SkPath::Convexity -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#Convexity">Convexity</a> : uint8_t { <a href="#SkPath_kUnknown_Convexity">kUnknown Convexity</a>, <a href="#SkPath_kConvex_Convexity">kConvex Convexity</a>, @@ -2805,7 +2807,7 @@ line (156,20),(200,20) ## <a name="SkPath_ArcSize"></a> Enum SkPath::ArcSize -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPath_ArcSize">ArcSize</a> { <a href="#SkPath_kSmall_ArcSize">kSmall ArcSize</a>, <a href="#SkPath_kLarge_ArcSize">kLarge ArcSize</a>, @@ -2818,10 +2820,10 @@ Four <a href="undocumented#Oval">Oval</a> parts with radii (rx, ry) start at las <table> <tr> - <td><a name="SkPath_kSmall_ArcSize"> <code><strong>SkPath::kSmall_ArcSize </strong></code> </a></td><td>0</td><td>Smaller of <a href="#Arc">Arc</a> pair.</td> + <td><a name="SkPath_kSmall_ArcSize"> <code><strong>SkPath::kSmall_ArcSize </strong></code> </a></td><td>0</td><td>smaller of <a href="#Arc">Arc</a> pair</td> </tr> <tr> - <td><a name="SkPath_kLarge_ArcSize"> <code><strong>SkPath::kLarge_ArcSize </strong></code> </a></td><td>1</td><td>Larger of <a href="#Arc">Arc</a> pair.</td> + <td><a name="SkPath_kLarge_ArcSize"> <code><strong>SkPath::kLarge_ArcSize </strong></code> </a></td><td>1</td><td>larger of <a href="#Arc">Arc</a> pair</td> </tr> </table> @@ -2840,18 +2842,20 @@ void arcTo(SkScalar rx, SkScalar ry, SkScalar xAxisRotate, ArcSize largeArc, Direction sweep, SkScalar x, SkScalar y) </pre> -Append <a href="#Arc">Arc</a> to <a href="#Path">Path</a>. <a href="#Arc">Arc</a> is implemented by one or more <a href="#Conic">Conics</a> weighted to describe part of <a href="undocumented#Oval">Oval</a> -with radii (<a href="#SkPath_arcTo_4_rx">rx</a>, <a href="#SkPath_arcTo_4_ry">ry</a>) rotated by <a href="#SkPath_arcTo_4_xAxisRotate">xAxisRotate</a> degrees. <a href="#Arc">Arc</a> curves from last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> to (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>), -choosing one of four possible routes: clockwise or counterclockwise, and smaller or larger. +Append <a href="#Arc">Arc</a> to <a href="#Path">Path</a>. <a href="#Arc">Arc</a> is implemented by one or more <a href="#Conic">Conics</a> weighted to +describe part of <a href="undocumented#Oval">Oval</a> with radii (<a href="#SkPath_arcTo_4_rx">rx</a>, <a href="#SkPath_arcTo_4_ry">ry</a>) rotated by <a href="#SkPath_arcTo_4_xAxisRotate">xAxisRotate</a> degrees. <a href="#Arc">Arc</a> +curves from last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> to (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>), choosing one of four possible routes: +clockwise or counterclockwise, and smaller or larger. -<a href="#Arc">Arc</a> <a href="#SkPath_arcTo_4_sweep">sweep</a> is always less than 360 degrees. <a href="#SkPath_arcTo">arcTo</a> appends <a href="undocumented#Line">Line</a> to (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>) if either radii are zero, -or if last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> equals (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>). <a href="#SkPath_arcTo">arcTo</a> scales radii (<a href="#SkPath_arcTo_4_rx">rx</a>, <a href="#SkPath_arcTo_4_ry">ry</a>) to fit last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> and -(<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>) if both are greater than zero but too small. +<a href="#Arc">Arc</a> <a href="#SkPath_arcTo_4_sweep">sweep</a> is always less than 360 degrees. <a href="#SkPath_arcTo">arcTo</a> appends <a href="undocumented#Line">Line</a> to (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>) if +either radii are zero, or if last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> equals (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>). <a href="#SkPath_arcTo">arcTo</a> scales radii +(<a href="#SkPath_arcTo_4_rx">rx</a>, <a href="#SkPath_arcTo_4_ry">ry</a>) to fit last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> and (<a href="#SkPath_arcTo_4_x">x</a>, <a href="#SkPath_arcTo_4_y">y</a>) if both are greater than zero but +too small. <a href="#SkPath_arcTo">arcTo</a> appends up to four <a href="#Conic">Conic</a> curves. -<a href="#SkPath_arcTo">arcTo</a> implements the functionality of <a href="#Arc">SVG Arc</a>, although <a href="undocumented#SVG">SVG</a> "" value is -opposite the integer value of <a href="#SkPath_arcTo_4_sweep">sweep</a>; <a href="undocumented#SVG">SVG</a> "" uses 1 for clockwise, while <a href="#SkPath_kCW_Direction">kCW Direction</a> -cast to int is zero. +<a href="#SkPath_arcTo">arcTo</a> implements the functionality of <a href="#Arc">SVG Arc</a>, although <a href="undocumented#SVG">SVG</a> "" value +is opposite the integer value of <a href="#SkPath_arcTo_4_sweep">sweep</a>; <a href="undocumented#SVG">SVG</a> "" uses 1 for clockwise, +while <a href="#SkPath_kCW_Direction">kCW Direction</a> cast to int is zero. ### Parameters @@ -2936,7 +2940,9 @@ void rArcTo(SkScalar rx, SkScalar ry, SkScalar xAxisRotate, ArcSize largeArc, Append <a href="#Arc">Arc</a> to <a href="#Path">Path</a>, relative to last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a>. <a href="#Arc">Arc</a> is implemented by one or more <a href="#Conic">Conic</a>, weighted to describe part of <a href="undocumented#Oval">Oval</a> with radii (<a href="#SkPath_rArcTo_rx">rx</a>, <a href="#SkPath_rArcTo_ry">ry</a>) rotated by -<a href="#SkPath_rArcTo_xAxisRotate">xAxisRotate</a> degrees. <a href="#Arc">Arc</a> curves from last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> (x0, y0) to end <a href="undocumented#Point">Point</a>(x0 + <a href="#SkPath_rArcTo_dx">dx</a>, y0 + <a href="#SkPath_rArcTo_dy">dy</a>), +<a href="#SkPath_rArcTo_xAxisRotate">xAxisRotate</a> degrees. <a href="#Arc">Arc</a> curves from last <a href="#Path">Path</a> <a href="undocumented#Point">Point</a> (x0, y0) to end <a href="undocumented#Point">Point</a>: + +(x0 + <a href="#SkPath_rArcTo_dx">dx</a>, y0 + <a href="#SkPath_rArcTo_dy">dy</a>), choosing one of four possible routes: clockwise or counterclockwise, and smaller or larger. If <a href="#Path">Path</a> is empty, the start <a href="#Arc">Arc</a> <a href="undocumented#Point">Point</a> is (0, 0). @@ -3118,7 +3124,9 @@ control <a href="undocumented#Point">Point</a> <a href="#SkPath_ConvertConicToQu Maximum <a href="#Quad">Quad</a> count is 2 to the <a href="#SkPath_ConvertConicToQuads_pow2">pow2</a>. Every third point in array shares last <a href="undocumented#Point">Point</a> of previous <a href="#Quad">Quad</a> and first <a href="undocumented#Point">Point</a> of next <a href="#Quad">Quad</a>. Maximum <a href="#SkPath_ConvertConicToQuads_pts">pts</a> storage size is given by: -(1 + 2 * (1 << <a href="#SkPath_ConvertConicToQuads_pow2">pow2</a>)) * sizeof(SkPoint)<a href="#SkPath_ConvertConicToQuads">ConvertConicToQuads</a> returns <a href="#Quad">Quad</a> count used the approximation, which may be smaller +(1 + 2 * (1 << <a href="#SkPath_ConvertConicToQuads_pow2">pow2</a>)) * sizeof(SkPoint). + +Returns <a href="#Quad">Quad</a> count used the approximation, which may be smaller than the number requested. <a href="#Conic_Weight">Conic Weight</a> determines the amount of influence <a href="#Conic">Conic</a> control point has on the curve. <a href="#SkPath_ConvertConicToQuads_w">w</a> less than one represents an elliptical section. <a href="#SkPath_ConvertConicToQuads_w">w</a> greater than one represents @@ -3446,9 +3454,10 @@ void addCircle(SkScalar x, SkScalar y, SkScalar radius, </pre> Add <a href="undocumented#Circle">Circle</a> centered at (<a href="#SkPath_addCircle_x">x</a>, <a href="#SkPath_addCircle_y">y</a>) of size <a href="#SkPath_addCircle_radius">radius</a> to <a href="#Path">Path</a>, appending <a href="#SkPath_kMove_Verb">kMove Verb</a>, -four <a href="#SkPath_kConic_Verb">kConic Verb</a>, and <a href="#SkPath_kClose_Verb">kClose Verb</a>. <a href="undocumented#Circle">Circle</a> begins at(<a href="#SkPath_addCircle_x">x</a> + <a href="#SkPath_addCircle_radius">radius</a>, <a href="#SkPath_addCircle_y">y</a>), -continuing clockwise if <a href="#SkPath_addCircle_dir">dir</a> is <a href="#SkPath_kCW_Direction">kCW Direction</a>, and counterclockwise if <a href="#SkPath_addCircle_dir">dir</a> is -<a href="#SkPath_kCCW_Direction">kCCW Direction</a>. +four <a href="#SkPath_kConic_Verb">kConic Verb</a>, and <a href="#SkPath_kClose_Verb">kClose Verb</a>. <a href="undocumented#Circle">Circle</a> begins at: +(<a href="#SkPath_addCircle_x">x</a> + <a href="#SkPath_addCircle_radius">radius</a>, <a href="#SkPath_addCircle_y">y</a>), +continuing +clockwise if <a href="#SkPath_addCircle_dir">dir</a> is <a href="#SkPath_kCW_Direction">kCW Direction</a>, and counterclockwise if <a href="#SkPath_addCircle_dir">dir</a> is <a href="#SkPath_kCCW_Direction">kCCW Direction</a>. Has no effect if <a href="#SkPath_addCircle_radius">radius</a> is zero or negative. @@ -3725,7 +3734,7 @@ true to add <a href="undocumented#Line">Line</a> connecting <a href="#Contour">C ## <a name="SkPath_AddPathMode"></a> Enum SkPath::AddPathMode -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPath_AddPathMode">AddPathMode</a> { <a href="#SkPath_kAppend_AddPathMode">kAppend AddPathMode</a>, <a href="#SkPath_kExtend_AddPathMode">kExtend AddPathMode</a>, @@ -4096,7 +4105,7 @@ set value of <a href="#Last_Point">Last Point</a></td> ## <a name="SkPath_SegmentMask"></a> Enum SkPath::SegmentMask -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> enum <a href="#SkPath_SegmentMask">SegmentMask</a> { <a href="#SkPath_kLine_SegmentMask">kLine SegmentMask</a> = 1 << 0, <a href="#SkPath_kQuad_SegmentMask">kQuad SegmentMask</a> = 1 << 1, @@ -4225,9 +4234,9 @@ true if <a href="undocumented#Point">Point</a> is in <a href="#Path">Path</a> void dump(SkWStream* stream, bool forceClose, bool dumpAsHex) const </pre> -Writes text representation of <a href="#Path">Path</a> to <a href="#SkPath_dump_stream">stream</a>. If <a href="#SkPath_dump_stream">stream</a> is nullptr, <a href="#SkPath_dump_2">dump</a> writes to -standard output. Set <a href="#SkPath_dump_forceClose">forceClose</a> to true to get -edges used to fill <a href="#Path">Path</a>. Set <a href="#SkPath_dump_dumpAsHex">dumpAsHex</a> true to generate exact binary representations +Writes text representation of <a href="#Path">Path</a> to <a href="#SkPath_dump_stream">stream</a>. If <a href="#SkPath_dump_stream">stream</a> is nullptr, writes to +standard output. Set <a href="#SkPath_dump_forceClose">forceClose</a> to true to get edges used to fill <a href="#Path">Path</a>. +Set <a href="#SkPath_dump_dumpAsHex">dumpAsHex</a> true to generate exact binary representations of floating point numbers used in <a href="#Point_Array">Point Array</a> and <a href="#Weight">Conic Weights</a>. ### Parameters @@ -4554,7 +4563,7 @@ Iterates through <a href="#Verb_Array">Verb Array</a>, and associated <a href="# Provides options to treat open <a href="#Contour">Contours</a> as closed, and to ignore degenerate data. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> class <a href="#SkPath_Iter_Iter">Iter</a> { public: <a href="#SkPath_Iter_Iter">Iter()</a>; @@ -4899,7 +4908,7 @@ with close(), forceClose is true : isClosedContour returns true Iterates through <a href="#Verb_Array">Verb Array</a>, and associated <a href="#Point_Array">Point Array</a> and <a href="#Conic_Weight">Conic Weight</a>. <a href="#Verb_Array">Verb Array</a>, <a href="#Point_Array">Point Array</a>, and <a href="#Conic_Weight">Conic Weight</a> are returned unaltered. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> class <a href="#SkPath_RawIter_RawIter">RawIter</a> { public: <a href="#SkPath_RawIter_RawIter">RawIter()</a>; diff --git a/site/user/api/SkPixmap_Reference.md b/site/user/api/SkPixmap_Reference.md index 9c7deb64cb..6e44b60aff 100644 --- a/site/user/api/SkPixmap_Reference.md +++ b/site/user/api/SkPixmap_Reference.md @@ -49,13 +49,11 @@ to manage pixel memory; <a href="undocumented#Pixel_Ref">Pixel Ref</a> is safe a | <a href="#SkPixmap_bounds">bounds</a> | Returns <a href="#SkPixmap_width">width</a> and <a href="#SkPixmap_height">height</a> as Rectangle. | | <a href="#SkPixmap_colorSpace">colorSpace</a> | Returns <a href="#Info">Image Info</a> <a href="undocumented#Color_Space">Color Space</a>. | | <a href="#SkPixmap_colorType">colorType</a> | Returns <a href="#Info">Image Info</a> <a href="undocumented#Color_Type">Color Type</a>. | +| <a href="#SkPixmap_computeByteSize">computeByteSize</a> | Returns size required for pixels. | | <a href="#SkPixmap_computeIsOpaque">computeIsOpaque</a> | Returns true if all pixels are opaque. | | <a href="#SkPixmap_erase">erase</a> | Writes <a href="undocumented#Color">Color</a> to pixels. | | <a href="#SkPixmap_extractSubset">extractSubset</a> | Sets pointer to portion of original. | | <a href="#SkPixmap_getColor">getColor</a> | Returns one pixel as <a href="#Unpremultiply">Unpremultiplied</a> <a href="undocumented#Color">Color</a>. | -| <a href="#SkPixmap_getSafeSize">getSafeSize</a> | Returns minimum size required for pixels in 32 bits. | -| <a href="#SkPixmap_getSafeSize64">getSafeSize64</a> | Returns minimum size required for pixels in 64 bits. | -| <a href="#SkPixmap_getSize64">getSize64</a> | Returns conservative size required for pixels. | | <a href="#SkPixmap_height">height</a> | Returns pixel row count. | | <a href="#SkPixmap_info">info</a> | Returns <a href="#Info">Image Info</a>. | | <a href="#SkPixmap_isOpaque">isOpaque</a> | Returns true if <a href="#Info">Image Info</a> describes opaque pixels. | @@ -389,7 +387,8 @@ size_t rowBytes() const </pre> Returns row bytes, the interval from one pixel row to the next. Row bytes -is at least as large as<a href="#SkPixmap_width">width</a> * <a href="#SkPixmap_info">info</a>.bytesPerPixel(). +is at least as large as: +<a href="#SkPixmap_width">width</a> * <a href="#SkPixmap_info">info</a>.bytesPerPixel(). Returns zero if <a href="#SkPixmap_colorType">colorType</a> is <a href="undocumented#SkColorType">kUnknown SkColorType</a>. It is up to the <a href="SkBitmap_Reference#Bitmap">Bitmap</a> creator to ensure that row bytes is a useful value. @@ -460,6 +459,7 @@ int width() const </pre> Returns pixel count in each pixel row. Should be equal or less than: + <a href="#SkPixmap_rowBytes">rowBytes</a> / <a href="#SkPixmap_info">info</a>.bytesPerPixel(). ### Return Value @@ -657,7 +657,7 @@ isOpaque: true SkIRect bounds() const </pre> -Returns <a href="SkIRect_Reference#IRect">IRect</a>{ 0, 0, <a href="#SkPixmap_width">width</a>, <a href="#SkPixmap_height">height</a> }. +Returns <a href="SkIRect_Reference#IRect">IRect</a> { 0, 0, <a href="#SkPixmap_width">width</a>, <a href="#SkPixmap_height">height</a> }. ### Return Value @@ -759,68 +759,6 @@ color: kRGBA_F16_SkColorType bytesPerPixel: 8 shiftPerPixel: 3 --- -<a name="SkPixmap_getSize64"></a> -## getSize64 - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -uint64_t getSize64() const -</pre> - -Returns conservative memory required for pixel storage. -Includes unused memory on last row when <a href="#SkPixmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkPixmap_width">width</a>. - -### Return Value - -conservative pixel storage size - -### See Also - -<a href="#SkPixmap_getSafeSize64">getSafeSize64</a> <a href="#SkPixmap_getSafeSize">getSafeSize</a> <a href="#SkPixmap_height">height</a> <a href="#SkPixmap_rowBytes">rowBytes</a> <a href="#SkPixmap_width">width</a> <a href="#SkImageInfo_bytesPerPixel">SkImageInfo::bytesPerPixel</a> - ---- - -<a name="SkPixmap_getSafeSize64"></a> -## getSafeSize64 - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -uint64_t getSafeSize64() const -</pre> - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when <a href="#SkPixmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkPixmap_width">width</a>. - -### Return Value - -exact pixel storage size - -### See Also - -<a href="#SkPixmap_getSize64">getSize64</a> <a href="#SkPixmap_getSafeSize">getSafeSize</a> <a href="#SkPixmap_height">height</a> <a href="#SkPixmap_rowBytes">rowBytes</a> <a href="#SkPixmap_width">width</a> <a href="#SkImageInfo_bytesPerPixel">SkImageInfo::bytesPerPixel</a> - ---- - -<a name="SkPixmap_getSafeSize"></a> -## getSafeSize - -<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> -size_t getSafeSize() const -</pre> - -Returns minimum memory required for pixel storage. -Does not include unused memory on last row when <a href="#SkPixmap_rowBytesAsPixels">rowBytesAsPixels</a> exceeds <a href="#SkPixmap_width">width</a>. -Returns zero if value is does not fit in a signed 32-bit integer. -The largest value than can be returned is 2,147,483,647. - -### Return Value - -exact pixel storage size if size fits in signed 32 bits - -### See Also - -<a href="#SkPixmap_getSize64">getSize64</a> <a href="#SkPixmap_getSafeSize64">getSafeSize64</a> <a href="#SkPixmap_height">height</a> <a href="#SkPixmap_rowBytes">rowBytes</a> <a href="#SkPixmap_width">width</a> <a href="#SkImageInfo_bytesPerPixel">SkImageInfo::bytesPerPixel</a> <a href="undocumented#sk_64_isS32">sk 64 isS32</a> - ---- - <a name="SkPixmap_computeByteSize"></a> ## computeByteSize @@ -1679,7 +1617,8 @@ bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes, int srcX, int srcY, SkTransferFunctionBehavior behavior) const </pre> -Copies a <a href="SkRect_Reference#Rect">Rect</a> of pixels to <a href="#SkPixmap_readPixels_dstPixels">dstPixels</a>. Copy starts at (<a href="#SkPixmap_readPixels_srcX">srcX</a>, <a href="#SkPixmap_readPixels_srcY">srcY</a>), and does not exceed(this-><a href="#SkPixmap_width">width</a>, this-><a href="#SkPixmap_height">height</a>). +Copies a <a href="SkRect_Reference#Rect">Rect</a> of pixels to <a href="#SkPixmap_readPixels_dstPixels">dstPixels</a>. Copy starts at (<a href="#SkPixmap_readPixels_srcX">srcX</a>, <a href="#SkPixmap_readPixels_srcY">srcY</a>), and does not +exceed (this-><a href="#SkPixmap_width">width</a>, this-><a href="#SkPixmap_height">height</a>). <a href="#SkPixmap_readPixels_dstInfo">dstInfo</a> specifies <a href="#SkPixmap_width">width</a>, <a href="#SkPixmap_height">height</a>, <a href="undocumented#Color_Type">Color Type</a>, <a href="undocumented#Alpha_Type">Alpha Type</a>, and <a href="undocumented#Color_Space">Color Space</a> of destination. <a href="#SkPixmap_readPixels_dstRowBytes">dstRowBytes</a> specifics the gap from one destination @@ -1693,7 +1632,9 @@ If this-><a href="#SkPixmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkPixmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkPixmap_readPixels_dstInfo">dstInfo</a>.<a href="#SkPixmap_colorSpace">colorSpace</a> must match. Returns false if pixel conversion is not possible. <a href="#SkPixmap_readPixels_srcX">srcX</a> and <a href="#SkPixmap_readPixels_srcY">srcY</a> may be negative to copy only top or left of source. Returns -false if <a href="#SkPixmap_width">width</a> or <a href="#SkPixmap_height">height</a> is zero or negative. Returns false ifabs(srcX) >= this-><a href="#SkPixmap_width">width</a>, +false if <a href="#SkPixmap_width">width</a> or <a href="#SkPixmap_height">height</a> is zero or negative. Returns false if: + +abs(srcX) >= this-><a href="#SkPixmap_width">width</a>, or ifabs(srcY) >= this-><a href="#SkPixmap_height">height</a>. If <a href="#SkPixmap_readPixels_behavior">behavior</a> is <a href="#SkTransferFunctionBehavior_kRespect">SkTransferFunctionBehavior::kRespect</a>: converts source @@ -1738,7 +1679,7 @@ bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes) </pre> Copies a <a href="SkRect_Reference#Rect">Rect</a> of pixels to <a href="#SkPixmap_readPixels_2_dstPixels">dstPixels</a>. Copy starts at (0, 0), and does not -exceed(this-><a href="#SkPixmap_width">width</a>, this-><a href="#SkPixmap_height">height</a>). +exceed (this-><a href="#SkPixmap_width">width</a>, this-><a href="#SkPixmap_height">height</a>). <a href="#SkPixmap_readPixels_2_dstInfo">dstInfo</a> specifies <a href="#SkPixmap_width">width</a>, <a href="#SkPixmap_height">height</a>, <a href="undocumented#Color_Type">Color Type</a>, <a href="undocumented#Alpha_Type">Alpha Type</a>, and <a href="undocumented#Color_Space">Color Space</a> of destination. <a href="#SkPixmap_readPixels_2_dstRowBytes">dstRowBytes</a> specifics the gap from one destination @@ -1786,7 +1727,7 @@ bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes, </pre> Copies a <a href="SkRect_Reference#Rect">Rect</a> of pixels to <a href="#SkPixmap_readPixels_3_dstPixels">dstPixels</a>. Copy starts at (<a href="#SkPixmap_readPixels_3_srcX">srcX</a>, <a href="#SkPixmap_readPixels_3_srcY">srcY</a>), and does not -exceed(this-><a href="#SkPixmap_width">width</a>, this-><a href="#SkPixmap_height">height</a>). +exceed (this-><a href="#SkPixmap_width">width</a>, this-><a href="#SkPixmap_height">height</a>). <a href="#SkPixmap_readPixels_3_dstInfo">dstInfo</a> specifies <a href="#SkPixmap_width">width</a>, <a href="#SkPixmap_height">height</a>, <a href="undocumented#Color_Type">Color Type</a>, <a href="undocumented#Alpha_Type">Alpha Type</a>, and <a href="undocumented#Color_Space">Color Space</a> of destination. <a href="#SkPixmap_readPixels_3_dstRowBytes">dstRowBytes</a> specifics the gap from one destination @@ -1800,7 +1741,9 @@ If this-><a href="#SkPixmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkPixmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkPixmap_readPixels_3_dstInfo">dstInfo</a>.<a href="#SkPixmap_colorSpace">colorSpace</a> must match. Returns false if pixel conversion is not possible. <a href="#SkPixmap_readPixels_3_srcX">srcX</a> and <a href="#SkPixmap_readPixels_3_srcY">srcY</a> may be negative to copy only top or left of source. Returns -false if this-><a href="#SkPixmap_width">width</a> or this-><a href="#SkPixmap_height">height</a> is zero or negative. Returns false ifabs(srcX) >= this-><a href="#SkPixmap_width">width</a>, +false if this-><a href="#SkPixmap_width">width</a> or this-><a href="#SkPixmap_height">height</a> is zero or negative. Returns false if: + +abs(srcX) >= this-><a href="#SkPixmap_width">width</a>, or ifabs(srcY) >= this-><a href="#SkPixmap_height">height</a>. ### Parameters @@ -1849,7 +1792,9 @@ If this-><a href="#SkPixmap_alphaType">alphaType</a> is <a href="undocumented#Sk match. If this-><a href="#SkPixmap_colorSpace">colorSpace</a> is nullptr, <a href="#SkPixmap_readPixels_4_dst">dst</a>.<a href="#SkPixmap_info">info</a>.<a href="#SkPixmap_colorSpace">colorSpace</a> must match. Returns false if pixel conversion is not possible. <a href="#SkPixmap_readPixels_4_srcX">srcX</a> and <a href="#SkPixmap_readPixels_4_srcY">srcY</a> may be negative to copy only top or left of source. Returns -false this-><a href="#SkPixmap_width">width</a> or this-><a href="#SkPixmap_height">height</a> is zero or negative. Returns false ifabs(srcX) >= this-><a href="#SkPixmap_width">width</a>, +false this-><a href="#SkPixmap_width">width</a> or this-><a href="#SkPixmap_height">height</a> is zero or negative. Returns false if: + +abs(srcX) >= this-><a href="#SkPixmap_width">width</a>, or ifabs(srcY) >= this-><a href="#SkPixmap_height">height</a>. ### Parameters diff --git a/site/user/api/SkRect_Reference.md b/site/user/api/SkRect_Reference.md index 4dd16b897e..fe1f090331 100644 --- a/site/user/api/SkRect_Reference.md +++ b/site/user/api/SkRect_Reference.md @@ -32,7 +32,7 @@ integer input cannot convert to <a href="undocumented#SkScalar">SkScalar</a> wit | description | function | | --- | --- | | <a href="#SkRect_Intersects">Intersects</a> | Returns true if areas overlap. | -| <a href="#SkRect_Make">Make</a> | Constructs from <a href="#Size">ISize</a> returning (0, 0, <a href="#SkRect_width">width</a>, <a href="#SkRect_height">height</a>). | +| <a href="#SkRect_Make">Make</a> | Constructs from <a href="undocumented#ISize">ISize</a> returning (0, 0, <a href="#SkRect_width">width</a>, <a href="#SkRect_height">height</a>). | | <a href="#SkRect_MakeEmpty">MakeEmpty</a> | Constructs from bounds of (0, 0, 0, 0). | | <a href="#SkRect_MakeFromIRect">MakeFromIRect</a> | Deprecated. | | <a href="#SkRect_MakeIWH">MakeIWH</a> | Constructs from int input returning (0, 0, <a href="#SkRect_width">width</a>, <a href="#SkRect_height">height</a>). | @@ -2016,9 +2016,12 @@ rect: 5, 1, 55, 86 # <a name="Intersection"></a> Intersection <a href="#Rect">Rects</a> <a href="#SkRect_intersect">intersect</a> when they enclose a common area. To <a href="#SkRect_intersect">intersect</a>, each of the pair must describe area; <a href="#SkRect_fLeft">fLeft</a> is less than <a href="#SkRect_fRight">fRight</a>, and <a href="#SkRect_fTop">fTop</a> is less than <a href="#SkRect_fBottom">fBottom</a>; -empty() returns false. The intersection of <a href="#Rect">Rect</a> a and <a href="#Rect">Rect</a> b can be described by: +empty() returns false. The intersection of <a href="#Rect">Rect</a> pair can be described by: + (max(a.fLeft, b.fLeft), max(a.fTop, b.fTop), -min(a.fRight, b.fRight), min(a.fBottom, b.fBottom))The intersection is only meaningful if the resulting <a href="#Rect">Rect</a> is not empty and +min(a.fRight, b.fRight), min(a.fBottom, b.fBottom)). + +The intersection is only meaningful if the resulting <a href="#Rect">Rect</a> is not empty and describes an area: <a href="#SkRect_fLeft">fLeft</a> is less than <a href="#SkRect_fRight">fRight</a>, and <a href="#SkRect_fTop">fTop</a> is less than <a href="#SkRect_fBottom">fBottom</a>. <a name="SkRect_intersect"></a> @@ -2443,6 +2446,7 @@ void growToInclude(SkPoint pt) </pre> Grows <a href="#Rect">Rect</a> to include (<a href="#SkRect_growToInclude_pt">pt</a>.fX, <a href="#SkRect_growToInclude_pt">pt</a>.fY), modifying it so that: + <a href="#SkRect_fLeft">fLeft</a> <= <a href="#SkRect_growToInclude_pt">pt</a>.fX <= <a href="#SkRect_fRight">fRight</a> && <a href="#SkRect_fTop">fTop</a> <= <a href="#SkRect_growToInclude_pt">pt</a>.fY <= <a href="#SkRect_fBottom">fBottom</a>. If <a href="#Rect">Rect</a> is initialized with <a href="#SkRect_setLargestInverted">setLargestInverted</a>, then <a href="#Rect">Rect</a> will contain bounds of @@ -2518,6 +2522,7 @@ void growToInclude(const SkPoint pts[], size_t stride, int count) For each of <a href="#SkRect_growToInclude_3_count">count</a> <a href="undocumented#Point">Point</a> in <a href="#SkRect_growToInclude_3_pts">pts</a>, grows <a href="#Rect">Rect</a> to include (pt.fX, pt.fY), modifying it so that: <a href="#SkRect_fLeft">fLeft</a> <= pt.fX <= <a href="#SkRect_fRight">fRight</a> && <a href="#SkRect_fTop">fTop</a> <= pt.fY <= <a href="#SkRect_fBottom">fBottom</a>. + <a href="undocumented#Point">Point</a> may be followed with other data in each array element. <a href="#SkRect_growToInclude_3_stride">stride</a> is number of bytes in element; the interval to skip to advance from one <a href="undocumented#Point">Point</a> to the next. diff --git a/site/user/api/undocumented.md b/site/user/api/undocumented.md index cd6cb5fbd1..dc102f84ab 100644 --- a/site/user/api/undocumented.md +++ b/site/user/api/undocumented.md @@ -25,6 +25,8 @@ SkCanvas* beginPage(SkScalar width, SkScalar height, # <a name="Size"></a> Size +# <a name="SkSize"></a> Struct SkSize + # <a name="Arc"></a> Arc # <a name="Line"></a> Line @@ -85,6 +87,10 @@ bool equalsWithinTolerance(const SkPoint& p) const ## <a name="ArcTo"></a> ArcTo +# <a name="ISize"></a> ISize + +# <a name="SkISize"></a> Struct SkISize + # <a name="Alias"></a> Alias # <a name="Anti-alias"></a> Anti-alias @@ -521,6 +527,15 @@ size_t computeByteSize(size_t rowBytes) const --- +<a name="SkImageInfo_validate"></a> +## validate + +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> +void validate() const +</pre> + +--- + # <a name="SkImage"></a> Class SkImage <a name="SkImage_makeShader"></a> @@ -874,6 +889,10 @@ void setImmutable() --- +# <a name="Point3"></a> Point3 + +# <a name="SkPoint3"></a> Struct SkPoint3 + # <a name="Premultiply"></a> Premultiply # <a name="Raster_Engine"></a> Raster Engine @@ -952,7 +971,7 @@ static sk_sp<SkShader> MakeBitmapShader(const SkBitmap& src, TileMode tmx, # <a name="Stream"></a> Stream -# <a name="SkFlattenable"></a> Class SkFlattenable +# <a name="SkStream"></a> Class SkStream # <a name="String"></a> String diff --git a/site/user/api/usingBookmaker.md b/site/user/api/usingBookmaker.md index 7a93f7a304..96653510ba 100644 --- a/site/user/api/usingBookmaker.md +++ b/site/user/api/usingBookmaker.md @@ -8,22 +8,22 @@ Install<a href="usingBookmaker#Go">Go</a>if needed. Get the fiddle command line interface tool. By default this will appear in your home directory. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ go get go.skia.org/infra/fiddle/go/fiddlecli</pre> Build <a href="#Bookmaker">Bookmaker</a>. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ ninja -<a href="undocumented#C">C</a> out/dir bookmaker</pre> Generate an starter <a href="#Bookmaker">Bookmaker</a> file from an existing include. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ ./out/dir/bookmaker -i include/core/<a href="undocumented#SkXXX.h">SkXXX.h</a> -t docs</pre> If a method or function has an unnamed parameter, bookmaker generates an error: -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> <a href="undocumented#C">C</a>:/puregit/include/core/<a href="SkPixmap_Reference#SkPixmap">SkPixmap</a>.h(208): error: # missing param name bool erase(const SkColor4f&, const SkIRect* subset = nullptr) const ^ @@ -34,14 +34,14 @@ them. After naming all parameters, check in the include before continuing. A successful run generates -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> docs/<a href="undocumented#SkXXX_Reference">SkXXX Reference</a>.bmh</pre> . Next, use your favorite editor to fill out -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> docs/<a href="undocumented#SkXXX_Reference">SkXXX Reference</a>.bmh</pre> . @@ -82,13 +82,13 @@ correct parents. If you run <a href="#Bookmaker">Bookmaker</a> inside <a href="usingBookmaker#Visual_Studio">Visual Studio</a>, you can click on errors and it will take you to the source line in question. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ ./out/dir/bookmaker -e fiddle.json -b docs</pre> Once complete, run fiddlecli to generate the example hashes. Errors are contained by the output but aren't reported yet. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ $GOPATH/bin/fiddlecli --input fiddle.json --output fiddleout.json</pre> Generate <a href="usingBookmaker#bmh_SkXXX">bmh SkXXX</a>.md from <a href="usingBookmaker#SkXXX">SkXXX</a>.bmh and fiddleout.json. @@ -96,19 +96,19 @@ Error checking includes: undefined references, fiddle compiler errors, missing or mismatched printf output. Again, you can click on any errors inside <a href="usingBookmaker#Visual_Studio">Visual Studio</a>. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ ./out/dir/bookmaker -r site/user/api -b docs -f fiddleout.json</pre> The original include may have changed since you started creating the markdown. Check to see if it is up to date. This reports if a method no longer exists or its parameters have changed. -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ ./out/dir/bookmaker -x -b docs/<a href="usingBookmaker#SkXXX">SkXXX</a>.bmh -i include/core/<a href="usingBookmaker#SkXXX">SkXXX</a>.h</pre> Generate an updated include header. Run: -<pre style="padding: 1em 1em 1em 1em;width: 44em; background-color: #f0f0f0"> +<pre style="padding: 1em 1em 1em 1em;width: 50em; background-color: #f0f0f0"> $ ./out/dir/bookmaker -p -b docs -i include/core/<a href="usingBookmaker#SkXXX">SkXXX</a>.h</pre> to write the updated <a href="undocumented#SkXXX.h">SkXXX.h</a> to the current directory. diff --git a/tools/bookmaker/bookmaker.cpp b/tools/bookmaker/bookmaker.cpp index cc454982fd..e0694071e2 100644 --- a/tools/bookmaker/bookmaker.cpp +++ b/tools/bookmaker/bookmaker.cpp @@ -630,6 +630,9 @@ const Definition* Definition::hasParam(const string& ref) const { } bool Definition::methodHasReturn(const string& name, TextParser* methodParser) const { + if (methodParser->skipExact("static")) { + methodParser->skipWhiteSpace(); + } const char* lastStart = methodParser->fChar; const char* nameInParser = methodParser->strnstr(name.c_str(), methodParser->fEnd); methodParser->skipTo(nameInParser); @@ -1160,6 +1163,8 @@ bool BmhParser::addDefinition(const char* defStart, bool hasEnd, MarkType markTy case MarkType::kFile: case MarkType::kHeight: case MarkType::kImage: + case MarkType::kLiteral: + case MarkType::kOutdent: case MarkType::kPlatform: case MarkType::kSeeAlso: case MarkType::kSubstitute: @@ -2001,6 +2006,8 @@ vector<string> BmhParser::typeName(MarkType markType, bool* checkEnd) { case MarkType::kFile: case MarkType::kHeight: case MarkType::kImage: + case MarkType::kLiteral: + case MarkType::kOutdent: case MarkType::kPlatform: case MarkType::kReturn: case MarkType::kSeeAlso: @@ -2335,6 +2342,7 @@ int main(int argc, char** const argv) { } if (!done && !FLAGS_spellcheck.isEmpty() && FLAGS_examples.isEmpty()) { bmhParser.spellCheck(FLAGS_bmh[0], FLAGS_spellcheck); + bmhParser.fWroteOut = true; done = true; } int examples = 0; diff --git a/tools/bookmaker/bookmaker.h b/tools/bookmaker/bookmaker.h index 857caf4c10..f5f53ff7ab 100644 --- a/tools/bookmaker/bookmaker.h +++ b/tools/bookmaker/bookmaker.h @@ -40,6 +40,7 @@ using std::vector; enum class KeyWord { kNone, kSK_API, + kSK_BEGIN_REQUIRE_DENSE, kBool, kChar, kClass, @@ -107,10 +108,12 @@ enum class MarkType { kLegend, kLink, kList, + kLiteral, // don't lookup hyperlinks, do substitution, etc kMarkChar, kMember, kMethod, kNoExample, + kOutdent, kParam, kPlatform, kPrivate, @@ -1063,6 +1066,7 @@ public: fMaxLF = 2; fPendingLF = 0; fPendingSpace = 0; + fOutdentNext = false; nl(); } @@ -1078,46 +1082,14 @@ public: fMaxLF = 1; } - bool writeBlockTrim(int size, const char* data) { - while (size && ' ' >= data[0]) { - ++data; - --size; - } - while (size && ' ' >= data[size - 1]) { - --size; - } - if (size <= 0) { - fLastChar = '\0'; - return false; - } - SkASSERT(size < 16000); - if (size > 3 && !strncmp("#end", data, 4)) { - fMaxLF = 1; - } - if (this->leadingPunctuation(data, (size_t) size)) { - fPendingSpace = 0; - } - writePending(); - if (fDebugOut) { - string check(data, size); - SkDebugf("%s", check.c_str()); - } - fprintf(fOut, "%.*s", size, data); - int added = 0; - fLastChar = data[size - 1]; - while (size > 0 && '\n' != data[--size]) { - ++added; - } - fColumn = size ? added : fColumn + added; - fSpaces = 0; - fLinefeeds = 0; - fMaxLF = added > 2 && !strncmp("#if", &data[size + (size > 0)], 3) ? 1 : 2; - return true; - } void writeBlock(int size, const char* data) { SkAssertResult(writeBlockTrim(size, data)); } + + void writeBlockIndent(int size, const char* data); + bool writeBlockTrim(int size, const char* data); + void writeCommentHeader() { this->lf(2); this->writeString("/**"); @@ -1129,6 +1101,8 @@ public: this->lfcr(); } + void writePending(); + // write a pending space, so that two consecutive calls // don't double write, and trailing spaces on lines aren't written void writeSpace(int count = 1) { @@ -1139,62 +1113,12 @@ public: fPendingSpace = count; } - void writeString(const char* str) { - const size_t len = strlen(str); - SkASSERT(len > 0); - SkASSERT(' ' < str[0]); - fLastChar = str[len - 1]; - SkASSERT(' ' < fLastChar); - SkASSERT(!strchr(str, '\n')); - if (this->leadingPunctuation(str, strlen(str))) { - fPendingSpace = 0; - } - writePending(); - if (fDebugOut) { - SkDebugf("%s", str); - } - fprintf(fOut, "%s", str); - fColumn += len; - fSpaces = 0; - fLinefeeds = 0; - fMaxLF = 2; - } + void writeString(const char* str); void writeString(const string& str) { this->writeString(str.c_str()); } - void writePending() { - fPendingLF = SkTMin(fPendingLF, fMaxLF); - bool wroteLF = false; - while (fLinefeeds < fPendingLF) { - if (fDebugOut) { - SkDebugf("\n"); - } - fprintf(fOut, "\n"); - ++fLinefeeds; - wroteLF = true; - } - fPendingLF = 0; - if (wroteLF) { - SkASSERT(0 == fColumn); - SkASSERT(fIndent >= fSpaces); - if (fDebugOut) { - SkDebugf("%*s", fIndent - fSpaces, ""); - } - fprintf(fOut, "%*s", fIndent - fSpaces, ""); - fColumn = fIndent; - fSpaces = fIndent; - } - for (int index = 0; index < fPendingSpace; ++index) { - if (fDebugOut) { - SkDebugf(" "); - } - fprintf(fOut, " "); - ++fColumn; - } - fPendingSpace = 0; - } unordered_map<string, sk_sp<SkData>> fRawData; unordered_map<string, vector<char>> fLFOnly; @@ -1209,6 +1133,7 @@ public: int fPendingSpace; // one or two spaces should preceed the next string or block char fLastChar; // last written bool fDebugOut; // set true to write to std out + bool fOutdentNext; // set at end of embedded struct to prevent premature outdent private: typedef TextParser INHERITED; }; @@ -1226,6 +1151,7 @@ public: kNo, // neither resolved nor output kYes, // resolved, output kOut, // not resolved, but output + kLiteral, // output untouched (FIXME: is this really different from kOut?) }; enum class Exemplary { @@ -1267,7 +1193,7 @@ public: , { "Alias", nullptr, MarkType::kAlias, R_N, E_N, 0 } , { "Bug", nullptr, MarkType::kBug, R_N, E_N, 0 } , { "Class", &fClassMap, MarkType::kClass, R_Y, E_O, M_CSST | M(Root) } -, { "Code", nullptr, MarkType::kCode, R_O, E_N, M_CSST | M_E } +, { "Code", nullptr, MarkType::kCode, R_O, E_N, M_CSST | M_E | M(Method) } , { "", nullptr, MarkType::kColumn, R_Y, E_N, M(Row) } , { "", nullptr, MarkType::kComment, R_N, E_N, 0 } , { "Const", &fConstMap, MarkType::kConst, R_Y, E_N, M_E | M_ST } @@ -1291,10 +1217,12 @@ public: , { "Legend", nullptr, MarkType::kLegend, R_Y, E_N, M(Table) } , { "", nullptr, MarkType::kLink, R_N, E_N, M(Anchor) } , { "List", nullptr, MarkType::kList, R_Y, E_N, M(Method) | M_CSST | M_E | M_D } +, { "Literal", nullptr, MarkType::kLiteral, R_N, E_N, M(Code) } , { "", nullptr, MarkType::kMarkChar, R_N, E_N, 0 } , { "Member", nullptr, MarkType::kMember, R_Y, E_N, M(Class) | M(Struct) } , { "Method", &fMethodMap, MarkType::kMethod, R_Y, E_Y, M_CSST } , { "NoExample", nullptr, MarkType::kNoExample, R_Y, E_N, 0 } +, { "Outdent", nullptr, MarkType::kOutdent, R_N, E_N, M(Code) } , { "Param", nullptr, MarkType::kParam, R_Y, E_N, M(Method) } , { "Platform", nullptr, MarkType::kPlatform, R_N, E_N, M(Example) } , { "Private", nullptr, MarkType::kPrivate, R_N, E_N, 0 } @@ -1474,10 +1402,12 @@ public: , { nullptr, MarkType::kLegend } , { nullptr, MarkType::kLink } , { nullptr, MarkType::kList } + , { nullptr, MarkType::kLiteral } , { nullptr, MarkType::kMarkChar } , { nullptr, MarkType::kMember } , { nullptr, MarkType::kMethod } , { nullptr, MarkType::kNoExample } + , { nullptr, MarkType::kOutdent } , { nullptr, MarkType::kParam } , { nullptr, MarkType::kPlatform } , { nullptr, MarkType::kPrivate } @@ -1685,6 +1615,20 @@ public: this->writeEndTag(tagType, tagID.c_str(), spaces); } + void writeIncompleteTag(const char* tagType, const string& tagID, int spaces = 1) { + this->writeString(string("#") + tagType + " " + tagID); + this->writeSpace(spaces); + this->writeString("incomplete"); + this->writeSpace(); + this->writeString("##"); + this->lf(1); + } + + void writeIncompleteTag(const char* tagType) { + this->writeString(string("#") + tagType + " incomplete ##"); + this->lf(1); + } + void writeTableHeader(const char* col1, size_t pad, const char* col2) { this->lf(1); this->writeString("#Table"); @@ -1858,11 +1802,13 @@ public: fBmhParser = nullptr; fEnumDef = nullptr; fMethodDef = nullptr; - fStructDef = nullptr; + fBmhStructDef = nullptr; fAttrDeprecated = nullptr; fAnonymousEnumCount = 1; fInStruct = false; fWroteMethod = false; + fIndentNext = false; + fPendingMethod = false; } string resolveMethod(const char* start, const char* end, bool first); @@ -1880,7 +1826,7 @@ private: const Definition* fBmhMethod; const Definition* fEnumDef; const Definition* fMethodDef; - const Definition* fStructDef; + const Definition* fBmhStructDef; const Definition* fAttrDeprecated; const char* fContinuation; // used to construct paren-qualified method name int fAnonymousEnumCount; @@ -1891,6 +1837,8 @@ private: int fStructCommentTab; bool fInStruct; bool fWroteMethod; + bool fIndentNext; + bool fPendingMethod; typedef IncludeParser INHERITED; }; @@ -1988,7 +1936,15 @@ private: fInList = false; } - BmhParser::Resolvable resolvable(MarkType markType) { + BmhParser::Resolvable resolvable(const Definition* definition) const { + MarkType markType = definition->fMarkType; + if (MarkType::kCode == markType) { + for (auto child : definition->fChildren) { + if (MarkType::kLiteral == child->fMarkType) { + return BmhParser::Resolvable::kLiteral; + } + } + } if ((MarkType::kExample == markType || MarkType::kFunction == markType) && fHasFiddle) { return BmhParser::Resolvable::kNo; diff --git a/tools/bookmaker/includeParser.cpp b/tools/bookmaker/includeParser.cpp index 4ad83d8aa7..c4ee8e7217 100644 --- a/tools/bookmaker/includeParser.cpp +++ b/tools/bookmaker/includeParser.cpp @@ -10,6 +10,7 @@ const IncludeKey kKeyWords[] = { { "", KeyWord::kNone, KeyProperty::kNone }, { "SK_API", KeyWord::kSK_API, KeyProperty::kModifier }, + { "SK_BEGIN_REQUIRE_DENSE", KeyWord::kSK_BEGIN_REQUIRE_DENSE, KeyProperty::kModifier }, { "bool", KeyWord::kBool, KeyProperty::kNumber }, { "char", KeyWord::kChar, KeyProperty::kNumber }, { "class", KeyWord::kClass, KeyProperty::kObject }, @@ -105,7 +106,7 @@ void IncludeParser::checkForMissingParams(const vector<string>& methodParams, } } if (!found) { - this->writeEndTag("Param", methodParam, 2); + this->writeIncompleteTag("Param", methodParam, 2); } } for (auto& foundParam : foundParams) { @@ -508,11 +509,16 @@ void IncludeParser::dumpClassTokens(IClassDefinition& classDef) { } this->lf(2); this->writeTag("Example"); + this->lf(1); + this->writeString("// incomplete"); + this->lf(1); this->writeEndTag(); this->lf(2); - this->writeEndTag("ToDo", "incomplete"); + this->writeTag("SeeAlso"); + this->writeSpace(); + this->writeString("incomplete"); this->lf(2); - this->writeEndTag(); + this->writeEndTag("Method"); this->lf(2); } } @@ -673,7 +679,7 @@ void IncludeParser::dumpComment(const Definition& token) { this->nl(); } this->lf(2); - this->writeEndTag("Return"); + this->writeIncompleteTag("Return"); } } } @@ -1389,11 +1395,36 @@ bool IncludeParser::parseMethod(Definition* child, Definition* markupDef) { auto tokenIter = child->fParent->fTokens.begin(); std::advance(tokenIter, child->fParentIndex); tokenIter = std::prev(tokenIter); - string nameStr(tokenIter->fStart, tokenIter->fContentEnd - tokenIter->fStart); + const char* nameEnd = tokenIter->fContentEnd; + bool add2 = false; + if ('[' == tokenIter->fStart[0]) { + auto closeParen = std::next(tokenIter); + SkASSERT(Definition::Type::kBracket == closeParen->fType && + '(' == closeParen->fContentStart[0]); + nameEnd = closeParen->fContentEnd + 1; + closeParen = std::next(closeParen); + add2 = true; + if (Definition::Type::kKeyWord == closeParen->fType && + KeyWord::kConst == closeParen->fKeyWord) { + add2 = false; + } + tokenIter = std::prev(tokenIter); + } + string nameStr(tokenIter->fStart, nameEnd - tokenIter->fStart); + if (add2) { + nameStr += "_2"; + } while (tokenIter != child->fParent->fTokens.begin()) { auto testIter = std::prev(tokenIter); switch (testIter->fType) { case Definition::Type::kWord: + if (testIter == child->fParent->fTokens.begin() && + (KeyWord::kIfdef == child->fParent->fKeyWord || + KeyWord::kIfndef == child->fParent->fKeyWord || + KeyWord::kIf == child->fParent->fKeyWord)) { + std::next(tokenIter); + break; + } goto keepGoing; case Definition::Type::kKeyWord: { KeyProperty keyProperty = kKeyWords[(int) testIter->fKeyWord].fProperty; @@ -1608,7 +1639,9 @@ bool IncludeParser::parseObject(Definition* child, Definition* markupDef) { // pick up templated function pieces when method is found break; case Bracket::kDebugCode: - // todo: handle this + if (!this->parseObjects(child, markupDef)) { + return false; + } break; case Bracket::kSquare: { // check to see if parent is operator, the only case we handle so far diff --git a/tools/bookmaker/includeWriter.cpp b/tools/bookmaker/includeWriter.cpp index ff7c0e3c56..399fd4688b 100644 --- a/tools/bookmaker/includeWriter.cpp +++ b/tools/bookmaker/includeWriter.cpp @@ -11,8 +11,44 @@ void IncludeWriter::descriptionOut(const Definition* def) { const char* commentStart = def->fContentStart; int commentLen = (int) (def->fContentEnd - commentStart); bool breakOut = false; + SkDEBUGCODE(bool wroteCode = false); for (auto prop : def->fChildren) { switch (prop->fMarkType) { + case MarkType::kCode: { + bool literal = false; + bool literalOutdent = false; + commentLen = (int) (prop->fStart - commentStart); + if (commentLen > 0) { + SkASSERT(commentLen < 1000); + if (Wrote::kNone != this->rewriteBlock(commentLen, commentStart, Phrase::kNo)) { + this->lf(2); + } + } + size_t childSize = prop->fChildren.size(); + if (childSize) { + SkASSERT(1 == childSize || 2 == childSize); // incomplete + SkASSERT(MarkType::kLiteral == prop->fChildren[0]->fMarkType); + SkASSERT(1 == childSize || MarkType::kOutdent == prop->fChildren[1]->fMarkType); + commentStart = prop->fChildren[childSize - 1]->fContentStart; + literal = true; + literalOutdent = 2 == childSize && + MarkType::kOutdent == prop->fChildren[1]->fMarkType; + } + commentLen = (int) (prop->fContentEnd - commentStart); + SkASSERT(commentLen > 0); + if (literal) { + if (!literalOutdent) { + fIndent += 4; + } + this->writeBlockIndent(commentLen, commentStart); + this->lf(2); + if (!literalOutdent) { + fIndent -= 4; + } + commentStart = prop->fTerminator; + SkDEBUGCODE(wroteCode = true); + } + } break; case MarkType::kDefinedBy: commentStart = prop->fTerminator; break; @@ -48,20 +84,35 @@ void IncludeWriter::descriptionOut(const Definition* def) { commentStart = prop->fTerminator; commentLen = (int) (def->fContentEnd - commentStart); break; - case MarkType::kFormula: + case MarkType::kFormula: { commentLen = prop->fStart - commentStart; if (commentLen > 0) { if (Wrote::kNone != this->rewriteBlock(commentLen, commentStart, Phrase::kNo)) { - this->lfcr(); + if (commentLen > 1 && '\n' == prop->fStart[-1] && + '\n' == prop->fStart[-2]) { + this->lf(1); + } else { + this->writeSpace(); + } } } - this->writeBlock(prop->length(), prop->fContentStart); + int saveIndent = fIndent; + if (fIndent < fColumn + 1) { + fIndent = fColumn + 1; + } + this->writeBlockIndent(prop->length(), prop->fContentStart); + fIndent = saveIndent; commentStart = prop->fTerminator; commentLen = (int) (def->fContentEnd - commentStart); - if ('\n' == commentStart[0] && '\n' == commentStart[1]) { + if (commentLen > 1 && '\n' == commentStart[0] && '\n' == commentStart[1]) { this->lf(2); + } else { + SkASSERT('\n' == prop->fTerminator[0]); + if ('.' != prop->fTerminator[1] && !fLinefeeds) { + this->writeSpace(); + } } - break; + } break; case MarkType::kToDo: commentLen = (int) (prop->fStart - commentStart); if (commentLen > 0) { @@ -105,8 +156,10 @@ void IncludeWriter::descriptionOut(const Definition* def) { break; } } - SkASSERT(commentLen > 0 && commentLen < 1500); - this->rewriteBlock(commentLen, commentStart, Phrase::kNo); + SkASSERT(wroteCode || (commentLen > 0 && commentLen < 1500)); + if (commentLen > 0) { + this->rewriteBlock(commentLen, commentStart, Phrase::kNo); + } } void IncludeWriter::enumHeaderOut(const RootDefinition* root, @@ -116,6 +169,10 @@ void IncludeWriter::enumHeaderOut(const RootDefinition* root, child.fContentStart; this->writeBlockTrim((int) (bodyEnd - fStart), fStart); // may write nothing this->lf(2); + if (fIndentNext) { + fIndent += 4; + fIndentNext = false; + } fDeferComment = nullptr; fStart = child.fContentStart; const auto& nameDef = child.fTokens.front(); @@ -172,6 +229,9 @@ void IncludeWriter::enumHeaderOut(const RootDefinition* root, const char* commentEnd = test->fStart; if (!wroteHeader && !this->contentFree((int) (commentEnd - commentStart), commentStart)) { + if (fIndentNext) { + fIndent += 4; + } this->writeCommentHeader(); this->writeString("\\enum"); if (fullName.length() > 0) { @@ -193,9 +253,15 @@ void IncludeWriter::enumHeaderOut(const RootDefinition* root, } this->rewriteBlock((int) (commentEnd - commentStart), commentStart, Phrase::kNo); if (MarkType::kAnchor == test->fMarkType) { + bool newLine = commentEnd - commentStart > 1 && + '\n' == commentEnd[-1] && '\n' == commentEnd[-2]; commentStart = test->fContentStart; commentEnd = test->fChildren[0]->fStart; - this->writeSpace(); + if (newLine) { + this->lf(2); + } else { + this->writeSpace(); + } this->rewriteBlock((int) (commentEnd - commentStart), commentStart, Phrase::kNo); lastAnchor = true; // this->writeSpace(); } @@ -518,12 +584,17 @@ void IncludeWriter::enumSizeItems(const Definition& child) { // walk children and output complete method doxygen description void IncludeWriter::methodOut(const Definition* method, const Definition& child) { + if (fPendingMethod) { + fIndent -= 4; + fPendingMethod = false; + } fBmhMethod = method; fMethodDef = &child; fContinuation = nullptr; fDeferComment = nullptr; - if (0 == fIndent) { - fIndent = 4; + if (0 == fIndent || fIndentNext) { + fIndent += 4; + fIndentNext = false; } this->writeCommentHeader(); fIndent += 4; @@ -602,13 +673,17 @@ Definition* IncludeWriter::structMemberOut(const Definition* memberStart, const const char* blockEnd = fWroteMethod && fDeferComment ? fDeferComment->fStart - 1 : memberStart->fStart; this->writeBlockTrim((int) (blockEnd - blockStart), blockStart); + if (fIndentNext) { + fIndent += 4; + fIndentNext = false; + } fWroteMethod = false; const char* commentStart = nullptr; ptrdiff_t commentLen = 0; string name(child.fContentStart, (int) (child.fContentEnd - child.fContentStart)); bool isShort; Definition* commentBlock = nullptr; - for (auto memberDef : fStructDef->fChildren) { + for (auto memberDef : fBmhStructDef->fChildren) { if (memberDef->fName.length() - name.length() == memberDef->fName.find(name)) { commentStart = memberDef->fContentStart; commentLen = memberDef->fContentEnd - commentStart; @@ -668,8 +743,8 @@ Definition* IncludeWriter::structMemberOut(const Definition* memberStart, const this->writeString("//!<"); this->writeSpace(); this->rewriteBlock(commentLen, commentStart, Phrase::kNo); - this->lfcr(); } + this->lf(2); return valueEnd; } @@ -784,7 +859,7 @@ void IncludeWriter::structSizeMembers(const Definition& child) { fStructValueTab -= 1 /* ; */ ; } // iterate through bmh children and see which comments fit on include lines - for (auto& member : fStructDef->fChildren) { + for (auto& member : fBmhStructDef->fChildren) { if (MarkType::kMember != member->fMarkType) { continue; } @@ -800,6 +875,21 @@ void IncludeWriter::structSizeMembers(const Definition& child) { } } +static bool find_start(const Definition* startDef, const char* start) { + for (const auto& child : startDef->fTokens) { + if (child.fContentStart == start) { + return MarkType::kMethod == child.fMarkType; + } + if (child.fContentStart >= start) { + break; + } + if (find_start(&child, start)) { + return true; + } + } + return false; +} + bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefinition* root) { ParentPair pair = { def, prevPair }; // write bulk of original include up to class, method, enum, etc., excepting preceding comment @@ -816,11 +906,30 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti bool inStruct = false; bool inConstructor = false; bool inInline = false; + bool eatOperator = false; + const Definition* requireDense = nullptr; + const Definition* startDef = nullptr; for (auto& child : def->fTokens) { + if (KeyWord::kOperator == child.fKeyWord && method && + Definition::MethodType::kOperator == method->fMethodType) { + eatOperator = true; + continue; + } + if (eatOperator) { + if (Bracket::kSquare == child.fBracket || Bracket::kParen == child.fBracket) { + continue; + } + eatOperator = false; + fContinuation = nullptr; + if (KeyWord::kConst == child.fKeyWord) { + continue; + } + } if (memberEnd) { if (memberEnd != &child) { continue; } + startDef = &child; fStart = child.fContentStart + 1; memberEnd = nullptr; } @@ -958,6 +1067,7 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti continue; } const char* bodyEnd = fDeferComment ? fDeferComment->fContentStart - 1 : + fAttrDeprecated ? fAttrDeprecated->fContentStart - 1 : child.fContentStart; // FIXME: roll end-trimming into writeBlockTrim call while (fStart < bodyEnd && ' ' >= bodyEnd[-1]) { @@ -967,11 +1077,15 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti if (blockSize) { this->writeBlock(blockSize, fStart); } + startDef = &child; fStart = child.fContentStart; methodName = root->fName + "::" + child.fName; inConstructor = root->fName == child.fName; fContinuation = child.fContentEnd; method = root->find(methodName, RootDefinition::AllowParens::kNo); +// if (!method) { +// method = root->find(methodName + "()", RootDefinition::AllowParens::kNo); +// } if (!method) { continue; } @@ -981,13 +1095,26 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti } this->methodOut(method, child); if (fAttrDeprecated) { + startDef = fAttrDeprecated; fStart = fAttrDeprecated->fContentStart; fAttrDeprecated = nullptr; } continue; } if (Definition::Type::kKeyWord == child.fType) { - const Definition* structDef = nullptr; + if (fIndentNext) { + SkDebugf(""); + // too soon +#if 0 // makes struct Lattice indent when it oughtn't + if (KeyWord::kEnum == child.fKeyWord) { + fIndent += 4; + } + if (KeyWord::kPublic != child.fKeyWord) { + fIndentNext = false; + } +#endif + } + const Definition* cIncludeStructDef = nullptr; switch (child.fKeyWord) { case KeyWord::kStruct: case KeyWord::kClass: @@ -1002,20 +1129,51 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti } } if (fInStruct) { + // try child; root+child; root->parent+child; etc. + int trial = 0; + const RootDefinition* search = root; + const Definition* parent = search->fParent; + do { + string name; + if (0 == trial) { + name = child.fName; + } else if (1 == trial) { + name = root->fName + "::" + child.fName; + } else { + SkASSERT(parent); + name = parent->fName + "::" + child.fName; + search = parent->asRoot(); + parent = search->fParent; + } + fBmhStructDef = search->find(name, RootDefinition::AllowParens::kNo); + } while (!fBmhStructDef && ++trial); + root = const_cast<RootDefinition*>(fBmhStructDef->asRoot()); + SkASSERT(root); fIndent += 4; - fStructDef = root->find(child.fName, RootDefinition::AllowParens::kNo); - if (nullptr == structDef) { - fStructDef = root->find(root->fName + "::" + child.fName, - RootDefinition::AllowParens::kNo); - } this->structSizeMembers(child); fIndent -= 4; + SkASSERT(!fIndentNext); + fIndentNext = true; } if (child.fChildren.size() > 0) { const char* bodyEnd = fDeferComment ? fDeferComment->fContentStart - 1 : child.fContentStart; this->writeBlockTrim((int) (bodyEnd - fStart), fStart); - fStart = child.fContentStart; + if (fPendingMethod) { + fIndent -= 4; + fPendingMethod = false; + } + startDef = requireDense ? requireDense : &child; + fStart = requireDense ? requireDense->fContentStart : child.fContentStart; + requireDense = nullptr; + if (!fInStruct && child.fName != root->fName) { + root = &fBmhParser->fClassMap[child.fName]; + fRootTopic = root->fParent; + SkASSERT(!root->fVisited); + root->clearVisited(); + fIndent = 0; + fBmhStructDef = root; + } if (child.fName == root->fName) { if (Definition* parent = root->fParent) { if (MarkType::kTopic == parent->fMarkType || @@ -1030,36 +1188,43 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti SkASSERT(0); // incomplete } } else { - structDef = root->find(child.fName, RootDefinition::AllowParens::kNo); - if (nullptr == structDef) { - structDef = root->find(root->fName + "::" + child.fName, + SkASSERT(fInStruct); + #if 0 + fBmhStructDef = root->find(child.fName, RootDefinition::AllowParens::kNo); + if (nullptr == fBmhStructDef) { + fBmhStructDef = root->find(root->fName + "::" + child.fName, RootDefinition::AllowParens::kNo); } - if (!structDef) { + if (!fBmhStructDef) { this->lf(2); fIndent = 0; this->writeBlock((int) (fStart - bodyEnd), bodyEnd); this->lfcr(); continue; } + #endif Definition* codeBlock = nullptr; - SkDEBUGCODE(Definition* nextBlock = nullptr); - for (auto test : structDef->fChildren) { + Definition* nextBlock = nullptr; + for (auto test : fBmhStructDef->fChildren) { if (MarkType::kCode == test->fMarkType) { SkASSERT(!codeBlock); // FIXME: check enum for correct order earlier codeBlock = test; continue; } if (codeBlock) { - SkDEBUGCODE(nextBlock = test); + nextBlock = test; break; } } // FIXME: trigger error earlier if inner #Struct or #Class is missing #Code SkASSERT(nextBlock); // FIXME: check enum for correct order earlier - const char* commentStart = structDef->fContentStart; - const char* commentEnd = codeBlock->fStart; - this->structOut(root, *structDef, commentStart, commentEnd); + const char* commentStart = codeBlock->fTerminator; + const char* commentEnd = nextBlock->fStart; + if (fIndentNext) { +// fIndent += 4; + } + fIndentNext = true; + this->structOut(root, *fBmhStructDef, commentStart, commentEnd); } fDeferComment = nullptr; } else { @@ -1096,17 +1261,21 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti case KeyWord::kSK_API: case KeyWord::kTypedef: break; + case KeyWord::kSK_BEGIN_REQUIRE_DENSE: + requireDense = &child; + break; default: SkASSERT(0); } - if (structDef) { + if (cIncludeStructDef) { TextParser structName(&child); SkAssertResult(structName.skipToEndBracket('{')); + startDef = &child; fStart = structName.fChar + 1; this->writeBlock((int) (fStart - child.fStart), child.fStart); this->lf(2); fIndent += 4; - if (!this->populate(&child, &pair, const_cast<Definition*>(structDef)->asRoot())) { + if (!this->populate(&child, &pair, const_cast<Definition*>(cIncludeStructDef)->asRoot())) { return false; } // output any remaining definitions at current indent level @@ -1126,8 +1295,28 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti if (!this->populate(child.fChildren[0], &pair, root)) { return false; } - } else if (!this->populate(&child, &pair, root)) { - return false; + } else { + if (!this->populate(&child, &pair, root)) { + return false; + } + if (KeyWord::kClass == child.fKeyWord || KeyWord::kStruct == child.fKeyWord) { + fStructMemberTab = 0; + if (fInStruct) { + fInStruct = false; + do { + SkASSERT(root); + root = const_cast<RootDefinition*>(root->fParent->asRoot()); + } while (MarkType::kTopic == root->fMarkType || + MarkType::kSubtopic == root->fMarkType); + SkASSERT(MarkType::kStruct == root->fMarkType || + MarkType::kClass == root->fMarkType); + fPendingMethod = false; + if (startDef) { + fPendingMethod = find_start(startDef, fStart); + } + fOutdentNext = !fPendingMethod; + } + } } } continue; @@ -1140,17 +1329,25 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti this->enumMembersOut(root, child); this->writeString("};"); this->lf(2); + startDef = child.fParent; fStart = child.fParent->fContentEnd; SkASSERT(';' == fStart[0]); ++fStart; fDeferComment = nullptr; fInEnum = false; + if (fIndentNext) { +// fIndent -= 4; + fIndentNext = false; + } continue; } if (fAttrDeprecated) { continue; } fDeferComment = nullptr; + if (KeyWord::kClass == def->fKeyWord || KeyWord::kStruct == def->fKeyWord) { + fIndentNext = true; + } if (!this->populate(&child, &pair, root)) { return false; } @@ -1162,13 +1359,17 @@ bool IncludeWriter::populate(Definition* def, ParentPair* prevPair, RootDefiniti auto iter = def->fTokens.begin(); std::advance(iter, child.fParentIndex - 1); memberStart = &*iter; - if (!fStructDef) { + if (!fStructMemberTab) { SkASSERT(KeyWord::kStruct == def->fParent->fKeyWord); - fStructDef = def->fParent; - this->structSizeMembers(*fStructDef); + fIndent += 4; + this->structSizeMembers(*def->fParent); + fIndent -= 4; +// SkASSERT(!fIndentNext); + fIndentNext = true; } } memberEnd = this->structMemberOut(memberStart, child); + startDef = &child; fStart = child.fContentEnd + 1; fDeferComment = nullptr; } @@ -1322,8 +1523,8 @@ string IncludeWriter::resolveRef(const char* start, const char* end, bool first, rootDefIter = fBmhParser->fTopicMap.find(prefixedName); if (fBmhParser->fTopicMap.end() != rootDefIter) { rootDef = rootDefIter->second; - } else if (fStructDef) { - string localPrefix = fStructDef->fFiddle + '_' + undername; + } else if (fBmhStructDef) { + string localPrefix = fBmhStructDef->fFiddle + '_' + undername; rootDefIter = fBmhParser->fTopicMap.find(localPrefix); if (fBmhParser->fTopicMap.end() != rootDefIter) { rootDef = rootDefIter->second; @@ -1648,7 +1849,7 @@ IncludeWriter::Wrote IncludeWriter::rewriteBlock(int size, const char* data, Phr break; case Word::kCap: case Word::kFirst: - if (!isupper(last)) { + if (!isupper(last) && '~' != last) { word = Word::kMixed; } break; @@ -1697,6 +1898,14 @@ IncludeWriter::Wrote IncludeWriter::rewriteBlock(int size, const char* data, Phr hasIndirection |= embeddedIndirection; hasSymbol |= embeddedSymbol; break; + case '~': + SkASSERT(Word::kStart == word); + word = PunctuationState::kStart == punctuation ? Word::kFirst : Word::kCap; + start = run; + hasUpper = true; + hasIndirection |= embeddedIndirection; + hasSymbol |= embeddedSymbol; + break; default: SkASSERT(0); } diff --git a/tools/bookmaker/mdOut.cpp b/tools/bookmaker/mdOut.cpp index 242d667736..ed3cd2bcaf 100644 --- a/tools/bookmaker/mdOut.cpp +++ b/tools/bookmaker/mdOut.cpp @@ -324,7 +324,7 @@ bool MdOut::buildRefFromFile(const char* name, const char* outDir) { bool MdOut::checkParamReturnBody(const Definition* def) const { TextParser paramBody(def); const char* descriptionStart = paramBody.fChar; - if (!islower(descriptionStart[0])) { + if (!islower(descriptionStart[0]) && !isdigit(descriptionStart[0])) { paramBody.skipToNonAlphaNum(); string ref = string(descriptionStart, paramBody.fChar - descriptionStart); if (!this->isDefined(paramBody, ref, true)) { @@ -349,7 +349,7 @@ void MdOut::childrenOut(const Definition* def, const char* start) { } else if (MarkType::kEnumClass == def->fMarkType) { fEnumClass = def; } - BmhParser::Resolvable resolvable = this->resolvable(def->fMarkType); + BmhParser::Resolvable resolvable = this->resolvable(def); for (auto& child : def->fChildren) { end = child->fStart; if (BmhParser::Resolvable::kNo != resolvable) { @@ -640,7 +640,7 @@ void MdOut::markTypeOut(Definition* def) { case MarkType::kCode: this->lfAlways(2); fprintf(fOut, "<pre style=\"padding: 1em 1em 1em 1em;" - "width: 44em; background-color: #f0f0f0\">"); + "width: 50em; background-color: #f0f0f0\">"); this->lf(1); break; case MarkType::kColumn: @@ -714,7 +714,7 @@ void MdOut::markTypeOut(Definition* def) { fprintf(fOut, "<div><fiddle-embed name=\"%s\">", def->fHash.c_str()); } else { fprintf(fOut, "<pre style=\"padding: 1em 1em 1em 1em;" - "width: 44em; background-color: #f0f0f0\">"); + "width: 50em; background-color: #f0f0f0\">"); this->lf(1); } } break; @@ -742,6 +742,8 @@ void MdOut::markTypeOut(Definition* def) { fprintf(fOut, "<table>"); this->lf(1); break; + case MarkType::kLiteral: + break; case MarkType::kMarkChar: fBmhParser.fMC = def->fContentStart[0]; break; @@ -768,7 +770,7 @@ void MdOut::markTypeOut(Definition* def) { } // TODO: put in css spec that we can define somewhere else (if markup supports that) - // TODO: 50em below should match limt = 80 in formatFunction() + // TODO: 50em below should match limit = 80 in formatFunction() this->writePending(); string preformattedStr = preformat(formattedStr); fprintf(fOut, "<pre style=\"padding: 1em 1em 1em 1em;" @@ -781,6 +783,8 @@ void MdOut::markTypeOut(Definition* def) { } break; case MarkType::kNoExample: break; + case MarkType::kOutdent: + break; case MarkType::kParam: { if (TableState::kNone == fTableState) { this->mdHeaderOut(3); @@ -1004,6 +1008,24 @@ void MdOut::mdHeaderOutLF(int depth, int lf) { } void MdOut::resolveOut(const char* start, const char* end, BmhParser::Resolvable resolvable) { + if (BmhParser::Resolvable::kLiteral == resolvable && end > start) { + while ('\n' == *start) { + ++start; + } + const char* spaceStart = start; + while (' ' == *start) { + ++start; + } + if (start > spaceStart) { + fIndent = start - spaceStart; + } + this->writeBlockTrim(end - start, start); + if ('\n' == end[-1]) { + this->lf(1); + } + fIndent = 0; + return; + } // FIXME: this needs the markdown character present when the def was defined, // not the last markdown character the parser would have seen... while (fBmhParser.fMC == end[-1]) { diff --git a/tools/bookmaker/parserCommon.cpp b/tools/bookmaker/parserCommon.cpp index cb55bcb640..fbfcbae728 100644 --- a/tools/bookmaker/parserCommon.cpp +++ b/tools/bookmaker/parserCommon.cpp @@ -7,6 +7,11 @@ #include "bookmaker.h" +static void debug_out(int len, const char* data) { + // convenient place to intercept arbitrary output + SkDebugf("%.*s", len, data); +} + bool ParserCommon::parseSetup(const char* path) { this->reset(); sk_sp<SkData> data = SkData::MakeFromFileName(path); @@ -49,3 +54,131 @@ bool ParserCommon::parseSetup(const char* path) { fLineCount = 1; return true; } + +void ParserCommon::writeBlockIndent(int size, const char* data) { + while (size && ' ' >= data[size - 1]) { + --size; + } + bool newLine = false; + while (size) { + while (size && ' ' > data[0]) { + ++data; + --size; + } + if (!size) { + return; + } + if (newLine) { + this->lf(1); + } + TextParser parser(fFileName, data, data + size, fLineCount); + const char* lineEnd = parser.strnchr('\n', data + size); + int len = lineEnd ? (int) (lineEnd - data) : size; + this->writePending(); + this->indentToColumn(fIndent); + if (fDebugOut) { + debug_out(len, data); + } + fprintf(fOut, "%.*s", len, data); + size -= len; + data += len; + newLine = true; + } +} + +bool ParserCommon::writeBlockTrim(int size, const char* data) { + if (fOutdentNext) { + fIndent -= 4; + fOutdentNext = false; + } + while (size && ' ' >= data[0]) { + ++data; + --size; + } + while (size && ' ' >= data[size - 1]) { + --size; + } + if (size <= 0) { + fLastChar = '\0'; + return false; + } + SkASSERT(size < 16000); + if (size > 3 && !strncmp("#end", data, 4)) { + fMaxLF = 1; + } + if (this->leadingPunctuation(data, (size_t) size)) { + fPendingSpace = 0; + } + this->writePending(); + if (fDebugOut) { + debug_out(size, data); + } + fprintf(fOut, "%.*s", size, data); + int added = 0; + fLastChar = data[size - 1]; + while (size > 0 && '\n' != data[--size]) { + ++added; + } + fColumn = size ? added : fColumn + added; + fSpaces = 0; + fLinefeeds = 0; + fMaxLF = added > 2 && !strncmp("#if", &data[size + (size > 0)], 3) ? 1 : 2; + if (fOutdentNext) { + fIndent -= 4; + fOutdentNext = false; + } + return true; +} + +void ParserCommon::writePending() { + fPendingLF = SkTMin(fPendingLF, fMaxLF); + bool wroteLF = false; + while (fLinefeeds < fPendingLF) { + if (fDebugOut) { + SkDebugf("\n"); + } + fprintf(fOut, "\n"); + ++fLinefeeds; + wroteLF = true; + } + fPendingLF = 0; + if (wroteLF) { + SkASSERT(0 == fColumn); + SkASSERT(fIndent >= fSpaces); + if (fDebugOut) { + SkDebugf("%*s", fIndent - fSpaces, ""); + } + fprintf(fOut, "%*s", fIndent - fSpaces, ""); + fColumn = fIndent; + fSpaces = fIndent; + } + for (int index = 0; index < fPendingSpace; ++index) { + if (fDebugOut) { + SkDebugf(" "); + } + fprintf(fOut, " "); + ++fColumn; + } + fPendingSpace = 0; +} + +void ParserCommon::writeString(const char* str) { + const size_t len = strlen(str); + SkASSERT(len > 0); + SkASSERT(' ' < str[0]); + fLastChar = str[len - 1]; + SkASSERT(' ' < fLastChar); + SkASSERT(!strchr(str, '\n')); + if (this->leadingPunctuation(str, strlen(str))) { + fPendingSpace = 0; + } + this->writePending(); + if (fDebugOut) { + debug_out((int) strlen(str), str); + } + fprintf(fOut, "%s", str); + fColumn += len; + fSpaces = 0; + fLinefeeds = 0; + fMaxLF = 2; +} diff --git a/tools/bookmaker/spellCheck.cpp b/tools/bookmaker/spellCheck.cpp index 3a32f37bc4..e2c4286e18 100644 --- a/tools/bookmaker/spellCheck.cpp +++ b/tools/bookmaker/spellCheck.cpp @@ -202,6 +202,8 @@ bool SpellCheck::check(Definition* def) { break; case MarkType::kList: break; + case MarkType::kLiteral: + break; case MarkType::kMarkChar: break; case MarkType::kMember: @@ -220,6 +222,8 @@ bool SpellCheck::check(Definition* def) { } break; case MarkType::kNoExample: break; + case MarkType::kOutdent: + break; case MarkType::kParam: { if (TableState::kNone == fTableState) { fTableState = TableState::kRow; @@ -490,6 +494,7 @@ void SpellCheck::report(SkCommandLineFlags::StringArray report) { if (report.contains("all")) { int column = 0; char lastInitial = 'a'; + int count = 0; for (auto iter : elems) { if (string::npos != iter.second.fFile.find("undocumented.bmh")) { continue; @@ -521,8 +526,9 @@ void SpellCheck::report(SkCommandLineFlags::StringArray report) { } SkDebugf("%s ", check.c_str()); column += check.length(); + ++count; } - SkDebugf("\n\n"); + SkDebugf("\n\ncount = %d\n", count); return; } int index = 0; |