diff options
Diffstat (limited to 'core/io/image.h')
-rw-r--r-- | core/io/image.h | 251 |
1 files changed, 115 insertions, 136 deletions
diff --git a/core/io/image.h b/core/io/image.h index 78757246e0..3149314ad8 100644 --- a/core/io/image.h +++ b/core/io/image.h @@ -43,12 +43,17 @@ class Image; +// Function pointer prototypes. + typedef Error (*SavePNGFunc)(const String &p_path, const Ref<Image> &p_img); typedef Vector<uint8_t> (*SavePNGBufferFunc)(const Ref<Image> &p_img); + typedef Error (*SaveJPGFunc)(const String &p_path, const Ref<Image> &p_img, float p_quality); typedef Vector<uint8_t> (*SaveJPGBufferFunc)(const Ref<Image> &p_img, float p_quality); + typedef Ref<Image> (*ImageMemLoadFunc)(const uint8_t *p_png, int p_size); typedef Ref<Image> (*ScalableImageMemLoadFunc)(const uint8_t *p_data, int p_size, float p_scale); + typedef Error (*SaveWebPFunc)(const String &p_path, const Ref<Image> &p_img, const bool p_lossy, const float p_quality); typedef Vector<uint8_t> (*SaveWebPBufferFunc)(const Ref<Image> &p_img, const bool p_lossy, const float p_quality); @@ -59,57 +64,48 @@ class Image : public Resource { GDCLASS(Image, Resource); public: - static SavePNGFunc save_png_func; - static SaveJPGFunc save_jpg_func; - static SaveEXRFunc save_exr_func; - static SavePNGBufferFunc save_png_buffer_func; - static SaveEXRBufferFunc save_exr_buffer_func; - static SaveJPGBufferFunc save_jpg_buffer_func; - static SaveWebPFunc save_webp_func; - static SaveWebPBufferFunc save_webp_buffer_func; - enum { - MAX_WIDTH = (1 << 24), // force a limit somehow - MAX_HEIGHT = (1 << 24), // force a limit somehow - MAX_PIXELS = 268435456 + MAX_WIDTH = (1 << 24), // Force a limit somehow. + MAX_HEIGHT = (1 << 24), // Force a limit somehow. + MAX_PIXELS = 268435456 // 16384 ^ 2 }; enum Format { - FORMAT_L8, //luminance - FORMAT_LA8, //luminance-alpha + FORMAT_L8, // Luminance + FORMAT_LA8, // Luminance-Alpha FORMAT_R8, FORMAT_RG8, FORMAT_RGB8, FORMAT_RGBA8, FORMAT_RGBA4444, FORMAT_RGB565, - FORMAT_RF, //float + FORMAT_RF, // Float FORMAT_RGF, FORMAT_RGBF, FORMAT_RGBAF, - FORMAT_RH, //half float + FORMAT_RH, // Half FORMAT_RGH, FORMAT_RGBH, FORMAT_RGBAH, FORMAT_RGBE9995, - FORMAT_DXT1, //s3tc bc1 - FORMAT_DXT3, //bc2 - FORMAT_DXT5, //bc3 - FORMAT_RGTC_R, - FORMAT_RGTC_RG, - FORMAT_BPTC_RGBA, //btpc bc7 - FORMAT_BPTC_RGBF, //float bc6h - FORMAT_BPTC_RGBFU, //unsigned float bc6hu - FORMAT_ETC, //etc1 - FORMAT_ETC2_R11, //etc2 - FORMAT_ETC2_R11S, //signed, NOT srgb. + FORMAT_DXT1, // BC1 + FORMAT_DXT3, // BC2 + FORMAT_DXT5, // BC3 + FORMAT_RGTC_R, // BC4 + FORMAT_RGTC_RG, // BC5 + FORMAT_BPTC_RGBA, // BC7 + FORMAT_BPTC_RGBF, // BC6 Signed + FORMAT_BPTC_RGBFU, // BC6 Unsigned + FORMAT_ETC, // ETC1 + FORMAT_ETC2_R11, + FORMAT_ETC2_R11S, // Signed, NOT srgb. FORMAT_ETC2_RG11, - FORMAT_ETC2_RG11S, + FORMAT_ETC2_RG11S, // Signed, NOT srgb. FORMAT_ETC2_RGB8, FORMAT_ETC2_RGBA8, FORMAT_ETC2_RGB8A1, - FORMAT_ETC2_RA_AS_RG, //used to make basis universal happy - FORMAT_DXT5_RA_AS_RG, //used to make basis universal happy + FORMAT_ETC2_RA_AS_RG, // ETC2 RGBA with a RA-RG swizzle for normal maps. + FORMAT_DXT5_RA_AS_RG, // BC3 with a RA-RG swizzle for normal maps. FORMAT_ASTC_4x4, FORMAT_ASTC_4x4_HDR, FORMAT_ASTC_8x8, @@ -118,17 +114,18 @@ public: }; static const char *format_names[FORMAT_MAX]; + enum Interpolation { INTERPOLATE_NEAREST, INTERPOLATE_BILINEAR, INTERPOLATE_CUBIC, INTERPOLATE_TRILINEAR, INTERPOLATE_LANCZOS, - /* INTERPOLATE_TRICUBIC, */ - /* INTERPOLATE GAUSS */ + // INTERPOLATE_TRICUBIC, + // INTERPOLATE_GAUSS }; - //this is used for compression + // Used for obtaining optimal compression quality. enum UsedChannels { USED_CHANNELS_L, USED_CHANNELS_LA, @@ -137,13 +134,66 @@ public: USED_CHANNELS_RGB, USED_CHANNELS_RGBA, }; - //some functions provided by something else + // ASTC supports block formats other than 4x4. enum ASTCFormat { ASTC_FORMAT_4x4, ASTC_FORMAT_8x8, }; + enum RoughnessChannel { + ROUGHNESS_CHANNEL_R, + ROUGHNESS_CHANNEL_G, + ROUGHNESS_CHANNEL_B, + ROUGHNESS_CHANNEL_A, + ROUGHNESS_CHANNEL_L, + }; + + enum Image3DValidateError { + VALIDATE_3D_OK, + VALIDATE_3D_ERR_IMAGE_EMPTY, + VALIDATE_3D_ERR_MISSING_IMAGES, + VALIDATE_3D_ERR_EXTRA_IMAGES, + VALIDATE_3D_ERR_IMAGE_SIZE_MISMATCH, + VALIDATE_3D_ERR_IMAGE_FORMAT_MISMATCH, + VALIDATE_3D_ERR_IMAGE_HAS_MIPMAPS, + }; + + enum CompressMode { + COMPRESS_S3TC, + COMPRESS_ETC, + COMPRESS_ETC2, + COMPRESS_BPTC, + COMPRESS_ASTC, + COMPRESS_MAX, + }; + + enum CompressSource { + COMPRESS_SOURCE_GENERIC, + COMPRESS_SOURCE_SRGB, + COMPRESS_SOURCE_NORMAL, + COMPRESS_SOURCE_MAX, + }; + + enum AlphaMode { + ALPHA_NONE, + ALPHA_BIT, + ALPHA_BLEND + }; + + // External saver function pointers. + + static SavePNGFunc save_png_func; + static SaveJPGFunc save_jpg_func; + static SaveEXRFunc save_exr_func; + static SaveWebPFunc save_webp_func; + static SavePNGBufferFunc save_png_buffer_func; + static SaveEXRBufferFunc save_exr_buffer_func; + static SaveJPGBufferFunc save_jpg_buffer_func; + static SaveWebPBufferFunc save_webp_buffer_func; + + // External loader function pointers. + static ImageMemLoadFunc _png_mem_loader_func; static ImageMemLoadFunc _png_mem_unpacker_func; static ImageMemLoadFunc _jpg_mem_loader_func; @@ -153,6 +203,8 @@ public: static ScalableImageMemLoadFunc _svg_scalable_mem_loader_func; static ImageMemLoadFunc _ktx_mem_loader_func; + // External VRAM compression function pointers. + static void (*_image_compress_bc_func)(Image *, UsedChannels p_channels); static void (*_image_compress_bptc_func)(Image *, UsedChannels p_channels); static void (*_image_compress_etc1_func)(Image *); @@ -162,24 +214,26 @@ public: static Error (*_image_compress_bptc_rd_func)(Image *, UsedChannels p_channels); static Error (*_image_compress_bc_rd_func)(Image *, UsedChannels p_channels); + // External VRAM decompression function pointers. + static void (*_image_decompress_bc)(Image *); static void (*_image_decompress_bptc)(Image *); static void (*_image_decompress_etc1)(Image *); static void (*_image_decompress_etc2)(Image *); static void (*_image_decompress_astc)(Image *); + // External packer function pointers. + static Vector<uint8_t> (*webp_lossy_packer)(const Ref<Image> &p_image, float p_quality); static Vector<uint8_t> (*webp_lossless_packer)(const Ref<Image> &p_image); - static Ref<Image> (*webp_unpacker)(const Vector<uint8_t> &p_buffer); static Vector<uint8_t> (*png_packer)(const Ref<Image> &p_image); - static Ref<Image> (*png_unpacker)(const Vector<uint8_t> &p_buffer); static Vector<uint8_t> (*basis_universal_packer)(const Ref<Image> &p_image, UsedChannels p_channels); + + static Ref<Image> (*webp_unpacker)(const Vector<uint8_t> &p_buffer); + static Ref<Image> (*png_unpacker)(const Vector<uint8_t> &p_buffer); static Ref<Image> (*basis_universal_unpacker)(const Vector<uint8_t> &p_buffer); static Ref<Image> (*basis_universal_unpacker_ptr)(const uint8_t *p_data, int p_size); - _FORCE_INLINE_ Color _get_color_at_ofs(const uint8_t *ptr, uint32_t ofs) const; - _FORCE_INLINE_ void _set_color_at_ofs(uint8_t *ptr, uint32_t ofs, const Color &p_color); - protected: static void _bind_methods(); @@ -190,15 +244,12 @@ private: int height = 0; bool mipmaps = false; - void _copy_internals_from(const Image &p_image) { - format = p_image.format; - width = p_image.width; - height = p_image.height; - mipmaps = p_image.mipmaps; - data = p_image.data; - } + void _copy_internals_from(const Image &p_image); + + _FORCE_INLINE_ Color _get_color_at_ofs(const uint8_t *ptr, uint32_t ofs) const; + _FORCE_INLINE_ void _set_color_at_ofs(uint8_t *ptr, uint32_t ofs, const Color &p_color); - _FORCE_INLINE_ void _get_mipmap_offset_and_size(int p_mipmap, int64_t &r_offset, int &r_width, int &r_height) const; //get where the mipmap begins in data + _FORCE_INLINE_ void _get_mipmap_offset_and_size(int p_mipmap, int64_t &r_offset, int &r_width, int &r_height) const; // Get where the mipmap begins in data. static int64_t _get_dst_image_size(int p_width, int p_height, Format p_format, int &r_mipmaps, int p_mipmaps = -1, int *r_mm_width = nullptr, int *r_mm_height = nullptr); bool _can_modify(Format p_format) const; @@ -225,52 +276,32 @@ private: static void renormalize_rgbe9995(uint32_t *p_rgb); public: - int get_width() const; ///< Get image width - int get_height() const; ///< Get image height + int get_width() const; + int get_height() const; Size2i get_size() const; bool has_mipmaps() const; int get_mipmap_count() const; - /** - * Convert the image to another format, conversion only to raw byte format - */ + // Convert the image to another format, conversion only to raw byte format. void convert(Format p_new_format); - /** - * Get the current image format. - */ Format get_format() const; - /** - * Get where the mipmap begins in data. - */ + // Get where the mipmap begins in data. int64_t get_mipmap_offset(int p_mipmap) const; void get_mipmap_offset_and_size(int p_mipmap, int64_t &r_ofs, int64_t &r_size) const; void get_mipmap_offset_size_and_dimensions(int p_mipmap, int64_t &r_ofs, int64_t &r_size, int &w, int &h) const; - enum Image3DValidateError { - VALIDATE_3D_OK, - VALIDATE_3D_ERR_IMAGE_EMPTY, - VALIDATE_3D_ERR_MISSING_IMAGES, - VALIDATE_3D_ERR_EXTRA_IMAGES, - VALIDATE_3D_ERR_IMAGE_SIZE_MISMATCH, - VALIDATE_3D_ERR_IMAGE_FORMAT_MISMATCH, - VALIDATE_3D_ERR_IMAGE_HAS_MIPMAPS, - }; - static Image3DValidateError validate_3d_image(Format p_format, int p_width, int p_height, int p_depth, bool p_mipmaps, const Vector<Ref<Image>> &p_images); static String get_3d_image_validation_error_text(Image3DValidateError p_error); - /** - * Resize the image, using the preferred interpolation method. - */ + // Resize the image, using the preferred interpolation method. void resize_to_po2(bool p_square = false, Interpolation p_interpolation = INTERPOLATE_BILINEAR); void resize(int p_width, int p_height, Interpolation p_interpolation = INTERPOLATE_BILINEAR); void shrink_x2(); bool is_size_po2() const; - /** - * Crop the image to a specific size, if larger, then the image is filled by black - */ + + // Crop the image to a specific size, if larger, then the image is filled by black. void crop_from_point(int p_x, int p_y, int p_width, int p_height); void crop(int p_width, int p_height); @@ -280,34 +311,20 @@ public: void flip_x(); void flip_y(); - /** - * Generate a mipmap to an image (creates an image 1/4 the size, with averaging of 4->1) - */ + // Generate a mipmap chain of an image (creates an image 1/4 the size, with averaging of 4->1). Error generate_mipmaps(bool p_renormalize = false); - enum RoughnessChannel { - ROUGHNESS_CHANNEL_R, - ROUGHNESS_CHANNEL_G, - ROUGHNESS_CHANNEL_B, - ROUGHNESS_CHANNEL_A, - ROUGHNESS_CHANNEL_L, - }; - Error generate_mipmap_roughness(RoughnessChannel p_roughness_channel, const Ref<Image> &p_normal_map); void clear_mipmaps(); - void normalize(); //for normal maps + void normalize(); - /** - * Creates new internal image data of a given size and format. Current image will be lost. - */ + // Creates new internal image data of a given size and format. Current image will be lost. void initialize_data(int p_width, int p_height, bool p_use_mipmaps, Format p_format); void initialize_data(int p_width, int p_height, bool p_use_mipmaps, Format p_format, const Vector<uint8_t> &p_data); void initialize_data(const char **p_xpm); - /** - * returns true when the image is empty (0,0) in size - */ + // Returns true when the image is empty (0,0) in size. bool is_empty() const; Vector<uint8_t> get_data() const; @@ -327,27 +344,14 @@ public: static Ref<Image> create_from_data(int p_width, int p_height, bool p_use_mipmaps, Format p_format, const Vector<uint8_t> &p_data); void set_data(int p_width, int p_height, bool p_use_mipmaps, Format p_format, const Vector<uint8_t> &p_data); - /** - * create an empty image - */ - Image() {} - /** - * create an empty image of a specific size and format - */ - Image(int p_width, int p_height, bool p_use_mipmaps, Format p_format); - /** - * import an image of a specific size and format from a pointer - */ - Image(int p_width, int p_height, bool p_mipmaps, Format p_format, const Vector<uint8_t> &p_data); + Image() = default; // Create an empty image. + Image(int p_width, int p_height, bool p_use_mipmaps, Format p_format); // Create an empty image of a specific size and format. + Image(int p_width, int p_height, bool p_mipmaps, Format p_format, const Vector<uint8_t> &p_data); // Import an image of a specific size and format from a byte vector. + Image(const uint8_t *p_mem_png_jpg, int p_len = -1); // Import either a png or jpg from a pointer. + Image(const char **p_xpm); // Import an XPM image. ~Image() {} - enum AlphaMode { - ALPHA_NONE, - ALPHA_BIT, - ALPHA_BLEND - }; - AlphaMode detect_alpha() const; bool is_invisible() const; @@ -362,21 +366,6 @@ public: static int64_t get_image_mipmap_offset(int p_width, int p_height, Format p_format, int p_mipmap); static int64_t get_image_mipmap_offset_and_dimensions(int p_width, int p_height, Format p_format, int p_mipmap, int &r_w, int &r_h); - enum CompressMode { - COMPRESS_S3TC, - COMPRESS_ETC, - COMPRESS_ETC2, - COMPRESS_BPTC, - COMPRESS_ASTC, - COMPRESS_MAX, - }; - enum CompressSource { - COMPRESS_SOURCE_GENERIC, - COMPRESS_SOURCE_SRGB, - COMPRESS_SOURCE_NORMAL, - COMPRESS_SOURCE_MAX, - }; - Error compress(CompressMode p_mode, CompressSource p_source = COMPRESS_SOURCE_GENERIC, ASTCFormat p_astc_format = ASTC_FORMAT_4x4); Error compress_from_channels(CompressMode p_mode, UsedChannels p_channels, ASTCFormat p_astc_format = ASTC_FORMAT_4x4); Error decompress(); @@ -422,9 +411,6 @@ public: void convert_ra_rgba8_to_rg(); void convert_rgba8_to_bgra8(); - Image(const uint8_t *p_mem_png_jpg, int p_len = -1); - Image(const char **p_xpm); - virtual Ref<Resource> duplicate(bool p_subresources = false) const override; UsedChannels detect_used_channels(CompressSource p_source = COMPRESS_SOURCE_GENERIC) const; @@ -443,14 +429,7 @@ public: void set_as_black(); - void copy_internals_from(const Ref<Image> &p_image) { - ERR_FAIL_COND_MSG(p_image.is_null(), "Cannot copy image internals: invalid Image object."); - format = p_image->format; - width = p_image->width; - height = p_image->height; - mipmaps = p_image->mipmaps; - data = p_image->data; - } + void copy_internals_from(const Ref<Image> &p_image); Dictionary compute_image_metrics(const Ref<Image> p_compared_image, bool p_luma_metric = true); }; |