2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*  image.cpp                                                            */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                       This file is part of:                           */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                           GODOT ENGINE                                */  
						 
					
						
							
								
									
										
										
										
											2017-08-27 14:16:55 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								/*                      https://godotengine.org                          */  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
									
										
										
										
											2022-01-03 21:27:34 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								/* Copyright (c) 2007-2022 Juan Linietsky, Ariel Manzur.                 */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* Copyright (c) 2014-2022 Godot Engine contributors (cf. AUTHORS.md).   */  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/*                                                                       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* Permission is hereby granted, free of charge, to any person obtaining */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* a copy of this software and associated documentation files (the       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* "Software"), to deal in the Software without restriction, including   */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* without limitation the rights to use, copy, modify, merge, publish,   */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* distribute, sublicense, and/or sell copies of the Software, and to    */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* permit persons to whom the Software is furnished to do so, subject to */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* the following conditions:                                             */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                                                                       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* The above copyright notice and this permission notice shall be        */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* included in all copies or substantial portions of the Software.       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                                                                       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY  */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,  */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE     */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.                */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*************************************************************************/  
						 
					
						
							
								
									
										
										
										
											2018-01-05 00:50:27 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  "image.h" 
  
						 
					
						
							
								
									
										
										
										
											2017-01-16 08:04:19 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/error/error_list.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-11-07 19:33:38 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/error/error_macros.h" 
  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  "core/io/image_loader.h" 
  
						 
					
						
							
								
									
										
										
										
											2018-09-11 18:13:45 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/io/resource_loader.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "core/math/math_funcs.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-11-07 19:33:38 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/string/print_string.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "core/templates/hash_map.h" 
  
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/variant/dictionary.h" 
  
						 
					
						
							
								
									
										
										
										
											2017-01-16 08:04:19 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  <stdio.h> 
  
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  <cmath> 
  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								const  char  * Image : : format_names [ Image : : FORMAT_MAX ]  =  {  
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									" Lum8 " ,  //luminance
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" LumAlpha8 " ,  //luminance-alpha
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" Red8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RedGreen " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGB8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBA8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBA4444 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBA5551 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RFloat " ,  //float
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGFloat " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBFloat " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBAFloat " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RHalf " ,  //half float
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGHalf " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBHalf " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGBAHalf " , 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									" RGBE9995 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" DXT1 RGB8 " ,  //s3tc
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" DXT3 RGBA8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" DXT5 RGBA8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGTC Red8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" RGTC RedGreen8 " , 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									" BPTC_RGBA " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" BPTC_RGBF " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" BPTC_RGBFU " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC " ,  //etc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_R11 " ,  //etc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_R11S " ,  //signed", NOT srgb.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_RG11 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_RG11S " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_RGB8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_RGBA8 " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" ETC2_RGB8A1 " , 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									" ETC2_RA_AS_RG " , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									" FORMAT_DXT5_RA_AS_RG " , 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-21 09:50:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SavePNGFunc  Image : : save_png_func  =  nullptr ;  
						 
					
						
							
								
									
										
											 
										
											
												Implement Running Godot as Movie Writer
* Allows running the game in "movie writer" mode.
* It ensures entirely stable framerate, so your run can be saved stable and with proper sound (which is impossible if your CPU/GPU can't sustain doing this in real-time).
* If disabling vsync, it can save movies faster than the game is run, but if you want to control the interaction it can get difficult.
* Implements a simple, default MJPEG writer.
This new features has two main use cases, which have high demand:
* Saving game videos in high quality and ensuring the frame rate is *completely* stable, always.
* Using Godot as a tool to make movies and animations (which is ideal if you want interaction, or creating them procedurally. No other software is as good for this).
**Note**: This feature **IS NOT** for capturing real-time footage. Use something like OBS, SimpleScreenRecorder or FRAPS to achieve that, as they do a much better job at intercepting the compositor than Godot can probably do using Vulkan or OpenGL natively. If your game runs near real-time when capturing, you can still use this feature but it will play no sound (sound will be saved directly).
Usage:
$ godot --write-movie movie.avi [scene_file.tscn]
Missing:
* Options for configuring video writing via GLOBAL_DEF
* UI Menu for launching with this mode from the editor.
* Add to list of command line options.
* Add a feature tag to override configurations when movie writing (fantastic for saving videos with highest quality settings).
											 
										 
										
											2022-06-17 00:55:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SaveJPGFunc  Image : : save_jpg_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SaveEXRFunc  Image : : save_exr_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SavePNGBufferFunc  Image : : save_png_buffer_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2022-06-19 18:55:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SaveEXRBufferFunc  Image : : save_exr_buffer_func  =  nullptr ;  
						 
					
						
							
								
									
										
											 
										
											
												Implement Running Godot as Movie Writer
* Allows running the game in "movie writer" mode.
* It ensures entirely stable framerate, so your run can be saved stable and with proper sound (which is impossible if your CPU/GPU can't sustain doing this in real-time).
* If disabling vsync, it can save movies faster than the game is run, but if you want to control the interaction it can get difficult.
* Implements a simple, default MJPEG writer.
This new features has two main use cases, which have high demand:
* Saving game videos in high quality and ensuring the frame rate is *completely* stable, always.
* Using Godot as a tool to make movies and animations (which is ideal if you want interaction, or creating them procedurally. No other software is as good for this).
**Note**: This feature **IS NOT** for capturing real-time footage. Use something like OBS, SimpleScreenRecorder or FRAPS to achieve that, as they do a much better job at intercepting the compositor than Godot can probably do using Vulkan or OpenGL natively. If your game runs near real-time when capturing, you can still use this feature but it will play no sound (sound will be saved directly).
Usage:
$ godot --write-movie movie.avi [scene_file.tscn]
Missing:
* Options for configuring video writing via GLOBAL_DEF
* UI Menu for launching with this mode from the editor.
* Add to list of command line options.
* Add a feature tag to override configurations when movie writing (fantastic for saving videos with highest quality settings).
											 
										 
										
											2022-06-17 00:55:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SaveJPGBufferFunc  Image : : save_jpg_buffer_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2019-10-31 19:54:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-06-04 16:05:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								SaveWebPFunc  Image : : save_webp_func  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								SaveWebPBufferFunc  Image : : save_webp_buffer_func  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 10:16:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : _put_pixelb ( int  p_x ,  int  p_y ,  uint32_t  p_pixel_size ,  uint8_t  * p_data ,  const  uint8_t  * p_pixel )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  ofs  =  ( p_y  *  width  +  p_x )  *  p_pixel_size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									memcpy ( p_data  +  ofs ,  p_pixel ,  p_pixel_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 10:16:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : _get_pixelb ( int  p_x ,  int  p_y ,  uint32_t  p_pixel_size ,  const  uint8_t  * p_data ,  uint8_t  * p_pixel )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  ofs  =  ( p_y  *  width  +  p_x )  *  p_pixel_size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									memcpy ( p_pixel ,  p_data  +  ofs ,  p_pixel_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_format_pixel_size ( Format  p_format )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( p_format )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //luminance
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  2 ;  //luminance-alpha
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_R8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA4444 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB565 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ;  //float
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  12 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBAF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  16 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  2 ;  //half float
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  6 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBAH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBE9995 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_DXT1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //s3tc bc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //bc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //bc3
 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGTC_R : 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  1 ;  //bc4
 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGTC_RG : 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  1 ;  //bc5
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBA : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //btpc bc6h
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //float /
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBFU : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //unsigned float
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //etc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_R11 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //etc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_R11S : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ;  //signed: return 1; NOT srgb.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RG11 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RG11S : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGB8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGBA8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGB8A1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RA_AS_RG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5_RA_AS_RG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_MAX :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : get_format_min_pixel_size ( Format  p_format ,  int  & r_w ,  int  & r_h )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									switch  ( p_format )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_DXT1 :  //s3tc bc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT3 :  //bc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5 :  //bc3
 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGTC_R :  //bc4
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGTC_RG :  {  //bc5		case case FORMAT_DXT1:
 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											r_w  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											r_h  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											r_w  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											r_h  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBA : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBFU :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											r_w  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											r_h  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC2_R11 :  //etc2
 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC2_R11S :  //signed: NOT srgb.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RG11 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RG11S : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGB8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGBA8 : 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGB8A1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RA_AS_RG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5_RA_AS_RG :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											r_w  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											r_h  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											r_w  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											r_h  =  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_format_pixel_rshift ( Format  p_format )  {  
						 
					
						
							
								
									
										
										
										
											2021-12-29 02:06:12 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_format  = =  FORMAT_DXT1  | |  p_format  = =  FORMAT_RGTC_R  | |  p_format  = =  FORMAT_ETC  | |  p_format  = =  FORMAT_ETC2_R11  | |  p_format  = =  FORMAT_ETC2_R11S  | |  p_format  = =  FORMAT_ETC2_RGB8  | |  p_format  = =  FORMAT_ETC2_RGB8A1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_format_block_size ( Format  p_format )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									switch  ( p_format )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT1 :  //s3tc bc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT3 :  //bc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5 :  //bc3
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGTC_R :  //bc4
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGTC_RG :  {  //bc5		case case FORMAT_DXT1:
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBA : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_BPTC_RGBFU :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC2_R11 :  //etc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_R11S :  //signed: NOT srgb.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RG11 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RG11S : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGB8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGBA8 : 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RGB8A1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_ETC2_RA_AS_RG :  //used to make basis universal happy
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5_RA_AS_RG :  //used to make basis universal happy
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : _get_mipmap_offset_and_size ( int  p_mipmap ,  int  & r_offset ,  int  & r_width ,  int  & r_height )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  w  =  width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  h  =  height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ofs  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pixel_rshift  =  get_format_pixel_rshift ( format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  block  =  get_format_block_size ( format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  minw ,  minh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									get_format_min_pixel_size ( format ,  minw ,  minh ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_mipmap ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  bw  =  w  %  block  ! =  0  ?  w  +  ( block  -  w  %  block )  :  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  bh  =  h  %  block  ! =  0  ?  h  +  ( block  -  h  %  block )  :  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  s  =  bw  *  bh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s  * =  pixel_size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										s  > > =  pixel_rshift ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ofs  + =  s ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w  =  MAX ( minw ,  w  > >  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										h  =  MAX ( minh ,  h  > >  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									r_offset  =  ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_width  =  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_height  =  h ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								int  Image : : get_mipmap_offset ( int  p_mipmap )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_mipmap ,  get_mipmap_count ( )  +  1 ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ofs ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_mipmap_byte_size ( int  p_mipmap )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_mipmap ,  get_mipmap_count ( )  +  1 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ofs ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ofs2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap  +  1 ,  ofs2 ,  w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ofs2  -  ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : get_mipmap_offset_and_size ( int  p_mipmap ,  int  & r_ofs ,  int  & r_size )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ofs ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									int  ofs2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap  +  1 ,  ofs2 ,  w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_ofs  =  ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_size  =  ofs2  -  ofs ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : get_mipmap_offset_size_and_dimensions ( int  p_mipmap ,  int  & r_ofs ,  int  & r_size ,  int  & w ,  int  & h )  const  {  
						 
					
						
							
								
									
										
										
										
											2015-04-06 21:48:20 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ofs ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ofs2 ,  w2 ,  h2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( p_mipmap  +  1 ,  ofs2 ,  w2 ,  h2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_ofs  =  ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_size  =  ofs2  -  ofs ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-04-06 21:48:20 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Image : : Image3DValidateError  Image : : validate_3d_image ( Image : : Format  p_format ,  int  p_width ,  int  p_height ,  int  p_depth ,  bool  p_mipmaps ,  const  Vector < Ref < Image > >  & p_images )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  w  =  p_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  h  =  p_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  d  =  p_depth ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  arr_ofs  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  d ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  idx  =  i  +  arr_ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( idx  > =  p_images . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  VALIDATE_3D_ERR_MISSING_IMAGES ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_images [ idx ] . is_null ( )  | |  p_images [ idx ] - > is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												return  VALIDATE_3D_ERR_IMAGE_EMPTY ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_images [ idx ] - > get_format ( )  ! =  p_format )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  VALIDATE_3D_ERR_IMAGE_FORMAT_MISMATCH ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_images [ idx ] - > get_width ( )  ! =  w  | |  p_images [ idx ] - > get_height ( )  ! =  h )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  VALIDATE_3D_ERR_IMAGE_SIZE_MISMATCH ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_images [ idx ] - > has_mipmaps ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  VALIDATE_3D_ERR_IMAGE_HAS_MIPMAPS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										arr_ofs  + =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! p_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( w  = =  1  & &  h  = =  1  & &  d  = =  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w  =  MAX ( 1 ,  w  > >  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										h  =  MAX ( 1 ,  h  > >  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d  =  MAX ( 1 ,  d  > >  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( arr_ofs  ! =  p_images . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  VALIDATE_3D_ERR_EXTRA_IMAGES ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  VALIDATE_3D_OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								String  Image : : get_3d_image_validation_error_text ( Image3DValidateError  p_error )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									switch  ( p_error )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_OK :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Ok " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_ERR_IMAGE_EMPTY :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Empty Image found " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_ERR_MISSING_IMAGES :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Missing Images " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_ERR_EXTRA_IMAGES :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Too many Images " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_ERR_IMAGE_SIZE_MISMATCH :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Image size mismatch " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_ERR_IMAGE_FORMAT_MISMATCH :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Image format mismatch " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  VALIDATE_3D_ERR_IMAGE_HAS_MIPMAPS :  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:24:14 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  " Image has included mipmaps " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-09 12:40:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  String ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_width ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  width ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_height ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  height ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-01 11:34:15 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Size2i  Image : : get_size ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  Size2i ( width ,  height ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-26 14:45:03 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								bool  Image : : has_mipmaps ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  mipmaps ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_mipmap_count ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  get_image_required_mipmaps ( width ,  height ,  format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								//using template generates perfectly optimized code due to constant expression reduction and unused variable removal present in all compilers
  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								template  < uint32_t  read_bytes ,  bool  read_alpha ,  uint32_t  write_bytes ,  bool  write_alpha ,  bool  read_gray ,  bool  write_gray >  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  void  _convert ( int  p_width ,  int  p_height ,  const  uint8_t  * p_src ,  uint8_t  * p_dst )  {  
						 
					
						
							
								
									
										
										
										
											2018-04-21 22:35:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint32_t  max_bytes  =  MAX ( read_bytes ,  write_bytes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  y  =  0 ;  y  <  p_height ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  x  =  0 ;  x  <  p_width ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  uint8_t  * rofs  =  & p_src [ ( ( y  *  p_width )  +  x )  *  ( read_bytes  +  ( read_alpha  ?  1  :  0 ) ) ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint8_t  * wofs  =  & p_dst [ ( ( y  *  p_width )  +  x )  *  ( write_bytes  +  ( write_alpha  ?  1  :  0 ) ) ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-05-11 16:12:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint8_t  rgba [ 4 ]  =  {  0 ,  0 ,  0 ,  255  } ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  constexpr  ( read_gray )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												rgba [ 0 ]  =  rofs [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												rgba [ 1 ]  =  rofs [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												rgba [ 2 ]  =  rofs [ 0 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-21 22:35:23 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( uint32_t  i  =  0 ;  i  <  max_bytes ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													rgba [ i ]  =  ( i  <  read_bytes )  ?  rofs [ i ]  :  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  constexpr  ( read_alpha  | |  write_alpha )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												rgba [ 3 ]  =  read_alpha  ?  rofs [ read_bytes ]  :  255 ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  constexpr  ( write_gray )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												//TODO: not correct grayscale, should use fixed point version of actual weights
 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-11 16:12:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												wofs [ 0 ]  =  uint8_t ( ( uint16_t ( rgba [ 0 ] )  +  uint16_t ( rgba [ 1 ] )  +  uint16_t ( rgba [ 2 ] ) )  /  3 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( uint32_t  i  =  0 ;  i  <  write_bytes ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													wofs [ i ]  =  rgba [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  constexpr  ( write_alpha )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												wofs [ write_bytes ]  =  rgba [ 3 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : convert ( Format  p_new_format )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( data . size ( )  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_new_format  = =  format )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( format  >  FORMAT_RGBE9995  | |  p_new_format  >  FORMAT_RGBE9995 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-14 20:57:49 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_MSG ( " Cannot convert to <-> from compressed formats. Use compress() and decompress() instead. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( format  >  FORMAT_RGBA8  | |  p_new_format  >  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//use put/set pixel which is slower but works with non byte formats
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 11:00:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Image  new_img ( width ,  height ,  false ,  p_new_format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  width ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  j  =  0 ;  j  <  height ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-07-07 19:05:45 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												new_img . set_pixel ( i ,  j ,  get_pixel ( i ,  j ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( has_mipmaps ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											new_img . generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_copy_internals_from ( new_img ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 11:00:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Image  new_img ( width ,  height ,  false ,  p_new_format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * rptr  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint8_t  * wptr  =  new_img . data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  conversion_type  =  format  |  p_new_format  < <  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									switch  ( conversion_type )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_L8  |  ( FORMAT_LA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  1 ,  true ,  true ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8  |  ( FORMAT_R8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  1 ,  false ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8  |  ( FORMAT_RG8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  2 ,  false ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8  |  ( FORMAT_RGB8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  3 ,  false ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8  |  ( FORMAT_RGBA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  3 ,  true ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8  |  ( FORMAT_L8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  true ,  1 ,  false ,  true ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8  |  ( FORMAT_R8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  true ,  1 ,  false ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8  |  ( FORMAT_RG8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  true ,  2 ,  false ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8  |  ( FORMAT_RGB8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  true ,  3 ,  false ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8  |  ( FORMAT_RGBA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  true ,  3 ,  true ,  true ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_R8  |  ( FORMAT_L8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  1 ,  false ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_R8  |  ( FORMAT_LA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  1 ,  true ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_R8  |  ( FORMAT_RG8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  2 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_R8  |  ( FORMAT_RGB8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  3 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_R8  |  ( FORMAT_RGBA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 1 ,  false ,  3 ,  true ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8  |  ( FORMAT_L8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 2 ,  false ,  1 ,  false ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8  |  ( FORMAT_LA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 2 ,  false ,  1 ,  true ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8  |  ( FORMAT_R8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 2 ,  false ,  1 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8  |  ( FORMAT_RGB8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 2 ,  false ,  3 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8  |  ( FORMAT_RGBA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 2 ,  false ,  3 ,  true ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8  |  ( FORMAT_L8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  false ,  1 ,  false ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8  |  ( FORMAT_LA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  false ,  1 ,  true ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8  |  ( FORMAT_R8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  false ,  1 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8  |  ( FORMAT_RG8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  false ,  2 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8  |  ( FORMAT_RGBA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  false ,  3 ,  true ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8  |  ( FORMAT_L8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  true ,  1 ,  false ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8  |  ( FORMAT_LA8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  true ,  1 ,  true ,  false ,  true > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8  |  ( FORMAT_R8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  true ,  1 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8  |  ( FORMAT_RG8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  true ,  2 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8  |  ( FORMAT_RGB8  < <  8 ) : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert < 3 ,  true ,  3 ,  false ,  false ,  false > ( width ,  height ,  rptr ,  wptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  gen_mipmaps  =  mipmaps ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_copy_internals_from ( new_img ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( gen_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Image : : Format  Image : : get_format ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  double  _bicubic_interp_kernel ( double  x )  {  
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									x  =  ABS ( x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  bc  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( x  < =  1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										bc  =  ( 1.5  *  x  -  2.5 )  *  x  *  x  +  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( x  <  2 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										bc  =  ( ( - 0.5  *  x  +  2.5 )  *  x  -  4 )  *  x  +  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  bc ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 17:56:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								template  < int  CC ,  class  T >  
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:56:55 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  void  _scale_cubic ( const  uint8_t  * __restrict  p_src ,  uint8_t  * __restrict  p_dst ,  uint32_t  p_src_width ,  uint32_t  p_src_height ,  uint32_t  p_dst_width ,  uint32_t  p_dst_height )  {  
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// get source image size
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  width  =  p_src_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  height  =  p_src_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  xfac  =  ( double ) width  /  p_dst_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  yfac  =  ( double ) height  /  p_dst_height ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-21 23:58:29 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// coordinates of source points and coefficients
 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									double  ox ,  oy ,  dx ,  dy ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ox1 ,  oy1 ,  ox2 ,  oy2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// destination pixel values
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// width and height decreased by 1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ymax  =  height  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  xmax  =  width  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// temporary pointer
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( uint32_t  y  =  0 ;  y  <  p_dst_height ;  y + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Y coordinates
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										oy  =  ( double ) y  *  yfac  -  0.5f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										oy1  =  ( int ) oy ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dy  =  oy  -  ( double ) oy1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( uint32_t  x  =  0 ;  x  <  p_dst_width ;  x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// X coordinates
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ox  =  ( double ) x  *  xfac  -  0.5f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ox1  =  ( int ) ox ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											dx  =  ox  -  ( double ) ox1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// initial pixel value
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											T  * __restrict  dst  =  ( ( T  * ) p_dst )  +  ( y  *  p_dst_width  +  x )  *  CC ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											double  color [ CC ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												color [ i ]  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  n  =  - 1 ;  n  <  3 ;  n + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-21 23:58:29 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// get Y coefficient
 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												[[maybe_unused]]  double  k1  =  _bicubic_interp_kernel ( dy  -  ( double ) n ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												oy2  =  oy1  +  n ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( oy2  <  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													oy2  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( oy2  >  ymax )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													oy2  =  ymax ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( int  m  =  - 1 ;  m  <  3 ;  m + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-21 23:58:29 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													// get X coefficient
 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													[[maybe_unused]]  double  k2  =  k1  *  _bicubic_interp_kernel ( ( double ) m  -  dx ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ox2  =  ox1  +  m ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( ox2  <  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														ox2  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ox2  >  xmax )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														ox2  =  xmax ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// get pixel of original image
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													const  T  * __restrict  p  =  ( ( T  * ) p_src )  +  ( oy2  *  p_src_width  +  ox2 )  *  CC ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  constexpr  ( sizeof ( T )  = =  2 )  {  //half float
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															color [ i ]  =  Math : : half_to_float ( p [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															color [ i ]  + =  p [ i ]  *  k2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  constexpr  ( sizeof ( T )  = =  1 )  {  //byte
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													dst [ i ]  =  CLAMP ( Math : : fast_ftoi ( color [ i ] ) ,  0 ,  255 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  if  constexpr  ( sizeof ( T )  = =  2 )  {  //half float
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													dst [ i ]  =  Math : : make_half_float ( color [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst [ i ]  =  color [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 17:56:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								template  < int  CC ,  class  T >  
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:56:55 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  void  _scale_bilinear ( const  uint8_t  * __restrict  p_src ,  uint8_t  * __restrict  p_dst ,  uint32_t  p_src_width ,  uint32_t  p_src_height ,  uint32_t  p_dst_width ,  uint32_t  p_dst_height )  {  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									enum  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										FRAC_BITS  =  8 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										FRAC_LEN  =  ( 1  < <  FRAC_BITS ) , 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-17 16:26:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										FRAC_HALF  =  ( FRAC_LEN  > >  1 ) , 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										FRAC_MASK  =  FRAC_LEN  -  1 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  p_dst_height ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-17 16:26:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Add 0.5 in order to interpolate based on pixel center
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  src_yofs_up_fp  =  ( i  +  0.5 )  *  p_src_height  *  FRAC_LEN  /  p_dst_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Calculate nearest src pixel center above current, and truncate to get y index
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  src_yofs_up  =  src_yofs_up_fp  > =  FRAC_HALF  ?  ( src_yofs_up_fp  -  FRAC_HALF )  > >  FRAC_BITS  :  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  src_yofs_down  =  ( src_yofs_up_fp  +  FRAC_HALF )  > >  FRAC_BITS ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( src_yofs_down  > =  p_src_height )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											src_yofs_down  =  p_src_height  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-17 16:26:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Calculate distance to pixel center of src_yofs_up
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  src_yofs_frac  =  src_yofs_up_fp  &  FRAC_MASK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										src_yofs_frac  =  src_yofs_frac  > =  FRAC_HALF  ?  src_yofs_frac  -  FRAC_HALF  :  src_yofs_frac  +  FRAC_HALF ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  y_ofs_up  =  src_yofs_up  *  p_src_width  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  y_ofs_down  =  src_yofs_down  *  p_src_width  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( uint32_t  j  =  0 ;  j  <  p_dst_width ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-17 16:26:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint32_t  src_xofs_left_fp  =  ( j  +  0.5 )  *  p_src_width  *  FRAC_LEN  /  p_dst_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint32_t  src_xofs_left  =  src_xofs_left_fp  > =  FRAC_HALF  ?  ( src_xofs_left_fp  -  FRAC_HALF )  > >  FRAC_BITS  :  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint32_t  src_xofs_right  =  ( src_xofs_left_fp  +  FRAC_HALF )  > >  FRAC_BITS ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( src_xofs_right  > =  p_src_width )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												src_xofs_right  =  p_src_width  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-06-17 16:26:57 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint32_t  src_xofs_frac  =  src_xofs_left_fp  &  FRAC_MASK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_xofs_frac  =  src_xofs_frac  > =  FRAC_HALF  ?  src_xofs_frac  -  FRAC_HALF  :  src_xofs_frac  +  FRAC_HALF ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											src_xofs_left  * =  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_xofs_right  * =  CC ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( uint32_t  l  =  0 ;  l  <  CC ;  l + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  constexpr  ( sizeof ( T )  = =  1 )  {  //uint8
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													uint32_t  p00  =  p_src [ y_ofs_up  +  src_xofs_left  +  l ]  < <  FRAC_BITS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  p10  =  p_src [ y_ofs_up  +  src_xofs_right  +  l ]  < <  FRAC_BITS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  p01  =  p_src [ y_ofs_down  +  src_xofs_left  +  l ]  < <  FRAC_BITS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  p11  =  p_src [ y_ofs_down  +  src_xofs_right  +  l ]  < <  FRAC_BITS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  interp_up  =  p00  +  ( ( ( p10  -  p00 )  *  src_xofs_frac )  > >  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  interp_down  =  p01  +  ( ( ( p11  -  p01 )  *  src_xofs_frac )  > >  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  interp  =  interp_up  +  ( ( ( interp_down  -  interp_up )  *  src_yofs_frac )  > >  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													interp  > > =  FRAC_BITS ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 12:43:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_dst [ i  *  p_dst_width  *  CC  +  j  *  CC  +  l ]  =  uint8_t ( interp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  if  constexpr  ( sizeof ( T )  = =  2 )  {  //half float
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  xofs_frac  =  float ( src_xofs_frac )  /  ( 1  < <  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  yofs_frac  =  float ( src_yofs_frac )  /  ( 1  < <  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  T  * src  =  ( ( const  T  * ) p_src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													T  * dst  =  ( ( T  * ) p_dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p00  =  Math : : half_to_float ( src [ y_ofs_up  +  src_xofs_left  +  l ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p10  =  Math : : half_to_float ( src [ y_ofs_up  +  src_xofs_right  +  l ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p01  =  Math : : half_to_float ( src [ y_ofs_down  +  src_xofs_left  +  l ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p11  =  Math : : half_to_float ( src [ y_ofs_down  +  src_xofs_right  +  l ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  interp_up  =  p00  +  ( p10  -  p00 )  *  xofs_frac ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  interp_down  =  p01  +  ( p11  -  p01 )  *  xofs_frac ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  interp  =  interp_up  +  ( ( interp_down  -  interp_up )  *  yofs_frac ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst [ i  *  p_dst_width  *  CC  +  j  *  CC  +  l ]  =  Math : : make_half_float ( interp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  if  constexpr  ( sizeof ( T )  = =  4 )  {  //float
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  xofs_frac  =  float ( src_xofs_frac )  /  ( 1  < <  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  yofs_frac  =  float ( src_yofs_frac )  /  ( 1  < <  FRAC_BITS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  T  * src  =  ( ( const  T  * ) p_src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													T  * dst  =  ( ( T  * ) p_dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p00  =  src [ y_ofs_up  +  src_xofs_left  +  l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p10  =  src [ y_ofs_up  +  src_xofs_right  +  l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p01  =  src [ y_ofs_down  +  src_xofs_left  +  l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  p11  =  src [ y_ofs_down  +  src_xofs_right  +  l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  interp_up  =  p00  +  ( p10  -  p00 )  *  xofs_frac ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  interp_down  =  p01  +  ( p11  -  p01 )  *  xofs_frac ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  interp  =  interp_up  +  ( ( interp_down  -  interp_up )  *  yofs_frac ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst [ i  *  p_dst_width  *  CC  +  j  *  CC  +  l ]  =  interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 17:56:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								template  < int  CC ,  class  T >  
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:56:55 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  void  _scale_nearest ( const  uint8_t  * __restrict  p_src ,  uint8_t  * __restrict  p_dst ,  uint32_t  p_src_width ,  uint32_t  p_src_height ,  uint32_t  p_dst_width ,  uint32_t  p_dst_height )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  p_dst_height ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  src_yofs  =  i  *  p_src_height  /  p_dst_height ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										uint32_t  y_ofs  =  src_yofs  *  p_src_width  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( uint32_t  j  =  0 ;  j  <  p_dst_width ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint32_t  src_xofs  =  j  *  p_src_width  /  p_dst_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_xofs  * =  CC ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( uint32_t  l  =  0 ;  l  <  CC ;  l + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  T  * src  =  ( ( const  T  * ) p_src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												T  * dst  =  ( ( T  * ) p_dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												T  p  =  src [ y_ofs  +  src_xofs  +  l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												dst [ i  *  p_dst_width  *  CC  +  j  *  CC  +  l ]  =  p ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define LANCZOS_TYPE 3 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  float  _lanczos ( float  p_x )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  Math : : abs ( p_x )  > =  LANCZOS_TYPE  ?  0  :  Math : : sincn ( p_x )  *  Math : : sincn ( p_x  /  LANCZOS_TYPE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								template  < int  CC ,  class  T >  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  void  _scale_lanczos ( const  uint8_t  * __restrict  p_src ,  uint8_t  * __restrict  p_dst ,  uint32_t  p_src_width ,  uint32_t  p_src_height ,  uint32_t  p_dst_width ,  uint32_t  p_dst_height )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int32_t  src_width  =  p_src_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int32_t  src_height  =  p_src_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int32_t  dst_height  =  p_dst_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int32_t  dst_width  =  p_dst_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  buffer_size  =  src_height  *  dst_width  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									float  * buffer  =  memnew_arr ( float ,  buffer_size ) ;  // Store the first pass in a buffer
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{  // FIRST PASS (horizontal)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  x_scale  =  float ( src_width )  /  float ( dst_width ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  scale_factor  =  MAX ( x_scale ,  1 ) ;  // A larger kernel is required only when downscaling
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int32_t  half_kernel  =  LANCZOS_TYPE  *  scale_factor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-05-31 13:22:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										float  * kernel  =  memnew_arr ( float ,  half_kernel  *  2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  buffer_x  =  0 ;  buffer_x  <  dst_width ;  buffer_x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-15 01:35:23 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// The corresponding point on the source image
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  src_x  =  ( buffer_x  +  0.5f )  *  x_scale ;  // Offset by 0.5 so it uses the pixel's center
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  start_x  =  MAX ( 0 ,  int32_t ( src_x )  -  half_kernel  +  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  end_x  =  MIN ( src_width  -  1 ,  int32_t ( src_x )  +  half_kernel ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Create the kernel used by all the pixels of the column
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int32_t  target_x  =  start_x ;  target_x  < =  end_x ;  target_x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-15 01:35:23 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												kernel [ target_x  -  start_x ]  =  _lanczos ( ( target_x  +  0.5f  -  src_x )  /  scale_factor ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int32_t  buffer_y  =  0 ;  buffer_y  <  src_height ;  buffer_y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  pixel [ CC ]  =  {  0  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  weight  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int32_t  target_x  =  start_x ;  target_x  < =  end_x ;  target_x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  lanczos_val  =  kernel [ target_x  -  start_x ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weight  + =  lanczos_val ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  T  * __restrict  src_data  =  ( ( const  T  * ) p_src )  +  ( buffer_y  *  src_width  +  target_x )  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( uint32_t  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  constexpr  ( sizeof ( T )  = =  2 )  {  //half float
 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															pixel [ i ]  + =  Math : : half_to_float ( src_data [ i ] )  *  lanczos_val ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															pixel [ i ]  + =  src_data [ i ]  *  lanczos_val ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  * dst_data  =  ( ( float  * ) buffer )  +  ( buffer_y  *  dst_width  +  buffer_x )  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( uint32_t  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													dst_data [ i ]  =  pixel [ i ]  /  weight ;  // Normalize the sum of all the samples
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										memdelete_arr ( kernel ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  // End of first pass
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{  // SECOND PASS (vertical + result)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  y_scale  =  float ( src_height )  /  float ( dst_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  scale_factor  =  MAX ( y_scale ,  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int32_t  half_kernel  =  LANCZOS_TYPE  *  scale_factor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-05-31 13:22:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										float  * kernel  =  memnew_arr ( float ,  half_kernel  *  2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  dst_y  =  0 ;  dst_y  <  dst_height ;  dst_y + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-15 01:35:23 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											float  buffer_y  =  ( dst_y  +  0.5f )  *  y_scale ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  start_y  =  MAX ( 0 ,  int32_t ( buffer_y )  -  half_kernel  +  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  end_y  =  MIN ( src_height  -  1 ,  int32_t ( buffer_y )  +  half_kernel ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int32_t  target_y  =  start_y ;  target_y  < =  end_y ;  target_y + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-15 01:35:23 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												kernel [ target_y  -  start_y ]  =  _lanczos ( ( target_y  +  0.5f  -  buffer_y )  /  scale_factor ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int32_t  dst_x  =  0 ;  dst_x  <  dst_width ;  dst_x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  pixel [ CC ]  =  {  0  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  weight  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int32_t  target_y  =  start_y ;  target_y  < =  end_y ;  target_y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  lanczos_val  =  kernel [ target_y  -  start_y ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weight  + =  lanczos_val ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  * buffer_data  =  ( ( float  * ) buffer )  +  ( target_y  *  dst_width  +  dst_x )  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( uint32_t  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														pixel [ i ]  + =  buffer_data [ i ]  *  lanczos_val ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												T  * dst_data  =  ( ( T  * ) p_dst )  +  ( dst_y  *  dst_width  +  dst_x )  *  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( uint32_t  i  =  0 ;  i  <  CC ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													pixel [ i ]  / =  weight ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  constexpr  ( sizeof ( T )  = =  1 )  {  //byte
 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														dst_data [ i ]  =  CLAMP ( Math : : fast_ftoi ( pixel [ i ] ) ,  0 ,  255 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 09:18:07 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													}  else  if  constexpr  ( sizeof ( T )  = =  2 )  {  //half float
 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														dst_data [ i ]  =  Math : : make_half_float ( pixel [ i ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													}  else  {  // float
 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														dst_data [ i ]  =  pixel [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										memdelete_arr ( kernel ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  // End of second pass
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									memdelete_arr ( buffer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:56:55 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  void  _overlay ( const  uint8_t  * __restrict  p_src ,  uint8_t  * __restrict  p_dst ,  float  p_alpha ,  uint32_t  p_width ,  uint32_t  p_height ,  uint32_t  p_pixel_size )  {  
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint16_t  alpha  =  MIN ( ( uint16_t ) ( p_alpha  *  256.0f ) ,  256 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  p_width  *  p_height  *  p_pixel_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_dst [ i ]  =  ( p_dst [ i ]  *  ( 256  -  alpha )  +  p_src [ i ]  *  alpha )  > >  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-03-07 12:15:10 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								bool  Image : : is_size_po2 ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  uint32_t ( width )  = =  next_power_of_2 ( width )  & &  uint32_t ( height )  = =  next_power_of_2 ( height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-18 10:14:55 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : resize_to_po2 ( bool  p_square ,  Interpolation  p_interpolation )  {  
						 
					
						
							
								
									
										
										
										
											2019-08-26 18:21:19 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot resize in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-08-17 18:35:55 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  w  =  next_power_of_2 ( width ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  h  =  next_power_of_2 ( height ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-18 13:29:01 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_square )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w  =  h  =  MAX ( w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( w  = =  width  & &  h  = =  height )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! p_square  | |  w  = =  h )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return ;  //nothing to do
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-18 10:14:55 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									resize ( w ,  h ,  p_interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : resize ( int  p_width ,  int  p_height ,  Interpolation  p_interpolation )  {  
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( data . size ( )  = =  0 ,  " Cannot resize image before creating it, use set_data() first. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-26 18:21:19 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot resize in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  mipmap_aware  =  p_interpolation  = =  INTERPOLATE_TRILINEAR  /* || p_interpolation == INTERPOLATE_TRICUBIC */ ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-28 08:07:29 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  < =  0 ,  " Image width must be greater than 0. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  < =  0 ,  " Image height must be greater than 0. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  >  MAX_WIDTH ,  " Image width cannot be greater than  "  +  itos ( MAX_WIDTH )  +  " . " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  >  MAX_HEIGHT ,  " Image height cannot be greater than  "  +  itos ( MAX_HEIGHT )  +  " . " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-10-31 19:54:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  *  p_height  >  MAX_PIXELS ,  " Too many pixels for image, maximum is  "  +  itos ( MAX_PIXELS ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_width  = =  width  & &  p_height  = =  height )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 11:00:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Image  dst ( p_width ,  p_height ,  false ,  format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Setup mipmap-aware scaling
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Image  dst2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-04 13:04:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  mip1  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mip2  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									float  mip1_weight  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( mipmap_aware )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  avg_scale  =  ( ( float ) p_width  /  width  +  ( float ) p_height  /  height )  *  0.5f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( avg_scale  > =  1.0f )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mipmap_aware  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  level  =  Math : : log ( 1.0f  /  avg_scale )  /  Math : : log ( 2.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mip1  =  CLAMP ( ( int ) Math : : floor ( level ) ,  0 ,  get_mipmap_count ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mip2  =  CLAMP ( ( int ) Math : : ceil ( level ) ,  0 ,  get_mipmap_count ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mip1_weight  =  1.0f  -  ( level  -  mip1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  interpolate_mipmaps  =  mipmap_aware  & &  mip1  ! =  mip2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( interpolate_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										dst2 . initialize_data ( p_width ,  p_height ,  false ,  format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  had_mipmaps  =  mipmaps ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( interpolate_mipmaps  & &  ! had_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// --
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * r  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  unsigned  char  * r_ptr  =  r ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * w  =  dst . data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									unsigned  char  * w_ptr  =  w ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( p_interpolation )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										case  INTERPOLATE_NEAREST :  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( format  > =  FORMAT_L8  & &  format  < =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 1 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 2 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 3 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 4 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( format  > =  FORMAT_RF  & &  format  < =  FORMAT_RGBAF )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 1 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 2 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  12 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 3 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 4 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( format  > =  FORMAT_RH  & &  format  < =  FORMAT_RGBAH )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 1 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 2 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  6 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 3 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_nearest < 4 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  INTERPOLATE_BILINEAR : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  INTERPOLATE_TRILINEAR :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  2 ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  src_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  src_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  unsigned  char  * src_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! mipmap_aware )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( i  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// Standard behavior
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														src_width  =  width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														src_height  =  height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														src_ptr  =  r_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// No need for a second iteration
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( i  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// Read from the first mipmap that will be interpolated
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// (if both levels are the same, we will not interpolate, but at least we'll sample from the right level)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														int  offs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_get_mipmap_offset_and_size ( mip1 ,  offs ,  src_width ,  src_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														src_ptr  =  r_ptr  +  offs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( ! interpolate_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// No need generate a second image
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// Switch to read from the second mipmap that will be interpolated
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														int  offs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_get_mipmap_offset_and_size ( mip2 ,  offs ,  src_width ,  src_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														src_ptr  =  r_ptr  +  offs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// Switch to write to the second destination image
 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														w  =  dst2 . data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														w_ptr  =  w ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( format  > =  FORMAT_L8  & &  format  < =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														case  1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 1 ,  uint8_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 2 ,  uint8_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 3 ,  uint8_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 4 ,  uint8_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( format  > =  FORMAT_RF  & &  format  < =  FORMAT_RGBAF )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 1 ,  float > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 2 ,  float > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  12 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 3 ,  float > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  16 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 4 ,  float > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( format  > =  FORMAT_RH  & &  format  < =  FORMAT_RGBAH )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 1 ,  uint16_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 2 ,  uint16_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  6 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 3 ,  uint16_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															_scale_bilinear < 4 ,  uint16_t > ( src_ptr ,  w_ptr ,  src_width ,  src_height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( interpolate_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Switch to read again from the first scaled mipmap to overlay it over the second
 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												r  =  dst . data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_overlay ( r ,  w ,  mip1_weight ,  p_width ,  p_height ,  get_format_pixel_size ( format ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  INTERPOLATE_CUBIC :  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( format  > =  FORMAT_L8  & &  format  < =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 1 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 2 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 3 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 4 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( format  > =  FORMAT_RF  & &  format  < =  FORMAT_RGBAF )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 1 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 2 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  12 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 3 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 4 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( format  > =  FORMAT_RH  & &  format  < =  FORMAT_RGBAH )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 1 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 2 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  6 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 3 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_cubic < 4 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-22 16:40:43 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-01 16:25:36 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  INTERPOLATE_LANCZOS :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( format  > =  FORMAT_L8  & &  format  < =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 1 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 2 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 3 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 4 ,  uint8_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( format  > =  FORMAT_RF  & &  format  < =  FORMAT_RGBAF )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 1 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 2 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  12 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 3 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 4 ,  float > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( format  > =  FORMAT_RH  & &  format  < =  FORMAT_RGBAH )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( get_format_pixel_size ( format ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 1 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 2 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  6 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 3 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														_scale_lanczos < 4 ,  uint16_t > ( r_ptr ,  w_ptr ,  width ,  height ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( interpolate_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										dst . _copy_internals_from ( dst2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( had_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										dst . generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_copy_internals_from ( dst ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-11-17 21:42:14 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : crop_from_point ( int  p_x ,  int  p_y ,  int  p_width ,  int  p_height )  {  
						 
					
						
							
								
									
										
										
										
											2019-08-26 18:21:19 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot crop in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-14 20:57:49 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_x  <  0 ,  " Start x position cannot be smaller than 0. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_y  <  0 ,  " Start y position cannot be smaller than 0. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  < =  0 ,  " Width of image must be greater than 0. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  < =  0 ,  " Height of image must be greater than 0. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_x  +  p_width  >  MAX_WIDTH ,  " End x position cannot be greater than  "  +  itos ( MAX_WIDTH )  +  " . " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_y  +  p_height  >  MAX_HEIGHT ,  " End y position cannot be greater than  "  +  itos ( MAX_HEIGHT )  +  " . " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									/* to save memory, cropping should be done in-place, however, since this function
 
							 
						 
					
						
							
								
									
										
										
										
											2018-01-18 21:37:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									   will  most  likely  either  not  be  used  much ,  or  in  critical  areas ,  for  now  it  won ' t ,  because 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									   it ' s  a  waste  of  time .  */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_width  = =  width  & &  p_height  = =  height  & &  p_x  = =  0  & &  p_y  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  pdata [ 16 ] ;  //largest is 16
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 11:00:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Image  dst ( p_width ,  p_height ,  false ,  format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  uint8_t  * r  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  * w  =  dst . data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-11-17 21:42:14 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  m_h  =  p_y  +  p_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  m_w  =  p_x  +  p_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  y  =  p_y ;  y  <  m_h ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  x  =  p_x ;  x  <  m_w ;  x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( ( x  > =  width  | |  y  > =  height ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( uint32_t  i  =  0 ;  i  <  pixel_size ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														pdata [ i ]  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_get_pixelb ( x ,  y ,  pixel_size ,  r ,  pdata ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												dst . _put_pixelb ( x  -  p_x ,  y  -  p_y ,  pixel_size ,  w ,  pdata ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( has_mipmaps ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										dst . generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_copy_internals_from ( dst ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-11-17 21:42:14 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : crop ( int  p_width ,  int  p_height )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									crop_from_point ( 0 ,  0 ,  p_width ,  p_height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-14 22:20:12 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : rotate_90 ( ClockDirection  p_direction )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot rotate in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( width  < =  1 ,  " The Image width specified ( "  +  itos ( width )  +  "  pixels) must be greater than 1 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( height  < =  1 ,  " The Image height specified ( "  +  itos ( height )  +  "  pixels) must be greater than 1 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  saved_width  =  height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  saved_height  =  width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( width  ! =  height )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  n  =  MAX ( width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										resize ( n ,  n ,  INTERPOLATE_NEAREST ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  used_mipmaps  =  has_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										clear_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  src [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  dst [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Flip.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_direction  = =  CLOCKWISE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  y  =  0 ;  y  <  height  /  2 ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  x  =  0 ;  x  <  width ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_get_pixelb ( x ,  y ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_get_pixelb ( x ,  height  -  y  -  1 ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_put_pixelb ( x ,  height  -  y  -  1 ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_put_pixelb ( x ,  y ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  y  =  0 ;  y  <  height ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  x  =  0 ;  x  <  width  /  2 ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_get_pixelb ( x ,  y ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_get_pixelb ( width  -  x  -  1 ,  y ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_put_pixelb ( width  -  x  -  1 ,  y ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_put_pixelb ( x ,  y ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Transpose.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  y  =  0 ;  y  <  height ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  x  =  0 ;  x  <  width ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( x  <  y )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_get_pixelb ( x ,  y ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_get_pixelb ( y ,  x ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_put_pixelb ( y ,  x ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_put_pixelb ( x ,  y ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( saved_width  ! =  saved_height )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										resize ( saved_width ,  saved_height ,  INTERPOLATE_NEAREST ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : rotate_180 ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot rotate in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( width  < =  1 ,  " The Image width specified ( "  +  itos ( width )  +  "  pixels) must be greater than 1 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( height  < =  1 ,  " The Image height specified ( "  +  itos ( height )  +  "  pixels) must be greater than 1 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  used_mipmaps  =  has_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										clear_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  src [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  dst [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  y  =  0 ;  y  <  height  /  2 ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  x  =  0 ;  x  <  width ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_get_pixelb ( x ,  y ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_get_pixelb ( width  -  x  -  1 ,  height  -  y  -  1 ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_put_pixelb ( width  -  x  -  1 ,  height  -  y  -  1 ,  pixel_size ,  w ,  src ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_put_pixelb ( x ,  y ,  pixel_size ,  w ,  dst ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								void  Image : : flip_y ( )  {  
						 
					
						
							
								
									
										
										
										
											2019-08-26 18:21:19 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot flip_y in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  used_mipmaps  =  has_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-01-14 18:03:38 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										clear_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  up [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  down [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-09 00:23:50 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  y  =  0 ;  y  <  height  /  2 ;  y + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  x  =  0 ;  x  <  width ;  x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												_get_pixelb ( x ,  y ,  pixel_size ,  w ,  up ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_get_pixelb ( x ,  height  -  y  -  1 ,  pixel_size ,  w ,  down ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												_put_pixelb ( x ,  height  -  y  -  1 ,  pixel_size ,  w ,  up ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_put_pixelb ( x ,  y ,  pixel_size ,  w ,  down ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-01-14 18:03:38 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : flip_x ( )  {  
						 
					
						
							
								
									
										
										
										
											2019-08-26 18:21:19 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot flip_x in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  used_mipmaps  =  has_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-01-14 18:03:38 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										clear_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  up [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  down [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  y  =  0 ;  y  <  height ;  y + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-09 00:23:50 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  x  =  0 ;  x  <  width  /  2 ;  x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												_get_pixelb ( x ,  y ,  pixel_size ,  w ,  up ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_get_pixelb ( width  -  x  -  1 ,  y ,  pixel_size ,  w ,  down ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												_put_pixelb ( width  -  x  -  1 ,  y ,  pixel_size ,  w ,  up ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_put_pixelb ( x ,  y ,  pixel_size ,  w ,  down ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-01-14 18:03:38 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-03 17:27:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								/// Get mipmap size and offset.
  
						 
					
						
							
								
									
										
										
										
											2019-07-27 10:23:24 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : _get_dst_image_size ( int  p_width ,  int  p_height ,  Format  p_format ,  int  & r_mipmaps ,  int  p_mipmaps ,  int  * r_mm_width ,  int  * r_mm_height )  {  
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Data offset in mipmaps (including the original texture).
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  size  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  w  =  p_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  h  =  p_height ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Current mipmap index in the loop below. p_mipmaps is the target mipmap index.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// In this function, mipmap 0 represents the first mipmap instead of the original texture.
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  mm  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  pixsize  =  get_format_pixel_size ( p_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pixshift  =  get_format_pixel_rshift ( p_format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  block  =  get_format_block_size ( p_format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Technically, you can still compress up to 1 px no matter the format, so commenting this.
 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-06 14:56:06 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									//int minw, minh;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//get_format_min_pixel_size(p_format, minw, minh);
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  minw  =  1 ,  minh  =  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									while  ( true )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  bw  =  w  %  block  ! =  0  ?  w  +  ( block  -  w  %  block )  :  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  bh  =  h  %  block  ! =  0  ?  h  +  ( block  -  h  %  block )  :  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  s  =  bw  *  bh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										s  * =  pixsize ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										s  > > =  pixshift ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										size  + =  s ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_mipmaps  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											w  =  MAX ( minw ,  w  > >  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											h  =  MAX ( minh ,  h  > >  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( w  = =  minw  & &  h  = =  minh )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											w  =  MAX ( minw ,  w  > >  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											h  =  MAX ( minh ,  h  > >  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Set mipmap size.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( r_mm_width )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 20:29:39 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											* r_mm_width  =  w ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( r_mm_height )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 20:29:39 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											* r_mm_height  =  h ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-08 21:38:45 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Reach target mipmap.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_mipmaps  > =  0  & &  mm  = =  p_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										mm + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-19 15:46:49 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									r_mipmaps  =  mm ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								bool  Image : : _can_modify ( Format  p_format )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  p_format  < =  FORMAT_RGBE9995 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								template  < class  Component ,  int  CC ,  bool  renormalize ,  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										void  ( * average_func ) ( Component  & ,  const  Component  & ,  const  Component  & ,  const  Component  & ,  const  Component  & ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										void  ( * renormalize_func ) ( Component  * ) > 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  void  _generate_po2_mipmap ( const  Component  * p_src ,  Component  * p_dst ,  uint32_t  p_width ,  uint32_t  p_height )  {  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									//fast power of 2 mipmap generation
 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-08 15:10:48 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint32_t  dst_w  =  MAX ( p_width  > >  1 ,  1u ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  dst_h  =  MAX ( p_height  > >  1 ,  1u ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-25 16:39:43 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  right_step  =  ( p_width  = =  1 )  ?  0  :  CC ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  down_step  =  ( p_height  = =  1 )  ?  0  :  ( p_width  *  CC ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  dst_h ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-25 16:39:43 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Component  * rup_ptr  =  & p_src [ i  *  2  *  down_step ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Component  * rdown_ptr  =  rup_ptr  +  down_step ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Component  * dst_ptr  =  & p_dst [ i  *  dst_w  *  CC ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint32_t  count  =  dst_w ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-11-01 16:16:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										while  ( count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											count - - ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  j  =  0 ;  j  <  CC ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-25 16:39:43 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												average_func ( dst_ptr [ j ] ,  rup_ptr [ j ] ,  rup_ptr [ j  +  right_step ] ,  rdown_ptr [ j ] ,  rdown_ptr [ j  +  right_step ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												renormalize_func ( dst_ptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											dst_ptr  + =  CC ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-25 16:39:43 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											rup_ptr  + =  right_step  *  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rdown_ptr  + =  right_step  *  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : shrink_x2 ( )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( data . size ( )  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//just use the lower mipmap as base and copy all
 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Vector < uint8_t >  new_img ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  ofs  =  get_mipmap_offset ( 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  new_size  =  data . size ( )  -  ofs ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_img . resize ( new_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-06-22 15:52:51 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND ( new_img . size ( )  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint8_t  * w  =  new_img . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  uint8_t  * r  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-04-27 16:19:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											memcpy ( w ,  & r [ ofs ] ,  new_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-09-30 17:21:10 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										width  =  MAX ( width  /  2 ,  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										height  =  MAX ( height  /  2 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										data  =  new_img ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Vector < uint8_t >  new_img ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND ( ! _can_modify ( format ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  ps  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_img . resize ( ( width  /  2 )  *  ( height  /  2 )  *  ps ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-06-22 15:52:51 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND ( new_img . size ( )  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-11-01 16:16:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND ( data . size ( )  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint8_t  * w  =  new_img . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  uint8_t  * r  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											switch  ( format )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  FORMAT_L8 : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  FORMAT_R8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  1 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( r ,  w ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_LA8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  2 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( r ,  w ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RG8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  2 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( r ,  w ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGB8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  3 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( r ,  w ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGBA8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  4 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( r ,  w ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  1 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( r ) ,  reinterpret_cast < float  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  2 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( r ) ,  reinterpret_cast < float  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGBF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  3 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( r ) ,  reinterpret_cast < float  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGBAF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  4 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( r ) ,  reinterpret_cast < float  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  1 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( r ) ,  reinterpret_cast < uint16_t  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  2 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( r ) ,  reinterpret_cast < uint16_t  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGBH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  3 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( r ) ,  reinterpret_cast < uint16_t  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGBAH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  4 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( r ) ,  reinterpret_cast < uint16_t  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  FORMAT_RGBE9995 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint32_t ,  1 ,  false ,  Image : : average_4_rgbe9995 ,  Image : : renormalize_rgbe9995 > ( reinterpret_cast < const  uint32_t  * > ( r ) ,  reinterpret_cast < uint32_t  * > ( w ) ,  width ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-09 17:08:36 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										width  / =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										height  / =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										data  =  new_img ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-05-04 12:36:51 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-07-03 10:55:50 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : normalize ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  used_mipmaps  =  has_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										clear_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  y  =  0 ;  y  <  height ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  x  =  0 ;  x  <  width ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Color  c  =  get_pixel ( x ,  y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector3  v ( c . r  *  2.0  -  1.0 ,  c . g  *  2.0  -  1.0 ,  c . b  *  2.0  -  1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											v . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											c . r  =  v . x  *  0.5  +  0.5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											c . g  =  v . y  *  0.5  +  0.5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											c . b  =  v . z  *  0.5  +  0.5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											set_pixel ( x ,  y ,  c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( used_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										generate_mipmaps ( true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : generate_mipmaps ( bool  p_renormalize )  {  
						 
					
						
							
								
									
										
										
										
											2019-08-26 18:21:19 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( ! _can_modify ( format ) ,  ERR_UNAVAILABLE ,  " Cannot generate mipmaps in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-29 19:30:43 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( format  = =  FORMAT_RGBA4444 ,  ERR_UNAVAILABLE ,  " Cannot generate mipmaps from RGBA4444 format. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-08-14 20:57:49 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( width  = =  0  | |  height  = =  0 ,  ERR_UNCONFIGURED ,  " Cannot generate mipmaps with width or height equal to 0. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-02-06 00:38:39 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mmcount ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  size  =  _get_dst_image_size ( width ,  height ,  format ,  mmcount ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									data . resize ( size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * wp  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-03-03 23:19:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  prev_ofs  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  prev_h  =  height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  prev_w  =  width ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-25 16:39:43 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  1 ;  i  < =  mmcount ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-03-03 23:19:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  ofs ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_get_mipmap_offset_and_size ( i ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-03-03 23:19:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										switch  ( format )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_L8 : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											case  FORMAT_R8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_generate_po2_mipmap < uint8_t ,  1 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( & wp [ prev_ofs ] ,  & wp [ ofs ] ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-03-03 23:19:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											case  FORMAT_LA8 : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											case  FORMAT_RG8 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_generate_po2_mipmap < uint8_t ,  2 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( & wp [ prev_ofs ] ,  & wp [ ofs ] ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											case  FORMAT_RGB8 : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  3 ,  true ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( & wp [ prev_ofs ] ,  & wp [ ofs ] ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  3 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( & wp [ prev_ofs ] ,  & wp [ ofs ] ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGBA8 : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  4 ,  true ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( & wp [ prev_ofs ] ,  & wp [ ofs ] ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint8_t ,  4 ,  false ,  Image : : average_4_uint8 ,  Image : : renormalize_uint8 > ( & wp [ prev_ofs ] ,  & wp [ ofs ] ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_generate_po2_mipmap < float ,  1 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < float  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGF : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_generate_po2_mipmap < float ,  2 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < float  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGBF : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  3 ,  true ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < float  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  3 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < float  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGBAF : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  4 ,  true ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < float  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < float ,  4 ,  false ,  Image : : average_4_float ,  Image : : renormalize_float > ( reinterpret_cast < const  float  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < float  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_generate_po2_mipmap < uint16_t ,  1 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint16_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGH : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_generate_po2_mipmap < uint16_t ,  2 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint16_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGBH : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  3 ,  true ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint16_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  3 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint16_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGBAH : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  4 ,  true ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint16_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint16_t ,  4 ,  false ,  Image : : average_4_half ,  Image : : renormalize_half > ( reinterpret_cast < const  uint16_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint16_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  FORMAT_RGBE9995 : 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_renormalize )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint32_t ,  1 ,  true ,  Image : : average_4_rgbe9995 ,  Image : : renormalize_rgbe9995 > ( reinterpret_cast < const  uint32_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint32_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_generate_po2_mipmap < uint32_t ,  1 ,  false ,  Image : : average_4_rgbe9995 ,  Image : : renormalize_rgbe9995 > ( reinterpret_cast < const  uint32_t  * > ( & wp [ prev_ofs ] ) ,  reinterpret_cast < uint32_t  * > ( & wp [ ofs ] ) ,  prev_w ,  prev_h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-09 17:08:36 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-03-03 23:19:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										prev_ofs  =  ofs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										prev_w  =  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										prev_h  =  h ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									mipmaps  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : generate_mipmap_roughness ( RoughnessChannel  p_roughness_channel ,  const  Ref < Image >  & p_normal_map )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  normal_sat_vec ;  //summed area table
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-23 09:34:26 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									double  * normal_sat  =  nullptr ;  //summed area table for normal map
 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  normal_w  =  0 ,  normal_h  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-23 09:34:26 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( p_normal_map . is_null ( )  | |  p_normal_map - > is_empty ( ) ,  ERR_INVALID_PARAMETER ,  " Must provide a valid normal map for roughness mipmaps " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  nm  =  p_normal_map - > duplicate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( nm - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										nm - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									normal_w  =  nm - > get_width ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									normal_h  =  nm - > get_height ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									normal_sat_vec . resize ( normal_w  *  normal_h  *  3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									normal_sat  =  normal_sat_vec . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//create summed area table
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  y  =  0 ;  y  <  normal_h ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										double  line_sum [ 3 ]  =  {  0 ,  0 ,  0  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  x  =  0 ;  x  <  normal_w ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											double  normal [ 3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Color  color  =  nm - > get_pixel ( x ,  y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											normal [ 0 ]  =  color . r  *  2.0  -  1.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											normal [ 1 ]  =  color . g  *  2.0  -  1.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											normal [ 2 ]  =  Math : : sqrt ( MAX ( 0.0 ,  1.0  -  ( normal [ 0 ]  *  normal [ 0 ]  +  normal [ 1 ]  *  normal [ 1 ] ) ) ) ;  //reconstruct if missing
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											line_sum [ 0 ]  + =  normal [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											line_sum [ 1 ]  + =  normal [ 1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											line_sum [ 2 ]  + =  normal [ 2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint32_t  ofs  =  ( y  *  normal_w  +  x )  *  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											normal_sat [ ofs  +  0 ]  =  line_sum [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											normal_sat [ ofs  +  1 ]  =  line_sum [ 1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											normal_sat [ ofs  +  2 ]  =  line_sum [ 2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( y  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												uint32_t  prev_ofs  =  ( ( y  -  1 )  *  normal_w  +  x )  *  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												normal_sat [ ofs  +  0 ]  + =  normal_sat [ prev_ofs  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												normal_sat [ ofs  +  1 ]  + =  normal_sat [ prev_ofs  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												normal_sat [ ofs  +  2 ]  + =  normal_sat [ prev_ofs  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								#if 0 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  beg ( normal_sat_vec [ 0 ] ,  normal_sat_vec [ 1 ] ,  normal_sat_vec [ 2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  end ( normal_sat_vec [ normal_sat_vec . size ( )  -  3 ] ,  normal_sat_vec [ normal_sat_vec . size ( )  -  2 ] ,  normal_sat_vec [ normal_sat_vec . size ( )  -  1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  avg  =  ( end  -  beg )  /  ( normal_w  *  normal_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										print_line ( " average:  "  +  avg ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mmcount ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_dst_image_size ( width ,  height ,  format ,  mmcount ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * base_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  1 ;  i  < =  mmcount ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  ofs ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_get_mipmap_offset_and_size ( i ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  * ptr  =  & base_ptr [ ofs ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  x  =  0 ;  x  <  w ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  y  =  0 ;  y  <  h ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  from_x  =  x  *  normal_w  /  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  from_y  =  y  *  normal_h  /  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  to_x  =  ( x  +  1 )  *  normal_w  /  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  to_y  =  ( y  +  1 )  *  normal_h  /  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												to_x  =  MIN ( to_x  -  1 ,  normal_w ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												to_y  =  MIN ( to_y  -  1 ,  normal_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  size_x  =  ( to_x  -  from_x )  +  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  size_y  =  ( to_y  -  from_y )  +  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												//summed area table version (much faster)
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												double  avg [ 3 ]  =  {  0 ,  0 ,  0  } ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( from_x  >  0  & &  from_y  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  tofs  =  ( ( from_y  -  1 )  *  normal_w  +  ( from_x  -  1 ) )  *  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 0 ]  + =  normal_sat [ tofs  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 1 ]  + =  normal_sat [ tofs  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 2 ]  + =  normal_sat [ tofs  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( from_y  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  tofs  =  ( ( from_y  -  1 )  *  normal_w  +  to_x )  *  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 0 ]  - =  normal_sat [ tofs  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 1 ]  - =  normal_sat [ tofs  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 2 ]  - =  normal_sat [ tofs  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( from_x  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint32_t  tofs  =  ( to_y  *  normal_w  +  ( from_x  -  1 ) )  *  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 0 ]  - =  normal_sat [ tofs  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 1 ]  - =  normal_sat [ tofs  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													avg [ 2 ]  - =  normal_sat [ tofs  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												uint32_t  tofs  =  ( to_y  *  normal_w  +  to_x )  *  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												avg [ 0 ]  + =  normal_sat [ tofs  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												avg [ 1 ]  + =  normal_sat [ tofs  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												avg [ 2 ]  + =  normal_sat [ tofs  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												double  div  =  double ( size_x  *  size_y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  vec ( avg [ 0 ]  /  div ,  avg [ 1 ]  /  div ,  avg [ 2 ]  /  div ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  r  =  vec . length ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  pixel_ofs  =  y  *  w  +  x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Color  c  =  _get_color_at_ofs ( ptr ,  pixel_ofs ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
											 
										
											
												Fix some -Wmaybe-uninitialized warnings
Namely:
```
modules/basis_universal/register_types.cpp: In function 'Ref<Image> basis_universal_unpacker(const Vector<unsigned char>&)':
modules/basis_universal/register_types.cpp:266:15: warning: 'imgfmt' may be used uninitialized in this function [-Wmaybe-uninitialized]
  266 |  image->create(info.m_width, info.m_height, info.m_total_levels > 1, imgfmt, gpudata);
      |  ~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
modules/basis_universal/register_types.cpp:255:39: warning: 'format' may be used uninitialized in this function [-Wmaybe-uninitialized]
  255 |    bool ret = tr.transcode_image_level(ptr, size, 0, i, dst + ofs, level.m_total_blocks - i, format);
      |               ~~~~~~~~~~~~~~~~~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
```
```
servers/visual_server.cpp: In member function 'Error VisualServer::_surface_set_data(Array, uint32_t, uint32_t*, uint32_t, Vector<unsigned char>&, int, Vector<unsigned char>&, int, AABB&, Vector<AABB>&)':
servers/visual_server.cpp:636:15: warning: 'iw' may be used uninitialized in this function [-Wmaybe-uninitialized]
  636 |       copymem(&iw[i * 2], &v, 2);
      |               ^
```
```
core/image.cpp: In member function 'Error Image::generate_mipmap_roughness(Image::RoughnessChannel, const Ref<Image>&)':
core/image.cpp:1683:11: warning: 'roughness' may be used uninitialized in this function [-Wmaybe-uninitialized]
 1683 |     float roughness;
      |           ^~~~~~~~~
```
											 
										 
										
											2020-03-27 12:36:59 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												float  roughness  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( p_roughness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_R :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														roughness  =  c . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_G :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														roughness  =  c . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_B :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														roughness  =  c . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_L :  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-23 20:01:26 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														roughness  =  c . get_v ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_A :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														roughness  =  c . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  variance  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( r  <  1.0f )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  r2  =  r  *  r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  kappa  =  ( 3.0f  *  r  -  r  *  r2 )  /  ( 1.0f  -  r2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													variance  =  0.25f  /  kappa ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  threshold  =  0.4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												roughness  =  Math : : sqrt ( roughness  *  roughness  +  MIN ( 3.0f  *  variance ,  threshold  *  threshold ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( p_roughness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_R :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . r  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_G :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . g  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_B :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . b  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_L :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . r  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . g  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . b  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  ROUGHNESS_CHANNEL_A :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														c . a  =  roughness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_set_color_at_ofs ( ptr ,  pixel_ofs ,  c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								#if 0 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  size  =  get_mipmap_byte_size ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											print_line ( " size for mimpap  "  +  itos ( i )  +  " :  "  +  itos ( size ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Vector < uint8_t >  imgdata ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											imgdata . resize ( size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint8_t *  wr  =  imgdata . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-27 16:19:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											memcpy ( wr . ptr ( ) ,  ptr ,  size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											wr  =  uint8_t * ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Ref < Image >  im  =  Image : : create_from_data ( w ,  h ,  false ,  format ,  imgdata ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											im - > save_png ( " res://mipmap_ "  +  itos ( i )  +  " .png " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								void  Image : : clear_mipmaps ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! mipmaps )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ofs ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( 1 ,  ofs ,  w ,  h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									data . resize ( ofs ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									mipmaps  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								bool  Image : : is_empty ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  ( data . size ( )  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < uint8_t >  Image : : get_data ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  Image : : create_empty ( int  p_width ,  int  p_height ,  bool  p_use_mipmaps ,  Format  p_format )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image - > initialize_data ( p_width ,  p_height ,  p_use_mipmaps ,  p_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Ref < Image >  Image : : create_from_data ( int  p_width ,  int  p_height ,  bool  p_use_mipmaps ,  Format  p_format ,  const  Vector < uint8_t >  & p_data )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image - > initialize_data ( p_width ,  p_height ,  p_use_mipmaps ,  p_format ,  p_data ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : set_data ( int  p_width ,  int  p_height ,  bool  p_use_mipmaps ,  Format  p_format ,  const  Vector < uint8_t >  & p_data )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									initialize_data ( p_width ,  p_height ,  p_use_mipmaps ,  p_format ,  p_data ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : initialize_data ( int  p_width ,  int  p_height ,  bool  p_use_mipmaps ,  Format  p_format )  {  
						 
					
						
							
								
									
										
										
										
											2022-04-11 01:11:00 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  < =  0 ,  " The Image width specified ( "  +  itos ( p_width )  +  "  pixels) must be greater than 0 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  < =  0 ,  " The Image height specified ( "  +  itos ( p_height )  +  "  pixels) must be greater than 0 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  >  MAX_WIDTH , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" The Image width specified ( "  +  itos ( p_width )  +  "  pixels) cannot be greater than  "  +  itos ( MAX_WIDTH )  +  " pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  >  MAX_HEIGHT , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" The Image height specified ( "  +  itos ( p_height )  +  "  pixels) cannot be greater than  "  +  itos ( MAX_HEIGHT )  +  " pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  *  p_height  >  MAX_PIXELS , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" Too many pixels for Image. Maximum is  "  +  itos ( MAX_WIDTH )  +  " x "  +  itos ( MAX_HEIGHT )  +  "  =  "  +  itos ( MAX_PIXELS )  +  " pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_MSG ( p_format ,  FORMAT_MAX ,  " The Image format specified ( "  +  itos ( p_format )  +  " ) is out of range. See Image's Format enum. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-05-05 16:46:51 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  mm  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  size  =  _get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  p_use_mipmaps  ?  - 1  :  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									data . resize ( size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-27 16:19:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										memset ( w ,  0 ,  size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									width  =  p_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									height  =  p_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mipmaps  =  p_use_mipmaps ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									format  =  p_format ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : initialize_data ( int  p_width ,  int  p_height ,  bool  p_use_mipmaps ,  Format  p_format ,  const  Vector < uint8_t >  & p_data )  {  
						 
					
						
							
								
									
										
										
										
											2022-04-11 01:11:00 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  < =  0 ,  " The Image width specified ( "  +  itos ( p_width )  +  "  pixels) must be greater than 0 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  < =  0 ,  " The Image height specified ( "  +  itos ( p_height )  +  "  pixels) must be greater than 0 pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  >  MAX_WIDTH , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" The Image width specified ( "  +  itos ( p_width )  +  "  pixels) cannot be greater than  "  +  itos ( MAX_WIDTH )  +  "  pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_height  >  MAX_HEIGHT , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" The Image height specified ( "  +  itos ( p_height )  +  "  pixels) cannot be greater than  "  +  itos ( MAX_HEIGHT )  +  "  pixels. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_width  *  p_height  >  MAX_PIXELS , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" Too many pixels for Image. Maximum is  "  +  itos ( MAX_WIDTH )  +  " x "  +  itos ( MAX_HEIGHT )  +  "  =  "  +  itos ( MAX_PIXELS )  +  " pixels . " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_MSG ( p_format ,  FORMAT_MAX ,  " The Image format specified ( "  +  itos ( p_format )  +  " ) is out of range. See Image's Format enum. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  mm ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  size  =  _get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  p_use_mipmaps  ?  - 1  :  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-11 01:11:00 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( unlikely ( p_data . size ( )  ! =  size ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  description_mipmaps ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_use_mipmaps )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  num_mipmaps  =  get_image_required_mipmaps ( p_width ,  p_height ,  p_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( num_mipmaps  ! =  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												description_mipmaps  =  vformat ( " with %d mipmaps " ,  num_mipmaps ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												description_mipmaps  =  " with 1 mipmap " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											description_mipmaps  =  " without mipmaps " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  String  description  =  vformat ( " %dx%dx%d (%s) " ,  p_width ,  p_height ,  get_format_pixel_size ( p_format ) ,  description_mipmaps ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_MSG ( vformat ( " Expected Image data size of %s = %d bytes, got %d bytes instead. " ,  description ,  size ,  p_data . size ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									height  =  p_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									width  =  p_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									format  =  p_format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									data  =  p_data ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									mipmaps  =  p_use_mipmaps ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : initialize_data ( const  char  * * p_xpm )  {  
						 
					
						
							
								
									
										
										
										
											2018-10-04 18:54:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  size_width  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  size_height  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  pixelchars  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mipmaps  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  has_alpha  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									enum  Status  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										READING_HEADER , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										READING_COLORS , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										READING_PIXELS , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										DONE 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Status  status  =  READING_HEADER ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  line  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									HashMap < String ,  Color >  colormap ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-10-04 18:54:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  colormap_size  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  pixel_size  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-13 13:09:56 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * data_write  =  nullptr ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									while  ( status  ! =  DONE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  char  * line_ptr  =  p_xpm [ line ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										switch  ( status )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											case  READING_HEADER :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  line_str  =  line_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												line_str . replace ( " \t " ,  "   " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												size_width  =  line_str . get_slicec ( '   ' ,  0 ) . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												size_height  =  line_str . get_slicec ( '   ' ,  1 ) . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												colormap_size  =  line_str . get_slicec ( '   ' ,  2 ) . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												pixelchars  =  line_str . get_slicec ( '   ' ,  3 ) . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND ( colormap_size  >  32766 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND ( pixelchars  >  5 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND ( size_width  >  32767 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND ( size_height  >  32767 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												status  =  READING_COLORS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  READING_COLORS :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  colorstring ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  i  =  0 ;  i  <  pixelchars ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													colorstring  + =  * line_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													line_ptr + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												//skip spaces
 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												while  ( * line_ptr  = =  '   '  | |  * line_ptr  = =  ' \t '  | |  * line_ptr  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( * line_ptr  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													line_ptr + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( * line_ptr  = =  ' c ' )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													line_ptr + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													while  ( * line_ptr  = =  '   '  | |  * line_ptr  = =  ' \t '  | |  * line_ptr  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( * line_ptr  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														line_ptr + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( * line_ptr  = =  ' # ' )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														line_ptr + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-09-01 22:33:39 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														uint8_t  col_r  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														uint8_t  col_g  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														uint8_t  col_b  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														//uint8_t col_a=255;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														for  ( int  i  =  0 ;  i  <  6 ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															char  v  =  line_ptr [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-04 10:32:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															if  ( is_digit ( v ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																v  - =  ' 0 ' ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															}  else  if  ( v  > =  ' A '  & &  v  < =  ' F ' )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																v  =  ( v  -  ' A ' )  +  10 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															}  else  if  ( v  > =  ' a '  & &  v  < =  ' f ' )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																v  =  ( v  -  ' a ' )  +  10 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															switch  ( i )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																case  0 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	col_r  =  v  < <  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																case  1 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	col_r  | =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																case  2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	col_g  =  v  < <  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																case  3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	col_g  | =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																case  4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	col_b  =  v  < <  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																case  5 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	col_b  | =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-19 15:46:49 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// magenta mask
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( col_r  = =  255  & &  col_g  = =  0  & &  col_b  = =  255 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															colormap [ colorstring ]  =  Color ( 0 ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															has_alpha  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															colormap [ colorstring ]  =  Color ( col_r  /  255.0 ,  col_g  /  255.0 ,  col_b  /  255.0 ,  1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( line  = =  colormap_size )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													status  =  READING_PIXELS ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													initialize_data ( size_width ,  size_height ,  false ,  has_alpha  ?  FORMAT_RGBA8  :  FORMAT_RGB8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-13 13:09:56 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													data_write  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													pixel_size  =  has_alpha  ?  4  :  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  READING_PIXELS :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  y  =  line  -  colormap_size  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  x  =  0 ;  x  <  size_width ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													char  pixelstr [ 6 ]  =  {  0 ,  0 ,  0 ,  0 ,  0 ,  0  } ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  pixelchars ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														pixelstr [ i ]  =  line_ptr [ x  *  pixelchars  +  i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Color  * colorptr  =  colormap . getptr ( pixelstr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_COND ( ! colorptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													uint8_t  pixel [ 4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( uint32_t  i  =  0 ;  i  <  pixel_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														pixel [ i ]  =  CLAMP ( ( * colorptr ) [ i ]  *  255 ,  0 ,  255 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-13 13:09:56 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													_put_pixelb ( x ,  y ,  pixel_size ,  data_write ,  pixel ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( y  = =  ( size_height  -  1 ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													status  =  DONE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-09 17:08:36 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-09 00:00:52 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										line + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2017-07-08 22:12:18 +07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define DETECT_ALPHA_MAX_THRESHOLD 254 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# define DETECT_ALPHA_MIN_THRESHOLD 2 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# define DETECT_ALPHA(m_value)                          \ 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{                                                   \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  value  =  m_value ;                        \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( value  <  DETECT_ALPHA_MIN_THRESHOLD )         \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bit  =  true ;                                 \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										else  if  ( value  <  DETECT_ALPHA_MAX_THRESHOLD )  {  \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											detected  =  true ;                            \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ;                                      \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}                                               \
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define DETECT_NON_ALPHA(m_value) \ 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{                              \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  value  =  m_value ;   \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( value  >  0 )  {           \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											detected  =  true ;       \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ;                 \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}                          \
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								bool  Image : : is_invisible ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( format  = =  FORMAT_L8  | | 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											format  = =  FORMAT_RGB8  | |  format  = =  FORMAT_RG8 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  len  =  data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( len  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( 1 ,  len ,  w ,  h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * r  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  unsigned  char  * data_ptr  =  r ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  detected  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( format )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_LA8 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  ( len  > >  1 ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												DETECT_NON_ALPHA ( data_ptr [ ( i  < <  1 )  +  1 ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBA8 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  ( len  > >  2 ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												DETECT_NON_ALPHA ( data_ptr [ ( i  < <  2 )  +  3 ] ) 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_DXT3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											detected  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-09 17:08:36 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2015-06-01 19:42:34 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ! detected ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								Image : : AlphaMode  Image : : detect_alpha ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  len  =  data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( len  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ALPHA_NONE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_mipmap_offset_and_size ( 1 ,  len ,  w ,  h ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * r  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  unsigned  char  * data_ptr  =  r ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  bit  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  detected  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( format )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_LA8 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  ( len  > >  1 ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												DETECT_ALPHA ( data_ptr [ ( i  < <  1 )  +  1 ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBA8 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  ( len  > >  2 ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												DETECT_ALPHA ( data_ptr [ ( i  < <  2 )  +  3 ] ) 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_DXT3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_DXT5 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											detected  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-09 17:08:36 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( detected )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ALPHA_BLEND ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( bit )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ALPHA_BIT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ALPHA_NONE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : load ( const  String  & p_path )  {  
						 
					
						
							
								
									
										
										
										
											2018-08-14 16:52:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# ifdef DEBUG_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_path . begins_with ( " res:// " )  & &  ResourceLoader : : exists ( p_path ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-11-07 09:44:15 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										WARN_PRINT ( " Loaded resource as image file, this will not work on export: ' "  +  p_path  +  " '. Instead, import the image file as an Image resource and load it normally as a resource. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-14 16:52:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  ImageLoader : : load_image ( p_path ,  this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-05-04 01:49:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  Image : : load_from_file ( const  String  & p_path )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef DEBUG_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_path . begins_with ( " res:// " )  & &  ResourceLoader : : exists ( p_path ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										WARN_PRINT ( " Loaded resource as image file, this will not work on export: ' "  +  p_path  +  " '. Instead, import the image file as an Image resource and load it normally as a resource. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  ImageLoader : : load_image ( p_path ,  image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_V_MSG ( Ref < Image > ( ) ,  vformat ( " Failed to load image. Error %d " ,  err ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-04-29 20:14:14 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : save_png ( const  String  & p_path )  const  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( save_png_func  = =  nullptr )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-11-13 00:53:12 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  ERR_UNAVAILABLE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-11-13 00:53:12 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-09 00:23:50 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  save_png_func ( p_path ,  Ref < Image > ( ( Image  * ) this ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
											 
										
											
												Implement Running Godot as Movie Writer
* Allows running the game in "movie writer" mode.
* It ensures entirely stable framerate, so your run can be saved stable and with proper sound (which is impossible if your CPU/GPU can't sustain doing this in real-time).
* If disabling vsync, it can save movies faster than the game is run, but if you want to control the interaction it can get difficult.
* Implements a simple, default MJPEG writer.
This new features has two main use cases, which have high demand:
* Saving game videos in high quality and ensuring the frame rate is *completely* stable, always.
* Using Godot as a tool to make movies and animations (which is ideal if you want interaction, or creating them procedurally. No other software is as good for this).
**Note**: This feature **IS NOT** for capturing real-time footage. Use something like OBS, SimpleScreenRecorder or FRAPS to achieve that, as they do a much better job at intercepting the compositor than Godot can probably do using Vulkan or OpenGL natively. If your game runs near real-time when capturing, you can still use this feature but it will play no sound (sound will be saved directly).
Usage:
$ godot --write-movie movie.avi [scene_file.tscn]
Missing:
* Options for configuring video writing via GLOBAL_DEF
* UI Menu for launching with this mode from the editor.
* Add to list of command line options.
* Add a feature tag to override configurations when movie writing (fantastic for saving videos with highest quality settings).
											 
										 
										
											2022-06-17 00:55:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : save_jpg ( const  String  & p_path ,  float  p_quality )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( save_jpg_func  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  ERR_UNAVAILABLE ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  save_jpg_func ( p_path ,  Ref < Image > ( ( Image  * ) this ) ,  p_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < uint8_t >  Image : : save_png_to_buffer ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( save_png_buffer_func  = =  nullptr )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  Vector < uint8_t > ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-10-31 19:54:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  save_png_buffer_func ( Ref < Image > ( ( Image  * ) this ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
											 
										
											
												Implement Running Godot as Movie Writer
* Allows running the game in "movie writer" mode.
* It ensures entirely stable framerate, so your run can be saved stable and with proper sound (which is impossible if your CPU/GPU can't sustain doing this in real-time).
* If disabling vsync, it can save movies faster than the game is run, but if you want to control the interaction it can get difficult.
* Implements a simple, default MJPEG writer.
This new features has two main use cases, which have high demand:
* Saving game videos in high quality and ensuring the frame rate is *completely* stable, always.
* Using Godot as a tool to make movies and animations (which is ideal if you want interaction, or creating them procedurally. No other software is as good for this).
**Note**: This feature **IS NOT** for capturing real-time footage. Use something like OBS, SimpleScreenRecorder or FRAPS to achieve that, as they do a much better job at intercepting the compositor than Godot can probably do using Vulkan or OpenGL natively. If your game runs near real-time when capturing, you can still use this feature but it will play no sound (sound will be saved directly).
Usage:
$ godot --write-movie movie.avi [scene_file.tscn]
Missing:
* Options for configuring video writing via GLOBAL_DEF
* UI Menu for launching with this mode from the editor.
* Add to list of command line options.
* Add a feature tag to override configurations when movie writing (fantastic for saving videos with highest quality settings).
											 
										 
										
											2022-06-17 00:55:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < uint8_t >  Image : : save_jpg_to_buffer ( float  p_quality )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( save_jpg_buffer_func  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Vector < uint8_t > ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  save_jpg_buffer_func ( Ref < Image > ( ( Image  * ) this ) ,  p_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-08-03 01:07:13 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : save_exr ( const  String  & p_path ,  bool  p_grayscale )  const  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( save_exr_func  = =  nullptr )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-03 01:07:13 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  ERR_UNAVAILABLE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-03 01:07:13 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  save_exr_func ( p_path ,  Ref < Image > ( ( Image  * ) this ) ,  p_grayscale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-06-23 20:55:37 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < uint8_t >  Image : : save_exr_to_buffer ( bool  p_grayscale )  const  {  
						 
					
						
							
								
									
										
										
										
											2022-06-19 18:55:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( save_exr_buffer_func  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Vector < uint8_t > ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-06-23 20:55:37 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  save_exr_buffer_func ( Ref < Image > ( ( Image  * ) this ) ,  p_grayscale ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-06-19 18:55:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-06-04 16:05:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : save_webp ( const  String  & p_path ,  const  bool  p_lossy ,  const  float  p_quality )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( save_webp_func  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  ERR_UNAVAILABLE ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( p_lossy  & &  ! ( 0.0f  < =  p_quality  & &  p_quality  < =  1.0f ) ,  ERR_INVALID_PARAMETER ,  " The WebP lossy quality was set to  "  +  rtos ( p_quality )  +  " , which is not valid. WebP lossy quality must be between 0.0 and 1.0 (inclusive). " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  save_webp_func ( p_path ,  Ref < Image > ( ( Image  * ) this ) ,  p_lossy ,  p_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Vector < uint8_t >  Image : : save_webp_to_buffer ( const  bool  p_lossy ,  const  float  p_quality )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( save_webp_buffer_func  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Vector < uint8_t > ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( p_lossy  & &  ! ( 0.0f  < =  p_quality  & &  p_quality  < =  1.0f ) ,  Vector < uint8_t > ( ) ,  " The WebP lossy quality was set to  "  +  rtos ( p_quality )  +  " , which is not valid. WebP lossy quality must be between 0.0 and 1.0 (inclusive). " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  save_webp_buffer_func ( Ref < Image > ( ( Image  * ) this ) ,  p_lossy ,  p_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-06 14:56:06 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_image_data_size ( int  p_width ,  int  p_height ,  Format  p_format ,  bool  p_mipmaps )  {  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									int  mm ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-06 14:56:06 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  p_mipmaps  ?  - 1  :  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								int  Image : : get_image_required_mipmaps ( int  p_width ,  int  p_height ,  Format  p_format )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mm ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  mm ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-07-27 10:23:24 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Size2i  Image : : get_image_mipmap_size ( int  p_width ,  int  p_height ,  Format  p_format ,  int  p_mipmap )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mm ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Size2i  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  p_mipmap ,  & ret . x ,  & ret . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-11-16 19:12:00 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_image_mipmap_offset ( int  p_width ,  int  p_height ,  Format  p_format ,  int  p_mipmap )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_mipmap  < =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mm ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  p_mipmap  -  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  Image : : get_image_mipmap_offset_and_dimensions ( int  p_width ,  int  p_height ,  Format  p_format ,  int  p_mipmap ,  int  & r_w ,  int  & r_h )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_mipmap  < =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_w  =  p_width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_h  =  p_height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mm ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _get_dst_image_size ( p_width ,  p_height ,  p_format ,  mm ,  p_mipmap  -  1 ,  & r_w ,  & r_h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-05-31 01:59:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								bool  Image : : is_compressed ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  format  >  FORMAT_RGBE9995 ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-05-31 01:59:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-06-11 10:41:03 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : decompress ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ( ( format  > =  FORMAT_DXT1  & &  format  < =  FORMAT_RGTC_RG )  | |  ( format  = =  FORMAT_DXT5_RA_AS_RG ) )  & &  _image_decompress_bc )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-29 20:14:14 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_image_decompress_bc ( this ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( format  > =  FORMAT_BPTC_RGBA  & &  format  < =  FORMAT_BPTC_RGBFU  & &  _image_decompress_bptc )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_image_decompress_bptc ( this ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( format  = =  FORMAT_ETC  & &  _image_decompress_etc1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-26 10:49:08 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_image_decompress_etc1 ( this ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( format  > =  FORMAT_ETC2_R11  & &  format  < =  FORMAT_ETC2_RA_AS_RG  & &  _image_decompress_etc2 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_image_decompress_etc2 ( this ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-11 10:41:03 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  ERR_UNAVAILABLE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-11 10:41:03 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-16 21:47:28 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : compress ( CompressMode  p_mode ,  CompressSource  p_source ,  float  p_lossy_quality )  {  
						 
					
						
							
								
									
										
										
										
											2021-06-25 13:50:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V_MSG ( p_mode ,  COMPRESS_MAX ,  ERR_INVALID_PARAMETER ,  " Invalid compress mode. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V_MSG ( p_source ,  COMPRESS_SOURCE_MAX ,  ERR_INVALID_PARAMETER ,  " Invalid compress source. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  compress_from_channels ( p_mode ,  detect_used_channels ( p_source ) ,  p_lossy_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2020-05-14 14:29:06 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : compress_from_channels ( CompressMode  p_mode ,  UsedChannels  p_channels ,  float  p_lossy_quality )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( p_mode )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  COMPRESS_S3TC :  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! _image_compress_bc_func ,  ERR_UNAVAILABLE ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_image_compress_bc_func ( this ,  p_lossy_quality ,  p_channels ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  COMPRESS_ETC :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-26 10:49:08 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! _image_compress_etc1_func ,  ERR_UNAVAILABLE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_image_compress_etc1_func ( this ,  p_lossy_quality ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  COMPRESS_ETC2 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-04-26 10:49:08 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! _image_compress_etc2_func ,  ERR_UNAVAILABLE ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_image_compress_etc2_func ( this ,  p_lossy_quality ,  p_channels ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  COMPRESS_BPTC :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! _image_compress_bptc_func ,  ERR_UNAVAILABLE ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_image_compress_bptc_func ( this ,  p_lossy_quality ,  p_channels ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-25 13:50:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  COMPRESS_MAX :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V ( ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Image : : Image ( const  char  * * p_xpm )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									width  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									height  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mipmaps  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									format  =  FORMAT_L8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									initialize_data ( p_xpm ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Image : : Image ( int  p_width ,  int  p_height ,  bool  p_use_mipmaps ,  Format  p_format )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									width  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									height  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mipmaps  =  p_use_mipmaps ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									format  =  FORMAT_L8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									initialize_data ( p_width ,  p_height ,  p_use_mipmaps ,  p_format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Image : : Image ( int  p_width ,  int  p_height ,  bool  p_mipmaps ,  Format  p_format ,  const  Vector < uint8_t >  & p_data )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									width  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									height  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mipmaps  =  p_mipmaps ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									format  =  FORMAT_L8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									initialize_data ( p_width ,  p_height ,  p_mipmaps ,  p_format ,  p_data ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Rect2i  Image : : get_used_rect ( )  const  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( format  ! =  FORMAT_LA8  & &  format  ! =  FORMAT_RGBA8  & &  format  ! =  FORMAT_RGBAF  & &  format  ! =  FORMAT_RGBAH  & &  format  ! =  FORMAT_RGBA4444  & &  format  ! =  FORMAT_RGB565 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  Rect2i ( 0 ,  0 ,  width ,  height ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  len  =  data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( len  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  Rect2i ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  minx  =  0xFFFFFF ,  miny  =  0xFFFFFFF ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  maxx  =  - 1 ,  maxy  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  j  =  0 ;  j  <  height ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  width ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( ! ( get_pixel ( i ,  j ) . a  >  0 ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( i  >  maxx )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												maxx  =  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( j  >  maxy )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												maxy  =  j ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( i  <  minx )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												minx  =  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( j  <  miny )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												miny  =  j ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( maxx  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  Rect2i ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  Rect2i ( minx ,  miny ,  maxx  -  minx  +  1 ,  maxy  -  miny  +  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  Image : : get_rect ( const  Rect2i  & p_area )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Image >  img  =  memnew ( Image ( p_area . size . x ,  p_area . size . y ,  mipmaps ,  format ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									img - > blit_rect ( Ref < Image > ( ( Image  * ) this ) ,  p_area ,  Point2i ( 0 ,  0 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  img ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : _get_clipped_src_and_dest_rects ( const  Ref < Image >  & p_src ,  const  Rect2i  & p_src_rect ,  const  Point2i  & p_dest ,  Rect2i  & r_clipped_src_rect ,  Rect2i  & r_clipped_dest_rect )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_clipped_dest_rect . position  =  p_dest ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_clipped_src_rect  =  p_src_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_clipped_src_rect . position . x  <  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_dest_rect . position . x  - =  r_clipped_src_rect . position . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . size . x  + =  r_clipped_src_rect . position . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . position . x  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_clipped_src_rect . position . y  <  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_dest_rect . position . y  - =  r_clipped_src_rect . position . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . size . y  + =  r_clipped_src_rect . position . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . position . y  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_clipped_dest_rect . position . x  <  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . position . x  - =  r_clipped_dest_rect . position . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . size . x  + =  r_clipped_dest_rect . position . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_dest_rect . position . x  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_clipped_dest_rect . position . y  <  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . position . y  - =  r_clipped_dest_rect . position . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_src_rect . size . y  + =  r_clipped_dest_rect . position . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_clipped_dest_rect . position . y  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_clipped_src_rect . size . x  =  MAX ( 0 ,  MIN ( r_clipped_src_rect . size . x ,  MIN ( p_src - > width  -  r_clipped_src_rect . position . x ,  width  -  r_clipped_dest_rect . position . x ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_clipped_src_rect . size . y  =  MAX ( 0 ,  MIN ( r_clipped_src_rect . size . y ,  MIN ( p_src - > height  -  r_clipped_src_rect . position . y ,  height  -  r_clipped_dest_rect . position . y ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_clipped_dest_rect . size . x  =  r_clipped_src_rect . size . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_clipped_dest_rect . size . y  =  r_clipped_src_rect . size . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : blit_rect ( const  Ref < Image >  & p_src ,  const  Rect2i  & p_src_rect ,  const  Point2i  & p_dest )  {  
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src . is_null ( ) ,  " It's not a reference to a valid Image object. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  dsize  =  data . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  srcdsize  =  p_src - > data . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( dsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( srcdsize  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  p_src - > format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-28 12:35:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot blit_rect in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rect2i  src_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Rect2i  dest_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_clipped_src_and_dest_rects ( p_src ,  p_src_rect ,  p_dest ,  src_rect ,  dest_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-14 21:51:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! src_rect . has_area ( )  | |  ! dest_rect . has_area ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-14 15:56:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * wp  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint8_t  * dst_data_ptr  =  wp ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * rp  =  p_src - > data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint8_t  * src_data_ptr  =  rp ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-14 15:56:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  dest_rect . size . y ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  dest_rect . size . x ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  src_x  =  src_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  src_y  =  src_rect . position . y  +  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-14 15:56:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  dst_x  =  dest_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  dst_y  =  dest_rect . position . y  +  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  uint8_t  * src  =  & src_data_ptr [ ( src_y  *  p_src - > width  +  src_x )  *  pixel_size ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint8_t  * dst  =  & dst_data_ptr [ ( dst_y  *  width  +  dst_x )  *  pixel_size ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  k  =  0 ;  k  <  pixel_size ;  k + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												dst [ k ]  =  src [ k ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : blit_rect_mask ( const  Ref < Image >  & p_src ,  const  Ref < Image >  & p_mask ,  const  Rect2i  & p_src_rect ,  const  Point2i  & p_dest )  {  
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src . is_null ( ) ,  " It's not a reference to a valid Image object. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_mask . is_null ( ) ,  " It's not a reference to a valid Image object. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  dsize  =  data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  srcdsize  =  p_src - > data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  maskdsize  =  p_mask - > data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( dsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( srcdsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( maskdsize  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src - > width  ! =  p_mask - > width ,  " Source image width is different from mask width. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src - > height  ! =  p_mask - > height ,  " Source image height is different from mask height. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  p_src - > format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rect2i  src_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Rect2i  dest_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_clipped_src_and_dest_rects ( p_src ,  p_src_rect ,  p_dest ,  src_rect ,  dest_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-14 21:51:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! src_rect . has_area ( )  | |  ! dest_rect . has_area ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * wp  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint8_t  * dst_data_ptr  =  wp ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * rp  =  p_src - > data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint8_t  * src_data_ptr  =  rp ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-07-08 22:12:18 +07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Image >  msk  =  p_mask ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  dest_rect . size . y ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  dest_rect . size . x ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  src_x  =  src_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  src_y  =  src_rect . position . y  +  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-07-08 22:12:18 +07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-06-24 08:53:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( msk - > get_pixel ( src_x ,  src_y ) . a  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  dst_x  =  dest_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  dst_y  =  dest_rect . position . y  +  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  uint8_t  * src  =  & src_data_ptr [ ( src_y  *  p_src - > width  +  src_x )  *  pixel_size ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												uint8_t  * dst  =  & dst_data_ptr [ ( dst_y  *  width  +  dst_x )  *  pixel_size ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  k  =  0 ;  k  <  pixel_size ;  k + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst [ k ]  =  src [ k ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : blend_rect ( const  Ref < Image >  & p_src ,  const  Rect2i  & p_src_rect ,  const  Point2i  & p_dest )  {  
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src . is_null ( ) ,  " It's not a reference to a valid Image object. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  dsize  =  data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  srcdsize  =  p_src - > data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( dsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( srcdsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  p_src - > format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rect2i  src_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Rect2i  dest_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_clipped_src_and_dest_rects ( p_src ,  p_src_rect ,  p_dest ,  src_rect ,  dest_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-14 21:51:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! src_rect . has_area ( )  | |  ! dest_rect . has_area ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  img  =  p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  dest_rect . size . y ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  dest_rect . size . x ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  src_x  =  src_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  src_y  =  src_rect . position . y  +  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  dst_x  =  dest_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  dst_y  =  dest_rect . position . y  +  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Color  sc  =  img - > get_pixel ( src_x ,  src_y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-01 14:05:33 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( sc . a  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Color  dc  =  get_pixel ( dst_x ,  dst_y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												dc  =  dc . blend ( sc ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												set_pixel ( dst_x ,  dst_y ,  dc ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : blend_rect_mask ( const  Ref < Image >  & p_src ,  const  Ref < Image >  & p_mask ,  const  Rect2i  & p_src_rect ,  const  Point2i  & p_dest )  {  
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src . is_null ( ) ,  " It's not a reference to a valid Image object. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_mask . is_null ( ) ,  " It's not a reference to a valid Image object. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  dsize  =  data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  srcdsize  =  p_src - > data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  maskdsize  =  p_mask - > data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( dsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( srcdsize  = =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( maskdsize  = =  0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-25 10:28:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src - > width  ! =  p_mask - > width ,  " Source image width is different from mask width. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( p_src - > height  ! =  p_mask - > height ,  " Source image height is different from mask height. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  p_src - > format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Rect2i  src_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Rect2i  dest_rect ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_get_clipped_src_and_dest_rects ( p_src ,  p_src_rect ,  p_dest ,  src_rect ,  dest_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-14 21:51:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! src_rect . has_area ( )  | |  ! dest_rect . has_area ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  img  =  p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  msk  =  p_mask ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  dest_rect . size . y ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  dest_rect . size . x ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-07-05 10:48:25 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  src_x  =  src_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  src_y  =  src_rect . position . y  +  i ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// If the mask's pixel is transparent then we skip it
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											//Color c = msk->get_pixel(src_x, src_y);
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											//if (c.a == 0) continue;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( msk - > get_pixel ( src_x ,  src_y ) . a  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  dst_x  =  dest_rect . position . x  +  j ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  dst_y  =  dest_rect . position . y  +  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Color  sc  =  img - > get_pixel ( src_x ,  src_y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-01 14:05:33 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( sc . a  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Color  dc  =  get_pixel ( dst_x ,  dst_y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dc  =  dc . blend ( sc ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													set_pixel ( dst_x ,  dst_y ,  dc ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 10:16:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// Repeats `p_pixel` `p_count` times in consecutive memory.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// Results in the original pixel and `p_count - 1` subsequent copies of it.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : _repeat_pixel_over_subsequent_memory ( uint8_t  * p_pixel ,  int  p_pixel_size ,  int  p_count )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  offset  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  stride  =  1 ;  offset  +  stride  < =  p_count ;  stride  * =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										memcpy ( p_pixel  +  offset  *  p_pixel_size ,  p_pixel ,  stride  *  p_pixel_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										offset  + =  stride ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( offset  <  p_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										memcpy ( p_pixel  +  offset  *  p_pixel_size ,  p_pixel ,  ( p_count  -  offset )  *  p_pixel_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : fill ( const  Color  & p_color )  {  
						 
					
						
							
								
									
										
										
										
											2020-01-28 12:35:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot fill in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * dst_data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Put first pixel with the format-aware API.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_set_color_at_ofs ( dst_data_ptr ,  0 ,  p_color ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 10:16:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_repeat_pixel_over_subsequent_memory ( dst_data_ptr ,  pixel_size ,  width  *  height ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-09 15:43:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : fill_rect ( const  Rect2i  & p_rect ,  const  Color  & p_color )  {  
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot fill rect in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Rect2i  r  =  Rect2i ( 0 ,  0 ,  width ,  height ) . intersection ( p_rect . abs ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-14 21:51:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! r . has_area ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint8_t  * dst_data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Put first pixel with the format-aware API.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint8_t  * rect_first_pixel_ptr  =  & dst_data_ptr [ ( r . position . y  *  width  +  r . position . x )  *  pixel_size ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_set_color_at_ofs ( rect_first_pixel_ptr ,  0 ,  p_color ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 10:16:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( r . size . x  = =  width )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// No need to fill rows separately.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_repeat_pixel_over_subsequent_memory ( rect_first_pixel_ptr ,  pixel_size ,  width  *  r . size . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_repeat_pixel_over_subsequent_memory ( rect_first_pixel_ptr ,  pixel_size ,  r . size . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  y  =  1 ;  y  <  r . size . y ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( rect_first_pixel_ptr  +  y  *  width  *  pixel_size ,  rect_first_pixel_ptr ,  r . size . x  *  pixel_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								ImageMemLoadFunc  Image : : _png_mem_loader_func  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								ImageMemLoadFunc  Image : : _jpg_mem_loader_func  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								ImageMemLoadFunc  Image : : _webp_mem_loader_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2020-05-21 13:46:44 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								ImageMemLoadFunc  Image : : _tga_mem_loader_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2020-10-20 23:25:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								ImageMemLoadFunc  Image : : _bmp_mem_loader_func  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_compress_bc_func ) ( Image  * ,  float ,  Image : : UsedChannels )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_compress_bptc_func ) ( Image  * ,  float ,  Image : : UsedChannels )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_compress_etc1_func ) ( Image  * ,  float )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_compress_etc2_func ) ( Image  * ,  float ,  Image : : UsedChannels )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_decompress_bc ) ( Image  * )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_decompress_bptc ) ( Image  * )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_decompress_etc1 ) ( Image  * )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  ( * Image : : _image_decompress_etc2 ) ( Image  * )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-04-12 18:56:50 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < uint8_t >  ( * Image : : webp_lossy_packer ) ( const  Ref < Image >  & ,  float )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Vector < uint8_t >  ( * Image : : webp_lossless_packer ) ( const  Ref < Image >  & )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Ref < Image >  ( * Image : : webp_unpacker ) ( const  Vector < uint8_t >  & )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Vector < uint8_t >  ( * Image : : png_packer ) ( const  Ref < Image >  & )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Ref < Image >  ( * Image : : png_unpacker ) ( const  Vector < uint8_t >  & )  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2020-04-02 01:20:12 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < uint8_t >  ( * Image : : basis_universal_packer ) ( const  Ref < Image >  & ,  Image : : UsedChannels )  =  nullptr ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Ref < Image >  ( * Image : : basis_universal_unpacker ) ( const  Vector < uint8_t >  & )  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2022-03-24 18:18:55 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  ( * Image : : basis_universal_unpacker_ptr ) ( const  uint8_t  * ,  int )  =  nullptr ;  
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : _set_data ( const  Dictionary  & p_data )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! p_data . has ( " width " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! p_data . has ( " height " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! p_data . has ( " format " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! p_data . has ( " mipmaps " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! p_data . has ( " data " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  dwidth  =  p_data [ " width " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  dheight  =  p_data [ " height " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									String  dformat  =  p_data [ " format " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  dmipmaps  =  p_data [ " mipmaps " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector < uint8_t >  ddata  =  p_data [ " data " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Format  ddformat  =  FORMAT_MAX ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  FORMAT_MAX ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( dformat  = =  get_format_name ( Format ( i ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ddformat  =  Format ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ddformat  = =  FORMAT_MAX ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									initialize_data ( dwidth ,  dheight ,  dmipmaps ,  ddformat ,  ddata ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Dictionary  Image : : _get_data ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									d [ " width " ]  =  width ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									d [ " height " ]  =  height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									d [ " format " ]  =  get_format_name ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									d [ " mipmaps " ]  =  mipmaps ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									d [ " data " ]  =  data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-11-21 02:42:29 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Color  Image : : get_pixelv ( const  Point2i  & p_point )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  get_pixel ( p_point . x ,  p_point . y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 15:17:06 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Color  Image : : _get_color_at_ofs ( const  uint8_t  * ptr ,  uint32_t  ofs )  const  {  
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( format )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  l  =  ptr [ ofs ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( l ,  l ,  l ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_LA8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  l  =  ptr [ ofs  *  2  +  0 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  a  =  ptr [ ofs  *  2  +  1 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( l ,  l ,  l ,  a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_R8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ptr [ ofs ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  0 ,  0 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RG8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ptr [ ofs  *  2  +  0 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ptr [ ofs  *  2  +  1 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  0 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGB8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ptr [ ofs  *  3  +  0 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ptr [ ofs  *  3  +  1 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  b  =  ptr [ ofs  *  3  +  2 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  b ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBA8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ptr [ ofs  *  4  +  0 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ptr [ ofs  *  4  +  1 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  b  =  ptr [ ofs  *  4  +  2 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  a  =  ptr [ ofs  *  4  +  3 ]  /  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  b ,  a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBA4444 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  u  =  ( ( uint16_t  * ) ptr ) [ ofs ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-02 21:37:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											float  r  =  ( ( u  > >  12 )  &  0xF )  /  15.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ( ( u  > >  8 )  &  0xF )  /  15.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  b  =  ( ( u  > >  4 )  &  0xF )  /  15.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  a  =  ( u  &  0xF )  /  15.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  b ,  a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGB565 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint16_t  u  =  ( ( uint16_t  * ) ptr ) [ ofs ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											float  r  =  ( u  &  0x1F )  /  31.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ( ( u  > >  5 )  &  0x3F )  /  63.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  b  =  ( ( u  > >  11 )  &  0x1F )  /  31.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  b ,  1.0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ( ( float  * ) ptr ) [ ofs ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  0 ,  0 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ( ( float  * ) ptr ) [ ofs  *  2  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ( ( float  * ) ptr ) [ ofs  *  2  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  0 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ( ( float  * ) ptr ) [ ofs  *  3  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ( ( float  * ) ptr ) [ ofs  *  3  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  b  =  ( ( float  * ) ptr ) [ ofs  *  3  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  b ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBAF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  r  =  ( ( float  * ) ptr ) [ ofs  *  4  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  g  =  ( ( float  * ) ptr ) [ ofs  *  4  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  b  =  ( ( float  * ) ptr ) [ ofs  *  4  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											float  a  =  ( ( float  * ) ptr ) [ ofs  *  4  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( r ,  g ,  b ,  a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  r  =  ( ( uint16_t  * ) ptr ) [ ofs ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( Math : : half_to_float ( r ) ,  0 ,  0 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  r  =  ( ( uint16_t  * ) ptr ) [ ofs  *  2  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  g  =  ( ( uint16_t  * ) ptr ) [ ofs  *  2  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( Math : : half_to_float ( r ) ,  Math : : half_to_float ( g ) ,  0 ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  r  =  ( ( uint16_t  * ) ptr ) [ ofs  *  3  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  g  =  ( ( uint16_t  * ) ptr ) [ ofs  *  3  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  b  =  ( ( uint16_t  * ) ptr ) [ ofs  *  3  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( Math : : half_to_float ( r ) ,  Math : : half_to_float ( g ) ,  Math : : half_to_float ( b ) ,  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBAH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  r  =  ( ( uint16_t  * ) ptr ) [ ofs  *  4  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  g  =  ( ( uint16_t  * ) ptr ) [ ofs  *  4  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  b  =  ( ( uint16_t  * ) ptr ) [ ofs  *  4  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  a  =  ( ( uint16_t  * ) ptr ) [ ofs  *  4  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Color ( Math : : half_to_float ( r ) ,  Math : : half_to_float ( g ) ,  Math : : half_to_float ( b ) ,  Math : : half_to_float ( a ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGBE9995 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  Color : : from_rgbe9995 ( ( ( uint32_t  * ) ptr ) [ ofs ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-07-20 08:09:57 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-14 20:57:49 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_V_MSG ( Color ( ) ,  " Can't get_pixel() on compressed image, sorry. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : _set_color_at_ofs ( uint8_t  * ptr ,  uint32_t  ofs ,  const  Color  & p_color )  {  
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( format )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_L8 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 17:47:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ptr [ ofs ]  =  uint8_t ( CLAMP ( p_color . get_v ( )  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_LA8 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 17:47:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ptr [ ofs  *  2  +  0 ]  =  uint8_t ( CLAMP ( p_color . get_v ( )  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ptr [ ofs  *  2  +  1 ]  =  uint8_t ( CLAMP ( p_color . a  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_R8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs ]  =  uint8_t ( CLAMP ( p_color . r  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RG8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  2  +  0 ]  =  uint8_t ( CLAMP ( p_color . r  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  2  +  1 ]  =  uint8_t ( CLAMP ( p_color . g  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGB8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  3  +  0 ]  =  uint8_t ( CLAMP ( p_color . r  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  3  +  1 ]  =  uint8_t ( CLAMP ( p_color . g  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  3  +  2 ]  =  uint8_t ( CLAMP ( p_color . b  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA8 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  4  +  0 ]  =  uint8_t ( CLAMP ( p_color . r  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  4  +  1 ]  =  uint8_t ( CLAMP ( p_color . g  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  4  +  2 ]  =  uint8_t ( CLAMP ( p_color . b  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ ofs  *  4  +  3 ]  =  uint8_t ( CLAMP ( p_color . a  *  255.0 ,  0 ,  255 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBA4444 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint16_t  rgba  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-01-02 21:37:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											rgba  =  uint16_t ( CLAMP ( p_color . r  *  15.0 ,  0 ,  15 ) )  < <  12 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rgba  | =  uint16_t ( CLAMP ( p_color . g  *  15.0 ,  0 ,  15 ) )  < <  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rgba  | =  uint16_t ( CLAMP ( p_color . b  *  15.0 ,  0 ,  15 ) )  < <  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rgba  | =  uint16_t ( CLAMP ( p_color . a  *  15.0 ,  0 ,  15 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs ]  =  rgba ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  FORMAT_RGB565 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint16_t  rgba  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											rgba  =  uint16_t ( CLAMP ( p_color . r  *  31.0 ,  0 ,  31 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rgba  | =  uint16_t ( CLAMP ( p_color . g  *  63.0 ,  0 ,  33 ) )  < <  5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rgba  | =  uint16_t ( CLAMP ( p_color . b  *  31.0 ,  0 ,  31 ) )  < <  11 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs ]  =  rgba ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs ]  =  p_color . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  2  +  0 ]  =  p_color . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  2  +  1 ]  =  p_color . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  3  +  0 ]  =  p_color . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  3  +  1 ]  =  p_color . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  3  +  2 ]  =  p_color . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBAF :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  4  +  0 ]  =  p_color . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  4  +  1 ]  =  p_color . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  4  +  2 ]  =  p_color . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( float  * ) ptr ) [ ofs  *  4  +  3 ]  =  p_color . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs ]  =  Math : : make_half_float ( p_color . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  2  +  0 ]  =  Math : : make_half_float ( p_color . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  2  +  1 ]  =  Math : : make_half_float ( p_color . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  3  +  0 ]  =  Math : : make_half_float ( p_color . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  3  +  1 ]  =  Math : : make_half_float ( p_color . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  3  +  2 ]  =  Math : : make_half_float ( p_color . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBAH :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  4  +  0 ]  =  Math : : make_half_float ( p_color . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  4  +  1 ]  =  Math : : make_half_float ( p_color . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  4  +  2 ]  =  Math : : make_half_float ( p_color . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											( ( uint16_t  * ) ptr ) [ ofs  *  4  +  3 ]  =  Math : : make_half_float ( p_color . a ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  FORMAT_RGBE9995 :  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-28 21:46:48 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											( ( uint32_t  * ) ptr ) [ ofs ]  =  p_color . to_rgbe9995 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-14 20:57:49 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_MSG ( " Can't set_pixel() on compressed image, sorry. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Color  Image : : get_pixel ( int  p_x ,  int  p_y )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef DEBUG_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_x ,  width ,  Color ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_y ,  height ,  Color ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  ofs  =  p_y  *  width  +  p_x ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _get_color_at_ofs ( data . ptr ( ) ,  ofs ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-11-21 02:42:29 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : set_pixelv ( const  Point2i  & p_point ,  const  Color  & p_color )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									set_pixel ( p_point . x ,  p_point . y ,  p_color ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : set_pixel ( int  p_x ,  int  p_y ,  const  Color  & p_color )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef DEBUG_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX ( p_x ,  width ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX ( p_y ,  height ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  ofs  =  p_y  *  width  +  p_x ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_set_color_at_ofs ( data . ptrw ( ) ,  ofs ,  p_color ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-01-26 20:09:40 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-02-12 12:16:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : adjust_bcs ( float  p_brightness ,  float  p_contrast ,  float  p_saturation )  {  
						 
					
						
							
								
									
										
										
										
											2021-06-27 20:52:42 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_MSG ( ! _can_modify ( format ) ,  " Cannot adjust_bcs in compressed or custom image formats. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-02-12 12:16:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  pixel_size  =  get_format_pixel_size ( format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  pixel_count  =  data . size ( )  /  pixel_size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  pixel_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Color  c  =  _get_color_at_ofs ( w ,  i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  rgb ( c . r ,  c . g ,  c . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rgb  * =  p_brightness ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rgb  =  Vector3 ( 0.5 ,  0.5 ,  0.5 ) . lerp ( rgb ,  p_contrast ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  center  =  ( rgb . x  +  rgb . y  +  rgb . z )  /  3.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										rgb  =  Vector3 ( center ,  center ,  center ) . lerp ( rgb ,  p_saturation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										c . r  =  rgb . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										c . g  =  rgb . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										c . b  =  rgb . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_set_color_at_ofs ( w ,  i ,  c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-24 18:18:55 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Image : : UsedChannels  Image : : detect_used_channels ( CompressSource  p_source )  const  {  
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( data . size ( )  = =  0 ,  USED_CHANNELS_RGBA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( is_compressed ( ) ,  USED_CHANNELS_RGBA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bool  r  =  false ,  g  =  false ,  b  =  false ,  a  =  false ,  c  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-26 15:14:12 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * data_ptr  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-26 15:14:12 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint32_t  data_total  =  width  *  height ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-26 15:14:12 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  data_total ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Color  col  =  _get_color_at_ofs ( data_ptr ,  i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( col . r  >  0.001 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											r  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( col . g  >  0.001 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											g  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( col . b  >  0.001 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											b  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( col . a  <  0.999 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											a  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( col . r  ! =  col . b  | |  col . r  ! =  col . g  | |  col . b  ! =  col . g )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											c  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									UsedChannels  used_channels ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! c  & &  ! a )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_L ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( ! c  & &  a )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_LA ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( r  & &  ! g  & &  ! b  & &  ! a )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_R ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( r  & &  g  & &  ! b  & &  ! a )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_RG ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( r  & &  g  & &  b  & &  ! a )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_RGB ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_RGBA ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_source  = =  COMPRESS_SOURCE_SRGB  & &  ( used_channels  = =  USED_CHANNELS_R  | |  used_channels  = =  USED_CHANNELS_RG ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//R and RG do not support SRGB
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_RGB ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_source  = =  COMPRESS_SOURCE_NORMAL )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//use RG channels only for normal
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										used_channels  =  USED_CHANNELS_RG ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  used_channels ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-06 14:56:06 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : optimize_channels ( )  {  
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( detect_used_channels ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 13:00:47 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  USED_CHANNELS_L : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											convert ( FORMAT_L8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  USED_CHANNELS_LA : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											convert ( FORMAT_LA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  USED_CHANNELS_R : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											convert ( FORMAT_R8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  USED_CHANNELS_RG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											convert ( FORMAT_RG8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  USED_CHANNELS_RGB : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											convert ( FORMAT_RGB8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  USED_CHANNELS_RGBA : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											convert ( FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-08-06 14:56:06 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : _bind_methods ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_width " ) ,  & Image : : get_width ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_height " ) ,  & Image : : get_height ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-26 14:45:03 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_size " ) ,  & Image : : get_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " has_mipmaps " ) ,  & Image : : has_mipmaps ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_format " ) ,  & Image : : get_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_data " ) ,  & Image : : get_data ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " convert " ,  " format " ) ,  & Image : : convert ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_mipmap_offset " ,  " mipmap " ) ,  & Image : : get_mipmap_offset ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-18 10:14:55 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " resize_to_po2 " ,  " square " ,  " interpolation " ) ,  & Image : : resize_to_po2 ,  DEFVAL ( false ) ,  DEFVAL ( INTERPOLATE_BILINEAR ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 18:45:56 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " resize " ,  " width " ,  " height " ,  " interpolation " ) ,  & Image : : resize ,  DEFVAL ( INTERPOLATE_BILINEAR ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " shrink_x2 " ) ,  & Image : : shrink_x2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " crop " ,  " width " ,  " height " ) ,  & Image : : crop ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " flip_x " ) ,  & Image : : flip_x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " flip_y " ) ,  & Image : : flip_y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 21:51:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " generate_mipmaps " ,  " renormalize " ) ,  & Image : : generate_mipmaps ,  DEFVAL ( false ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " clear_mipmaps " ) ,  & Image : : clear_mipmaps ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " Image " ,  D_METHOD ( " create " ,  " width " ,  " height " ,  " use_mipmaps " ,  " format " ) ,  & Image : : create_empty ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " Image " ,  D_METHOD ( " create_from_data " ,  " width " ,  " height " ,  " use_mipmaps " ,  " format " ,  " data " ) ,  & Image : : create_from_data ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_data " ,  " width " ,  " height " ,  " use_mipmaps " ,  " format " ,  " data " ) ,  & Image : : set_data ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " is_empty " ) ,  & Image : : is_empty ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " load " ,  " path " ) ,  & Image : : load ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-04 01:49:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " Image " ,  D_METHOD ( " load_from_file " ,  " path " ) ,  & Image : : load_from_file ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_png " ,  " path " ) ,  & Image : : save_png ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-20 14:43:24 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_png_to_buffer " ) ,  & Image : : save_png_to_buffer ) ; 
							 
						 
					
						
							
								
									
										
											 
										
											
												Implement Running Godot as Movie Writer
* Allows running the game in "movie writer" mode.
* It ensures entirely stable framerate, so your run can be saved stable and with proper sound (which is impossible if your CPU/GPU can't sustain doing this in real-time).
* If disabling vsync, it can save movies faster than the game is run, but if you want to control the interaction it can get difficult.
* Implements a simple, default MJPEG writer.
This new features has two main use cases, which have high demand:
* Saving game videos in high quality and ensuring the frame rate is *completely* stable, always.
* Using Godot as a tool to make movies and animations (which is ideal if you want interaction, or creating them procedurally. No other software is as good for this).
**Note**: This feature **IS NOT** for capturing real-time footage. Use something like OBS, SimpleScreenRecorder or FRAPS to achieve that, as they do a much better job at intercepting the compositor than Godot can probably do using Vulkan or OpenGL natively. If your game runs near real-time when capturing, you can still use this feature but it will play no sound (sound will be saved directly).
Usage:
$ godot --write-movie movie.avi [scene_file.tscn]
Missing:
* Options for configuring video writing via GLOBAL_DEF
* UI Menu for launching with this mode from the editor.
* Add to list of command line options.
* Add a feature tag to override configurations when movie writing (fantastic for saving videos with highest quality settings).
											 
										 
										
											2022-06-17 00:55:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_jpg " ,  " path " ,  " quality " ) ,  & Image : : save_jpg ,  DEFVAL ( 0.75 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_jpg_to_buffer " ,  " quality " ) ,  & Image : : save_jpg_to_buffer ,  DEFVAL ( 0.75 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-08-03 01:07:13 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_exr " ,  " path " ,  " grayscale " ) ,  & Image : : save_exr ,  DEFVAL ( false ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-06-19 18:55:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_exr_to_buffer " ,  " grayscale " ) ,  & Image : : save_exr_to_buffer ,  DEFVAL ( false ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-06-04 16:05:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_webp " ,  " path " ,  " lossy " ,  " quality " ) ,  & Image : : save_webp ,  DEFVAL ( false ) ,  DEFVAL ( 0.75f ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " save_webp_to_buffer " ,  " lossy " ,  " quality " ) ,  & Image : : save_webp_to_buffer ,  DEFVAL ( false ) ,  DEFVAL ( 0.75f ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " detect_alpha " ) ,  & Image : : detect_alpha ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " is_invisible " ) ,  & Image : : is_invisible ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " detect_used_channels " ,  " source " ) ,  & Image : : detect_used_channels ,  DEFVAL ( COMPRESS_SOURCE_GENERIC ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " compress " ,  " mode " ,  " source " ,  " lossy_quality " ) ,  & Image : : compress ,  DEFVAL ( COMPRESS_SOURCE_GENERIC ) ,  DEFVAL ( 0.7 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-04-01 07:19:23 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " compress_from_channels " ,  " mode " ,  " channels " ,  " lossy_quality " ) ,  & Image : : compress_from_channels ,  DEFVAL ( 0.7 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " decompress " ) ,  & Image : : decompress ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " is_compressed " ) ,  & Image : : is_compressed ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-14 22:20:12 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " rotate_90 " ,  " direction " ) ,  & Image : : rotate_90 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " rotate_180 " ) ,  & Image : : rotate_180 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " fix_alpha_edges " ) ,  & Image : : fix_alpha_edges ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " premultiply_alpha " ) ,  & Image : : premultiply_alpha ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " srgb_to_linear " ) ,  & Image : : srgb_to_linear ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-23 09:34:26 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " normal_map_to_xy " ) ,  & Image : : normal_map_to_xy ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-05-30 21:14:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " rgbe_to_srgb " ) ,  & Image : : rgbe_to_srgb ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-23 09:34:26 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " bump_map_to_normal_map " ,  " bump_scale " ) ,  & Image : : bump_map_to_normal_map ,  DEFVAL ( 1.0 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " compute_image_metrics " ,  " compared_image " ,  " use_luma " ) ,  & Image : : compute_image_metrics ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-08-09 13:19:41 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " blit_rect " ,  " src " ,  " src_rect " ,  " dst " ) ,  & Image : : blit_rect ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " blit_rect_mask " ,  " src " ,  " mask " ,  " src_rect " ,  " dst " ) ,  & Image : : blit_rect_mask ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " blend_rect " ,  " src " ,  " src_rect " ,  " dst " ) ,  & Image : : blend_rect ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " blend_rect_mask " ,  " src " ,  " mask " ,  " src_rect " ,  " dst " ) ,  & Image : : blend_rect_mask ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-06-18 09:38:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " fill " ,  " color " ) ,  & Image : : fill ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-07 10:27:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " fill_rect " ,  " rect " ,  " color " ) ,  & Image : : fill_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_used_rect " ) ,  & Image : : get_used_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-09 13:19:41 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_rect " ,  " rect " ) ,  & Image : : get_rect ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-08-09 13:19:41 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " copy_from " ,  " src " ) ,  & Image : : copy_internals_from ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " _set_data " ,  " data " ) ,  & Image : : _set_data ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " _get_data " ) ,  & Image : : _get_data ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-11-21 02:42:29 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_pixelv " ,  " point " ) ,  & Image : : get_pixelv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_pixel " ,  " x " ,  " y " ) ,  & Image : : get_pixel ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-21 02:42:29 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_pixelv " ,  " point " ,  " color " ) ,  & Image : : set_pixelv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-04-29 15:17:06 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_pixel " ,  " x " ,  " y " ,  " color " ) ,  & Image : : set_pixel ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-26 21:49:49 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-02-12 12:16:37 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " adjust_bcs " ,  " brightness " ,  " contrast " ,  " saturation " ) ,  & Image : : adjust_bcs ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " load_png_from_buffer " ,  " buffer " ) ,  & Image : : load_png_from_buffer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " load_jpg_from_buffer " ,  " buffer " ) ,  & Image : : load_jpg_from_buffer ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-07-15 01:42:37 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " load_webp_from_buffer " ,  " buffer " ) ,  & Image : : load_webp_from_buffer ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-21 13:46:44 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " load_tga_from_buffer " ,  " buffer " ) ,  & Image : : load_tga_from_buffer ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-10-20 23:25:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " load_bmp_from_buffer " ,  " buffer " ) ,  & Image : : load_bmp_from_buffer ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : DICTIONARY ,  " data " ,  PROPERTY_HINT_NONE ,  " " ,  PROPERTY_USAGE_STORAGE ) ,  " _set_data " ,  " _get_data " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-01-28 15:33:56 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_CONSTANT ( MAX_WIDTH ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_CONSTANT ( MAX_HEIGHT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-08-20 17:45:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_L8 ) ;  //luminance
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_LA8 ) ;  //luminance-alpha
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_R8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RG8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGB8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBA4444 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGB565 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-20 17:45:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RF ) ;  //float
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBAF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RH ) ;  //half float
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGH ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBH ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBAH ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGBE9995 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_DXT1 ) ;  //s3tc bc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_DXT3 ) ;  //bc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_DXT5 ) ;  //bc3
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGTC_R ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_RGTC_RG ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_BPTC_RGBA ) ;  //btpc bc6h
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_BPTC_RGBF ) ;  //float /
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_BPTC_RGBFU ) ;  //unsigned float
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC ) ;  //etc1
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_R11 ) ;  //etc2
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_R11S ) ;  //signed ); NOT srgb.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_RG11 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_RG11S ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_RGB8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_RGB8A1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_ETC2_RA_AS_RG ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_DXT5_RA_AS_RG ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-20 17:45:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( FORMAT_MAX ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( INTERPOLATE_NEAREST ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( INTERPOLATE_BILINEAR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( INTERPOLATE_CUBIC ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-06-01 21:53:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( INTERPOLATE_TRILINEAR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-05 14:03:52 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( INTERPOLATE_LANCZOS ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-20 17:45:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( ALPHA_NONE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( ALPHA_BIT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( ALPHA_BLEND ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_S3TC ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_ETC ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_ETC2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-10 23:01:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_BPTC ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-08-20 17:45:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( USED_CHANNELS_L ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( USED_CHANNELS_LA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( USED_CHANNELS_R ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( USED_CHANNELS_RG ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( USED_CHANNELS_RGB ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( USED_CHANNELS_RGBA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-08-20 17:45:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_SOURCE_GENERIC ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_SOURCE_SRGB ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( COMPRESS_SOURCE_NORMAL ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : set_compress_bc_func ( void  ( * p_compress_func ) ( Image  * ,  float ,  UsedChannels ) )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_image_compress_bc_func  =  p_compress_func ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : set_compress_bptc_func ( void  ( * p_compress_func ) ( Image  * ,  float ,  UsedChannels ) )  {  
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_image_compress_bptc_func  =  p_compress_func ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-23 09:34:26 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : normal_map_to_xy ( )  {  
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									convert ( Image : : FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 08:58:41 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int  len  =  data . size ( )  /  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 08:58:41 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  len ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  < <  2 )  +  3 ]  =  data_ptr [ ( i  < <  2 )  +  0 ] ;  //x to w
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  < <  2 )  +  0 ]  =  data_ptr [ ( i  < <  2 )  +  1 ] ;  //y to xz
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  < <  2 )  +  2 ]  =  data_ptr [ ( i  < <  2 )  +  1 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 08:58:41 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									convert ( Image : : FORMAT_LA8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-10-03 08:58:41 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-05-30 21:14:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  Image : : rgbe_to_srgb ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( data . size ( )  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-05-30 21:14:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  Ref < Image > ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2018-05-30 21:14:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( format  ! =  FORMAT_RGBE9995 ,  Ref < Image > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Image >  new_image  =  create_empty ( width ,  height ,  false ,  Image : : FORMAT_RGB8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-05-30 21:14:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  row  =  0 ;  row  <  height ;  row + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  col  =  0 ;  col  <  width ;  col + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											new_image - > set_pixel ( col ,  row ,  get_pixel ( col ,  row ) . linear_to_srgb ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-05-30 21:14:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( has_mipmaps ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										new_image - > generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  new_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  Image : : get_image_from_mipmap ( int  p_mipamp )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  ofs ,  size ,  w ,  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									get_mipmap_offset_size_and_dimensions ( p_mipamp ,  ofs ,  size ,  w ,  h ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector < uint8_t >  new_data ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									new_data . resize ( size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * wr  =  new_data . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  uint8_t  * rd  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-27 16:19:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										memcpy ( wr ,  rd  +  ofs ,  size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  image ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									image . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									image - > width  =  w ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image - > height  =  h ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image - > format  =  format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image - > data  =  new_data ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									image - > mipmaps  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-23 09:34:26 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : bump_map_to_normal_map ( float  bump_scale )  {  
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! _can_modify ( format ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									convert ( Image : : FORMAT_RF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector < uint8_t >  result_image ;  //rgba output
 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-24 13:59:02 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									result_image . resize ( width  *  height  *  4 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  uint8_t  * rp  =  data . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint8_t  * wp  =  result_image . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND ( ! rp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-10-28 08:07:29 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										unsigned  char  * write_ptr  =  wp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										float  * read_ptr  =  ( float  * ) rp ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  ty  =  0 ;  ty  <  height ;  ty + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-24 13:59:02 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  py  =  ty  +  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( py  > =  height )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												py  - =  height ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  tx  =  0 ;  tx  <  width ;  tx + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-24 13:59:02 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												int  px  =  tx  +  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( px  > =  width )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-10 12:56:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													px  - =  width ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-24 13:59:02 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												float  here  =  read_ptr [ ty  *  width  +  tx ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  to_right  =  read_ptr [ ty  *  width  +  px ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  above  =  read_ptr [ py  *  width  +  tx ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  up  =  Vector3 ( 0 ,  1 ,  ( here  -  above )  *  bump_scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  across  =  Vector3 ( 1 ,  0 ,  ( to_right  -  here )  *  bump_scale ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  normal  =  across . cross ( up ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												normal . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-03-16 10:22:48 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												write_ptr [ ( ( ty  *  width  +  tx )  < <  2 )  +  0 ]  =  ( 127.5  +  normal . x  *  127.5 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												write_ptr [ ( ( ty  *  width  +  tx )  < <  2 )  +  1 ]  =  ( 127.5  +  normal . y  *  127.5 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												write_ptr [ ( ( ty  *  width  +  tx )  < <  2 )  +  2 ]  =  ( 127.5  +  normal . z  *  127.5 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-24 13:59:02 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												write_ptr [ ( ( ty  *  width  +  tx )  < <  2 )  +  3 ]  =  255 ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-24 13:59:02 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									format  =  FORMAT_RGBA8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									data  =  result_image ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-02-21 11:43:58 +13:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : srgb_to_linear ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( data . size ( )  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-30 05:39:05 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									static  const  uint8_t  srgb2lin [ 256 ]  =  {  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  0 ,  1 ,  1 ,  1 ,  1 ,  1 ,  1 ,  1 ,  1 ,  1 ,  2 ,  2 ,  2 ,  2 ,  2 ,  2 ,  2 ,  3 ,  3 ,  3 ,  3 ,  3 ,  4 ,  4 ,  4 ,  4 ,  4 ,  5 ,  5 ,  5 ,  5 ,  6 ,  6 ,  6 ,  6 ,  7 ,  7 ,  7 ,  8 ,  8 ,  8 ,  9 ,  9 ,  9 ,  10 ,  10 ,  10 ,  11 ,  11 ,  11 ,  12 ,  12 ,  13 ,  13 ,  13 ,  14 ,  14 ,  15 ,  15 ,  16 ,  16 ,  16 ,  17 ,  17 ,  18 ,  18 ,  19 ,  19 ,  20 ,  20 ,  21 ,  22 ,  22 ,  23 ,  23 ,  24 ,  24 ,  25 ,  26 ,  26 ,  27 ,  27 ,  28 ,  29 ,  29 ,  30 ,  31 ,  31 ,  32 ,  33 ,  33 ,  34 ,  35 ,  36 ,  36 ,  37 ,  38 ,  38 ,  39 ,  40 ,  41 ,  42 ,  42 ,  43 ,  44 ,  45 ,  46 ,  47 ,  47 ,  48 ,  49 ,  50 ,  51 ,  52 ,  53 ,  54 ,  55 ,  55 ,  56 ,  57 ,  58 ,  59 ,  60 ,  61 ,  62 ,  63 ,  64 ,  65 ,  66 ,  67 ,  68 ,  70 ,  71 ,  72 ,  73 ,  74 ,  75 ,  76 ,  77 ,  78 ,  80 ,  81 ,  82 ,  83 ,  84 ,  85 ,  87 ,  88 ,  89 ,  90 ,  92 ,  93 ,  94 ,  95 ,  97 ,  98 ,  99 ,  101 ,  102 ,  103 ,  105 ,  106 ,  107 ,  109 ,  110 ,  112 ,  113 ,  114 ,  116 ,  117 ,  119 ,  120 ,  122 ,  123 ,  125 ,  126 ,  128 ,  129 ,  131 ,  132 ,  134 ,  135 ,  137 ,  139 ,  140 ,  142 ,  144 ,  145 ,  147 ,  148 ,  150 ,  152 ,  153 ,  155 ,  157 ,  159 ,  160 ,  162 ,  164 ,  166 ,  167 ,  169 ,  171 ,  173 ,  175 ,  176 ,  178 ,  180 ,  182 ,  184 ,  186 ,  188 ,  190 ,  192 ,  193 ,  195 ,  197 ,  199 ,  201 ,  203 ,  205 ,  207 ,  209 ,  211 ,  213 ,  215 ,  218 ,  220 ,  222 ,  224 ,  226 ,  228 ,  230 ,  232 ,  235 ,  237 ,  239 ,  241 ,  243 ,  245 ,  248 ,  250 ,  252 ,  255  } ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  FORMAT_RGB8  & &  format  ! =  FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( format  = =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  len  =  data . size ( )  /  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  len ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  < <  2 )  +  0 ]  =  srgb2lin [ data_ptr [ ( i  < <  2 )  +  0 ] ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  < <  2 )  +  1 ]  =  srgb2lin [ data_ptr [ ( i  < <  2 )  +  1 ] ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  < <  2 )  +  2 ]  =  srgb2lin [ data_ptr [ ( i  < <  2 )  +  2 ] ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( format  = =  FORMAT_RGB8 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  len  =  data . size ( )  /  3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint8_t  * data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  len ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  *  3 )  +  0 ]  =  srgb2lin [ data_ptr [ ( i  *  3 )  +  0 ] ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  *  3 )  +  1 ]  =  srgb2lin [ data_ptr [ ( i  *  3 )  +  1 ] ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data_ptr [ ( i  *  3 )  +  2 ]  =  srgb2lin [ data_ptr [ ( i  *  3 )  +  2 ] ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-06-16 10:22:26 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : premultiply_alpha ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( data . size ( )  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( format  ! =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ;  //not needed
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  height ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  width ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint8_t  * ptr  =  & data_ptr [ ( i  *  width  +  j )  *  4 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ptr [ 0 ]  =  ( uint16_t ( ptr [ 0 ] )  *  uint16_t ( ptr [ 3 ] ) )  > >  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ 1 ]  =  ( uint16_t ( ptr [ 1 ] )  *  uint16_t ( ptr [ 3 ] ) )  > >  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ptr [ 2 ]  =  ( uint16_t ( ptr [ 2 ] )  *  uint16_t ( ptr [ 3 ] ) )  > >  8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-05-24 01:35:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								void  Image : : fix_alpha_edges ( )  {  
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( data . size ( )  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( format  ! =  FORMAT_RGBA8 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ;  //not needed
 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector < uint8_t >  dcopy  =  data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint8_t  * srcptr  =  dcopy . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * data_ptr  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  max_radius  =  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-07-08 22:12:18 +07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  alpha_threshold  =  20 ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  max_dist  =  0x7FFFFFFF ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  height ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  width ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  uint8_t  * rptr  =  & srcptr [ ( i  *  width  +  j )  *  4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											uint8_t  * wptr  =  & data_ptr [ ( i  *  width  +  j )  *  4 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( rptr [ 3 ]  > =  alpha_threshold )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  closest_dist  =  max_dist ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint8_t  closest_color [ 3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  from_x  =  MAX ( 0 ,  j  -  max_radius ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  to_x  =  MIN ( width  -  1 ,  j  +  max_radius ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  from_y  =  MAX ( 0 ,  i  -  max_radius ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  to_y  =  MIN ( height  -  1 ,  i  +  max_radius ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  k  =  from_y ;  k  < =  to_y ;  k + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  l  =  from_x ;  l  < =  to_x ;  l + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  dy  =  i  -  k ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  dx  =  j  -  l ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  dist  =  dy  *  dy  +  dx  *  dx ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( dist  > =  closest_dist )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-12 21:10:08 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													const  uint8_t  * rp2  =  & srcptr [ ( k  *  width  +  l )  < <  2 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( rp2 [ 3 ]  <  alpha_threshold )  { 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-14 16:41:43 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-10-13 16:03:05 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													closest_dist  =  dist ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-12 21:10:08 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													closest_color [ 0 ]  =  rp2 [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													closest_color [ 1 ]  =  rp2 [ 1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													closest_color [ 2 ]  =  rp2 [ 2 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( closest_dist  ! =  max_dist )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												wptr [ 0 ]  =  closest_color [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												wptr [ 1 ]  =  closest_color [ 1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												wptr [ 2 ]  =  closest_color [ 2 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-10-03 16:33:42 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2015-10-21 09:50:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  Image : : get_format_name ( Format  p_format )  {  
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_format ,  FORMAT_MAX ,  String ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2015-10-21 09:50:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  format_names [ p_format ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : load_png_from_buffer ( const  Vector < uint8_t >  & p_array )  {  
						 
					
						
							
								
									
										
										
										
											2018-07-15 01:42:37 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _load_from_buffer ( p_array ,  _png_mem_loader_func ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : load_jpg_from_buffer ( const  Vector < uint8_t >  & p_array )  {  
						 
					
						
							
								
									
										
										
										
											2018-07-15 01:42:37 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _load_from_buffer ( p_array ,  _jpg_mem_loader_func ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : load_webp_from_buffer ( const  Vector < uint8_t >  & p_array )  {  
						 
					
						
							
								
									
										
										
										
											2018-07-15 01:42:37 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _load_from_buffer ( p_array ,  _webp_mem_loader_func ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-21 13:46:44 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : load_tga_from_buffer ( const  Vector < uint8_t >  & p_array )  {  
						 
					
						
							
								
									
										
										
										
											2020-10-20 23:25:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V_MSG ( 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_tga_mem_loader_func , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_UNAVAILABLE , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" The TGA module isn't enabled. Recompile the Godot editor or export template binary with the `module_tga_enabled=yes` SCons option. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-21 13:46:44 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _load_from_buffer ( p_array ,  _tga_mem_loader_func ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-10-20 23:25:58 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : load_bmp_from_buffer ( const  Vector < uint8_t >  & p_array )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V_MSG ( 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_bmp_mem_loader_func , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_UNAVAILABLE , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											" The BMP module isn't enabled. Recompile the Godot editor or export template binary with the `module_bmp_enabled=yes` SCons option. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _load_from_buffer ( p_array ,  _bmp_mem_loader_func ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : convert_rg_to_ra_rgba8 ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! data . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  s  =  data . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  s ;  i  + =  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w [ i  +  3 ]  =  w [ i  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w [ i  +  1 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w [ i  +  2 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2020-05-14 14:29:06 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : convert_ra_rgba8_to_rg ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( format  ! =  FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( ! data . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  s  =  data . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint8_t  * w  =  data . ptrw ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2019-09-26 23:16:44 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  s ;  i  + =  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w [ i  +  1 ]  =  w [ i  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w [ i  +  2 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										w [ i  +  3 ]  =  255 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  Image : : _load_from_buffer ( const  Vector < uint8_t >  & p_array ,  ImageMemLoadFunc  p_loader )  {  
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  buffer_size  =  p_array . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( buffer_size  = =  0 ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2018-07-15 01:42:37 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! p_loader ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint8_t  * r  =  p_array . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-02-17 18:06:54 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Image >  image  =  p_loader ( r ,  buffer_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-12-20 17:16:21 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! image . is_valid ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									copy_internals_from ( image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2018-08-21 22:56:04 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : average_4_uint8 ( uint8_t  & p_out ,  const  uint8_t  & p_a ,  const  uint8_t  & p_b ,  const  uint8_t  & p_c ,  const  uint8_t  & p_d )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_out  =  static_cast < uint8_t > ( ( p_a  +  p_b  +  p_c  +  p_d  +  2 )  > >  2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : average_4_float ( float  & p_out ,  const  float  & p_a ,  const  float  & p_b ,  const  float  & p_c ,  const  float  & p_d )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_out  =  ( p_a  +  p_b  +  p_c  +  p_d )  *  0.25f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : average_4_half ( uint16_t  & p_out ,  const  uint16_t  & p_a ,  const  uint16_t  & p_b ,  const  uint16_t  & p_c ,  const  uint16_t  & p_d )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_out  =  Math : : make_half_float ( ( Math : : half_to_float ( p_a )  +  Math : : half_to_float ( p_b )  +  Math : : half_to_float ( p_c )  +  Math : : half_to_float ( p_d ) )  *  0.25f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : average_4_rgbe9995 ( uint32_t  & p_out ,  const  uint32_t  & p_a ,  const  uint32_t  & p_b ,  const  uint32_t  & p_c ,  const  uint32_t  & p_d )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_out  =  ( ( Color : : from_rgbe9995 ( p_a )  +  Color : : from_rgbe9995 ( p_b )  +  Color : : from_rgbe9995 ( p_c )  +  Color : : from_rgbe9995 ( p_d ) )  *  0.25f ) . to_rgbe9995 ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : renormalize_uint8 ( uint8_t  * p_rgb )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  n ( p_rgb [ 0 ]  /  255.0 ,  p_rgb [ 1 ]  /  255.0 ,  p_rgb [ 2 ]  /  255.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n  * =  2.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n  - =  Vector3 ( 1 ,  1 ,  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n  + =  Vector3 ( 1 ,  1 ,  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n  * =  0.5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n  * =  255 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 0 ]  =  CLAMP ( int ( n . x ) ,  0 ,  255 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 1 ]  =  CLAMP ( int ( n . y ) ,  0 ,  255 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 2 ]  =  CLAMP ( int ( n . z ) ,  0 ,  255 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : renormalize_float ( float  * p_rgb )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  n ( p_rgb [ 0 ] ,  p_rgb [ 1 ] ,  p_rgb [ 2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 0 ]  =  n . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 1 ]  =  n . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 2 ]  =  n . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : renormalize_half ( uint16_t  * p_rgb )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  n ( Math : : half_to_float ( p_rgb [ 0 ] ) ,  Math : : half_to_float ( p_rgb [ 1 ] ) ,  Math : : half_to_float ( p_rgb [ 2 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									n . normalize ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 0 ]  =  Math : : make_half_float ( n . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 1 ]  =  Math : : make_half_float ( n . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_rgb [ 2 ]  =  Math : : make_half_float ( n . z ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  Image : : renormalize_rgbe9995 ( uint32_t  * p_rgb )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Never used
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-03-05 16:44:50 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Image : : Image ( const  uint8_t  * p_mem_png_jpg ,  int  p_len )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									width  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									height  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mipmaps  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									format  =  FORMAT_L8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( _png_mem_loader_func )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										copy_internals_from ( _png_mem_loader_func ( p_mem_png_jpg ,  p_len ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2016-03-12 10:44:12 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( is_empty ( )  & &  _jpg_mem_loader_func )  { 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										copy_internals_from ( _jpg_mem_loader_func ( p_mem_png_jpg ,  p_len ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-24 18:18:55 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( is_empty ( )  & &  _webp_mem_loader_func )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										copy_internals_from ( _webp_mem_loader_func ( p_mem_png_jpg ,  p_len ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2014-02-09 22:10:30 -03:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Resource >  Image : : duplicate ( bool  p_subresources )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  copy ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									copy . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2017-05-17 07:36:47 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									copy - > _copy_internals_from ( * this ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  copy ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-05-01 09:34:23 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  Image : : set_as_black ( )  {  
						 
					
						
							
								
									
										
										
										
											2021-04-27 16:19:21 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									memset ( data . ptrw ( ) ,  0 ,  data . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-05-01 09:34:23 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Dictionary  Image : : compute_image_metrics ( const  Ref < Image >  p_compared_image ,  bool  p_luma_metric )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// https://github.com/richgel999/bc7enc_rdo/blob/master/LICENSE
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This is free and unencumbered software released into the public domain.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Anyone is free to copy, modify, publish, use, compile, sell, or distribute this
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// software, either in source code form or as a compiled binary, for any purpose,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// commercial or non - commercial, and by any means.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// In jurisdictions that recognize copyright laws, the author or authors of this
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// software dedicate any and all copyright interest in the software to the public
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// domain. We make this dedication for the benefit of the public at large and to
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// the detriment of our heirs and successors. We intend this dedication to be an
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// overt act of relinquishment in perpetuity of all present and future rights to
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// this software under copyright law.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  result ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " max " ]  =  INFINITY ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " mean " ]  =  INFINITY ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " mean_squared " ]  =  INFINITY ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " root_mean_squared " ]  =  INFINITY ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " peak_snr " ]  =  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( p_compared_image ,  result ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  compared_image  =  duplicate ( true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( compared_image - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  compared_image - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  result ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Image >  source_image  =  p_compared_image - > duplicate ( true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( source_image - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  source_image - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  result ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  result ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( ( compared_image - > get_format ( )  > =  Image : : FORMAT_RH )  & &  ( compared_image - > get_format ( )  < =  Image : : FORMAT_RGBE9995 ) ,  result ,  " Metrics on HDR images are not supported. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( ( source_image - > get_format ( )  > =  Image : : FORMAT_RH )  & &  ( source_image - > get_format ( )  < =  Image : : FORMAT_RGBE9995 ) ,  result ,  " Metrics on HDR images are not supported. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  image_metric_max ,  image_metric_mean ,  image_metric_mean_squared ,  image_metric_root_mean_squared ,  image_metric_peak_snr  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  bool  average_component_error  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint32_t  w  =  MIN ( compared_image - > get_width ( ) ,  source_image - > get_width ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint32_t  h  =  MIN ( compared_image - > get_height ( ) ,  source_image - > get_height ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Histogram approach originally due to Charles Bloom.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  hist [ 256 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									memset ( hist ,  0 ,  sizeof ( hist ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( uint32_t  y  =  0 ;  y  <  h ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( uint32_t  x  =  0 ;  x  <  w ;  x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  Color  color_a  =  compared_image - > get_pixel ( x ,  y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Color  color_b  =  source_image - > get_pixel ( x ,  y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! p_luma_metric )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_a . r  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_b . r  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												hist [ Math : : abs ( color_a . get_r8 ( )  -  color_b . get_r8 ( ) ) ] + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_a . g  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_b . g  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												hist [ Math : : abs ( color_a . get_g8 ( )  -  color_b . get_g8 ( ) ) ] + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_a . b  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_b . b  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												hist [ Math : : abs ( color_a . get_b8 ( )  -  color_b . get_b8 ( ) ) ] + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_a . a  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_b . a  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												hist [ Math : : abs ( color_a . get_a8 ( )  -  color_b . get_a8 ( ) ) ] + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_a . r  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V_MSG ( color_b . r  >  1.0f ,  Dictionary ( ) ,  " Can't compare HDR colors. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// REC709 weightings
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  luma_a  =  ( 13938U  *  color_a . get_r8 ( )  +  46869U  *  color_a . get_g8 ( )  +  4729U  *  color_a . get_b8 ( )  +  32768U )  > >  16U ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  luma_b  =  ( 13938U  *  color_b . get_r8 ( )  +  46869U  *  color_b . get_g8 ( )  +  4729U  *  color_b . get_b8 ( )  +  32768U )  > >  16U ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												hist [ Math : : abs ( luma_a  -  luma_b ) ] + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image_metric_max  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  sum  =  0.0f ,  sum2  =  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( uint32_t  i  =  0 ;  i  <  256 ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! hist [ i ] )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										image_metric_max  =  MAX ( image_metric_max ,  i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										double  x  =  i  *  hist [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sum  + =  x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sum2  + =  i  *  x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// See http://richg42.blogspot.com/2016/09/how-to-compute-psnr-from-old-berkeley.html
 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									double  total_values  =  w  *  h ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-18 04:39:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( average_component_error )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										total_values  * =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image_metric_mean  =  CLAMP ( sum  /  total_values ,  0.0f ,  255.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image_metric_mean_squared  =  CLAMP ( sum2  /  total_values ,  0.0f ,  255.0f  *  255.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									image_metric_root_mean_squared  =  sqrt ( image_metric_mean_squared ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! image_metric_root_mean_squared )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										image_metric_peak_snr  =  1e+10 f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										image_metric_peak_snr  =  CLAMP ( log10 ( 255.0f  /  image_metric_root_mean_squared )  *  20.0f ,  0.0f ,  500.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " max " ]  =  image_metric_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " mean " ]  =  image_metric_mean ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " mean_squared " ]  =  image_metric_mean_squared ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " root_mean_squared " ]  =  image_metric_root_mean_squared ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									result [ " peak_snr " ]  =  image_metric_peak_snr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  result ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}