1 | /* |
2 | * Copyright 2012 Google Inc. |
3 | * |
4 | * Use of this source code is governed by a BSD-style license that can be |
5 | * found in the LICENSE file. |
6 | */ |
7 | |
8 | #ifndef SkImage_DEFINED |
9 | #define SkImage_DEFINED |
10 | |
11 | #include "include/core/SkFilterQuality.h" |
12 | #include "include/core/SkImageEncoder.h" |
13 | #include "include/core/SkImageInfo.h" |
14 | #include "include/core/SkM44.h" |
15 | #include "include/core/SkRefCnt.h" |
16 | #include "include/core/SkScalar.h" |
17 | #include "include/core/SkShader.h" |
18 | #include "include/core/SkTileMode.h" |
19 | #include "include/gpu/GrTypes.h" |
20 | #include <functional> // std::function |
21 | |
22 | #if defined(SK_BUILD_FOR_ANDROID) && __ANDROID_API__ >= 26 |
23 | #include <android/hardware_buffer.h> |
24 | #endif |
25 | |
26 | class SkData; |
27 | class SkCanvas; |
28 | class SkImageFilter; |
29 | class SkImageGenerator; |
30 | class SkMipmap; |
31 | class SkPaint; |
32 | class SkPicture; |
33 | class SkSurface; |
34 | class GrBackendTexture; |
35 | class GrContext; |
36 | class GrDirectContext; |
37 | class GrRecordingContext; |
38 | class GrContextThreadSafeProxy; |
39 | |
40 | struct SkYUVAIndex; |
41 | |
42 | enum class SkSamplingMode { |
43 | kNearest, // single sample point (nearest neighbor) |
44 | kLinear, // interporate between 2x2 sample points (bilinear interpolation) |
45 | }; |
46 | |
47 | enum class SkMipmapMode { |
48 | kNone, // ignore mipmap levels, sample from the "base" |
49 | kNearest, // sample from the nearest level |
50 | kLinear, // interpolate between the two nearest levels |
51 | }; |
52 | |
53 | struct SkFilterOptions { |
54 | SkSamplingMode fSampling; |
55 | SkMipmapMode fMipmap; |
56 | }; |
57 | |
58 | class SkMipmapBuilder { |
59 | public: |
60 | SkMipmapBuilder(const SkImageInfo&); |
61 | ~SkMipmapBuilder(); |
62 | |
63 | int countLevels() const; |
64 | SkPixmap level(int index) const; |
65 | |
66 | sk_sp<SkMipmap> detach(); |
67 | |
68 | private: |
69 | sk_sp<SkMipmap> fMM; |
70 | }; |
71 | |
72 | /** \class SkImage |
73 | SkImage describes a two dimensional array of pixels to draw. The pixels may be |
74 | decoded in a raster bitmap, encoded in a SkPicture or compressed data stream, |
75 | or located in GPU memory as a GPU texture. |
76 | |
77 | SkImage cannot be modified after it is created. SkImage may allocate additional |
78 | storage as needed; for instance, an encoded SkImage may decode when drawn. |
79 | |
80 | SkImage width and height are greater than zero. Creating an SkImage with zero width |
81 | or height returns SkImage equal to nullptr. |
82 | |
83 | SkImage may be created from SkBitmap, SkPixmap, SkSurface, SkPicture, encoded streams, |
84 | GPU texture, YUV_ColorSpace data, or hardware buffer. Encoded streams supported |
85 | include BMP, GIF, HEIF, ICO, JPEG, PNG, WBMP, WebP. Supported encoding details |
86 | vary with platform. |
87 | */ |
88 | class SK_API SkImage : public SkRefCnt { |
89 | public: |
90 | |
91 | /** Caller data passed to RasterReleaseProc; may be nullptr. |
92 | */ |
93 | typedef void* ReleaseContext; |
94 | |
95 | /** Creates SkImage from SkPixmap and copy of pixels. Since pixels are copied, SkPixmap |
96 | pixels may be modified or deleted without affecting SkImage. |
97 | |
98 | SkImage is returned if SkPixmap is valid. Valid SkPixmap parameters include: |
99 | dimensions are greater than zero; |
100 | each dimension fits in 29 bits; |
101 | SkColorType and SkAlphaType are valid, and SkColorType is not kUnknown_SkColorType; |
102 | row bytes are large enough to hold one row of pixels; |
103 | pixel address is not nullptr. |
104 | |
105 | @param pixmap SkImageInfo, pixel address, and row bytes |
106 | @return copy of SkPixmap pixels, or nullptr |
107 | |
108 | example: https://fiddle.skia.org/c/@Image_MakeRasterCopy |
109 | */ |
110 | static sk_sp<SkImage> MakeRasterCopy(const SkPixmap& pixmap); |
111 | |
112 | /** Creates SkImage from SkImageInfo, sharing pixels. |
113 | |
114 | SkImage is returned if SkImageInfo is valid. Valid SkImageInfo parameters include: |
115 | dimensions are greater than zero; |
116 | each dimension fits in 29 bits; |
117 | SkColorType and SkAlphaType are valid, and SkColorType is not kUnknown_SkColorType; |
118 | rowBytes are large enough to hold one row of pixels; |
119 | pixels is not nullptr, and contains enough data for SkImage. |
120 | |
121 | @param info contains width, height, SkAlphaType, SkColorType, SkColorSpace |
122 | @param pixels address or pixel storage |
123 | @param rowBytes size of pixel row or larger |
124 | @return SkImage sharing pixels, or nullptr |
125 | */ |
126 | static sk_sp<SkImage> MakeRasterData(const SkImageInfo& info, sk_sp<SkData> pixels, |
127 | size_t rowBytes); |
128 | |
129 | /** Function called when SkImage no longer shares pixels. ReleaseContext is |
130 | provided by caller when SkImage is created, and may be nullptr. |
131 | */ |
132 | typedef void (*RasterReleaseProc)(const void* pixels, ReleaseContext); |
133 | |
134 | /** Creates SkImage from pixmap, sharing SkPixmap pixels. Pixels must remain valid and |
135 | unchanged until rasterReleaseProc is called. rasterReleaseProc is passed |
136 | releaseContext when SkImage is deleted or no longer refers to pixmap pixels. |
137 | |
138 | Pass nullptr for rasterReleaseProc to share SkPixmap without requiring a callback |
139 | when SkImage is released. Pass nullptr for releaseContext if rasterReleaseProc |
140 | does not require state. |
141 | |
142 | SkImage is returned if pixmap is valid. Valid SkPixmap parameters include: |
143 | dimensions are greater than zero; |
144 | each dimension fits in 29 bits; |
145 | SkColorType and SkAlphaType are valid, and SkColorType is not kUnknown_SkColorType; |
146 | row bytes are large enough to hold one row of pixels; |
147 | pixel address is not nullptr. |
148 | |
149 | @param pixmap SkImageInfo, pixel address, and row bytes |
150 | @param rasterReleaseProc function called when pixels can be released; or nullptr |
151 | @param releaseContext state passed to rasterReleaseProc; or nullptr |
152 | @return SkImage sharing pixmap |
153 | */ |
154 | static sk_sp<SkImage> MakeFromRaster(const SkPixmap& pixmap, |
155 | RasterReleaseProc rasterReleaseProc, |
156 | ReleaseContext releaseContext); |
157 | |
158 | /** Creates SkImage from bitmap, sharing or copying bitmap pixels. If the bitmap |
159 | is marked immutable, and its pixel memory is shareable, it may be shared |
160 | instead of copied. |
161 | |
162 | SkImage is returned if bitmap is valid. Valid SkBitmap parameters include: |
163 | dimensions are greater than zero; |
164 | each dimension fits in 29 bits; |
165 | SkColorType and SkAlphaType are valid, and SkColorType is not kUnknown_SkColorType; |
166 | row bytes are large enough to hold one row of pixels; |
167 | pixel address is not nullptr. |
168 | |
169 | @param bitmap SkImageInfo, row bytes, and pixels |
170 | @return created SkImage, or nullptr |
171 | |
172 | example: https://fiddle.skia.org/c/@Image_MakeFromBitmap |
173 | */ |
174 | static sk_sp<SkImage> MakeFromBitmap(const SkBitmap& bitmap); |
175 | |
176 | /** Creates SkImage from data returned by imageGenerator. Generated data is owned by SkImage and |
177 | may not be shared or accessed. |
178 | |
179 | SkImage is returned if generator data is valid. Valid data parameters vary by type of data |
180 | and platform. |
181 | |
182 | imageGenerator may wrap SkPicture data, codec data, or custom data. |
183 | |
184 | @param imageGenerator stock or custom routines to retrieve SkImage |
185 | @return created SkImage, or nullptr |
186 | */ |
187 | static sk_sp<SkImage> MakeFromGenerator(std::unique_ptr<SkImageGenerator> imageGenerator); |
188 | |
189 | /** |
190 | * Return an image backed by the encoded data, but attempt to defer decoding until the image |
191 | * is actually used/drawn. This deferral allows the system to cache the result, either on the |
192 | * CPU or on the GPU, depending on where the image is drawn. If memory is low, the cache may |
193 | * be purged, causing the next draw of the image to have to re-decode. |
194 | * |
195 | * The subset parameter specifies a area within the decoded image to create the image from. |
196 | * If subset is null, then the entire image is returned. |
197 | * |
198 | * This is similar to DecodeTo[Raster,Texture], but this method will attempt to defer the |
199 | * actual decode, while the DecodeTo... method explicitly decode and allocate the backend |
200 | * when the call is made. |
201 | * |
202 | * If the encoded format is not supported, or subset is outside of the bounds of the decoded |
203 | * image, nullptr is returned. |
204 | * |
205 | * @param encoded the encoded data |
206 | * @param length the number of bytes of encoded data |
207 | * @return created SkImage, or nullptr |
208 | |
209 | example: https://fiddle.skia.org/c/@Image_MakeFromEncoded |
210 | */ |
211 | static sk_sp<SkImage> MakeFromEncoded(sk_sp<SkData> encoded); |
212 | |
213 | /* |
214 | * Experimental: |
215 | * Skia | GL_COMPRESSED_* | MTLPixelFormat* | VK_FORMAT_*_BLOCK |
216 | * -------------------------------------------------------------------------------------- |
217 | * kETC2_RGB8_UNORM | ETC1_RGB8 | ETC2_RGB8 (iOS-only) | ETC2_R8G8B8_UNORM |
218 | * | RGB8_ETC2 | | |
219 | * -------------------------------------------------------------------------------------- |
220 | * kBC1_RGB8_UNORM | RGB_S3TC_DXT1_EXT | N/A | BC1_RGB_UNORM |
221 | * -------------------------------------------------------------------------------------- |
222 | * kBC1_RGBA8_UNORM | RGBA_S3TC_DXT1_EXT | BC1_RGBA (macOS-only)| BC1_RGBA_UNORM |
223 | */ |
224 | enum class CompressionType { |
225 | kNone, |
226 | kETC2_RGB8_UNORM, // the same as ETC1 |
227 | |
228 | kBC1_RGB8_UNORM, |
229 | kBC1_RGBA8_UNORM, |
230 | kLast = kBC1_RGBA8_UNORM, |
231 | }; |
232 | |
233 | static constexpr int kCompressionTypeCount = static_cast<int>(CompressionType::kLast) + 1; |
234 | |
235 | static const CompressionType kETC1_CompressionType = CompressionType::kETC2_RGB8_UNORM; |
236 | |
237 | /** Creates a GPU-backed SkImage from compressed data. |
238 | |
239 | This method will return an SkImage representing the compressed data. |
240 | If the GPU doesn't support the specified compression method, the data |
241 | will be decompressed and then wrapped in a GPU-backed image. |
242 | |
243 | Note: one can query the supported compression formats via |
244 | GrContext::compressedBackendFormat. |
245 | |
246 | @param context GPU context |
247 | @param data compressed data to store in SkImage |
248 | @param width width of full SkImage |
249 | @param height height of full SkImage |
250 | @param type type of compression used |
251 | @param mipMapped does 'data' contain data for all the mipmap levels? |
252 | @param isProtected do the contents of 'data' require DRM protection (on Vulkan)? |
253 | @return created SkImage, or nullptr |
254 | */ |
255 | static sk_sp<SkImage> MakeTextureFromCompressed(GrDirectContext* direct, |
256 | sk_sp<SkData> data, |
257 | int width, int height, |
258 | CompressionType type, |
259 | GrMipmapped mipMapped = GrMipmapped::kNo, |
260 | GrProtected isProtected = GrProtected::kNo); |
261 | |
262 | /** Creates a CPU-backed SkImage from compressed data. |
263 | |
264 | This method will decompress the compressed data and create an image wrapping |
265 | it. Any mipmap levels present in the compressed data are discarded. |
266 | |
267 | @param data compressed data to store in SkImage |
268 | @param width width of full SkImage |
269 | @param height height of full SkImage |
270 | @param type type of compression used |
271 | @return created SkImage, or nullptr |
272 | */ |
273 | static sk_sp<SkImage> MakeRasterFromCompressed(sk_sp<SkData> data, |
274 | int width, int height, |
275 | CompressionType type); |
276 | |
277 | /** User function called when supplied texture may be deleted. |
278 | */ |
279 | typedef void (*TextureReleaseProc)(ReleaseContext releaseContext); |
280 | |
281 | /** Creates SkImage from GPU texture associated with context. GPU texture must stay |
282 | valid and unchanged until textureReleaseProc is called. textureReleaseProc is |
283 | passed releaseContext when SkImage is deleted or no longer refers to texture. |
284 | |
285 | SkImage is returned if format of backendTexture is recognized and supported. |
286 | Recognized formats vary by GPU back-end. |
287 | |
288 | @note When using a DDL recording context, textureReleaseProc will be called on the |
289 | GPU thread after the DDL is played back on the direct context. |
290 | |
291 | @param context GPU context |
292 | @param backendTexture texture residing on GPU |
293 | @param colorSpace This describes the color space of this image's contents, as |
294 | seen after sampling. In general, if the format of the backend |
295 | texture is SRGB, some linear colorSpace should be supplied |
296 | (e.g., SkColorSpace::MakeSRGBLinear()). If the format of the |
297 | backend texture is linear, then the colorSpace should include |
298 | a description of the transfer function as |
299 | well (e.g., SkColorSpace::MakeSRGB()). |
300 | @param textureReleaseProc function called when texture can be released |
301 | @param releaseContext state passed to textureReleaseProc |
302 | @return created SkImage, or nullptr |
303 | */ |
304 | static sk_sp<SkImage> MakeFromTexture(GrRecordingContext* context, |
305 | const GrBackendTexture& backendTexture, |
306 | GrSurfaceOrigin origin, |
307 | SkColorType colorType, |
308 | SkAlphaType alphaType, |
309 | sk_sp<SkColorSpace> colorSpace, |
310 | TextureReleaseProc textureReleaseProc = nullptr, |
311 | ReleaseContext releaseContext = nullptr); |
312 | |
313 | /** Creates an SkImage from a GPU backend texture. The backend texture must stay |
314 | valid and unchanged until textureReleaseProc is called. The textureReleaseProc is |
315 | called when the SkImage is deleted or no longer refers to the texture and will be |
316 | passed the releaseContext. |
317 | |
318 | An SkImage is returned if the format of backendTexture is recognized and supported. |
319 | Recognized formats vary by GPU back-end. |
320 | |
321 | @note When using a DDL recording context, textureReleaseProc will be called on the |
322 | GPU thread after the DDL is played back on the direct context. |
323 | |
324 | @param context the GPU context |
325 | @param backendTexture a texture already allocated by the GPU |
326 | @param alphaType This characterizes the nature of the alpha values in the |
327 | backend texture. For opaque compressed formats (e.g., ETC1) |
328 | this should usually be set to kOpaque_SkAlphaType. |
329 | @param colorSpace This describes the color space of this image's contents, as |
330 | seen after sampling. In general, if the format of the backend |
331 | texture is SRGB, some linear colorSpace should be supplied |
332 | (e.g., SkColorSpace::MakeSRGBLinear()). If the format of the |
333 | backend texture is linear, then the colorSpace should include |
334 | a description of the transfer function as |
335 | well (e.g., SkColorSpace::MakeSRGB()). |
336 | @param textureReleaseProc function called when the backend texture can be released |
337 | @param releaseContext state passed to textureReleaseProc |
338 | @return created SkImage, or nullptr |
339 | */ |
340 | static sk_sp<SkImage> MakeFromCompressedTexture(GrRecordingContext* context, |
341 | const GrBackendTexture& backendTexture, |
342 | GrSurfaceOrigin origin, |
343 | SkAlphaType alphaType, |
344 | sk_sp<SkColorSpace> colorSpace, |
345 | TextureReleaseProc textureReleaseProc = nullptr, |
346 | ReleaseContext releaseContext = nullptr); |
347 | |
348 | /** Creates SkImage from pixmap. SkImage is uploaded to GPU back-end using context. |
349 | |
350 | Created SkImage is available to other GPU contexts, and is available across thread |
351 | boundaries. All contexts must be in the same GPU share group, or otherwise |
352 | share resources. |
353 | |
354 | When SkImage is no longer referenced, context releases texture memory |
355 | asynchronously. |
356 | |
357 | GrBackendTexture created from pixmap is uploaded to match SkSurface created with |
358 | dstColorSpace. SkColorSpace of SkImage is determined by pixmap.colorSpace(). |
359 | |
360 | SkImage is returned referring to GPU back-end if context is not nullptr, |
361 | format of data is recognized and supported, and if context supports moving |
362 | resources between contexts. Otherwise, pixmap pixel data is copied and SkImage |
363 | as returned in raster format if possible; nullptr may be returned. |
364 | Recognized GPU formats vary by platform and GPU back-end. |
365 | |
366 | @param context GPU context |
367 | @param pixmap SkImageInfo, pixel address, and row bytes |
368 | @param buildMips create SkImage as mip map if true |
369 | @param dstColorSpace range of colors of matching SkSurface on GPU |
370 | @param limitToMaxTextureSize downscale image to GPU maximum texture size, if necessary |
371 | @return created SkImage, or nullptr |
372 | */ |
373 | static sk_sp<SkImage> MakeCrossContextFromPixmap(GrDirectContext* context, |
374 | const SkPixmap& pixmap, |
375 | bool buildMips, |
376 | bool limitToMaxTextureSize = false); |
377 | |
378 | /** Creates SkImage from backendTexture associated with context. backendTexture and |
379 | returned SkImage are managed internally, and are released when no longer needed. |
380 | |
381 | SkImage is returned if format of backendTexture is recognized and supported. |
382 | Recognized formats vary by GPU back-end. |
383 | |
384 | @param context GPU context |
385 | @param backendTexture texture residing on GPU |
386 | @param imageOrigin origin of the resulting image |
387 | @param colorType color type of the resulting image |
388 | @param alphaType alpha type of the resulting image |
389 | @param colorSpace range of colors; may be nullptr |
390 | @return created SkImage, or nullptr |
391 | */ |
392 | static sk_sp<SkImage> MakeFromAdoptedTexture(GrRecordingContext* context, |
393 | const GrBackendTexture& backendTexture, |
394 | GrSurfaceOrigin imageOrigin, |
395 | SkColorType colorType, |
396 | SkAlphaType alphaType = kPremul_SkAlphaType, |
397 | sk_sp<SkColorSpace> colorSpace = nullptr); |
398 | |
399 | /** Creates an SkImage by flattening the specified YUVA planes into a single, interleaved RGBA |
400 | image. |
401 | |
402 | @param context GPU context |
403 | @param yuvColorSpace How the YUV values are converted to RGB |
404 | @param yuvaTextures array of (up to four) YUVA textures on GPU which contain the, |
405 | possibly interleaved, YUVA planes |
406 | @param yuvaIndices array indicating which texture in yuvaTextures, and channel |
407 | in that texture, maps to each component of YUVA. |
408 | @param imageSize size of the resulting image |
409 | @param imageOrigin origin of the resulting image. |
410 | @param imageColorSpace range of colors of the resulting image; may be nullptr |
411 | @return created SkImage, or nullptr |
412 | */ |
413 | static sk_sp<SkImage> MakeFromYUVATexturesCopy(GrRecordingContext* context, |
414 | SkYUVColorSpace yuvColorSpace, |
415 | const GrBackendTexture yuvaTextures[], |
416 | const SkYUVAIndex yuvaIndices[4], |
417 | SkISize imageSize, |
418 | GrSurfaceOrigin imageOrigin, |
419 | sk_sp<SkColorSpace> imageColorSpace = nullptr); |
420 | |
421 | /** Creates an SkImage by flattening the specified YUVA planes into a single, interleaved RGBA |
422 | image. 'backendTexture' is used to store the result of the flattening. |
423 | |
424 | @param context GPU context |
425 | @param yuvColorSpace How the YUV values are converted to RGB |
426 | @param yuvaTextures array of (up to four) YUVA textures on GPU which contain the, |
427 | possibly interleaved, YUVA planes |
428 | @param yuvaIndices array indicating which texture in yuvaTextures, and channel |
429 | in that texture, maps to each component of YUVA. |
430 | @param imageSize size of the resulting image |
431 | @param imageOrigin origin of the resulting image. |
432 | @param backendTexture the resource that stores the final pixels |
433 | @param imageColorSpace range of colors of the resulting image; may be nullptr |
434 | @param textureReleaseProc function called when backendTexture can be released |
435 | @param releaseContext state passed to textureReleaseProc |
436 | @return created SkImage, or nullptr |
437 | */ |
438 | static sk_sp<SkImage> MakeFromYUVATexturesCopyWithExternalBackend( |
439 | GrRecordingContext* context, |
440 | SkYUVColorSpace yuvColorSpace, |
441 | const GrBackendTexture yuvaTextures[], |
442 | const SkYUVAIndex yuvaIndices[4], |
443 | SkISize imageSize, |
444 | GrSurfaceOrigin imageOrigin, |
445 | const GrBackendTexture& backendTexture, |
446 | sk_sp<SkColorSpace> imageColorSpace = nullptr, |
447 | TextureReleaseProc textureReleaseProc = nullptr, |
448 | ReleaseContext releaseContext = nullptr); |
449 | |
450 | /** Creates an SkImage by storing the specified YUVA planes into an image, to be rendered |
451 | via multitexturing. |
452 | |
453 | When all the provided backend textures can be released 'textureReleaseProc' will be called |
454 | with 'releaseContext'. It will be called even if this method fails. |
455 | |
456 | @param context GPU context |
457 | @param yuvColorSpace How the YUV values are converted to RGB |
458 | @param yuvaTextures array of (up to four) YUVA textures on GPU which contain the, |
459 | possibly interleaved, YUVA planes |
460 | @param yuvaIndices array indicating which texture in yuvaTextures, and channel |
461 | in that texture, maps to each component of YUVA. |
462 | @param imageSize size of the resulting image |
463 | @param imageOrigin origin of the resulting image. |
464 | @param imageColorSpace range of colors of the resulting image; may be nullptr |
465 | @param textureReleaseProc called when the backend textures can be released |
466 | @param releaseContext state passed to textureReleaseProc |
467 | @return created SkImage, or nullptr |
468 | */ |
469 | static sk_sp<SkImage> MakeFromYUVATextures(GrContext* context, |
470 | SkYUVColorSpace yuvColorSpace, |
471 | const GrBackendTexture yuvaTextures[], |
472 | const SkYUVAIndex yuvaIndices[4], |
473 | SkISize imageSize, |
474 | GrSurfaceOrigin imageOrigin, |
475 | sk_sp<SkColorSpace> imageColorSpace = nullptr, |
476 | TextureReleaseProc textureReleaseProc = nullptr, |
477 | ReleaseContext releaseContext = nullptr); |
478 | |
479 | /** Creates SkImage from pixmap array representing YUVA data. |
480 | SkImage is uploaded to GPU back-end using context. |
481 | |
482 | Each GrBackendTexture created from yuvaPixmaps array is uploaded to match SkSurface |
483 | using SkColorSpace of SkPixmap. SkColorSpace of SkImage is determined by imageColorSpace. |
484 | |
485 | SkImage is returned referring to GPU back-end if context is not nullptr and |
486 | format of data is recognized and supported. Otherwise, nullptr is returned. |
487 | Recognized GPU formats vary by platform and GPU back-end. |
488 | |
489 | @param context GPU context |
490 | @param yuvColorSpace How the YUV values are converted to RGB |
491 | @param yuvaPixmaps array of (up to four) SkPixmap which contain the, |
492 | possibly interleaved, YUVA planes |
493 | @param yuvaIndices array indicating which pixmap in yuvaPixmaps, and channel |
494 | in that pixmap, maps to each component of YUVA. |
495 | @param imageSize size of the resulting image |
496 | @param imageOrigin origin of the resulting image. |
497 | @param buildMips create internal YUVA textures as mip map if true |
498 | @param limitToMaxTextureSize downscale image to GPU maximum texture size, if necessary |
499 | @param imageColorSpace range of colors of the resulting image; may be nullptr |
500 | @return created SkImage, or nullptr |
501 | */ |
502 | static sk_sp<SkImage> MakeFromYUVAPixmaps( |
503 | GrContext* context, SkYUVColorSpace yuvColorSpace, const SkPixmap yuvaPixmaps[], |
504 | const SkYUVAIndex yuvaIndices[4], SkISize imageSize, GrSurfaceOrigin imageOrigin, |
505 | bool buildMips, bool limitToMaxTextureSize = false, |
506 | sk_sp<SkColorSpace> imageColorSpace = nullptr); |
507 | |
508 | /** To be deprecated. |
509 | */ |
510 | static sk_sp<SkImage> MakeFromYUVTexturesCopyWithExternalBackend( |
511 | GrContext* context, |
512 | SkYUVColorSpace yuvColorSpace, |
513 | const GrBackendTexture yuvTextures[3], |
514 | GrSurfaceOrigin imageOrigin, |
515 | const GrBackendTexture& backendTexture, |
516 | sk_sp<SkColorSpace> imageColorSpace = nullptr); |
517 | |
518 | /** Creates SkImage from copy of nv12Textures, an array of textures on GPU. |
519 | nv12Textures[0] contains pixels for YUV component y plane. |
520 | nv12Textures[1] contains pixels for YUV component u plane, |
521 | followed by pixels for YUV component v plane. |
522 | Returned SkImage has the dimensions nv12Textures[2]. |
523 | yuvColorSpace describes how YUV colors convert to RGB colors. |
524 | |
525 | @param context GPU context |
526 | @param yuvColorSpace How the YUV values are converted to RGB |
527 | @param nv12Textures array of YUV textures on GPU |
528 | @param imageColorSpace range of colors; may be nullptr |
529 | @return created SkImage, or nullptr |
530 | */ |
531 | static sk_sp<SkImage> MakeFromNV12TexturesCopy(GrContext* context, |
532 | SkYUVColorSpace yuvColorSpace, |
533 | const GrBackendTexture nv12Textures[2], |
534 | GrSurfaceOrigin imageOrigin, |
535 | sk_sp<SkColorSpace> imageColorSpace = nullptr); |
536 | |
537 | /** Creates SkImage from copy of nv12Textures, an array of textures on GPU. |
538 | nv12Textures[0] contains pixels for YUV component y plane. |
539 | nv12Textures[1] contains pixels for YUV component u plane, |
540 | followed by pixels for YUV component v plane. |
541 | Returned SkImage has the dimensions nv12Textures[2] and stores pixels in backendTexture. |
542 | yuvColorSpace describes how YUV colors convert to RGB colors. |
543 | |
544 | @param context GPU context |
545 | @param yuvColorSpace How the YUV values are converted to RGB |
546 | @param nv12Textures array of YUV textures on GPU |
547 | @param backendTexture the resource that stores the final pixels |
548 | @param imageColorSpace range of colors; may be nullptr |
549 | @param textureReleaseProc function called when backendTexture can be released |
550 | @param releaseContext state passed to textureReleaseProc |
551 | @return created SkImage, or nullptr |
552 | */ |
553 | static sk_sp<SkImage> MakeFromNV12TexturesCopyWithExternalBackend( |
554 | GrContext* context, |
555 | SkYUVColorSpace yuvColorSpace, |
556 | const GrBackendTexture nv12Textures[2], |
557 | GrSurfaceOrigin imageOrigin, |
558 | const GrBackendTexture& backendTexture, |
559 | sk_sp<SkColorSpace> imageColorSpace = nullptr, |
560 | TextureReleaseProc textureReleaseProc = nullptr, |
561 | ReleaseContext releaseContext = nullptr); |
562 | |
563 | enum class BitDepth { |
564 | kU8, //!< uses 8-bit unsigned int per color component |
565 | kF16, //!< uses 16-bit float per color component |
566 | }; |
567 | |
568 | /** Creates SkImage from picture. Returned SkImage width and height are set by dimensions. |
569 | SkImage draws picture with matrix and paint, set to bitDepth and colorSpace. |
570 | |
571 | If matrix is nullptr, draws with identity SkMatrix. If paint is nullptr, draws |
572 | with default SkPaint. colorSpace may be nullptr. |
573 | |
574 | @param picture stream of drawing commands |
575 | @param dimensions width and height |
576 | @param matrix SkMatrix to rotate, scale, translate, and so on; may be nullptr |
577 | @param paint SkPaint to apply transparency, filtering, and so on; may be nullptr |
578 | @param bitDepth 8-bit integer or 16-bit float: per component |
579 | @param colorSpace range of colors; may be nullptr |
580 | @return created SkImage, or nullptr |
581 | */ |
582 | static sk_sp<SkImage> MakeFromPicture(sk_sp<SkPicture> picture, const SkISize& dimensions, |
583 | const SkMatrix* matrix, const SkPaint* paint, |
584 | BitDepth bitDepth, |
585 | sk_sp<SkColorSpace> colorSpace); |
586 | |
587 | #if defined(SK_BUILD_FOR_ANDROID) && __ANDROID_API__ >= 26 |
588 | /** (See Skia bug 7447) |
589 | Creates SkImage from Android hardware buffer. |
590 | Returned SkImage takes a reference on the buffer. |
591 | |
592 | Only available on Android, when __ANDROID_API__ is defined to be 26 or greater. |
593 | |
594 | @param hardwareBuffer AHardwareBuffer Android hardware buffer |
595 | @param colorSpace range of colors; may be nullptr |
596 | @return created SkImage, or nullptr |
597 | */ |
598 | static sk_sp<SkImage> MakeFromAHardwareBuffer( |
599 | AHardwareBuffer* hardwareBuffer, |
600 | SkAlphaType alphaType = kPremul_SkAlphaType, |
601 | sk_sp<SkColorSpace> colorSpace = nullptr, |
602 | GrSurfaceOrigin surfaceOrigin = kTopLeft_GrSurfaceOrigin); |
603 | |
604 | /** Creates SkImage from Android hardware buffer and uploads the data from the SkPixmap to it. |
605 | Returned SkImage takes a reference on the buffer. |
606 | |
607 | Only available on Android, when __ANDROID_API__ is defined to be 26 or greater. |
608 | |
609 | @param pixmap SkPixmap that contains data to be uploaded to the AHardwareBuffer |
610 | @param hardwareBuffer AHardwareBuffer Android hardware buffer |
611 | @return created SkImage, or nullptr |
612 | */ |
613 | static sk_sp<SkImage> MakeFromAHardwareBufferWithData( |
614 | GrContext* context, |
615 | const SkPixmap& pixmap, |
616 | AHardwareBuffer* hardwareBuffer, |
617 | GrSurfaceOrigin surfaceOrigin = kTopLeft_GrSurfaceOrigin); |
618 | #endif |
619 | |
620 | /** Returns a SkImageInfo describing the width, height, color type, alpha type, and color space |
621 | of the SkImage. |
622 | |
623 | @return image info of SkImage. |
624 | */ |
625 | const SkImageInfo& imageInfo() const { return fInfo; } |
626 | |
627 | /** Returns pixel count in each row. |
628 | |
629 | @return pixel width in SkImage |
630 | */ |
631 | int width() const { return fInfo.width(); } |
632 | |
633 | /** Returns pixel row count. |
634 | |
635 | @return pixel height in SkImage |
636 | */ |
637 | int height() const { return fInfo.height(); } |
638 | |
639 | /** Returns SkISize { width(), height() }. |
640 | |
641 | @return integral size of width() and height() |
642 | */ |
643 | SkISize dimensions() const { return SkISize::Make(fInfo.width(), fInfo.height()); } |
644 | |
645 | /** Returns SkIRect { 0, 0, width(), height() }. |
646 | |
647 | @return integral rectangle from origin to width() and height() |
648 | */ |
649 | SkIRect bounds() const { return SkIRect::MakeWH(fInfo.width(), fInfo.height()); } |
650 | |
651 | /** Returns value unique to image. SkImage contents cannot change after SkImage is |
652 | created. Any operation to create a new SkImage will receive generate a new |
653 | unique number. |
654 | |
655 | @return unique identifier |
656 | */ |
657 | uint32_t uniqueID() const { return fUniqueID; } |
658 | |
659 | /** Returns SkAlphaType. |
660 | |
661 | SkAlphaType returned was a parameter to an SkImage constructor, |
662 | or was parsed from encoded data. |
663 | |
664 | @return SkAlphaType in SkImage |
665 | |
666 | example: https://fiddle.skia.org/c/@Image_alphaType |
667 | */ |
668 | SkAlphaType alphaType() const; |
669 | |
670 | /** Returns SkColorType if known; otherwise, returns kUnknown_SkColorType. |
671 | |
672 | @return SkColorType of SkImage |
673 | |
674 | example: https://fiddle.skia.org/c/@Image_colorType |
675 | */ |
676 | SkColorType colorType() const; |
677 | |
678 | /** Returns SkColorSpace, the range of colors, associated with SkImage. The |
679 | reference count of SkColorSpace is unchanged. The returned SkColorSpace is |
680 | immutable. |
681 | |
682 | SkColorSpace returned was passed to an SkImage constructor, |
683 | or was parsed from encoded data. SkColorSpace returned may be ignored when SkImage |
684 | is drawn, depending on the capabilities of the SkSurface receiving the drawing. |
685 | |
686 | @return SkColorSpace in SkImage, or nullptr |
687 | |
688 | example: https://fiddle.skia.org/c/@Image_colorSpace |
689 | */ |
690 | SkColorSpace* colorSpace() const; |
691 | |
692 | /** Returns a smart pointer to SkColorSpace, the range of colors, associated with |
693 | SkImage. The smart pointer tracks the number of objects sharing this |
694 | SkColorSpace reference so the memory is released when the owners destruct. |
695 | |
696 | The returned SkColorSpace is immutable. |
697 | |
698 | SkColorSpace returned was passed to an SkImage constructor, |
699 | or was parsed from encoded data. SkColorSpace returned may be ignored when SkImage |
700 | is drawn, depending on the capabilities of the SkSurface receiving the drawing. |
701 | |
702 | @return SkColorSpace in SkImage, or nullptr, wrapped in a smart pointer |
703 | |
704 | example: https://fiddle.skia.org/c/@Image_refColorSpace |
705 | */ |
706 | sk_sp<SkColorSpace> refColorSpace() const; |
707 | |
708 | /** Returns true if SkImage pixels represent transparency only. If true, each pixel |
709 | is packed in 8 bits as defined by kAlpha_8_SkColorType. |
710 | |
711 | @return true if pixels represent a transparency mask |
712 | |
713 | example: https://fiddle.skia.org/c/@Image_isAlphaOnly |
714 | */ |
715 | bool isAlphaOnly() const; |
716 | |
717 | /** Returns true if pixels ignore their alpha value and are treated as fully opaque. |
718 | |
719 | @return true if SkAlphaType is kOpaque_SkAlphaType |
720 | */ |
721 | bool isOpaque() const { return SkAlphaTypeIsOpaque(this->alphaType()); } |
722 | |
723 | /** |
724 | * Make a shader with the specified tiling and mipmap sampling. |
725 | */ |
726 | sk_sp<SkShader> makeShader(SkTileMode tmx, SkTileMode tmy, const SkFilterOptions&, |
727 | const SkMatrix* localMatrix = nullptr) const; |
728 | |
729 | /* |
730 | * Specify B and C (each between 0...1) to create a shader that applies the corresponding |
731 | * cubic reconstruction filter to the image. |
732 | * |
733 | * Example values: |
734 | * B = 1/3, C = 1/3 "Mitchell" filter |
735 | * B = 0, C = 1/2 "Catmull-Rom" filter |
736 | * |
737 | * See "Reconstruction Filters in Computer Graphics" |
738 | * Don P. Mitchell |
739 | * Arun N. Netravali |
740 | * 1988 |
741 | * https://www.cs.utexas.edu/~fussell/courses/cs384g-fall2013/lectures/mitchell/Mitchell.pdf |
742 | * |
743 | * Desmos worksheet https://www.desmos.com/calculator/aghdpicrvr |
744 | * Nice overview https://entropymine.com/imageworsener/bicubic/ |
745 | */ |
746 | struct CubicResampler { |
747 | float B, C; |
748 | }; |
749 | |
750 | /** |
751 | * Make a shader with the specified tiling and CubicResampler parameters. |
752 | * Returns nullptr if the resampler values are outside of [0...1] |
753 | */ |
754 | sk_sp<SkShader> makeShader(SkTileMode tmx, SkTileMode tmy, CubicResampler, |
755 | const SkMatrix* localMatrix = nullptr) const; |
756 | |
757 | /** Creates SkShader from SkImage. SkShader dimensions are taken from SkImage. SkShader uses |
758 | SkTileMode rules to fill drawn area outside SkImage. localMatrix permits |
759 | transforming SkImage before SkCanvas matrix is applied. |
760 | |
761 | Note: since no filter-quality is specified, it will be determined at draw time using |
762 | the paint. |
763 | |
764 | @param tmx tiling in the x direction |
765 | @param tmy tiling in the y direction |
766 | @param localMatrix SkImage transformation, or nullptr |
767 | @return SkShader containing SkImage |
768 | */ |
769 | sk_sp<SkShader> makeShader(SkTileMode tmx, SkTileMode tmy, |
770 | const SkMatrix* localMatrix = nullptr) const; |
771 | sk_sp<SkShader> makeShader(SkTileMode tmx, SkTileMode tmy, const SkMatrix& localMatrix) const { |
772 | return this->makeShader(tmx, tmy, &localMatrix); |
773 | } |
774 | |
775 | sk_sp<SkShader> makeShader(SkTileMode tmx, SkTileMode tmy, const SkMatrix* localMatrix, |
776 | SkFilterQuality) const; |
777 | |
778 | /** Creates SkShader from SkImage. SkShader dimensions are taken from SkImage. SkShader uses |
779 | SkShader::kClamp_TileMode to fill drawn area outside SkImage. localMatrix permits |
780 | transforming SkImage before SkCanvas matrix is applied. |
781 | |
782 | @param localMatrix SkImage transformation, or nullptr |
783 | @return SkShader containing SkImage |
784 | */ |
785 | sk_sp<SkShader> makeShader(const SkMatrix* localMatrix = nullptr) const { |
786 | return this->makeShader(SkTileMode::kClamp, SkTileMode::kClamp, localMatrix); |
787 | } |
788 | sk_sp<SkShader> makeShader(const SkMatrix& localMatrix) const { |
789 | return this->makeShader(SkTileMode::kClamp, SkTileMode::kClamp, &localMatrix); |
790 | } |
791 | |
792 | |
793 | /** Copies SkImage pixel address, row bytes, and SkImageInfo to pixmap, if address |
794 | is available, and returns true. If pixel address is not available, return |
795 | false and leave pixmap unchanged. |
796 | |
797 | @param pixmap storage for pixel state if pixels are readable; otherwise, ignored |
798 | @return true if SkImage has direct access to pixels |
799 | |
800 | example: https://fiddle.skia.org/c/@Image_peekPixels |
801 | */ |
802 | bool peekPixels(SkPixmap* pixmap) const; |
803 | |
804 | /** Returns true the contents of SkImage was created on or uploaded to GPU memory, |
805 | and is available as a GPU texture. |
806 | |
807 | @return true if SkImage is a GPU texture |
808 | |
809 | example: https://fiddle.skia.org/c/@Image_isTextureBacked |
810 | */ |
811 | bool isTextureBacked() const; |
812 | |
813 | /** Returns true if SkImage can be drawn on either raster surface or GPU surface. |
814 | If context is nullptr, tests if SkImage draws on raster surface; |
815 | otherwise, tests if SkImage draws on GPU surface associated with context. |
816 | |
817 | SkImage backed by GPU texture may become invalid if associated context is |
818 | invalid. lazy image may be invalid and may not draw to raster surface or |
819 | GPU surface or both. |
820 | |
821 | @param context GPU context |
822 | @return true if SkImage can be drawn |
823 | |
824 | example: https://fiddle.skia.org/c/@Image_isValid |
825 | */ |
826 | bool isValid(GrRecordingContext* context) const; |
827 | |
828 | /** Flushes any pending uses of texture-backed images in the GPU backend. If the image is not |
829 | texture-backed (including promise texture images) or if the GrDirectContext does not |
830 | have the same context ID as the context backing the image then this is a no-op. |
831 | |
832 | If the image was not used in any non-culled draws in the current queue of work for the |
833 | passed GrDirectContext then this is a no-op unless the GrFlushInfo contains semaphores or |
834 | a finish proc. Those are respected even when the image has not been used. |
835 | |
836 | @param context the context on which to flush pending usages of the image. |
837 | @param info flush options |
838 | */ |
839 | GrSemaphoresSubmitted flush(GrDirectContext* context, const GrFlushInfo& flushInfo); |
840 | |
841 | void flush(GrDirectContext* context) { this->flush(context, {}); } |
842 | |
843 | /** Version of flush() that uses a default GrFlushInfo. Also submits the flushed work to the |
844 | GPU. |
845 | */ |
846 | void flushAndSubmit(GrDirectContext*); |
847 | |
848 | /** Retrieves the back-end texture. If SkImage has no back-end texture, an invalid |
849 | object is returned. Call GrBackendTexture::isValid to determine if the result |
850 | is valid. |
851 | |
852 | If flushPendingGrContextIO is true, completes deferred I/O operations. |
853 | |
854 | If origin in not nullptr, copies location of content drawn into SkImage. |
855 | |
856 | @param flushPendingGrContextIO flag to flush outstanding requests |
857 | @return back-end API texture handle; invalid on failure |
858 | */ |
859 | GrBackendTexture getBackendTexture(bool flushPendingGrContextIO, |
860 | GrSurfaceOrigin* origin = nullptr) const; |
861 | |
862 | /** \enum SkImage::CachingHint |
863 | CachingHint selects whether Skia may internally cache SkBitmap generated by |
864 | decoding SkImage, or by copying SkImage from GPU to CPU. The default behavior |
865 | allows caching SkBitmap. |
866 | |
867 | Choose kDisallow_CachingHint if SkImage pixels are to be used only once, or |
868 | if SkImage pixels reside in a cache outside of Skia, or to reduce memory pressure. |
869 | |
870 | Choosing kAllow_CachingHint does not ensure that pixels will be cached. |
871 | SkImage pixels may not be cached if memory requirements are too large or |
872 | pixels are not accessible. |
873 | */ |
874 | enum CachingHint { |
875 | kAllow_CachingHint, //!< allows internally caching decoded and copied pixels |
876 | kDisallow_CachingHint, //!< disallows internally caching decoded and copied pixels |
877 | }; |
878 | |
879 | /** Copies SkRect of pixels from SkImage to dstPixels. Copy starts at offset (srcX, srcY), |
880 | and does not exceed SkImage (width(), height()). |
881 | |
882 | dstInfo specifies width, height, SkColorType, SkAlphaType, and SkColorSpace of |
883 | destination. dstRowBytes specifies the gap from one destination row to the next. |
884 | Returns true if pixels are copied. Returns false if: |
885 | - dstInfo.addr() equals nullptr |
886 | - dstRowBytes is less than dstInfo.minRowBytes() |
887 | - SkPixelRef is nullptr |
888 | |
889 | Pixels are copied only if pixel conversion is possible. If SkImage SkColorType is |
890 | kGray_8_SkColorType, or kAlpha_8_SkColorType; dstInfo.colorType() must match. |
891 | If SkImage SkColorType is kGray_8_SkColorType, dstInfo.colorSpace() must match. |
892 | If SkImage SkAlphaType is kOpaque_SkAlphaType, dstInfo.alphaType() must |
893 | match. If SkImage SkColorSpace is nullptr, dstInfo.colorSpace() must match. Returns |
894 | false if pixel conversion is not possible. |
895 | |
896 | srcX and srcY may be negative to copy only top or left of source. Returns |
897 | false if width() or height() is zero or negative. |
898 | Returns false if abs(srcX) >= Image width(), or if abs(srcY) >= Image height(). |
899 | |
900 | If cachingHint is kAllow_CachingHint, pixels may be retained locally. |
901 | If cachingHint is kDisallow_CachingHint, pixels are not added to the local cache. |
902 | |
903 | @param dstInfo destination width, height, SkColorType, SkAlphaType, SkColorSpace |
904 | @param dstPixels destination pixel storage |
905 | @param dstRowBytes destination row length |
906 | @param srcX column index whose absolute value is less than width() |
907 | @param srcY row index whose absolute value is less than height() |
908 | @return true if pixels are copied to dstPixels |
909 | */ |
910 | bool readPixels(const SkImageInfo& dstInfo, void* dstPixels, size_t dstRowBytes, |
911 | int srcX, int srcY, CachingHint cachingHint = kAllow_CachingHint) const; |
912 | |
913 | /** Copies a SkRect of pixels from SkImage to dst. Copy starts at (srcX, srcY), and |
914 | does not exceed SkImage (width(), height()). |
915 | |
916 | dst specifies width, height, SkColorType, SkAlphaType, SkColorSpace, pixel storage, |
917 | and row bytes of destination. dst.rowBytes() specifics the gap from one destination |
918 | row to the next. Returns true if pixels are copied. Returns false if: |
919 | - dst pixel storage equals nullptr |
920 | - dst.rowBytes is less than SkImageInfo::minRowBytes |
921 | - SkPixelRef is nullptr |
922 | |
923 | Pixels are copied only if pixel conversion is possible. If SkImage SkColorType is |
924 | kGray_8_SkColorType, or kAlpha_8_SkColorType; dst.colorType() must match. |
925 | If SkImage SkColorType is kGray_8_SkColorType, dst.colorSpace() must match. |
926 | If SkImage SkAlphaType is kOpaque_SkAlphaType, dst.alphaType() must |
927 | match. If SkImage SkColorSpace is nullptr, dst.colorSpace() must match. Returns |
928 | false if pixel conversion is not possible. |
929 | |
930 | srcX and srcY may be negative to copy only top or left of source. Returns |
931 | false if width() or height() is zero or negative. |
932 | Returns false if abs(srcX) >= Image width(), or if abs(srcY) >= Image height(). |
933 | |
934 | If cachingHint is kAllow_CachingHint, pixels may be retained locally. |
935 | If cachingHint is kDisallow_CachingHint, pixels are not added to the local cache. |
936 | |
937 | @param dst destination SkPixmap: SkImageInfo, pixels, row bytes |
938 | @param srcX column index whose absolute value is less than width() |
939 | @param srcY row index whose absolute value is less than height() |
940 | @return true if pixels are copied to dst |
941 | */ |
942 | bool readPixels(const SkPixmap& dst, int srcX, int srcY, |
943 | CachingHint cachingHint = kAllow_CachingHint) const; |
944 | |
945 | /** The result from asyncRescaleAndReadPixels() or asyncRescaleAndReadPixelsYUV420(). */ |
946 | class AsyncReadResult { |
947 | public: |
948 | AsyncReadResult(const AsyncReadResult&) = delete; |
949 | AsyncReadResult(AsyncReadResult&&) = delete; |
950 | AsyncReadResult& operator=(const AsyncReadResult&) = delete; |
951 | AsyncReadResult& operator=(AsyncReadResult&&) = delete; |
952 | |
953 | virtual ~AsyncReadResult() = default; |
954 | virtual int count() const = 0; |
955 | virtual const void* data(int i) const = 0; |
956 | virtual size_t rowBytes(int i) const = 0; |
957 | |
958 | protected: |
959 | AsyncReadResult() = default; |
960 | }; |
961 | |
962 | /** Client-provided context that is passed to client-provided ReadPixelsContext. */ |
963 | using ReadPixelsContext = void*; |
964 | |
965 | /** Client-provided callback to asyncRescaleAndReadPixels() or |
966 | asyncRescaleAndReadPixelsYUV420() that is called when read result is ready or on failure. |
967 | */ |
968 | using ReadPixelsCallback = void(ReadPixelsContext, std::unique_ptr<const AsyncReadResult>); |
969 | |
970 | enum class RescaleGamma : bool { kSrc, kLinear }; |
971 | |
972 | /** Makes image pixel data available to caller, possibly asynchronously. It can also rescale |
973 | the image pixels. |
974 | |
975 | Currently asynchronous reads are only supported on the GPU backend and only when the |
976 | underlying 3D API supports transfer buffers and CPU/GPU synchronization primitives. In all |
977 | other cases this operates synchronously. |
978 | |
979 | Data is read from the source sub-rectangle, is optionally converted to a linear gamma, is |
980 | rescaled to the size indicated by 'info', is then converted to the color space, color type, |
981 | and alpha type of 'info'. A 'srcRect' that is not contained by the bounds of the image |
982 | causes failure. |
983 | |
984 | When the pixel data is ready the caller's ReadPixelsCallback is called with a |
985 | AsyncReadResult containing pixel data in the requested color type, alpha type, and color |
986 | space. The AsyncReadResult will have count() == 1. Upon failure the callback is called with |
987 | nullptr for AsyncReadResult. For a GPU image this flushes work but a submit must occur to |
988 | guarantee a finite time before the callback is called. |
989 | |
990 | The data is valid for the lifetime of AsyncReadResult with the exception that if the SkImage |
991 | is GPU-backed the data is immediately invalidated if the GrContext is abandoned or |
992 | destroyed. |
993 | |
994 | @param info info of the requested pixels |
995 | @param srcRect subrectangle of image to read |
996 | @param rescaleGamma controls whether rescaling is done in the image's gamma or whether |
997 | the source data is transformed to a linear gamma before rescaling. |
998 | @param rescaleQuality controls the quality (and cost) of the rescaling |
999 | @param callback function to call with result of the read |
1000 | @param context passed to callback |
1001 | */ |
1002 | void asyncRescaleAndReadPixels(const SkImageInfo& info, |
1003 | const SkIRect& srcRect, |
1004 | RescaleGamma rescaleGamma, |
1005 | SkFilterQuality rescaleQuality, |
1006 | ReadPixelsCallback callback, |
1007 | ReadPixelsContext context); |
1008 | |
1009 | /** |
1010 | Similar to asyncRescaleAndReadPixels but performs an additional conversion to YUV. The |
1011 | RGB->YUV conversion is controlled by 'yuvColorSpace'. The YUV data is returned as three |
1012 | planes ordered y, u, v. The u and v planes are half the width and height of the resized |
1013 | rectangle. The y, u, and v values are single bytes. Currently this fails if 'dstSize' |
1014 | width and height are not even. A 'srcRect' that is not contained by the bounds of the |
1015 | image causes failure. |
1016 | |
1017 | When the pixel data is ready the caller's ReadPixelsCallback is called with a |
1018 | AsyncReadResult containing the planar data. The AsyncReadResult will have count() == 3. |
1019 | Upon failure the callback is called with nullptr for AsyncReadResult. For a GPU image this |
1020 | flushes work but a submit must occur to guarantee a finite time before the callback is |
1021 | called. |
1022 | |
1023 | The data is valid for the lifetime of AsyncReadResult with the exception that if the SkImage |
1024 | is GPU-backed the data is immediately invalidated if the GrContext is abandoned or |
1025 | destroyed. |
1026 | |
1027 | @param yuvColorSpace The transformation from RGB to YUV. Applied to the resized image |
1028 | after it is converted to dstColorSpace. |
1029 | @param dstColorSpace The color space to convert the resized image to, after rescaling. |
1030 | @param srcRect The portion of the image to rescale and convert to YUV planes. |
1031 | @param dstSize The size to rescale srcRect to |
1032 | @param rescaleGamma controls whether rescaling is done in the image's gamma or whether |
1033 | the source data is transformed to a linear gamma before rescaling. |
1034 | @param rescaleQuality controls the quality (and cost) of the rescaling |
1035 | @param callback function to call with the planar read result |
1036 | @param context passed to callback |
1037 | */ |
1038 | void asyncRescaleAndReadPixelsYUV420(SkYUVColorSpace yuvColorSpace, |
1039 | sk_sp<SkColorSpace> dstColorSpace, |
1040 | const SkIRect& srcRect, |
1041 | const SkISize& dstSize, |
1042 | RescaleGamma rescaleGamma, |
1043 | SkFilterQuality rescaleQuality, |
1044 | ReadPixelsCallback callback, |
1045 | ReadPixelsContext context); |
1046 | |
1047 | /** Copies SkImage to dst, scaling pixels to fit dst.width() and dst.height(), and |
1048 | converting pixels to match dst.colorType() and dst.alphaType(). Returns true if |
1049 | pixels are copied. Returns false if dst.addr() is nullptr, or dst.rowBytes() is |
1050 | less than dst SkImageInfo::minRowBytes. |
1051 | |
1052 | Pixels are copied only if pixel conversion is possible. If SkImage SkColorType is |
1053 | kGray_8_SkColorType, or kAlpha_8_SkColorType; dst.colorType() must match. |
1054 | If SkImage SkColorType is kGray_8_SkColorType, dst.colorSpace() must match. |
1055 | If SkImage SkAlphaType is kOpaque_SkAlphaType, dst.alphaType() must |
1056 | match. If SkImage SkColorSpace is nullptr, dst.colorSpace() must match. Returns |
1057 | false if pixel conversion is not possible. |
1058 | |
1059 | Scales the image, with filterQuality, to match dst.width() and dst.height(). |
1060 | filterQuality kNone_SkFilterQuality is fastest, typically implemented with |
1061 | nearest neighbor filter. kLow_SkFilterQuality is typically implemented with |
1062 | bilerp filter. kMedium_SkFilterQuality is typically implemented with |
1063 | bilerp filter, and mip-map filter when size is reduced. |
1064 | kHigh_SkFilterQuality is slowest, typically implemented with bicubic filter. |
1065 | |
1066 | If cachingHint is kAllow_CachingHint, pixels may be retained locally. |
1067 | If cachingHint is kDisallow_CachingHint, pixels are not added to the local cache. |
1068 | |
1069 | @param dst destination SkPixmap: SkImageInfo, pixels, row bytes |
1070 | @return true if pixels are scaled to fit dst |
1071 | */ |
1072 | bool scalePixels(const SkPixmap& dst, SkFilterQuality filterQuality, |
1073 | CachingHint cachingHint = kAllow_CachingHint) const; |
1074 | |
1075 | /** Encodes SkImage pixels, returning result as SkData. |
1076 | |
1077 | Returns nullptr if encoding fails, or if encodedImageFormat is not supported. |
1078 | |
1079 | SkImage encoding in a format requires both building with one or more of: |
1080 | SK_ENCODE_JPEG, SK_ENCODE_PNG, SK_ENCODE_WEBP; and platform support |
1081 | for the encoded format. |
1082 | |
1083 | If SK_BUILD_FOR_MAC or SK_BUILD_FOR_IOS is defined, encodedImageFormat can |
1084 | additionally be one of: SkEncodedImageFormat::kICO, SkEncodedImageFormat::kBMP, |
1085 | SkEncodedImageFormat::kGIF. |
1086 | |
1087 | quality is a platform and format specific metric trading off size and encoding |
1088 | error. When used, quality equaling 100 encodes with the least error. quality may |
1089 | be ignored by the encoder. |
1090 | |
1091 | @param encodedImageFormat one of: SkEncodedImageFormat::kJPEG, SkEncodedImageFormat::kPNG, |
1092 | SkEncodedImageFormat::kWEBP |
1093 | @param quality encoder specific metric with 100 equaling best |
1094 | @return encoded SkImage, or nullptr |
1095 | |
1096 | example: https://fiddle.skia.org/c/@Image_encodeToData |
1097 | */ |
1098 | sk_sp<SkData> encodeToData(SkEncodedImageFormat encodedImageFormat, int quality) const; |
1099 | |
1100 | /** Encodes SkImage pixels, returning result as SkData. Returns existing encoded data |
1101 | if present; otherwise, SkImage is encoded with SkEncodedImageFormat::kPNG. Skia |
1102 | must be built with SK_ENCODE_PNG to encode SkImage. |
1103 | |
1104 | Returns nullptr if existing encoded data is missing or invalid, and |
1105 | encoding fails. |
1106 | |
1107 | @return encoded SkImage, or nullptr |
1108 | |
1109 | example: https://fiddle.skia.org/c/@Image_encodeToData_2 |
1110 | */ |
1111 | sk_sp<SkData> encodeToData() const; |
1112 | |
1113 | /** Returns encoded SkImage pixels as SkData, if SkImage was created from supported |
1114 | encoded stream format. Platform support for formats vary and may require building |
1115 | with one or more of: SK_ENCODE_JPEG, SK_ENCODE_PNG, SK_ENCODE_WEBP. |
1116 | |
1117 | Returns nullptr if SkImage contents are not encoded. |
1118 | |
1119 | @return encoded SkImage, or nullptr |
1120 | |
1121 | example: https://fiddle.skia.org/c/@Image_refEncodedData |
1122 | */ |
1123 | sk_sp<SkData> refEncodedData() const; |
1124 | |
1125 | /** Returns subset of this image. |
1126 | |
1127 | Returns nullptr if any of the following are true: |
1128 | - Subset is empty |
1129 | - Subset is not contained inside the image's bounds |
1130 | - Pixels in the image could not be read or copied |
1131 | |
1132 | If this image is texture-backed, the context parameter is required and must match the |
1133 | context of the source image. If the context parameter is provided, and the image is |
1134 | raster-backed, the subset will be converted to texture-backed. |
1135 | |
1136 | @param subset bounds of returned SkImage |
1137 | @param context the GrDirectContext in play, if it exists |
1138 | @return the subsetted image, or nullptr |
1139 | |
1140 | example: https://fiddle.skia.org/c/@Image_makeSubset |
1141 | */ |
1142 | sk_sp<SkImage> makeSubset(const SkIRect& subset, GrDirectContext* direct = nullptr) const; |
1143 | |
1144 | /** |
1145 | * Returns true if the image has mipmap levels. |
1146 | */ |
1147 | bool hasMipmaps() const; |
1148 | |
1149 | /** |
1150 | * Returns an image with the same "base" pixels as the this image, but with mipmap levels |
1151 | * as well. If this image already has mipmap levels, they will be replaced with new ones. |
1152 | * |
1153 | * If data == nullptr, the mipmap levels are computed automatically. |
1154 | * If data != nullptr, then the caller has provided the data for each level. |
1155 | */ |
1156 | sk_sp<SkImage> withMipmaps(sk_sp<SkMipmap> data) const; |
1157 | |
1158 | /** Returns SkImage backed by GPU texture associated with context. Returned SkImage is |
1159 | compatible with SkSurface created with dstColorSpace. The returned SkImage respects |
1160 | mipMapped setting; if mipMapped equals GrMipmapped::kYes, the backing texture |
1161 | allocates mip map levels. |
1162 | |
1163 | The mipMapped parameter is effectively treated as kNo if MIP maps are not supported by the |
1164 | GPU. |
1165 | |
1166 | Returns original SkImage if the image is already texture-backed, the context matches, and |
1167 | mipMapped is compatible with the backing GPU texture. SkBudgeted is ignored in this case. |
1168 | |
1169 | Returns nullptr if context is nullptr, or if SkImage was created with another |
1170 | GrDirectContext. |
1171 | |
1172 | @param GrDirectContext the GrDirectContext in play, if it exists |
1173 | @param GrMipmapped whether created SkImage texture must allocate mip map levels |
1174 | @param SkBudgeted whether to count a newly created texture for the returned image |
1175 | counts against the GrContext's budget. |
1176 | @return created SkImage, or nullptr |
1177 | */ |
1178 | sk_sp<SkImage> makeTextureImage(GrDirectContext*, |
1179 | GrMipmapped = GrMipmapped::kNo, |
1180 | SkBudgeted = SkBudgeted::kYes) const; |
1181 | |
1182 | /** Returns raster image or lazy image. Copies SkImage backed by GPU texture into |
1183 | CPU memory if needed. Returns original SkImage if decoded in raster bitmap, |
1184 | or if encoded in a stream. |
1185 | |
1186 | Returns nullptr if backed by GPU texture and copy fails. |
1187 | |
1188 | @return raster image, lazy image, or nullptr |
1189 | |
1190 | example: https://fiddle.skia.org/c/@Image_makeNonTextureImage |
1191 | */ |
1192 | sk_sp<SkImage> makeNonTextureImage() const; |
1193 | |
1194 | /** Returns raster image. Copies SkImage backed by GPU texture into CPU memory, |
1195 | or decodes SkImage from lazy image. Returns original SkImage if decoded in |
1196 | raster bitmap. |
1197 | |
1198 | Returns nullptr if copy, decode, or pixel read fails. |
1199 | |
1200 | If cachingHint is kAllow_CachingHint, pixels may be retained locally. |
1201 | If cachingHint is kDisallow_CachingHint, pixels are not added to the local cache. |
1202 | |
1203 | @return raster image, or nullptr |
1204 | |
1205 | example: https://fiddle.skia.org/c/@Image_makeRasterImage |
1206 | */ |
1207 | sk_sp<SkImage> makeRasterImage(CachingHint cachingHint = kDisallow_CachingHint) const; |
1208 | |
1209 | /** Creates filtered SkImage. filter processes original SkImage, potentially changing |
1210 | color, position, and size. subset is the bounds of original SkImage processed |
1211 | by filter. clipBounds is the expected bounds of the filtered SkImage. outSubset |
1212 | is required storage for the actual bounds of the filtered SkImage. offset is |
1213 | required storage for translation of returned SkImage. |
1214 | |
1215 | Returns nullptr if SkImage could not be created or if the recording context provided doesn't |
1216 | match the GPU context in which the image was created. If nullptr is returned, outSubset |
1217 | and offset are undefined. |
1218 | |
1219 | Useful for animation of SkImageFilter that varies size from frame to frame. |
1220 | Returned SkImage is created larger than required by filter so that GPU texture |
1221 | can be reused with different sized effects. outSubset describes the valid bounds |
1222 | of GPU texture returned. offset translates the returned SkImage to keep subsequent |
1223 | animation frames aligned with respect to each other. |
1224 | |
1225 | @param context the GrRecordingContext in play - if it exists |
1226 | @param filter how SkImage is sampled when transformed |
1227 | @param subset bounds of SkImage processed by filter |
1228 | @param clipBounds expected bounds of filtered SkImage |
1229 | @param outSubset storage for returned SkImage bounds |
1230 | @param offset storage for returned SkImage translation |
1231 | @return filtered SkImage, or nullptr |
1232 | */ |
1233 | sk_sp<SkImage> makeWithFilter(GrRecordingContext* context, |
1234 | const SkImageFilter* filter, const SkIRect& subset, |
1235 | const SkIRect& clipBounds, SkIRect* outSubset, |
1236 | SkIPoint* offset) const; |
1237 | |
1238 | /** Defines a callback function, taking one parameter of type GrBackendTexture with |
1239 | no return value. Function is called when back-end texture is to be released. |
1240 | */ |
1241 | typedef std::function<void(GrBackendTexture)> BackendTextureReleaseProc; |
1242 | |
1243 | /** Creates a GrBackendTexture from the provided SkImage. Returns true and |
1244 | stores result in backendTexture and backendTextureReleaseProc if |
1245 | texture is created; otherwise, returns false and leaves |
1246 | backendTexture and backendTextureReleaseProc unmodified. |
1247 | |
1248 | Call backendTextureReleaseProc after deleting backendTexture. |
1249 | backendTextureReleaseProc cleans up auxiliary data related to returned |
1250 | backendTexture. The caller must delete returned backendTexture after use. |
1251 | |
1252 | If SkImage is both texture backed and singly referenced, image is returned in |
1253 | backendTexture without conversion or making a copy. SkImage is singly referenced |
1254 | if its was transferred solely using std::move(). |
1255 | |
1256 | If SkImage is not texture backed, returns texture with SkImage contents. |
1257 | |
1258 | @param context GPU context |
1259 | @param image SkImage used for texture |
1260 | @param backendTexture storage for back-end texture |
1261 | @param backendTextureReleaseProc storage for clean up function |
1262 | @return true if back-end texture was created |
1263 | */ |
1264 | static bool MakeBackendTextureFromSkImage(GrContext* context, |
1265 | sk_sp<SkImage> image, |
1266 | GrBackendTexture* backendTexture, |
1267 | BackendTextureReleaseProc* backendTextureReleaseProc); |
1268 | |
1269 | /** Deprecated. |
1270 | */ |
1271 | enum LegacyBitmapMode { |
1272 | kRO_LegacyBitmapMode, //!< returned bitmap is read-only and immutable |
1273 | }; |
1274 | |
1275 | /** Deprecated. |
1276 | Creates raster SkBitmap with same pixels as SkImage. If legacyBitmapMode is |
1277 | kRO_LegacyBitmapMode, returned bitmap is read-only and immutable. |
1278 | Returns true if SkBitmap is stored in bitmap. Returns false and resets bitmap if |
1279 | SkBitmap write did not succeed. |
1280 | |
1281 | @param bitmap storage for legacy SkBitmap |
1282 | @param legacyBitmapMode bitmap is read-only and immutable |
1283 | @return true if SkBitmap was created |
1284 | */ |
1285 | bool asLegacyBitmap(SkBitmap* bitmap, |
1286 | LegacyBitmapMode legacyBitmapMode = kRO_LegacyBitmapMode) const; |
1287 | |
1288 | /** Returns true if SkImage is backed by an image-generator or other service that creates |
1289 | and caches its pixels or texture on-demand. |
1290 | |
1291 | @return true if SkImage is created as needed |
1292 | |
1293 | example: https://fiddle.skia.org/c/@Image_isLazyGenerated_a |
1294 | example: https://fiddle.skia.org/c/@Image_isLazyGenerated_b |
1295 | */ |
1296 | bool isLazyGenerated() const; |
1297 | |
1298 | /** Creates SkImage in target SkColorSpace. |
1299 | Returns nullptr if SkImage could not be created. |
1300 | |
1301 | Returns original SkImage if it is in target SkColorSpace. |
1302 | Otherwise, converts pixels from SkImage SkColorSpace to target SkColorSpace. |
1303 | If SkImage colorSpace() returns nullptr, SkImage SkColorSpace is assumed to be sRGB. |
1304 | |
1305 | If this image is texture-backed, the context parameter is required and must match the |
1306 | context of the source image. |
1307 | |
1308 | @param target SkColorSpace describing color range of returned SkImage |
1309 | @param direct The GrDirectContext in play, if it exists |
1310 | @return created SkImage in target SkColorSpace |
1311 | |
1312 | example: https://fiddle.skia.org/c/@Image_makeColorSpace |
1313 | */ |
1314 | sk_sp<SkImage> makeColorSpace(sk_sp<SkColorSpace> target, |
1315 | GrDirectContext* direct = nullptr) const; |
1316 | |
1317 | /** Experimental. |
1318 | Creates SkImage in target SkColorType and SkColorSpace. |
1319 | Returns nullptr if SkImage could not be created. |
1320 | |
1321 | Returns original SkImage if it is in target SkColorType and SkColorSpace. |
1322 | |
1323 | If this image is texture-backed, the context parameter is required and must match the |
1324 | context of the source image. |
1325 | |
1326 | @param targetColorType SkColorType of returned SkImage |
1327 | @param targetColorSpace SkColorSpace of returned SkImage |
1328 | @param direct The GrDirectContext in play, if it exists |
1329 | @return created SkImage in target SkColorType and SkColorSpace |
1330 | */ |
1331 | sk_sp<SkImage> makeColorTypeAndColorSpace(SkColorType targetColorType, |
1332 | sk_sp<SkColorSpace> targetColorSpace, |
1333 | GrDirectContext* direct = nullptr) const; |
1334 | |
1335 | /** Creates a new SkImage identical to this one, but with a different SkColorSpace. |
1336 | This does not convert the underlying pixel data, so the resulting image will draw |
1337 | differently. |
1338 | */ |
1339 | sk_sp<SkImage> reinterpretColorSpace(sk_sp<SkColorSpace> newColorSpace) const; |
1340 | |
1341 | private: |
1342 | SkImage(const SkImageInfo& info, uint32_t uniqueID); |
1343 | friend class SkImage_Base; |
1344 | |
1345 | SkImageInfo fInfo; |
1346 | const uint32_t fUniqueID; |
1347 | |
1348 | typedef SkRefCnt INHERITED; |
1349 | }; |
1350 | |
1351 | #endif |
1352 | |