2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								/**************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*  gltf_document.cpp                                                     */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/**************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                         This file is part of:                          */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                             GODOT ENGINE                               */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                        https://godotengine.org                         */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/**************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur.                  */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/*                                                                        */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/* 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.                 */  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								/**************************************************************************/  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "gltf_document.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-07-15 00:46:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-09 23:53:58 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "extensions/gltf_document_extension_convert_importer_mesh.h" 
  
						 
					
						
							
								
									
										
										
										
											2022-07-24 14:20:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "extensions/gltf_spec_gloss.h" 
  
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "gltf_state.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "skin_tool.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 23:37:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/config/project_settings.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  "core/crypto/crypto_core.h" 
  
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/io/config_file.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-07-15 00:46:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/io/dir_access.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-06-11 14:51:48 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/io/file_access.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/io/file_access_memory.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  "core/io/json.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-10-08 14:13:06 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/io/stream_peer.h" 
  
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "core/object/object_id.h" 
  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								# include  "core/version.h" 
  
						 
					
						
							
								
									
										
										
										
											2024-12-20 22:05:53 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/2d/node_2d.h" 
  
						 
					
						
							
								
									
										
										
										
											2022-11-29 00:50:26 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/3d/bone_attachment_3d.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "scene/3d/camera_3d.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "scene/3d/importer_mesh_instance_3d.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "scene/3d/light_3d.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/3d/mesh_instance_3d.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-07-15 00:46:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/3d/multimesh_instance_3d.h" 
  
						 
					
						
							
								
									
										
										
										
											2024-12-20 22:05:53 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/animation/animation_player.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-08-13 11:42:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/resources/3d/skin.h" 
  
						 
					
						
							
								
									
										
										
										
											2023-07-11 22:29:09 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/resources/image_texture.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "scene/resources/portable_compressed_texture.h" 
  
						 
					
						
							
								
									
										
										
										
											2021-07-15 00:46:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "scene/resources/surface_tool.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-02-02 13:41:04 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# ifdef TOOLS_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "editor/editor_file_system.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
									
										
										
										
											2021-07-15 00:46:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-12-04 13:28:07 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  "modules/modules_enabled.gen.h"   // For csg, gridmap.
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef MODULE_CSG_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "modules/csg/csg_shape.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef MODULE_GRIDMAP_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  "modules/gridmap/grid_map.h" 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:39:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								// FIXME: Hardcoded to avoid editor dependency.
  
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define GLTF_IMPORT_GENERATE_TANGENT_ARRAYS 8 
  
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:39:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define GLTF_IMPORT_USE_NAMED_SKIN_BINDS 16 
  
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define GLTF_IMPORT_DISCARD_MESHES_AND_MATERIALS 32 
  
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# define GLTF_IMPORT_FORCE_DISABLE_MESH_COMPRESSION 64 
  
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:39:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-04-28 16:05:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# include  <cstdio> 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# include  <cstdlib> 
  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								constexpr  int  COMPONENT_COUNT_FOR_ACCESSOR_TYPE [ 7 ]  =  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									1 ,  2 ,  3 ,  4 ,  4 ,  9 ,  16 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  void  _attach_extras_to_meta ( const  Dictionary  & p_extras ,  Ref < Resource >  p_node )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_extras . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_node - > set_meta ( " extras " ,  p_extras ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  void  _attach_meta_to_extras ( Ref < Resource >  p_node ,  Dictionary  & p_json )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_node - > has_meta ( " extras " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Dictionary  node_extras  =  p_node - > get_meta ( " extras " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_json . has ( " extras " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  extras  =  p_json [ " extras " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											extras . merge ( node_extras ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_json [ " extras " ]  =  node_extras ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-20 21:39:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  Ref < ImporterMesh >  _mesh_to_importer_mesh ( Ref < Mesh >  p_mesh )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ImporterMesh >  importer_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									importer_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_mesh . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  importer_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ArrayMesh >  array_mesh  =  p_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_mesh - > get_blend_shape_count ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ArrayMesh : : BlendShapeMode  shape_mode  =  ArrayMesh : : BLEND_SHAPE_MODE_NORMALIZED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( array_mesh . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											shape_mode  =  array_mesh - > get_blend_shape_mode ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										importer_mesh - > set_blend_shape_mode ( shape_mode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  morph_i  =  0 ;  morph_i  <  p_mesh - > get_blend_shape_count ( ) ;  morph_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											importer_mesh - > add_blend_shape ( p_mesh - > get_blend_shape_name ( morph_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  surface_i  =  0 ;  surface_i  <  p_mesh - > get_surface_count ( ) ;  surface_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Array  array  =  p_mesh - > surface_get_arrays ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Material >  mat  =  p_mesh - > surface_get_material ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  mat_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( mat . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mat_name  =  mat - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Assign default material when no material is assigned.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-09 15:21:41 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mat . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-20 21:39:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										importer_mesh - > add_surface ( p_mesh - > surface_get_primitive_type ( surface_i ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array ,  p_mesh - > surface_get_blend_shape_arrays ( surface_i ) ,  p_mesh - > surface_get_lods ( surface_i ) ,  mat , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mat_name ,  p_mesh - > surface_get_format ( surface_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									importer_mesh - > merge_meta_from ( * p_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-20 21:39:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  importer_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-18 14:42:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2023-07-18 11:15:58 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Error  err  =  ext - > export_preserialize ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP CONVERT MESH INSTANCES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_convert_mesh_instances ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE CAMERAS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _serialize_cameras ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									/* STEP 3 CREATE SKINS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_skins ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE MESHES (we have enough info now) */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_meshes ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE TEXTURES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_materials ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE TEXTURE SAMPLERS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_texture_samplers ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE ANIMATIONS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_animations ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE ACCESSORS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _encode_accessors ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE IMAGES */ 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-18 14:42:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_images ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE TEXTURES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_textures ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFBufferViewIndex  i  =  0 ;  i  <  p_state - > buffer_views . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffer_views . write [ i ] - > buffer  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE BUFFER VIEWS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _encode_buffer_views ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE NODES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_nodes ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE SCENE */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_scenes ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE LIGHTS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_lights ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE EXTENSIONS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_gltf_extensions ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* STEP SERIALIZE VERSION */ 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-10 00:18:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _serialize_asset_header ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  ext - > export_post ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_gltf_extensions ( Ref < GLTFState >  p_state )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < String >  extensions_used  =  p_state - > extensions_used ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < String >  extensions_required  =  p_state - > extensions_required ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > lights . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										extensions_used . push_back ( " KHR_lights_punctual " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > use_khr_texture_transform )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										extensions_used . push_back ( " KHR_texture_transform " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										extensions_required . push_back ( " KHR_texture_transform " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! extensions_used . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:06:23 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										extensions_used . sort ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > json [ " extensionsUsed " ]  =  extensions_used ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! extensions_required . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:06:23 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										extensions_required . sort ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > json [ " extensionsRequired " ]  =  extensions_required ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_scenes ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2023-07-22 14:42:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Godot only supports one scene per glTF file.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  scenes ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 14:42:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Dictionary  scene_dict ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									scenes . append ( scene_dict ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " scenes " ]  =  scenes ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 14:42:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " scene " ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add nodes to the scene dict.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > root_nodes . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										scene_dict [ " nodes " ]  =  p_state - > root_nodes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 14:42:34 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > scene_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										scene_dict [ " name " ]  =  p_state - > scene_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_json ( const  String  & p_path ,  Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Error  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < FileAccess >  file  =  FileAccess : : open ( p_path ,  FileAccess : : READ ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( file . is_null ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < uint8_t >  array ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									array . resize ( file - > get_length ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									file - > get_buffer ( array . ptrw ( ) ,  array . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-30 19:56:38 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  text  =  String : : utf8 ( ( const  char  * ) array . ptr ( ) ,  array . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-29 18:12:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									JSON  json ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									err  =  json . parse ( text ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-22 17:36:40 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_err_print_error ( " " ,  p_path . utf8 ( ) . get_data ( ) ,  json . get_error_line ( ) ,  json . get_error_message ( ) . utf8 ( ) . get_data ( ) ,  false ,  ERR_HANDLER_SCRIPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json  =  json . get_data ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_glb ( Ref < FileAccess >  p_file ,  Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_file . is_null ( ) ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_state . is_null ( ) ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_file - > get_position ( )  ! =  0 ,  ERR_FILE_CANT_READ ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  magic  =  p_file - > get_32 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( magic  ! =  0x46546C67 ,  ERR_FILE_UNRECOGNIZED ) ;  //glTF
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_file - > get_32 ( ) ;  // version
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_file - > get_32 ( ) ;  // length
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  chunk_length  =  p_file - > get_32 ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  chunk_type  =  p_file - > get_32 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( chunk_type  ! =  0x4E4F534A ,  ERR_PARSE_ERROR ) ;  //JSON
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < uint8_t >  json_data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									json_data . resize ( chunk_length ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									uint32_t  len  =  p_file - > get_buffer ( json_data . ptrw ( ) ,  chunk_length ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( len  ! =  chunk_length ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-30 19:56:38 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  text  =  String : : utf8 ( ( const  char  * ) json_data . ptr ( ) ,  json_data . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-29 18:12:33 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									JSON  json ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  json . parse ( text ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_err_print_error ( " " ,  " " ,  json . get_error_line ( ) ,  json . get_error_message ( ) . utf8 ( ) . get_data ( ) ,  false ,  ERR_HANDLER_SCRIPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json  =  json . get_data ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//data?
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									chunk_length  =  p_file - > get_32 ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									chunk_type  =  p_file - > get_32 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_file - > eof_reached ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ;  //all good
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( chunk_type  ! =  0x004E4942 ,  ERR_PARSE_ERROR ) ;  //BIN
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > glb_data . resize ( chunk_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									len  =  p_file - > get_buffer ( p_state - > glb_data . ptrw ( ) ,  chunk_length ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( len  ! =  chunk_length ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  Array  _vec3_to_arr ( const  Vector3  & p_vec3 )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Array  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . resize ( 3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array [ 0 ]  =  p_vec3 . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array [ 1 ]  =  p_vec3 . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array [ 2 ]  =  p_vec3 . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								static  Vector3  _arr_to_vec3 ( const  Array  & p_array )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_array . size ( )  ! =  3 ,  Vector3 ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  Vector3 ( p_array [ 0 ] ,  p_array [ 1 ] ,  p_array [ 2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  Array  _quaternion_to_array ( const  Quaternion  & p_quaternion )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . resize ( 4 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									array [ 0 ]  =  p_quaternion . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array [ 1 ]  =  p_quaternion . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array [ 2 ]  =  p_quaternion . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array [ 3 ]  =  p_quaternion . w ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  Quaternion  _arr_to_quaternion ( const  Array  & p_array )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_array . size ( )  ! =  4 ,  Quaternion ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  Quaternion ( p_array [ 0 ] ,  p_array [ 1 ] ,  p_array [ 2 ] ,  p_array [ 3 ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  Transform3D  _arr_to_xform ( const  Array  & p_array )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_array . size ( )  ! =  16 ,  Transform3D ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Transform3D  xform ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									xform . basis . set_column ( Vector3 : : AXIS_X ,  Vector3 ( p_array [ 0 ] ,  p_array [ 1 ] ,  p_array [ 2 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									xform . basis . set_column ( Vector3 : : AXIS_Y ,  Vector3 ( p_array [ 4 ] ,  p_array [ 5 ] ,  p_array [ 6 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									xform . basis . set_column ( Vector3 : : AXIS_Z ,  Vector3 ( p_array [ 8 ] ,  p_array [ 9 ] ,  p_array [ 10 ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									xform . set_origin ( Vector3 ( p_array [ 12 ] ,  p_array [ 13 ] ,  p_array [ 14 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  xform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  Vector < real_t >  _xform_to_array ( const  Transform3D  p_transform )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < real_t >  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . resize ( 16 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector3  axis_x  =  p_transform . get_basis ( ) . get_column ( Vector3 : : AXIS_X ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									array . write [ 0 ]  =  axis_x . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 1 ]  =  axis_x . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 2 ]  =  axis_x . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 3 ]  =  0.0f ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector3  axis_y  =  p_transform . get_basis ( ) . get_column ( Vector3 : : AXIS_Y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									array . write [ 4 ]  =  axis_y . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 5 ]  =  axis_y . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 6 ]  =  axis_y . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 7 ]  =  0.0f ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector3  axis_z  =  p_transform . get_basis ( ) . get_column ( Vector3 : : AXIS_Z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									array . write [ 8 ]  =  axis_z . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 9 ]  =  axis_z . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 10 ]  =  axis_z . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 11 ]  =  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  origin  =  p_transform . get_origin ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 12 ]  =  origin . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 13 ]  =  origin . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 14 ]  =  origin . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									array . write [ 15 ]  =  1.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_nodes ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  nodes ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_state - > nodes . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  node ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										node [ " extensions " ]  =  extensions ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! gltf_node - > get_name ( ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node [ " name " ]  =  gltf_node - > get_name ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > camera  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node [ " camera " ]  =  gltf_node - > camera ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > light  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Dictionary  lights_punctual ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											extensions [ " KHR_lights_punctual " ]  =  lights_punctual ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											lights_punctual [ " light " ]  =  gltf_node - > light ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! gltf_node - > visible )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  khr_node_visibility ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											extensions [ " KHR_node_visibility " ]  =  khr_node_visibility ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											khr_node_visibility [ " visible " ]  =  gltf_node - > visible ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! p_state - > extensions_used . has ( " KHR_node_visibility " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > extensions_used . push_back ( " KHR_node_visibility " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( _visibility_mode  = =  VISIBILITY_MODE_INCLUDE_REQUIRED )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_state - > extensions_required . push_back ( " KHR_node_visibility " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > mesh  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node [ " mesh " ]  =  gltf_node - > mesh ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > skin  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node [ " skin " ]  =  gltf_node - > skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > skeleton  ! =  - 1  & &  gltf_node - > skin  <  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > transform . basis . is_orthogonal ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// An orthogonal transform is decomposable into TRS, so prefer that.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector3  position  =  gltf_node - > get_position ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! position . is_zero_approx ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												node [ " translation " ]  =  _vec3_to_arr ( position ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Quaternion  rotation  =  gltf_node - > get_rotation ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! rotation . is_equal_approx ( Quaternion ( ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												node [ " rotation " ]  =  _quaternion_to_array ( rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector3  scale  =  gltf_node - > get_scale ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! scale . is_equal_approx ( Vector3 ( 1.0f ,  1.0f ,  1.0f ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												node [ " scale " ]  =  _vec3_to_arr ( scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node [ " matrix " ]  =  _xform_to_array ( gltf_node - > transform ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > children . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Array  children ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  j  =  0 ;  j  <  gltf_node - > children . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												children . push_back ( gltf_node - > children [ j ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node [ " children " ]  =  children ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-10 16:08:25 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Node  * scene_node  =  nullptr ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-02 01:28:07 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( i  <  ( int ) p_state - > scene_nodes . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-10 16:08:25 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											scene_node  =  p_state - > scene_nodes [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-10 16:08:25 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Error  err  =  ext - > export_node ( p_state ,  gltf_node ,  node ,  scene_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( extensions . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node . erase ( " extensions " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_attach_meta_to_extras ( gltf_node ,  node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										nodes . push_back ( node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! nodes . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > json [ " nodes " ]  =  nodes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _gen_unique_name ( Ref < GLTFState >  p_state ,  const  String  & p_name )  {  
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  _gen_unique_name_static ( p_state - > unique_names ,  p_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _sanitize_animation_name ( const  String  & p_name )  {  
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  anim_name  =  p_name . validate_node_name ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 17:04:56 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  AnimationLibrary : : validate_library_name ( anim_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _gen_unique_animation_name ( Ref < GLTFState >  p_state ,  const  String  & p_name )  {  
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  String  s_name  =  _sanitize_animation_name ( p_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  u_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  index  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									while  ( true )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										u_name  =  s_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( index  >  1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											u_name  + =  itos ( index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! p_state - > unique_animation_names . has ( u_name ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										index + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > unique_animation_names . insert ( u_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  u_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-28 12:48:12 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-16 12:18:32 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _sanitize_bone_name ( const  String  & p_name )  {  
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  bone_name  =  p_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-28 12:15:00 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bone_name  =  bone_name . replace_chars ( " :/ " ,  ' _ ' ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  bone_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _gen_unique_bone_name ( Ref < GLTFState >  p_state ,  const  GLTFSkeletonIndex  p_skel_i ,  const  String  & p_name )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									String  s_name  =  _sanitize_bone_name ( p_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( s_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										s_name  =  " bone " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  u_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									int  index  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									while  ( true )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										u_name  =  s_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( index  >  1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											u_name  + =  " _ "  +  itos ( index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! p_state - > skeletons [ p_skel_i ] - > unique_names . has ( u_name ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										index + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > skeletons . write [ p_skel_i ] - > unique_names . insert ( u_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  u_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_scenes ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2023-01-26 09:14:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > unique_names . insert ( " Skeleton3D " ) ;  // Reserve skeleton name.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! p_state - > json . has ( " scenes " ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Array  & scenes  =  p_state - > json [ " scenes " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									int  loaded_scene  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > json . has ( " scene " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										loaded_scene  =  p_state - > json [ " scene " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										WARN_PRINT ( " The load-time scene is not defined in the glTF2 file. Picking the first scene. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( scenes . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( loaded_scene  > =  scenes . size ( ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 21:17:28 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Dictionary  & scene_dict  =  scenes [ loaded_scene ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! scene_dict . has ( " nodes " ) ,  ERR_UNAVAILABLE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Array  & nodes  =  scene_dict [ " nodes " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  nodes . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > root_nodes . push_back ( nodes [ j ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 21:17:28 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Determine what to use for the scene name.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( scene_dict . has ( " name " )  & &  ! String ( scene_dict [ " name " ] ) . is_empty ( )  & &  ! ( ( String ) scene_dict [ " name " ] ) . begins_with ( " Scene " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > scene_name  =  scene_dict [ " name " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-11-09 10:15:50 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  if  ( p_state - > scene_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 21:17:28 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > scene_name  =  p_state - > filename ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 17:55:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _naming_version  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > scene_name  =  _gen_unique_name ( p_state ,  p_state - > scene_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_nodes ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! p_state - > json . has ( " nodes " ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Array  & nodes  =  p_state - > json [ " nodes " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  nodes . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  node ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										node . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & n  =  nodes [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " name " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											node - > set_original_name ( n [ " name " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											node - > set_name ( n [ " name " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " camera " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node - > camera  =  n [ " camera " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " mesh " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node - > mesh  =  n [ " mesh " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " skin " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node - > skin  =  n [ " skin " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " matrix " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											node - > transform  =  _arr_to_xform ( n [ " matrix " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( n . has ( " translation " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												node - > set_position ( _arr_to_vec3 ( n [ " translation " ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( n . has ( " rotation " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												node - > set_rotation ( _arr_to_quaternion ( n [ " rotation " ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( n . has ( " scale " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												node - > set_scale ( _arr_to_vec3 ( n [ " scale " ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-07 09:28:57 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										node - > set_additional_data ( " GODOT_rest_transform " ,  node - > transform ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " extensions " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  extensions  =  n [ " extensions " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( extensions . has ( " KHR_lights_punctual " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  lights_punctual  =  extensions [ " KHR_lights_punctual " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( lights_punctual . has ( " light " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													GLTFLightIndex  light  =  lights_punctual [ " light " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													node - > light  =  light ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( extensions . has ( " KHR_node_visibility " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  khr_node_visibility  =  extensions [ " KHR_node_visibility " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( khr_node_visibility . has ( " visible " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													node - > visible  =  khr_node_visibility [ " visible " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  ext - > parse_node_extensions ( p_state ,  node ,  extensions ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE_MSG ( err  ! =  OK ,  " glTF: Encountered error  "  +  itos ( err )  +  "  when parsing node extensions for node  "  +  node - > get_name ( )  +  "  in file  "  +  p_state - > filename  +  " . Continuing. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( n . has ( " extras " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_attach_extras_to_meta ( n [ " extras " ] ,  node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( n . has ( " children " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Array  & children  =  n [ " children " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  j  =  0 ;  j  <  children . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												node - > children . push_back ( children [ j ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > nodes . push_back ( node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// build the hierarchy
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFNodeIndex  node_i  =  0 ;  node_i  <  p_state - > nodes . size ( ) ;  node_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  p_state - > nodes [ node_i ] - > children . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFNodeIndex  child_i  =  p_state - > nodes [ node_i ] - > children [ j ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_INDEX_V ( child_i ,  p_state - > nodes . size ( ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( p_state - > nodes [ child_i ] - > parent  ! =  - 1 ) ;  //node already has a parent, wtf.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > nodes . write [ child_i ] - > parent  =  node_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_compute_node_heights ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _compute_node_heights ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > root_nodes . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( GLTFNodeIndex  node_i  =  0 ;  node_i  <  p_state - > nodes . size ( ) ;  + + node_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  node  =  p_state - > nodes [ node_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										node - > height  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFNodeIndex  current_i  =  node_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										while  ( current_i  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  GLTFNodeIndex  parent_i  =  p_state - > nodes [ current_i ] - > parent ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( parent_i  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												+ + node - > height ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											current_i  =  parent_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( node - > height  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > root_nodes . push_back ( node_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								static  Vector < uint8_t >  _parse_base64_uri ( const  String  & p_uri )  {  
						 
					
						
							
								
									
										
										
										
											2024-11-16 18:52:15 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  start  =  p_uri . find_char ( ' , ' ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( start  = =  - 1 ,  Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CharString  substr  =  p_uri . substr ( start  +  1 ) . ascii ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  strlen  =  substr . length ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < uint8_t >  buf ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buf . resize ( strlen  /  4  *  3  +  1  +  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									size_t  len  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( CryptoCore : : b64_decode ( buf . ptrw ( ) ,  buf . size ( ) ,  & len ,  ( unsigned  char  * ) substr . get_data ( ) ,  strlen )  ! =  OK ,  Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buf . resize ( len ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  buf ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _encode_buffer_glb ( Ref < GLTFState >  p_state ,  const  String  & p_path )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total buffers:  "  +  itos ( p_state - > buffers . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Array  buffers ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Vector < uint8_t >  buffer_data  =  p_state - > buffers [ 0 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  gltf_buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_buffer [ " byteLength " ]  =  buffer_data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffers . push_back ( gltf_buffer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFBufferIndex  i  =  1 ;  i  <  p_state - > buffers . size ( )  -  1 ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < uint8_t >  buffer_data  =  p_state - > buffers [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  gltf_buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  filename  =  p_path . get_basename ( ) . get_file ( )  +  itos ( i )  +  " .bin " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  path  =  p_path . get_base_dir ( )  +  " / "  +  filename ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Error  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < FileAccess >  file  =  FileAccess : : open ( path ,  FileAccess : : WRITE ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( file . is_null ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( buffer_data . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										file - > create ( FileAccess : : ACCESS_RESOURCES ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_buffer ( buffer_data . ptr ( ) ,  buffer_data . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										gltf_buffer [ " uri " ]  =  filename ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_buffer [ " byteLength " ]  =  buffer_data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffers . push_back ( gltf_buffer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " buffers " ]  =  buffers ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _encode_buffer_bins ( Ref < GLTFState >  p_state ,  const  String  & p_path )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total buffers:  "  +  itos ( p_state - > buffers . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Array  buffers ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFBufferIndex  i  =  0 ;  i  <  p_state - > buffers . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < uint8_t >  buffer_data  =  p_state - > buffers [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  gltf_buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  filename  =  p_path . get_basename ( ) . get_file ( )  +  itos ( i )  +  " .bin " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  path  =  p_path . get_base_dir ( )  +  " / "  +  filename ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Error  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < FileAccess >  file  =  FileAccess : : open ( path ,  FileAccess : : WRITE ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( file . is_null ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( buffer_data . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										file - > create ( FileAccess : : ACCESS_RESOURCES ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_buffer ( buffer_data . ptr ( ) ,  buffer_data . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										gltf_buffer [ " uri " ]  =  filename ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_buffer [ " byteLength " ]  =  buffer_data . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffers . push_back ( gltf_buffer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " buffers " ]  =  buffers ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_buffers ( Ref < GLTFState >  p_state ,  const  String  & p_base_path )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " buffers " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & buffers  =  p_state - > json [ " buffers " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( GLTFBufferIndex  i  =  0 ;  i  <  buffers . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( i  = =  0  & &  p_state - > glb_data . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > buffers . push_back ( p_state - > glb_data ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & buffer  =  buffers [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( buffer . has ( " uri " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < uint8_t >  buffer_data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  uri  =  buffer [ " uri " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( uri . begins_with ( " data: " ) )  {  // Embedded data using base64.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Validate data MIME types and throw an error if it's one we don't know/support.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ! uri . begins_with ( " data:application/octet-stream;base64 " )  & & 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															! uri . begins_with ( " data:application/gltf-buffer;base64 " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_PRINT ( " glTF: Got buffer with an unknown URI data type:  "  +  uri ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													buffer_data  =  _parse_base64_uri ( uri ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  {  // Relative path to an external image file.
 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													ERR_FAIL_COND_V ( p_base_path . is_empty ( ) ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-04-07 22:49:57 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													uri  =  uri . uri_file_decode ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-28 12:15:00 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													uri  =  p_base_path . path_join ( uri ) . replace_char ( ' \\ ' ,  ' / ' ) ;  // Fix for Windows.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-18 14:04:16 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													ERR_FAIL_COND_V_MSG ( ! FileAccess : : exists ( uri ) ,  ERR_FILE_NOT_FOUND ,  " glTF: Binary file not found:  "  +  uri ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-21 15:04:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													buffer_data  =  FileAccess : : get_file_as_bytes ( uri ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-18 14:04:16 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													ERR_FAIL_COND_V_MSG ( buffer_data . is_empty ( ) ,  ERR_PARSE_ERROR ,  " glTF: Couldn't load binary file as an array:  "  +  uri ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( ! buffer . has ( " byteLength " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  byteLength  =  buffer [ " byteLength " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( byteLength  <  buffer_data . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_state - > buffers . push_back ( buffer_data ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total buffers:  "  +  itos ( p_state - > buffers . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _encode_buffer_views ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  buffers ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFBufferViewIndex  i  =  0 ;  i  <  p_state - > buffer_views . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFBufferView >  buffer_view  =  p_state - > buffer_views [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " buffer " ]  =  buffer_view - > buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " byteLength " ]  =  buffer_view - > byte_length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " byteOffset " ]  =  buffer_view - > byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( buffer_view - > byte_stride  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " byteStride " ]  =  buffer_view - > byte_stride ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( buffer_view - > indices )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " target " ]  =  GLTFDocument : : ELEMENT_ARRAY_BUFFER ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( buffer_view - > vertex_attributes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " target " ]  =  GLTFDocument : : ARRAY_BUFFER ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " buffer " ) ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " byteLength " ) ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffers . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total buffer views:  "  +  itos ( p_state - > buffer_views . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! buffers . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " bufferViews " ]  =  buffers ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_buffer_views ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " bufferViews " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-14 19:13:47 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & buffers  =  p_state - > json [ " bufferViews " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( GLTFBufferViewIndex  i  =  0 ;  i  <  buffers . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & d  =  buffers [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFBufferView >  buffer_view ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										buffer_view . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " buffer " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffer_view - > buffer  =  d [ " buffer " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " byteLength " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffer_view - > byte_length  =  d [ " byteLength " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " byteOffset " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer_view - > byte_offset  =  d [ " byteOffset " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " byteStride " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer_view - > byte_stride  =  d [ " byteStride " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 14:29:41 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( buffer_view - > byte_stride  <  4  | |  buffer_view - > byte_stride  >  252  | |  buffer_view - > byte_stride  %  4  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_PRINT ( " glTF import: Invalid byte stride  "  +  itos ( buffer_view - > byte_stride )  +  "  for buffer view at index  "  +  itos ( i )  +  "  while importing file ' "  +  p_state - > filename  +  " '. If defined, byte stride must be a multiple of 4 and between 4 and 252. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " target " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  target  =  d [ " target " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer_view - > indices  =  target  = =  GLTFDocument : : ELEMENT_ARRAY_BUFFER ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer_view - > vertex_attributes  =  target  = =  GLTFDocument : : ARRAY_BUFFER ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > buffer_views . push_back ( buffer_view ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total buffer views:  "  +  itos ( p_state - > buffer_views . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _encode_accessors ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  accessors ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFAccessorIndex  i  =  0 ;  i  <  p_state - > accessors . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFAccessor >  accessor  =  p_state - > accessors [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										d [ " componentType " ]  =  accessor - > component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " count " ]  =  accessor - > count ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										d [ " type " ]  =  _get_accessor_type_name ( accessor - > accessor_type ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 01:29:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										d [ " normalized " ]  =  accessor - > normalized ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										d [ " max " ]  =  accessor - > max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " min " ]  =  accessor - > min ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( accessor - > buffer_view  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// bufferView may be omitted to zero-initialize the buffer. When this happens, byteOffset MUST also be omitted.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " byteOffset " ]  =  accessor - > byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " bufferView " ]  =  accessor - > buffer_view ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( accessor - > sparse_count  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  s ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											s [ " count " ]  =  accessor - > sparse_count ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Dictionary  si ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											si [ " bufferView " ]  =  accessor - > sparse_indices_buffer_view ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											si [ " componentType " ]  =  accessor - > sparse_indices_component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( accessor - > sparse_indices_byte_offset  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												si [ " byteOffset " ]  =  accessor - > sparse_indices_byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! si . has ( " bufferView " )  | |  ! si . has ( " componentType " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											s [ " indices " ]  =  si ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Dictionary  sv ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sv [ " bufferView " ]  =  accessor - > sparse_values_buffer_view ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( accessor - > sparse_values_byte_offset  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												sv [ " byteOffset " ]  =  accessor - > sparse_values_byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! sv . has ( " bufferView " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											s [ " values " ]  =  sv ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! s . has ( " count " )  | |  ! s . has ( " indices " )  | |  ! s . has ( " values " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " sparse " ]  =  s ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										accessors . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! accessors . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " accessors " ]  =  accessors ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! p_state - > json . has ( " accessors " ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total accessors:  "  +  itos ( p_state - > accessors . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _get_accessor_type_name ( const  GLTFAccessor : : GLTFAccessorType  p_accessor_type )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_SCALAR )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " SCALAR " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_VEC2 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " VEC2 " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_VEC3 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " VEC3 " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_VEC4 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " VEC4 " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_MAT2 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " MAT2 " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_MAT3 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " MAT3 " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_MAT4 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  " MAT4 " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_V ( " SCALAR " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessor : : GLTFAccessorType  GLTFDocument : : _get_accessor_type_from_str ( const  String  & p_string )  {  
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_string  = =  " SCALAR " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_SCALAR ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_string  = =  " VEC2 " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_VEC2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_string  = =  " VEC3 " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_VEC3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_string  = =  " VEC4 " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_VEC4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_string  = =  " MAT2 " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_MAT2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_string  = =  " MAT3 " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_MAT3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_string  = =  " MAT4 " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  GLTFAccessor : : TYPE_MAT4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_V ( GLTFAccessor : : TYPE_SCALAR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_accessors ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " accessors " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-14 19:13:47 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & accessors  =  p_state - > json [ " accessors " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( GLTFAccessorIndex  i  =  0 ;  i  <  accessors . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & d  =  accessors [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " componentType " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										accessor - > component_type  =  ( GLTFAccessor : : GLTFComponentType ) ( int32_t ) d [ " componentType " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " count " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										accessor - > count  =  d [ " count " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 14:29:41 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( accessor - > count  < =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_PRINT ( " glTF import: Invalid accessor count  "  +  itos ( accessor - > count )  +  "  for accessor at index  "  +  itos ( i )  +  "  while importing file ' "  +  p_state - > filename  +  " '. Accessor count must be greater than 0. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " type " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										accessor - > accessor_type  =  _get_accessor_type_from_str ( d [ " type " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " bufferView " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > buffer_view  =  d [ " bufferView " ] ;  //optional because it may be sparse...
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " byteOffset " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > byte_offset  =  d [ " byteOffset " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 01:29:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( d . has ( " normalized " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > normalized  =  d [ " normalized " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " max " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > max  =  d [ " max " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " min " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > min  =  d [ " min " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " sparse " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & s  =  d [ " sparse " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! s . has ( " count " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > sparse_count  =  s [ " count " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! s . has ( " indices " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & si  =  s [ " indices " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! si . has ( " bufferView " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > sparse_indices_buffer_view  =  si [ " bufferView " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! si . has ( " componentType " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											accessor - > sparse_indices_component_type  =  ( GLTFAccessor : : GLTFComponentType ) ( int32_t ) si [ " componentType " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( si . has ( " byteOffset " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												accessor - > sparse_indices_byte_offset  =  si [ " byteOffset " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! s . has ( " values " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & sv  =  s [ " values " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! sv . has ( " bufferView " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											accessor - > sparse_values_buffer_view  =  sv [ " bufferView " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( sv . has ( " byteOffset " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												accessor - > sparse_values_byte_offset  =  sv [ " byteOffset " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total accessors:  "  +  itos ( p_state - > accessors . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								double  GLTFDocument : : _filter_number ( double  p_float )  {  
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! Math : : is_finite ( p_float ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// 3.6.2.2. "Values of NaN, +Infinity, and -Infinity MUST NOT be present."
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  ( double ) ( float ) p_float ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _get_component_type_name ( const  GLTFAccessor : : GLTFComponentType  p_component )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									switch  ( p_component )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_NONE : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  " None " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_BYTE : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  " Byte " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_BYTE : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  " UByte " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_SHORT : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  " Short " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  " UShort " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_INT : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  " Int " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_INT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  " UInt " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  " Float " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_DOUBLE_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  " Double " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_HALF_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  " Half " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_LONG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  " Long " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_LONG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  " ULong " ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  " <Error> " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _encode_buffer_view ( Ref < GLTFState >  p_state ,  const  double  * p_src ,  const  int  p_count ,  const  GLTFAccessor : : GLTFAccessorType  p_accessor_type ,  const  GLTFAccessor : : GLTFComponentType  p_component_type ,  const  bool  p_normalized ,  const  int  p_byte_offset ,  const  bool  p_for_vertex ,  GLTFBufferViewIndex  & r_accessor ,  const  bool  p_for_vertex_indices )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  component_count  =  COMPONENT_COUNT_FOR_ACCESSOR_TYPE [ p_accessor_type ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  component_size  =  _get_component_type_size ( p_component_type ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( component_size  = =  0 ,  FAILED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  skip_every  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  skip_bytes  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//special case of alignments, as described in spec
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( p_component_type )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_BYTE : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_BYTE :  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_MAT2 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skip_every  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skip_bytes  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_MAT3 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skip_every  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skip_bytes  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_SHORT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_accessor_type  = =  GLTFAccessor : : TYPE_MAT3 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skip_every  =  6 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skip_bytes  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFBufferView >  bv ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									bv . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint32_t  offset  =  bv - > byte_offset  =  p_byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < uint8_t >  & gltf_buffer  =  p_state - > buffers . write [ 0 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  stride  =  component_count  *  component_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_for_vertex  & &  stride  %  4 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										stride  + =  4  -  ( stride  %  4 ) ;  //according to spec must be multiple of 4
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//use to debug
 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: encoding accessor type  "  +  _get_accessor_type_name ( p_accessor_type )  +  "  component type:  "  +  _get_component_type_name ( p_component_type )  +  "  stride:  "  +  itos ( stride )  +  "  amount  "  +  itos ( p_count ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: encoding accessor offset  "  +  itos ( p_byte_offset )  +  "  view offset:  "  +  itos ( bv - > byte_offset )  +  "  total buffer len:  "  +  itos ( gltf_buffer . size ( ) )  +  "  view len  "  +  itos ( bv - > byte_length ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  buffer_end  =  ( stride  *  ( p_count  -  1 ) )  +  component_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									// TODO define bv->byte_stride
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bv - > byte_offset  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_for_vertex_indices )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bv - > indices  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( p_for_vertex )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bv - > vertex_attributes  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										bv - > byte_stride  =  stride ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( p_component_type )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_NONE :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V_MSG ( ERR_INVALID_DATA ,  " glTF: Failed to encode buffer view, component type not set. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_BYTE :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Vector < int8_t >  buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d  *  128.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( int8_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_BYTE :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Vector < uint8_t >  buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d  *  255.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . append_array ( buffer ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( uint8_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_SHORT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Vector < int16_t >  buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d  *  32768.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( int16_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Vector < uint16_t >  buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d  *  65535.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( uint16_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_INT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < int32_t >  buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( int32_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_INT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < uint32_t >  buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( uint32_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Vector < float >  buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( float ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_DOUBLE_FLOAT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < double >  buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( double ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_HALF_FLOAT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V_MSG ( ERR_UNAVAILABLE ,  " glTF: Half float not supported yet. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_LONG :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < int64_t >  buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// FIXME: This can result in precision loss because int64_t can store some values that double can't.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( int64_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_LONG :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < uint64_t >  buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer . resize ( p_count  *  component_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  dst_i  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( skip_every  & &  j  >  0  & &  ( j  %  skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														dst_i  + =  skip_bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// FIXME: This can result in precision loss because int64_t can store some values that double can't.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  d  =  * p_src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													buffer . write [ dst_i ]  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_src + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													dst_i + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2025-02-25 14:47:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  int64_t  old_size  =  gltf_buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  size_t  buffer_size  =  buffer . size ( )  *  sizeof ( uint64_t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_buffer . resize ( old_size  +  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											memcpy ( gltf_buffer . ptrw ( )  +  old_size ,  buffer . ptrw ( ) ,  buffer_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bv - > byte_length  =  buffer_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( buffer_end  >  bv - > byte_length ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ( int ) ( offset  +  buffer_end )  >  gltf_buffer . size ( ) ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  pad_bytes  =  ( 4  -  gltf_buffer . size ( ) )  &  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  pad_bytes ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_buffer . push_back ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									r_accessor  =  bv - > buffer  =  p_state - > buffer_views . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > buffer_views . push_back ( bv ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _decode_buffer_view ( Ref < GLTFState >  p_state ,  double  * p_dst ,  const  GLTFBufferViewIndex  p_buffer_view ,  const  int  p_skip_every ,  const  int  p_skip_bytes ,  const  int  p_element_size ,  const  int  p_count ,  const  GLTFAccessor : : GLTFAccessorType  p_accessor_type ,  const  int  p_component_count ,  const  GLTFAccessor : : GLTFComponentType  p_component_type ,  const  int  p_component_size ,  const  bool  p_normalized ,  const  int  p_byte_offset ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Ref < GLTFBufferView >  bv  =  p_state - > buffer_views [ p_buffer_view ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  stride  =  p_element_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 14:29:41 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( bv - > byte_stride  >  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										stride  =  bv - > byte_stride ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_for_vertex  & &  stride  %  4 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										stride  + =  4  -  ( stride  %  4 ) ;  //according to spec must be multiple of 4
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( bv - > buffer ,  p_state - > buffers . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  uint32_t  offset  =  bv - > byte_offset  +  p_byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < uint8_t >  buffer  =  p_state - > buffers [ bv - > buffer ] ;  //copy on write, so no performance hit
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									const  uint8_t  * bufptr  =  buffer . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//use to debug
 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: accessor type  "  +  _get_accessor_type_name ( p_accessor_type )  +  "  component type:  "  +  _get_component_type_name ( p_component_type )  +  "  stride:  "  +  itos ( stride )  +  "  amount  "  +  itos ( p_count ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: accessor offset  "  +  itos ( p_byte_offset )  +  "  view offset:  "  +  itos ( bv - > byte_offset )  +  "  total buffer len:  "  +  itos ( buffer . size ( ) )  +  "  view len  "  +  itos ( bv - > byte_length ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  buffer_end  =  ( stride  *  ( p_count  -  1 ) )  +  p_element_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( buffer_end  >  bv - > byte_length ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ( int ) ( offset  +  buffer_end )  >  buffer . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//fill everything as doubles
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										const  uint8_t  * src  =  & bufptr [ offset  +  i  *  stride ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  p_component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_skip_every  & &  j  >  0  & &  ( j  %  p_skip_every )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												src  + =  p_skip_bytes ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											double  d  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											switch  ( p_component_type )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_NONE :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_V_MSG ( ERR_INVALID_DATA ,  " glTF: Failed to decode buffer view, component type not set. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_BYTE :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													int8_t  b  =  int8_t ( * src ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														d  =  ( double ( b )  /  128.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														d  =  double ( b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_BYTE :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													uint8_t  b  =  * src ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														d  =  ( double ( b )  /  255.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														d  =  double ( b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_SHORT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													int16_t  s  =  * ( int16_t  * ) src ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														d  =  ( double ( s )  /  32768.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														d  =  double ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													uint16_t  s  =  * ( uint16_t  * ) src ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( p_normalized )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														d  =  ( double ( s )  /  65535.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														d  =  double ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_INT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													d  =  * ( int32_t  * ) src ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_INT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													d  =  * ( uint32_t  * ) src ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													d  =  * ( float  * ) src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_DOUBLE_FLOAT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													d  =  * ( double  * ) src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_HALF_FLOAT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_V_MSG ( ERR_UNAVAILABLE ,  " glTF: Half float not supported yet. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_LONG :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													d  =  * ( int64_t  * ) src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_LONG :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													d  =  * ( uint64_t  * ) src ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											* p_dst + +  =  d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src  + =  p_component_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								int  GLTFDocument : : _get_component_type_size ( const  GLTFAccessor : : GLTFComponentType  p_component_type )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									switch  ( p_component_type )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_NONE : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_BYTE : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_BYTE : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_SHORT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT : 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_HALF_FLOAT : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_INT : 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_INT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT : 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:39:04 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_DOUBLE_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_LONG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_LONG : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  8 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_V ( 0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < double >  GLTFDocument : : _decode_accessor ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									//spec, for reference:
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//https://github.com/KhronosGroup/glTF/tree/master/specification/2.0#data-alignment
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_accessor ,  p_state - > accessors . size ( ) ,  Vector < double > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Ref < GLTFAccessor >  a  =  p_state - > accessors [ p_accessor ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  component_count  =  COMPONENT_COUNT_FOR_ACCESSOR_TYPE [ a - > accessor_type ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									const  int  component_size  =  _get_component_type_size ( a - > component_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( component_size  = =  0 ,  Vector < double > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  element_size  =  component_count  *  component_size ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  skip_every  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  skip_bytes  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									//special case of alignments, as described in spec
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									switch  ( a - > component_type )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_BYTE : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_BYTE :  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( a - > accessor_type  = =  GLTFAccessor : : TYPE_MAT2 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skip_every  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skip_bytes  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												element_size  =  8 ;  //override for this case
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( a - > accessor_type  = =  GLTFAccessor : : TYPE_MAT3 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skip_every  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skip_bytes  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												element_size  =  12 ;  //override for this case
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_SIGNED_SHORT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT :  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( a - > accessor_type  = =  GLTFAccessor : : TYPE_MAT3 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skip_every  =  6 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skip_bytes  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												element_size  =  16 ;  //override for this case
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  dst_buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									dst_buffer . resize ( component_count  *  a - > count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  * dst  =  dst_buffer . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( a - > buffer_view  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_INDEX_V ( a - > buffer_view ,  p_state - > buffer_views . size ( ) ,  Vector < double > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Error  err  =  _decode_buffer_view ( p_state ,  dst ,  a - > buffer_view ,  skip_every ,  skip_bytes ,  element_size ,  a - > count ,  a - > accessor_type ,  component_count ,  a - > component_type ,  component_size ,  a - > normalized ,  a - > byte_offset ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  Vector < double > ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//fill with zeros, as bufferview is not defined.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  ( a - > count  *  component_count ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											dst_buffer . write [ i ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( a - > sparse_count  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// I could not find any file using this, so this code is so far untested
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < double >  indices ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										indices . resize ( a - > sparse_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  int  indices_component_size  =  _get_component_type_size ( a - > sparse_indices_component_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Error  err  =  _decode_buffer_view ( p_state ,  indices . ptrw ( ) ,  a - > sparse_indices_buffer_view ,  0 ,  0 ,  indices_component_size ,  a - > sparse_count ,  GLTFAccessor : : TYPE_SCALAR ,  1 ,  a - > sparse_indices_component_type ,  indices_component_size ,  false ,  a - > sparse_indices_byte_offset ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  Vector < double > ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < double >  data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										data . resize ( component_count  *  a - > sparse_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _decode_buffer_view ( p_state ,  data . ptrw ( ) ,  a - > sparse_values_buffer_view ,  skip_every ,  skip_bytes ,  element_size ,  a - > sparse_count ,  a - > accessor_type ,  component_count ,  a - > component_type ,  component_size ,  a - > normalized ,  a - > sparse_values_byte_offset ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  Vector < double > ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  indices . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  write_offset  =  int ( indices [ i ] )  *  component_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  j  =  0 ;  j  <  component_count ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												dst [ write_offset  +  j ]  =  data [ i  *  component_count  +  j ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  dst_buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_ints ( Ref < GLTFState >  p_state ,  const  Vector < int32_t >  p_attribs ,  const  bool  p_for_vertex ,  const  bool  p_for_vertex_indices )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  max_index  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ i ]  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_attribs [ i ]  >  max_index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											max_index  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( i  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int32_t  type_i  =  0 ;  type_i  <  element_count ;  type_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												type_max . write [ type_i ]  =  attribs [ ( i  *  element_count )  +  type_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												type_min . write [ type_i ]  =  attribs [ ( i  *  element_count )  +  type_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  type_i  =  0 ;  type_i  <  element_count ;  type_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											type_max . write [ type_i ]  =  MAX ( attribs [ ( i  *  element_count )  +  type_i ] ,  type_max [ type_i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											type_min . write [ type_i ]  =  MIN ( attribs [ ( i  *  element_count )  +  type_i ] ,  type_min [ type_i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-19 13:21:39 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . is_empty ( ) ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_SCALAR ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFAccessor : : GLTFComponentType  component_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( max_index  >  65535  | |  p_for_vertex )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										component_type  =  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_INT ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										component_type  =  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  ret_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ,  p_for_vertex_indices ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < int >  GLTFDocument : : _decode_accessor_as_ints ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex ,  const  Vector < int >  & p_packed_vertex_ids )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < int >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  double  * attribs_ptr  =  attribs . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ret_size  =  attribs . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( p_packed_vertex_ids [ p_packed_vertex_ids . size ( )  -  1 ]  > =  ret_size ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret_size  =  p_packed_vertex_ids . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  src_i  =  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_i  =  p_packed_vertex_ids [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ]  =  int ( attribs_ptr [ src_i ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < float >  GLTFDocument : : _decode_accessor_as_floats ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex ,  const  Vector < int >  & p_packed_vertex_ids )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < float >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  double  * attribs_ptr  =  attribs . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ret_size  =  attribs . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( p_packed_vertex_ids [ p_packed_vertex_ids . size ( )  -  1 ]  > =  ret_size ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret_size  =  p_packed_vertex_ids . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  src_i  =  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_i  =  p_packed_vertex_ids [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ]  =  float ( attribs_ptr [ src_i ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _round_min_max_components ( Vector < double >  & r_type_min ,  Vector < double >  & r_type_max )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// 3.6.2.5: For floating-point components, JSON-stored minimum and maximum values represent single precision
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// floats and SHOULD be rounded to single precision before usage to avoid any potential boundary mismatches.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  type_i  =  0 ;  type_i  <  r_type_min . size ( ) ;  type_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_type_min . write [ type_i ]  =  ( double ) ( float ) r_type_min [ type_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_type_max . write [ type_i ]  =  ( double ) ( float ) r_type_max [ type_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_vec2 ( Ref < GLTFState >  p_state ,  const  Vector < Vector2 >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  element_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector2  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( attrib . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( attrib . y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_color ( Ref < GLTFState >  p_state ,  const  Vector < Color >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Color  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( attrib . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( attrib . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  2 ]  =  _filter_number ( attrib . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  3 ]  =  _filter_number ( attrib . a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _calc_accessor_min_max ( int  p_i ,  const  int  p_element_count ,  Vector < double >  & p_type_max ,  Vector < double >  p_attribs ,  Vector < double >  & p_type_min )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_i  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  type_i  =  0 ;  type_i  <  p_element_count ;  type_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_type_max . write [ type_i ]  =  p_attribs [ ( p_i  *  p_element_count )  +  type_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_type_min . write [ type_i ]  =  p_attribs [ ( p_i  *  p_element_count )  +  type_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int32_t  type_i  =  0 ;  type_i  <  p_element_count ;  type_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_type_max . write [ type_i ]  =  MAX ( p_attribs [ ( p_i  *  p_element_count )  +  type_i ] ,  p_type_max [ type_i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_type_min . write [ type_i ]  =  MIN ( p_attribs [ ( p_i  *  p_element_count )  +  type_i ] ,  p_type_min [ type_i ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_weights ( Ref < GLTFState >  p_state ,  const  Vector < Color >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Color  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( attrib . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( attrib . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  2 ]  =  _filter_number ( attrib . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  3 ]  =  _filter_number ( attrib . a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_joints ( Ref < GLTFState >  p_state ,  const  Vector < Color >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  element_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Color  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( attrib . r ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( attrib . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  2 ]  =  _filter_number ( attrib . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  3 ]  =  _filter_number ( attrib . a ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_quaternions ( Ref < GLTFState >  p_state ,  const  Vector < Quaternion >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  element_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Quaternion  quaternion  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( quaternion . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( quaternion . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  2 ]  =  _filter_number ( quaternion . z ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  3 ]  =  _filter_number ( quaternion . w ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Vector2 >  GLTFDocument : : _decode_accessor_as_vec2 ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex ,  const  Vector < int >  & p_packed_vertex_ids )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < Vector2 >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  2  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  double  * attribs_ptr  =  attribs . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ret_size  =  attribs . size ( )  /  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( p_packed_vertex_ids [ p_packed_vertex_ids . size ( )  -  1 ]  > =  ret_size ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret_size  =  p_packed_vertex_ids . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  src_i  =  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_i  =  p_packed_vertex_ids [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ]  =  Vector2 ( attribs_ptr [ src_i  *  2  +  0 ] ,  attribs_ptr [ src_i  *  2  +  1 ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_floats ( Ref < GLTFState >  p_state ,  const  Vector < double >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ i ]  =  _filter_number ( p_attribs [ i ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-19 13:21:39 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . is_empty ( ) ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_SCALAR ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  ret_size ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_vec3 ( Ref < GLTFState >  p_state ,  const  Vector < Vector3 >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  element_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( attrib . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( attrib . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  2 ]  =  _filter_number ( attrib . z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_sparse_accessor_as_vec3 ( Ref < GLTFState >  p_state ,  const  Vector < Vector3 >  p_attribs ,  const  Vector < Vector3 >  p_reference_attribs ,  const  float  p_reference_multiplier ,  const  bool  p_for_vertex ,  const  GLTFAccessorIndex  p_reference_accessor )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( p_attribs . size ( )  *  element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  changed_indices ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  changed_values ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  max_changed_index  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bool  is_different  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( i  <  p_reference_attribs . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											is_different  =  ! ( attrib  *  p_reference_multiplier ) . is_equal_approx ( p_reference_attribs [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! is_different )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												attrib  =  p_reference_attribs [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											is_different  =  ! ( attrib  *  p_reference_multiplier ) . is_zero_approx ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! is_different )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												attrib  =  Vector3 ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  0 ]  =  _filter_number ( attrib . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  1 ]  =  _filter_number ( attrib . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ ( i  *  element_count )  +  2 ]  =  _filter_number ( attrib . z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( is_different )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											changed_indices . push_back ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( i  >  max_changed_index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												max_changed_index  =  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											changed_values . push_back ( _filter_number ( attrib . x ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											changed_values . push_back ( _filter_number ( attrib . y ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											changed_values . push_back ( _filter_number ( attrib . z ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( attribs . size ( )  %  element_count  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  sparse_accessor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sparse_accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_VEC3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sparse_accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sparse_accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sparse_accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									sparse_accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_reference_accessor  <  p_state - > accessors . size ( )  & &  p_reference_accessor  > =  0  & &  p_state - > accessors [ p_reference_accessor ] . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > byte_offset  =  p_state - > accessors [ p_reference_accessor ] - > byte_offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > buffer_view  =  p_state - > accessors [ p_reference_accessor ] - > buffer_view ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sparse_accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									sparse_accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  sparse_accessor_index_stride  =  max_changed_index  >  65535  ?  4  :  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  sparse_accessor_storage_size  =  changed_indices . size ( )  *  ( sparse_accessor_index_stride  +  element_count  *  sizeof ( float ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  conventional_storage_size  =  p_attribs . size ( )  *  element_count  *  sizeof ( float ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( changed_indices . size ( )  >  0  & &  sparse_accessor_storage_size  <  conventional_storage_size )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// It must be worthwhile to use a sparse accessor.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFBufferIndex  buffer_view_i_indices  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFBufferIndex  buffer_view_i_values  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( sparse_accessor_index_stride  = =  4 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											sparse_accessor - > sparse_indices_component_type  =  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_INT ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											sparse_accessor - > sparse_indices_component_type  =  GLTFAccessor : : COMPONENT_TYPE_UNSIGNED_SHORT ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _encode_buffer_view ( p_state ,  changed_indices . ptr ( ) ,  changed_indices . size ( ) ,  GLTFAccessor : : TYPE_SCALAR ,  sparse_accessor - > sparse_indices_component_type ,  sparse_accessor - > normalized ,  sparse_accessor - > sparse_indices_byte_offset ,  false ,  buffer_view_i_indices )  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// We use changed_indices.size() here, because we must pass the number of vec3 values rather than the number of components.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _encode_buffer_view ( p_state ,  changed_values . ptr ( ) ,  changed_indices . size ( ) ,  sparse_accessor - > accessor_type ,  sparse_accessor - > component_type ,  sparse_accessor - > normalized ,  sparse_accessor - > sparse_values_byte_offset ,  false ,  buffer_view_i_values )  ! =  OK )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > sparse_indices_buffer_view  =  buffer_view_i_indices ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > sparse_values_buffer_view  =  buffer_view_i_values ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > sparse_count  =  changed_indices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( changed_indices . size ( )  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  sparse_accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sparse_accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( sparse_accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_xform ( Ref < GLTFState >  p_state ,  const  Vector < Transform3D >  p_attribs ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  element_count  =  16 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  p_attribs . size ( )  *  element_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( element_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Transform3D  attrib  =  p_attribs [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Basis  basis  =  attrib . get_basis ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Vector3  axis_0  =  basis . get_column ( Vector3 : : AXIS_X ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  0 ]  =  _filter_number ( axis_0 . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  1 ]  =  _filter_number ( axis_0 . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  2 ]  =  _filter_number ( axis_0 . z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  3 ]  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Vector3  axis_1  =  basis . get_column ( Vector3 : : AXIS_Y ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  4 ]  =  _filter_number ( axis_1 . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  5 ]  =  _filter_number ( axis_1 . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  6 ]  =  _filter_number ( axis_1 . z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  7 ]  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Vector3  axis_2  =  basis . get_column ( Vector3 : : AXIS_Z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  8 ]  =  _filter_number ( axis_2 . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  9 ]  =  _filter_number ( axis_2 . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  10 ]  =  _filter_number ( axis_2 . z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  11 ]  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector3  origin  =  attrib . get_origin ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  12 ]  =  _filter_number ( origin . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  13 ]  =  _filter_number ( origin . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  14 ]  =  _filter_number ( origin . z ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										attribs . write [ i  *  element_count  +  15 ]  =  1.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  element_count ,  type_max ,  attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  element_count  ! =  0 ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int64_t  size  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFAccessorType  accessor_type  =  GLTFAccessor : : TYPE_MAT4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:02:36 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFAccessor : : GLTFComponentType  component_type  =  GLTFAccessor : : COMPONENT_TYPE_SINGLE_FLOAT ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > normalized  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									accessor - > accessor_type  =  accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  attribs . ptr ( ) ,  p_attribs . size ( ) ,  accessor_type ,  component_type ,  accessor - > normalized ,  size ,  p_for_vertex ,  buffer_view_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  p_state - > accessors . size ( )  -  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Vector3 >  GLTFDocument : : _decode_accessor_as_vec3 ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex ,  const  Vector < int >  & p_packed_vertex_ids )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < Vector3 >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  3  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  double  * attribs_ptr  =  attribs . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ret_size  =  attribs . size ( )  /  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( p_packed_vertex_ids [ p_packed_vertex_ids . size ( )  -  1 ]  > =  ret_size ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret_size  =  p_packed_vertex_ids . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  src_i  =  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_i  =  p_packed_vertex_ids [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ]  =  Vector3 ( attribs_ptr [ src_i  *  3  +  0 ] ,  attribs_ptr [ src_i  *  3  +  1 ] ,  attribs_ptr [ src_i  *  3  +  2 ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Color >  GLTFDocument : : _decode_accessor_as_color ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex ,  const  Vector < int >  & p_packed_vertex_ids )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < Color >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-04-11 21:29:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  int  accessor_type  =  p_state - > accessors [ p_accessor ] - > accessor_type ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! ( accessor_type  = =  GLTFAccessor : : TYPE_VEC3  | |  accessor_type  = =  GLTFAccessor : : TYPE_VEC4 ) ,  ret ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									int  vec_len  =  3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-03 19:57:17 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( accessor_type  = =  GLTFAccessor : : TYPE_VEC4 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										vec_len  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  vec_len  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  double  * attribs_ptr  =  attribs . ptr ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int  ret_size  =  attribs . size ( )  /  vec_len ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( p_packed_vertex_ids [ p_packed_vertex_ids . size ( )  -  1 ]  > =  ret_size ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret_size  =  p_packed_vertex_ids . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										int  src_i  =  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! p_packed_vertex_ids . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											src_i  =  p_packed_vertex_ids [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ]  =  Color ( attribs_ptr [ src_i  *  vec_len  +  0 ] ,  attribs_ptr [ src_i  *  vec_len  +  1 ] ,  attribs_ptr [ src_i  *  vec_len  +  2 ] ,  vec_len  = =  4  ?  attribs_ptr [ src_i  *  4  +  3 ]  :  1.0 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Quaternion >  GLTFDocument : : _decode_accessor_as_quaternion ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector < Quaternion >  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  4  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  double  * attribs_ptr  =  attribs . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  attribs . size ( )  /  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ret . write [ i ]  =  Quaternion ( attribs_ptr [ i  *  4  +  0 ] ,  attribs_ptr [ i  *  4  +  1 ] ,  attribs_ptr [ i  *  4  +  2 ] ,  attribs_ptr [ i  *  4  +  3 ] ) . normalized ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Transform2D >  GLTFDocument : : _decode_accessor_as_xform2d ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < Transform2D >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  4  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . resize ( attribs . size ( )  /  4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] [ 0 ]  =  Vector2 ( attribs [ i  *  4  +  0 ] ,  attribs [ i  *  4  +  1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] [ 1 ]  =  Vector2 ( attribs [ i  *  4  +  2 ] ,  attribs [ i  *  4  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Basis >  GLTFDocument : : _decode_accessor_as_basis ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < Basis >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  9  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . resize ( attribs . size ( )  /  9 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ] . set_column ( 0 ,  Vector3 ( attribs [ i  *  9  +  0 ] ,  attribs [ i  *  9  +  1 ] ,  attribs [ i  *  9  +  2 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] . set_column ( 1 ,  Vector3 ( attribs [ i  *  9  +  3 ] ,  attribs [ i  *  9  +  4 ] ,  attribs [ i  *  9  +  5 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] . set_column ( 2 ,  Vector3 ( attribs [ i  *  9  +  6 ] ,  attribs [ i  *  9  +  7 ] ,  attribs [ i  *  9  +  8 ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Transform3D >  GLTFDocument : : _decode_accessor_as_xform ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  const  bool  p_for_vertex )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  p_for_vertex ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector < Transform3D >  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( attribs . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( attribs . size ( )  %  16  ! =  0 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . resize ( attribs . size ( )  /  16 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-03 07:50:35 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ret . write [ i ] . basis . set_column ( 0 ,  Vector3 ( attribs [ i  *  16  +  0 ] ,  attribs [ i  *  16  +  1 ] ,  attribs [ i  *  16  +  2 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] . basis . set_column ( 1 ,  Vector3 ( attribs [ i  *  16  +  4 ] ,  attribs [ i  *  16  +  5 ] ,  attribs [ i  *  16  +  6 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] . basis . set_column ( 2 ,  Vector3 ( attribs [ i  *  16  +  8 ] ,  attribs [ i  *  16  +  9 ] ,  attribs [ i  *  16  +  10 ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										ret . write [ i ] . set_origin ( Vector3 ( attribs [ i  *  16  +  12 ] ,  attribs [ i  *  16  +  13 ] ,  attribs [ i  *  16  +  14 ] ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-29 11:14:09 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Variant >  GLTFDocument : : _decode_accessor_as_variant ( Ref < GLTFState >  p_state ,  const  GLTFAccessorIndex  p_accessor ,  Variant : : Type  p_variant_type ,  GLTFAccessor : : GLTFAccessorType  p_accessor_type )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < double >  attribs  =  _decode_accessor ( p_state ,  p_accessor ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < Variant >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( attribs . is_empty ( ) ,  ret ,  " glTF: The accessor was empty. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  component_count  =  COMPONENT_COUNT_FOR_ACCESSOR_TYPE [ p_accessor_type ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( attribs . size ( )  %  component_count  ! =  0 ,  ret ,  " glTF: The accessor size was not a multiple of the component count. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  ret_size  =  attribs . size ( )  /  component_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										switch  ( p_variant_type )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : BOOL :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  attribs [ i  *  component_count ]  ! =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : INT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  ( int64_t ) attribs [ i  *  component_count ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : FLOAT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  attribs [ i  *  component_count ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : RECT2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : PLANE : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : QUATERNION :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// General-purpose code for importing glTF accessor data with any component count into structs up to 4 `real_t`s in size.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Variant  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  1 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4 ( attribs [ i  *  component_count ] ,  0.0f ,  0.0f ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  2 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4 ( attribs [ i  *  component_count ] ,  attribs [ i  *  component_count  +  1 ] ,  0.0f ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  3 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4 ( attribs [ i  *  component_count ] ,  attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  2 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4 ( attribs [ i  *  component_count ] ,  attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Evil hack that relies on the structure of Variant, but it's the
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// only way to accomplish this without a ton of code duplication.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												* ( Variant : : Type  * ) & v  =  p_variant_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR2I : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : RECT2I : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR3I : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR4I :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// General-purpose code for importing glTF accessor data with any component count into structs up to 4 `int32_t`s in size.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Variant  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  1 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4i ( ( int32_t ) attribs [ i  *  component_count ] ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  2 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4i ( ( int32_t ) attribs [ i  *  component_count ] ,  ( int32_t ) attribs [ i  *  component_count  +  1 ] ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  3 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4i ( ( int32_t ) attribs [ i  *  component_count ] ,  ( int32_t ) attribs [ i  *  component_count  +  1 ] ,  ( int32_t ) attribs [ i  *  component_count  +  2 ] ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Vector4i ( ( int32_t ) attribs [ i  *  component_count ] ,  ( int32_t ) attribs [ i  *  component_count  +  1 ] ,  ( int32_t ) attribs [ i  *  component_count  +  2 ] ,  ( int32_t ) attribs [ i  *  component_count  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Evil hack that relies on the structure of Variant, but it's the
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// only way to accomplish this without a ton of code duplication.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												* ( Variant : : Type  * ) & v  =  p_variant_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// No more generalized hacks, each of the below types needs a lot of repetitive code.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : COLOR :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Variant  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  1 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Color ( attribs [ i  *  component_count ] ,  0.0f ,  0.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  2 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Color ( attribs [ i  *  component_count ] ,  attribs [ i  *  component_count  +  1 ] ,  0.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  3 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Color ( attribs [ i  *  component_count ] ,  attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  2 ] ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  Color ( attribs [ i  *  component_count ] ,  attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : TRANSFORM2D :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Transform2D  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 0 ]  =  Vector2 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 1 ]  =  Vector2 ( attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  9 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 0 ]  =  Vector2 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 1 ]  =  Vector2 ( attribs [ i  *  component_count  +  3 ] ,  attribs [ i  *  component_count  +  4 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 2 ]  =  Vector2 ( attribs [ i  *  component_count  +  6 ] ,  attribs [ i  *  component_count  +  7 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 0 ]  =  Vector2 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 1 ]  =  Vector2 ( attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  5 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . columns [ 2 ]  =  Vector2 ( attribs [ i  *  component_count  +  12 ] ,  attribs [ i  *  component_count  +  13 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : BASIS :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Basis  b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 0 ]  =  Vector3 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  2 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 1 ]  =  Vector3 ( attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  3 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  9 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 0 ]  =  Vector3 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  3 ] ,  attribs [ i  *  component_count  +  6 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 1 ]  =  Vector3 ( attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  7 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 2 ]  =  Vector3 ( attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  5 ] ,  attribs [ i  *  component_count  +  8 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 0 ]  =  Vector3 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  8 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 1 ]  =  Vector3 ( attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  5 ] ,  attribs [ i  *  component_count  +  9 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														b . rows [ 2 ]  =  Vector3 ( attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  6 ] ,  attribs [ i  *  component_count  +  10 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : TRANSFORM3D :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Transform3D  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 0 ]  =  Vector3 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  2 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 1 ]  =  Vector3 ( attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  3 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  9 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 0 ]  =  Vector3 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  3 ] ,  attribs [ i  *  component_count  +  6 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 1 ]  =  Vector3 ( attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  7 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 2 ]  =  Vector3 ( attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  5 ] ,  attribs [ i  *  component_count  +  8 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 0 ]  =  Vector3 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  8 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 1 ]  =  Vector3 ( attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  5 ] ,  attribs [ i  *  component_count  +  9 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . basis . rows [ 2 ]  =  Vector3 ( attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  6 ] ,  attribs [ i  *  component_count  +  10 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														t . origin  =  Vector3 ( attribs [ i  *  component_count  +  12 ] ,  attribs [ i  *  component_count  +  13 ] ,  attribs [ i  *  component_count  +  14 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : PROJECTION :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Projection  p ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												switch  ( component_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  4 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 0 ]  =  Vector4 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  1 ] ,  0.0f ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 1 ]  =  Vector4 ( attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  5 ] ,  0.0f ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  9 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 0 ]  =  Vector4 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  2 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 1 ]  =  Vector4 ( attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  5 ] ,  attribs [ i  *  component_count  +  6 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 2 ]  =  Vector4 ( attribs [ i  *  component_count  +  8 ] ,  attribs [ i  *  component_count  +  9 ] ,  attribs [ i  *  component_count  +  10 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													case  16 :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 0 ]  =  Vector4 ( attribs [ i  *  component_count  +  0 ] ,  attribs [ i  *  component_count  +  1 ] ,  attribs [ i  *  component_count  +  2 ] ,  attribs [ i  *  component_count  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 1 ]  =  Vector4 ( attribs [ i  *  component_count  +  4 ] ,  attribs [ i  *  component_count  +  5 ] ,  attribs [ i  *  component_count  +  6 ] ,  attribs [ i  *  component_count  +  7 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 2 ]  =  Vector4 ( attribs [ i  *  component_count  +  8 ] ,  attribs [ i  *  component_count  +  9 ] ,  attribs [ i  *  component_count  +  10 ] ,  attribs [ i  *  component_count  +  11 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p . columns [ 3 ]  =  Vector4 ( attribs [ i  *  component_count  +  12 ] ,  attribs [ i  *  component_count  +  13 ] ,  attribs [ i  *  component_count  +  14 ] ,  attribs [ i  *  component_count  +  15 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret . write [ i ]  =  p ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_V_MSG ( ret ,  " glTF: Cannot decode accessor as Variant of type  "  +  Variant : : get_type_name ( p_variant_type )  +  " . " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								GLTFAccessorIndex  GLTFDocument : : _encode_accessor_as_variant ( Ref < GLTFState >  p_state ,  Vector < Variant >  p_attribs ,  Variant : : Type  p_variant_type ,  GLTFAccessor : : GLTFAccessorType  p_accessor_type ,  GLTFAccessor : : GLTFComponentType  p_component_type )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  accessor_component_count  =  COMPONENT_COUNT_FOR_ACCESSOR_TYPE [ p_accessor_type ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  encoded_attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( const  Variant  & v  :  p_attribs )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										switch  ( p_variant_type )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : NIL : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : BOOL : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : INT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : FLOAT :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// For scalar values, just append them. Variant can convert all of these to double. Some padding may also be needed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												encoded_attribs . append ( v ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( unlikely ( accessor_component_count  >  1 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  1 ;  i  <  accessor_component_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( 0.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR2I : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR3 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR3I : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR4 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : VECTOR4I :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Variant can handle converting Vector2/2i/3/3i/4/4i to Vector4 for us.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector4  vec  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( likely ( accessor_component_count  <  5 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  accessor_component_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( vec [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : PLANE :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Plane  p  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( likely ( accessor_component_count  = =  4 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . normal . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . normal . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . normal . z ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : QUATERNION :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Quaternion  q  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( likely ( accessor_component_count  <  5 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  accessor_component_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( q [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : COLOR :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Color  c  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( likely ( accessor_component_count  <  5 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  accessor_component_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( c [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : RECT2 : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : RECT2I :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Variant can handle converting Rect2i to Rect2 for us.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Rect2  r  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( likely ( accessor_component_count  = =  4 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( r . position . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( r . position . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( r . size . x ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( r . size . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : TRANSFORM2D : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : BASIS : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : TRANSFORM3D : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											case  Variant : : PROJECTION :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Variant can handle converting Transform2D/Transform3D/Basis to Projection for us.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Projection  p  =  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( accessor_component_count  = =  16 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  4 ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 0 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( accessor_component_count  = =  9 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  3 ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 0 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														encoded_attribs . append ( p . columns [ i ] [ 2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( accessor_component_count  = =  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . columns [ 0 ] [ 0 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . columns [ 0 ] [ 1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . columns [ 1 ] [ 0 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													encoded_attribs . append ( p . columns [ 1 ] [ 1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_V_MSG ( - 1 ,  " glTF: Cannot encode accessor from Variant of type  "  +  Variant : : get_type_name ( p_variant_type )  +  " . " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Determine the min and max values for the accessor.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_max . resize ( accessor_component_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < double >  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									type_min . resize ( accessor_component_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  encoded_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( Math : : is_zero_approx ( encoded_attribs [ i ] ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											encoded_attribs . write [ i ]  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											encoded_attribs . write [ i ]  =  _filter_number ( encoded_attribs [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_attribs . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_calc_accessor_min_max ( i ,  accessor_component_count ,  type_max ,  encoded_attribs ,  type_min ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_round_min_max_components ( type_min ,  type_max ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Encode the data in a buffer view.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									GLTFBufferIndex  buffer_view_index  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_state - > buffers . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int64_t  buffer_size  =  p_state - > buffers [ buffer_view_index ] . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_view ( p_state ,  encoded_attribs . ptr ( ) ,  p_attribs . size ( ) ,  p_accessor_type ,  p_component_type ,  false ,  buffer_size ,  false ,  buffer_view_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Create the accessor and fill it with the data.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAccessor >  accessor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > max  =  type_max ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > min  =  type_min ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > count  =  p_attribs . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > accessor_type  =  p_accessor_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > component_type  =  p_component_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > byte_offset  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									accessor - > buffer_view  =  buffer_view_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  GLTFAccessorIndex  new_accessor_index  =  p_state - > accessors . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > accessors . push_back ( accessor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  new_accessor_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_meshes ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  meshes ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFMeshIndex  gltf_mesh_i  =  0 ;  gltf_mesh_i  <  p_state - > meshes . size ( ) ;  gltf_mesh_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										print_verbose ( " glTF: Serializing mesh:  "  +  itos ( gltf_mesh_i ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < ImporterMesh >  import_mesh  =  p_state - > meshes . write [ gltf_mesh_i ] - > get_mesh ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( import_mesh . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Array  instance_materials  =  p_state - > meshes . write [ gltf_mesh_i ] - > get_instance_materials ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Array  primitives ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Dictionary  gltf_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Array  target_names ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Array  weights ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  morph_i  =  0 ;  morph_i  <  import_mesh - > get_blend_shape_count ( ) ;  morph_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											target_names . push_back ( import_mesh - > get_blend_shape_name ( morph_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										for  ( int  surface_i  =  0 ;  surface_i  <  import_mesh - > get_surface_count ( ) ;  surface_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Array  targets ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Dictionary  primitive ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Mesh : : PrimitiveType  primitive_type  =  import_mesh - > get_surface_primitive_type ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											switch  ( primitive_type )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  Mesh : : PRIMITIVE_POINTS :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													primitive [ " mode " ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  Mesh : : PRIMITIVE_LINES :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													primitive [ " mode " ]  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// case Mesh::PRIMITIVE_LINE_LOOP: {
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// 	primitive["mode"] = 2;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// 	break;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// }
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  Mesh : : PRIMITIVE_LINE_STRIP :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													primitive [ " mode " ]  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  Mesh : : PRIMITIVE_TRIANGLES :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													primitive [ " mode " ]  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												case  Mesh : : PRIMITIVE_TRIANGLE_STRIP :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													primitive [ " mode " ]  =  5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// case Mesh::PRIMITIVE_TRIANGLE_FAN: {
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// 	primitive["mode"] = 6;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// 	break;
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// }
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												default :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_V ( FAILED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Array  array  =  import_mesh - > get_surface_arrays ( surface_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint64_t  format  =  import_mesh - > get_surface_format ( surface_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int32_t  vertex_num  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Dictionary  attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector3 >  a  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-19 13:21:39 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( a . is_empty ( ) ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												attributes [ " POSITION " ]  =  _encode_accessor_as_vec3 ( p_state ,  a ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												vertex_num  =  a . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < real_t >  a  =  array [ Mesh : : ARRAY_TANGENT ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  ret_size  =  a . size ( )  /  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < Color >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Color  out ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														out . r  =  a [ ( i  *  4 )  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														out . g  =  a [ ( i  *  4 )  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														out . b  =  a [ ( i  *  4 )  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														out . a  =  a [ ( i  *  4 )  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														attribs . write [ i ]  =  out ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " TANGENT " ]  =  _encode_accessor_as_color ( p_state ,  attribs ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector3 >  a  =  array [ Mesh : : ARRAY_NORMAL ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  ret_size  =  a . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < Vector3 >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														attribs . write [ i ]  =  Vector3 ( a [ i ] ) . normalized ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " NORMAL " ]  =  _encode_accessor_as_vec3 ( p_state ,  attribs ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector2 >  a  =  array [ Mesh : : ARRAY_TEX_UV ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " TEXCOORD_0 " ]  =  _encode_accessor_as_vec2 ( p_state ,  a ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector2 >  a  =  array [ Mesh : : ARRAY_TEX_UV2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " TEXCOORD_1 " ]  =  _encode_accessor_as_vec2 ( p_state ,  a ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  custom_i  =  0 ;  custom_i  <  3 ;  custom_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < float >  a  =  array [ Mesh : : ARRAY_CUSTOM0  +  custom_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  num_channels  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  custom_shift  =  Mesh : : ARRAY_FORMAT_CUSTOM0_SHIFT  +  custom_i  *  Mesh : : ARRAY_FORMAT_CUSTOM_BITS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													switch  ( ( format  > >  custom_shift )  &  Mesh : : ARRAY_FORMAT_CUSTOM_MASK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  Mesh : : ARRAY_CUSTOM_R_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															num_channels  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  Mesh : : ARRAY_CUSTOM_RG_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															num_channels  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  Mesh : : ARRAY_CUSTOM_RGB_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															num_channels  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														case  Mesh : : ARRAY_CUSTOM_RGBA_FLOAT : 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															num_channels  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  texcoord_i  =  2  +  2  *  custom_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													String  gltf_texcoord_key ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  prev_texcoord_i  =  0 ;  prev_texcoord_i  <  texcoord_i ;  prev_texcoord_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														gltf_texcoord_key  =  vformat ( " TEXCOORD_%d " ,  prev_texcoord_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( ! attributes . has ( gltf_texcoord_key ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															Vector < Vector2 >  empty ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															empty . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															attributes [ gltf_texcoord_key ]  =  _encode_accessor_as_vec2 ( p_state ,  empty ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													LocalVector < Vector2 >  first_channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													first_channel . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													LocalVector < Vector2 >  second_channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													second_channel . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  vert_i  =  0 ;  vert_i  <  vertex_num ;  vert_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														float  u  =  a [ vert_i  *  num_channels  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														float  v  =  ( num_channels  = =  1  ?  0.0f  :  a [ vert_i  *  num_channels  +  1 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														first_channel [ vert_i ]  =  Vector2 ( u ,  v ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														u  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														v  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( num_channels  > =  3 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															u  =  a [ vert_i  *  num_channels  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															v  =  ( num_channels  = =  3  ?  0.0f  :  a [ vert_i  *  num_channels  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															second_channel [ vert_i ]  =  Vector2 ( u ,  v ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_texcoord_key  =  vformat ( " TEXCOORD_%d " ,  texcoord_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ gltf_texcoord_key ]  =  _encode_accessor_as_vec2 ( p_state ,  first_channel ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													gltf_texcoord_key  =  vformat ( " TEXCOORD_%d " ,  texcoord_i  +  1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ gltf_texcoord_key ]  =  _encode_accessor_as_vec2 ( p_state ,  second_channel ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Color >  a  =  array [ Mesh : : ARRAY_COLOR ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " COLOR_0 " ]  =  _encode_accessor_as_color ( p_state ,  a ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-13 15:04:37 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											HashMap < int ,  int >  joint_i_to_bone_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( GLTFNodeIndex  node_i  =  0 ;  node_i  <  p_state - > nodes . size ( ) ;  node_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												GLTFSkinIndex  skin_i  =  - 1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( p_state - > nodes [ node_i ] - > mesh  = =  gltf_mesh_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													skin_i  =  p_state - > nodes [ node_i ] - > skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( skin_i  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													joint_i_to_bone_i  =  p_state - > skins [ skin_i ] - > joint_i_to_bone_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Array  & a  =  array [ Mesh : : ARRAY_BONES ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Vector < Vector3 >  & vertex_array  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ( a . size ( )  /  JOINT_GROUP_SIZE )  = =  vertex_array . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  ret_size  =  a . size ( )  /  JOINT_GROUP_SIZE ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													Vector < Color >  attribs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														for  ( int  array_i  =  0 ;  array_i  <  attribs . size ( ) ;  array_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															int32_t  joint_0  =  a [ ( array_i  *  JOINT_GROUP_SIZE )  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															int32_t  joint_1  =  a [ ( array_i  *  JOINT_GROUP_SIZE )  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															int32_t  joint_2  =  a [ ( array_i  *  JOINT_GROUP_SIZE )  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															int32_t  joint_3  =  a [ ( array_i  *  JOINT_GROUP_SIZE )  +  3 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
															attribs . write [ array_i ]  =  Color ( joint_0 ,  joint_1 ,  joint_2 ,  joint_3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " JOINTS_0 " ]  =  _encode_accessor_as_joints ( p_state ,  attribs ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  if  ( ( a . size ( )  /  ( JOINT_GROUP_SIZE  *  2 ) )  > =  vertex_array . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < Color >  joints_0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													joints_0 . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector < Color >  joints_1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													joints_1 . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													int32_t  weights_8_count  =  JOINT_GROUP_SIZE  *  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int32_t  vertex_i  =  0 ;  vertex_i  <  vertex_num ;  vertex_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														Color  joint_0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_0 . r  =  a [ vertex_i  *  weights_8_count  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_0 . g  =  a [ vertex_i  *  weights_8_count  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_0 . b  =  a [ vertex_i  *  weights_8_count  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_0 . a  =  a [ vertex_i  *  weights_8_count  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joints_0 . write [ vertex_i ]  =  joint_0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Color  joint_1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_1 . r  =  a [ vertex_i  *  weights_8_count  +  4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_1 . g  =  a [ vertex_i  *  weights_8_count  +  5 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_1 . b  =  a [ vertex_i  *  weights_8_count  +  6 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joint_1 . a  =  a [ vertex_i  *  weights_8_count  +  7 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														joints_1 . write [ vertex_i ]  =  joint_1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " JOINTS_0 " ]  =  _encode_accessor_as_joints ( p_state ,  joints_0 ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													attributes [ " JOINTS_1 " ]  =  _encode_accessor_as_joints ( p_state ,  joints_1 ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Array  & a  =  array [ Mesh : : ARRAY_WEIGHTS ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Vector < Vector3 >  & vertex_array  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ( a . size ( )  /  JOINT_GROUP_SIZE )  = =  vertex_array . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													int32_t  vertex_count  =  vertex_array . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													Vector < Color >  attribs ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attribs . resize ( vertex_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  vertex_count ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														Color  weight_0 ( a [ ( i  *  JOINT_GROUP_SIZE )  +  0 ] ,  a [ ( i  *  JOINT_GROUP_SIZE )  +  1 ] ,  a [ ( i  *  JOINT_GROUP_SIZE )  +  2 ] ,  a [ ( i  *  JOINT_GROUP_SIZE )  +  3 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														float  divisor  =  weight_0 . r  +  weight_0 . g  +  weight_0 . b  +  weight_0 . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( Math : : is_zero_approx ( divisor )  | |  ! Math : : is_finite ( divisor ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															divisor  =  1.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															weight_0  =  Color ( 1 ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														attribs . write [ i ]  =  weight_0  /  divisor ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " WEIGHTS_0 " ]  =  _encode_accessor_as_weights ( p_state ,  attribs ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  if  ( ( a . size ( )  /  ( JOINT_GROUP_SIZE  *  2 ) )  > =  vertex_array . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < Color >  weights_0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													weights_0 . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector < Color >  weights_1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													weights_1 . resize ( vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													int32_t  weights_8_count  =  JOINT_GROUP_SIZE  *  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int32_t  vertex_i  =  0 ;  vertex_i  <  vertex_num ;  vertex_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														Color  weight_0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_0 . r  =  a [ vertex_i  *  weights_8_count  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_0 . g  =  a [ vertex_i  *  weights_8_count  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_0 . b  =  a [ vertex_i  *  weights_8_count  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_0 . a  =  a [ vertex_i  *  weights_8_count  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Color  weight_1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_1 . r  =  a [ vertex_i  *  weights_8_count  +  4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_1 . g  =  a [ vertex_i  *  weights_8_count  +  5 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_1 . b  =  a [ vertex_i  *  weights_8_count  +  6 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_1 . a  =  a [ vertex_i  *  weights_8_count  +  7 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-09 23:51:52 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														float  divisor  =  weight_0 . r  +  weight_0 . g  +  weight_0 . b  +  weight_0 . a  +  weight_1 . r  +  weight_1 . g  +  weight_1 . b  +  weight_1 . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( Math : : is_zero_approx ( divisor )  | |  ! Math : : is_finite ( divisor ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															divisor  =  1.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															weight_0  =  Color ( 1 ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															weight_1  =  Color ( 0 ,  0 ,  0 ,  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weights_0 . write [ vertex_i ]  =  weight_0  /  divisor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weights_1 . write [ vertex_i ]  =  weight_1  /  divisor ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													attributes [ " WEIGHTS_0 " ]  =  _encode_accessor_as_weights ( p_state ,  weights_0 ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													attributes [ " WEIGHTS_1 " ]  =  _encode_accessor_as_weights ( p_state ,  weights_1 ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < int32_t >  mesh_indices  =  array [ Mesh : : ARRAY_INDEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( mesh_indices . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( primitive_type  = =  Mesh : : PRIMITIVE_TRIANGLES )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														// Swap around indices, convert ccw to cw for front face.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														const  int  is  =  mesh_indices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														for  ( int  k  =  0 ;  k  <  is ;  k  + =  3 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															SWAP ( mesh_indices . write [ k  +  0 ] ,  mesh_indices . write [ k  +  2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													primitive [ " indices " ]  =  _encode_accessor_as_ints ( p_state ,  mesh_indices ,  false ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( primitive_type  = =  Mesh : : PRIMITIVE_TRIANGLES )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														// Generate indices because they need to be swapped for CW/CCW.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														const  Vector < Vector3 >  & vertices  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Ref < SurfaceTool >  st ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														st . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														st - > create_from_triangle_arrays ( array ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														st - > index ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector < int32_t >  generated_indices  =  st - > commit_to_arrays ( ) [ Mesh : : ARRAY_INDEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  int  vs  =  vertices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														generated_indices . resize ( vs ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int  k  =  0 ;  k  <  vs ;  k  + =  3 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																generated_indices . write [ k ]  =  k ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																generated_indices . write [ k  +  1 ]  =  k  +  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																generated_indices . write [ k  +  2 ]  =  k  +  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														primitive [ " indices " ]  =  _encode_accessor_as_ints ( p_state ,  generated_indices ,  false ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											primitive [ " attributes " ]  =  attributes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// Blend shapes
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											print_verbose ( " glTF: Mesh has targets " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( import_mesh - > get_blend_shape_count ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ArrayMesh : : BlendShapeMode  shape_mode  =  import_mesh - > get_blend_shape_mode ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  float  normal_tangent_sparse_rounding  =  0.001 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  morph_i  =  0 ;  morph_i  <  import_mesh - > get_blend_shape_count ( ) ;  morph_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Array  array_morph  =  import_mesh - > get_surface_blend_shape_arrays ( surface_i ,  morph_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Dictionary  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < Vector3 >  varr  =  array_morph [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector < Vector3 >  src_varr  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													Array  mesh_arrays  =  import_mesh - > get_surface_arrays ( surface_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( varr . size ( )  & &  varr . size ( )  = =  src_varr . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														if  ( shape_mode  = =  ArrayMesh : : BlendShapeMode : : BLEND_SHAPE_MODE_NORMALIZED )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  int  max_idx  =  src_varr . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int  blend_i  =  0 ;  blend_i  <  max_idx ;  blend_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																varr . write [ blend_i ]  =  varr [ blend_i ]  -  src_varr [ blend_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														GLTFAccessorIndex  position_accessor  =  attributes [ " POSITION " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( position_accessor  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															int  new_accessor  =  _encode_sparse_accessor_as_vec3 ( p_state ,  varr ,  Vector < Vector3 > ( ) ,  1.0 ,  true ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															if  ( new_accessor  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																t [ " POSITION " ]  =  new_accessor ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < Vector3 >  narr  =  array_morph [ Mesh : : ARRAY_NORMAL ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector < Vector3 >  src_narr  =  array [ Mesh : : ARRAY_NORMAL ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( narr . size ( )  & &  narr . size ( )  = =  src_narr . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( shape_mode  = =  ArrayMesh : : BlendShapeMode : : BLEND_SHAPE_MODE_NORMALIZED )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  int  max_idx  =  src_narr . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int  blend_i  =  0 ;  blend_i  <  max_idx ;  blend_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																narr . write [ blend_i ]  =  narr [ blend_i ]  -  src_narr [ blend_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														GLTFAccessorIndex  normal_accessor  =  attributes [ " NORMAL " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( normal_accessor  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															int  new_accessor  =  _encode_sparse_accessor_as_vec3 ( p_state ,  narr ,  Vector < Vector3 > ( ) ,  normal_tangent_sparse_rounding ,  true ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															if  ( new_accessor  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																t [ " NORMAL " ]  =  new_accessor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < real_t >  tarr  =  array_morph [ Mesh : : ARRAY_TANGENT ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector < real_t >  src_tarr  =  array [ Mesh : : ARRAY_TANGENT ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( tarr . size ( )  & &  tarr . size ( )  = =  src_tarr . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														const  int  ret_size  =  tarr . size ( )  /  4 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														Vector < Vector3 >  attribs ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														attribs . resize ( ret_size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														for  ( int  i  =  0 ;  i  <  ret_size ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															Vector3  vec3 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															vec3 . x  =  tarr [ ( i  *  4 )  +  0 ]  -  src_tarr [ ( i  *  4 )  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															vec3 . y  =  tarr [ ( i  *  4 )  +  1 ]  -  src_tarr [ ( i  *  4 )  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															vec3 . z  =  tarr [ ( i  *  4 )  +  2 ]  -  src_tarr [ ( i  *  4 )  +  2 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															attribs . write [ i ]  =  vec3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														GLTFAccessorIndex  tangent_accessor  =  attributes [ " TANGENT " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( tangent_accessor  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 02:39:15 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															int  new_accessor  =  _encode_sparse_accessor_as_vec3 ( p_state ,  attribs ,  Vector < Vector3 > ( ) ,  normal_tangent_sparse_rounding ,  true ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-01 13:07:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															if  ( new_accessor  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																t [ " TANGENT " ]  =  new_accessor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													targets . push_back ( t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Variant  v ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( surface_i  <  instance_materials . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												v  =  instance_materials . get ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Ref < Material >  mat  =  v ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-25 14:15:10 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( mat . is_null ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												mat  =  import_mesh - > get_surface_material ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( mat . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												HashMap < Ref < Material > ,  GLTFMaterialIndex > : : Iterator  material_cache_i  =  p_state - > material_cache . find ( mat ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-13 15:04:37 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( material_cache_i  & &  material_cache_i - > value  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													primitive [ " material " ]  =  material_cache_i - > value ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													GLTFMaterialIndex  mat_i  =  p_state - > materials . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_state - > materials . push_back ( mat ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													primitive [ " material " ]  =  mat_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_state - > material_cache . insert ( mat ,  mat_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( targets . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												primitive [ " targets " ]  =  targets ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											primitives . push_back ( primitive ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-08 01:02:14 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! target_names . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  e ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											e [ " targetNames " ]  =  target_names ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_mesh [ " extras " ]  =  e ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_attach_meta_to_extras ( import_mesh ,  gltf_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										weights . resize ( target_names . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  name_i  =  0 ;  name_i  <  target_names . size ( ) ;  name_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-02-08 10:57:18 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											real_t  weight  =  0.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( name_i  <  p_state - > meshes . write [ gltf_mesh_i ] - > get_blend_weights ( ) . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												weight  =  p_state - > meshes . write [ gltf_mesh_i ] - > get_blend_weights ( ) [ name_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											weights [ name_i ]  =  weight ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( weights . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_mesh [ " weights " ]  =  weights ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( target_names . size ( )  ! =  weights . size ( ) ,  FAILED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_mesh [ " primitives " ]  =  primitives ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										meshes . push_back ( gltf_mesh ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! meshes . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " meshes " ]  =  meshes ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total meshes:  "  +  itos ( meshes . size ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_meshes ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " meshes " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Array  meshes  =  p_state - > json [ " meshes " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( GLTFMeshIndex  i  =  0 ;  i  <  meshes . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										print_verbose ( " glTF: Parsing mesh:  "  +  itos ( i ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  mesh_dict  =  meshes [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFMesh >  mesh ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										bool  has_vertex_color  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! mesh_dict . has ( " primitives " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Array  primitives  =  mesh_dict [ " primitives " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & extras  =  mesh_dict . has ( " extras " )  ?  ( Dictionary ) mesh_dict [ " extras " ]  :  Dictionary ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_attach_extras_to_meta ( extras ,  mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < ImporterMesh >  import_mesh ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										import_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-24 00:29:20 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										String  mesh_name  =  " mesh " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( mesh_dict . has ( " name " )  & &  ! String ( mesh_dict [ " name " ] ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mesh_name  =  mesh_dict [ " name " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mesh - > set_original_name ( mesh_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-24 00:29:20 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										import_mesh - > set_name ( _gen_unique_name ( p_state ,  vformat ( " %s_%s " ,  p_state - > scene_name ,  mesh_name ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mesh - > set_name ( import_mesh - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										TypedArray < Material >  instance_materials ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-24 00:29:20 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  primitives . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											uint64_t  flags  =  RS : : ARRAY_FLAG_COMPRESS_ATTRIBUTES ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Dictionary  mesh_prim  =  primitives [ j ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Array  array ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											array . resize ( Mesh : : ARRAY_MAX ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! mesh_prim . has ( " attributes " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Dictionary  a  =  mesh_prim [ " attributes " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Mesh : : PrimitiveType  primitive  =  Mesh : : PRIMITIVE_TRIANGLES ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( mesh_prim . has ( " mode " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  int  mode  =  mesh_prim [ " mode " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_INDEX_V ( mode ,  7 ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-12-27 17:36:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// Convert mesh.primitive.mode to Godot Mesh enum. See:
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// https://www.khronos.org/registry/glTF/specs/2.0/glTF-2.0.html#_mesh_primitive_mode
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												static  const  Mesh : : PrimitiveType  primitives2 [ 7 ]  =  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-12-27 17:36:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_POINTS ,  // 0 POINTS
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_LINES ,  // 1 LINES
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_LINES ,  // 2 LINE_LOOP; loop not supported, should be converted
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_LINE_STRIP ,  // 3 LINE_STRIP
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_TRIANGLES ,  // 4 TRIANGLES
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_TRIANGLE_STRIP ,  // 5 TRIANGLE_STRIP
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Mesh : : PRIMITIVE_TRIANGLES ,  // 6 TRIANGLE_FAN fan not supported, should be converted
 
							 
						 
					
						
							
								
									
										
										
										
											2022-10-10 13:04:01 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													// TODO: Line loop and triangle fan are not supported and need to be converted to lines and triangles.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												primitive  =  primitives2 [ mode ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int32_t  orig_vertex_num  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! a . has ( " POSITION " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " POSITION " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												PackedVector3Array  vertices  =  _decode_accessor_as_vec3 ( p_state ,  a [ " POSITION " ] ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_VERTEX ]  =  vertices ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												orig_vertex_num  =  vertices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  vertex_num  =  orig_vertex_num ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < int >  indices ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < int >  indices_mapping ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < int >  indices_rev_mapping ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < int >  indices_vec4_mapping ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( mesh_prim . has ( " indices " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												indices  =  _decode_accessor_as_ints ( p_state ,  mesh_prim [ " indices " ] ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  int  is  =  indices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( primitive  = =  Mesh : : PRIMITIVE_TRIANGLES )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Swap around indices, convert ccw to cw for front face.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  * w  =  indices . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  k  =  0 ;  k  <  is ;  k  + =  3 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														SWAP ( w [ k  +  1 ] ,  w [ k  +  2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  int  * indices_w  =  indices . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < bool >  used_indices ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-05-23 00:20:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												used_indices . resize_initialized ( orig_vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												bool  * used_w  =  used_indices . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  idx_i  =  0 ;  idx_i  <  is ;  idx_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_INDEX_V ( indices_w [ idx_i ] ,  orig_vertex_num ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													used_w [ indices_w [ idx_i ] ]  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2025-05-23 00:20:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												indices_rev_mapping . resize_initialized ( orig_vertex_num ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												int  * rev_w  =  indices_rev_mapping . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												vertex_num  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  vert_i  =  0 ;  vert_i  <  orig_vertex_num ;  vert_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( used_w [ vert_i ] )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														rev_w [ vert_i ]  =  indices_mapping . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														indices_mapping . push_back ( vert_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														indices_vec4_mapping . push_back ( vert_i  *  4  +  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														indices_vec4_mapping . push_back ( vert_i  *  4  +  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														indices_vec4_mapping . push_back ( vert_i  *  4  +  2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														indices_vec4_mapping . push_back ( vert_i  *  4  +  3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														vertex_num + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( vertex_num  < =  0 ,  ERR_INVALID_DECLARATION ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " POSITION " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												PackedVector3Array  vertices  =  _decode_accessor_as_vec3 ( p_state ,  a [ " POSITION " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_VERTEX ]  =  vertices ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " NORMAL " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_NORMAL ]  =  _decode_accessor_as_vec3 ( p_state ,  a [ " NORMAL " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " TANGENT " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_TANGENT ]  =  _decode_accessor_as_floats ( p_state ,  a [ " TANGENT " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " TEXCOORD_0 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_TEX_UV ]  =  _decode_accessor_as_vec2 ( p_state ,  a [ " TEXCOORD_0 " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " TEXCOORD_1 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_TEX_UV2 ]  =  _decode_accessor_as_vec2 ( p_state ,  a [ " TEXCOORD_1 " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  custom_i  =  0 ;  custom_i  <  3 ;  custom_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < float >  cur_custom ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector2 >  texcoord_first ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector2 >  texcoord_second ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  texcoord_i  =  2  +  2  *  custom_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  gltf_texcoord_key  =  vformat ( " TEXCOORD_%d " ,  texcoord_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  num_channels  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . has ( gltf_texcoord_key ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													texcoord_first  =  _decode_accessor_as_vec2 ( p_state ,  a [ gltf_texcoord_key ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													num_channels  =  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_texcoord_key  =  vformat ( " TEXCOORD_%d " ,  texcoord_i  +  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( a . has ( gltf_texcoord_key ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													texcoord_second  =  _decode_accessor_as_vec2 ( p_state ,  a [ gltf_texcoord_key ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													num_channels  =  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! num_channels )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( num_channels  = =  2  | |  num_channels  = =  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													cur_custom . resize ( vertex_num  *  num_channels ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  uv_i  =  0 ;  uv_i  <  texcoord_first . size ( )  & &  uv_i  <  vertex_num ;  uv_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  0 ]  =  texcoord_first [ uv_i ] . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  1 ]  =  texcoord_first [ uv_i ] . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Vector.resize seems to not zero-initialize. Ensure all unused elements are 0:
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  uv_i  =  texcoord_first . size ( ) ;  uv_i  <  vertex_num ;  uv_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  0 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  1 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( num_channels  = =  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  uv_i  =  0 ;  uv_i  <  texcoord_second . size ( )  & &  uv_i  <  vertex_num ;  uv_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// num_channels must be 4
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  2 ]  =  texcoord_second [ uv_i ] . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  3 ]  =  texcoord_second [ uv_i ] . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Vector.resize seems to not zero-initialize. Ensure all unused elements are 0:
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  uv_i  =  texcoord_second . size ( ) ;  uv_i  <  vertex_num ;  uv_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  2 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cur_custom . write [ uv_i  *  num_channels  +  3 ]  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( cur_custom . size ( )  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													array [ Mesh : : ARRAY_CUSTOM0  +  custom_i ]  =  cur_custom ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  custom_shift  =  Mesh : : ARRAY_FORMAT_CUSTOM0_SHIFT  +  custom_i  *  Mesh : : ARRAY_FORMAT_CUSTOM_BITS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( num_channels  = =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														flags  | =  Mesh : : ARRAY_CUSTOM_RG_FLOAT  < <  custom_shift ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														flags  | =  Mesh : : ARRAY_CUSTOM_RGBA_FLOAT  < <  custom_shift ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " COLOR_0 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_COLOR ]  =  _decode_accessor_as_color ( p_state ,  a [ " COLOR_0 " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												has_vertex_color  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( a . has ( " JOINTS_0 " )  & &  ! a . has ( " JOINTS_1 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												PackedInt32Array  joints_0  =  _decode_accessor_as_ints ( p_state ,  a [ " JOINTS_0 " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( joints_0 . size ( )  ! =  4  *  vertex_num ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_BONES ]  =  joints_0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( a . has ( " JOINTS_0 " )  & &  a . has ( " JOINTS_1 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												PackedInt32Array  joints_0  =  _decode_accessor_as_ints ( p_state ,  a [ " JOINTS_0 " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												PackedInt32Array  joints_1  =  _decode_accessor_as_ints ( p_state ,  a [ " JOINTS_1 " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-10 16:47:55 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( joints_0 . size ( )  ! =  joints_1 . size ( ) ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( joints_0 . size ( )  ! =  4  *  vertex_num ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												int32_t  weight_8_count  =  JOINT_GROUP_SIZE  *  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < int >  joints ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												joints . resize ( vertex_num  *  weight_8_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int32_t  vertex_i  =  0 ;  vertex_i  <  vertex_num ;  vertex_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  0 ]  =  joints_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  1 ]  =  joints_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  2 ]  =  joints_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  3 ]  =  joints_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  4 ]  =  joints_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  5 ]  =  joints_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  6 ]  =  joints_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													joints . write [ vertex_i  *  weight_8_count  +  7 ]  =  joints_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_BONES ]  =  joints ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( a . has ( " WEIGHTS_0 " )  & &  ! a . has ( " WEIGHTS_1 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < float >  weights  =  _decode_accessor_as_floats ( p_state ,  a [ " WEIGHTS_0 " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( weights . size ( )  ! =  4  *  vertex_num ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												{  // glTF does not seem to normalize the weights for some reason.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													int  wc  =  weights . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  * w  =  weights . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  k  =  0 ;  k  <  wc ;  k  + =  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														float  total  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( total  >  0.0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  0 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  1 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  2 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  3 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_WEIGHTS ]  =  weights ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( a . has ( " WEIGHTS_0 " )  & &  a . has ( " WEIGHTS_1 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < float >  weights_0  =  _decode_accessor_as_floats ( p_state ,  a [ " WEIGHTS_0 " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < float >  weights_1  =  _decode_accessor_as_floats ( p_state ,  a [ " WEIGHTS_1 " ] ,  true ,  indices_vec4_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < float >  weights ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( weights_0 . size ( )  ! =  weights_1 . size ( ) ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( weights_0 . size ( )  ! =  4  *  vertex_num ,  ERR_INVALID_DATA ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												int32_t  weight_8_count  =  JOINT_GROUP_SIZE  *  2 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-08 21:29:14 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												weights . resize ( vertex_num  *  weight_8_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int32_t  vertex_i  =  0 ;  vertex_i  <  vertex_num ;  vertex_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  0 ]  =  weights_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  1 ]  =  weights_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  2 ]  =  weights_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  3 ]  =  weights_0 [ vertex_i  *  JOINT_GROUP_SIZE  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  4 ]  =  weights_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  5 ]  =  weights_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  6 ]  =  weights_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weights . write [ vertex_i  *  weight_8_count  +  7 ]  =  weights_1 [ vertex_i  *  JOINT_GROUP_SIZE  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												{  // glTF does not seem to normalize the weights for some reason.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													int  wc  =  weights . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													float  * w  =  weights . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  k  =  0 ;  k  <  wc ;  k  + =  weight_8_count )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														float  total  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  5 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  6 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														total  + =  w [ k  +  7 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( total  >  0.0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  0 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  1 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  2 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  3 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  4 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  5 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  6 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															w [ k  +  7 ]  / =  total ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_WEIGHTS ]  =  weights ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-31 17:04:25 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												flags  | =  Mesh : : ARRAY_FLAG_USE_8_BONE_WEIGHTS ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( ! indices . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int  * w  =  indices . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  int  is  =  indices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  ind_i  =  0 ;  ind_i  <  is ;  ind_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													w [ ind_i ]  =  indices_rev_mapping [ indices [ ind_i ] ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_INDEX ]  =  indices ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( primitive  = =  Mesh : : PRIMITIVE_TRIANGLES )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// Generate indices because they need to be swapped for CW/CCW.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												const  Vector < Vector3 >  & vertices  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-19 13:21:39 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( vertices . is_empty ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												const  int  vs  =  vertices . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												indices . resize ( vs ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  * w  =  indices . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  k  =  0 ;  k  <  vs ;  k  + =  3 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														w [ k ]  =  k ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														w [ k  +  1 ]  =  k  +  2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														w [ k  +  2 ]  =  k  +  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_INDEX ]  =  indices ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 15:51:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											bool  generate_tangents  =  p_state - > force_generate_tangents  & &  ( primitive  = =  Mesh : : PRIMITIVE_TRIANGLES  & &  ! a . has ( " TANGENT " )  & &  a . has ( " NORMAL " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( generate_tangents  & &  ! a . has ( " TEXCOORD_0 " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// If we don't have UVs we provide a dummy tangent array.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < float >  tangents ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												tangents . resize ( vertex_num  *  4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												float  * tangentsw  =  tangents . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector3 >  normals  =  array [ Mesh : : ARRAY_NORMAL ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  k  =  0 ;  k  <  vertex_num ;  k + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-27 11:44:57 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector3  tan  =  Vector3 ( normals [ k ] . z ,  - normals [ k ] . x ,  normals [ k ] . y ) . cross ( normals [ k ] . normalized ( ) ) . normalized ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 15:51:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													tangentsw [ k  *  4  +  0 ]  =  tan . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													tangentsw [ k  *  4  +  1 ]  =  tan . y ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													tangentsw [ k  *  4  +  2 ]  =  tan . z ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													tangentsw [ k  *  4  +  3 ]  =  1.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												array [ Mesh : : ARRAY_TANGENT ]  =  tangents ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-12-13 19:18:50 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// Disable compression if all z equals 0 (the mesh is 2D).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < Vector3 >  & vertices  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  is_mesh_2d  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  k  =  0 ;  k  <  vertices . size ( ) ;  k + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! Math : : is_zero_approx ( vertices [ k ] . z ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													is_mesh_2d  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_state - > force_disable_compression  | |  is_mesh_2d  | |  ! a . has ( " POSITION " )  | |  ! a . has ( " NORMAL " )  | |  mesh_prim . has ( " targets " )  | |  ( a . has ( " JOINTS_0 " )  | |  a . has ( " JOINTS_1 " ) ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												flags  & =  ~ RS : : ARRAY_FLAG_COMPRESS_ATTRIBUTES ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Ref < SurfaceTool >  mesh_surface_tool ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mesh_surface_tool . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mesh_surface_tool - > create_from_triangle_arrays ( array ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( a . has ( " JOINTS_0 " )  & &  a . has ( " JOINTS_1 " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mesh_surface_tool - > set_skin_weight_count ( SurfaceTool : : SKIN_8_WEIGHTS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mesh_surface_tool - > index ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 15:51:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( generate_tangents  & &  a . has ( " TEXCOORD_0 " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												//must generate mikktspace tangents.. ergh..
 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												mesh_surface_tool - > generate_tangents ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											array  =  mesh_surface_tool - > commit_to_arrays ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-02-23 13:54:20 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( ( flags  &  RS : : ARRAY_FLAG_COMPRESS_ATTRIBUTES )  & &  a . has ( " NORMAL " )  & &  ( a . has ( " TANGENT " )  | |  generate_tangents ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Compression is enabled, so let's validate that the normals and tangents are correct.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < Vector3 >  normals  =  array [ Mesh : : ARRAY_NORMAL ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < float >  tangents  =  array [ Mesh : : ARRAY_TANGENT ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 14:29:41 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( unlikely ( tangents . size ( )  <  normals . size ( )  *  4 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_PRINT ( " glTF import: Mesh  "  +  itos ( i )  +  "  has invalid tangents. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													flags  & =  ~ RS : : ARRAY_FLAG_COMPRESS_ATTRIBUTES ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  vert  =  0 ;  vert  <  normals . size ( ) ;  vert + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  tan  =  Vector3 ( tangents [ vert  *  4  +  0 ] ,  tangents [ vert  *  4  +  1 ] ,  tangents [ vert  *  4  +  2 ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-19 14:18:09 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( std : : abs ( tan . dot ( normals [ vert ] ) )  >  0.0001 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 14:29:41 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															// Tangent is not perpendicular to the normal, so we can't use compression.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															flags  & =  ~ RS : : ARRAY_FLAG_COMPRESS_ATTRIBUTES ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-23 13:54:20 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Array  morphs ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// Blend shapes
 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( mesh_prim . has ( " targets " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												print_verbose ( " glTF: Mesh has targets " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Array  & targets  =  mesh_prim [ " targets " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												import_mesh - > set_blend_shape_mode ( Mesh : : BLEND_SHAPE_MODE_NORMALIZED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( j  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Array  & target_names  =  extras . has ( " targetNames " )  ?  ( Array ) extras [ " targetNames " ]  :  Array ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  k  =  0 ;  k  <  targets . size ( ) ;  k + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-04-12 16:05:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														String  bs_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( k  <  target_names . size ( )  & &  ( ( String ) target_names [ k ] ) . size ( )  ! =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bs_name  =  ( String ) target_names [ k ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bs_name  =  String ( " morph_ " )  +  itos ( k ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														import_mesh - > add_blend_shape ( bs_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  k  =  0 ;  k  <  targets . size ( ) ;  k + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Dictionary  & t  =  targets [ k ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Array  array_copy ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													array_copy . resize ( Mesh : : ARRAY_MAX ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  l  =  0 ;  l  <  Mesh : : ARRAY_MAX ;  l + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														array_copy [ l ]  =  array [ l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( t . has ( " POSITION " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														Vector < Vector3 >  varr  =  _decode_accessor_as_vec3 ( p_state ,  t [ " POSITION " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														const  Vector < Vector3 >  src_varr  =  array [ Mesh : : ARRAY_VERTEX ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  int  size  =  src_varr . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_V ( size  = =  0 ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  int  max_idx  =  varr . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															varr . resize ( size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															Vector3  * w_varr  =  varr . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  Vector3  * r_varr  =  varr . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  Vector3  * r_src_varr  =  src_varr . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int  l  =  0 ;  l  <  size ;  l + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																if  ( l  <  max_idx )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w_varr [ l ]  =  r_varr [ l ]  +  r_src_varr [ l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w_varr [ l ]  =  r_src_varr [ l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														array_copy [ Mesh : : ARRAY_VERTEX ]  =  varr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( t . has ( " NORMAL " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														Vector < Vector3 >  narr  =  _decode_accessor_as_vec3 ( p_state ,  t [ " NORMAL " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														const  Vector < Vector3 >  src_narr  =  array [ Mesh : : ARRAY_NORMAL ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														int  size  =  src_narr . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_V ( size  = =  0 ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															int  max_idx  =  narr . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															narr . resize ( size ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															Vector3  * w_narr  =  narr . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  Vector3  * r_narr  =  narr . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  Vector3  * r_src_narr  =  src_narr . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int  l  =  0 ;  l  <  size ;  l + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																if  ( l  <  max_idx )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w_narr [ l ]  =  r_narr [ l ]  +  r_src_narr [ l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w_narr [ l ]  =  r_src_narr [ l ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														array_copy [ Mesh : : ARRAY_NORMAL ]  =  narr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( t . has ( " TANGENT " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-12 04:50:54 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														const  Vector < Vector3 >  tangents_v3  =  _decode_accessor_as_vec3 ( p_state ,  t [ " TANGENT " ] ,  true ,  indices_mapping ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														const  Vector < float >  src_tangents  =  array [ Mesh : : ARRAY_TANGENT ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-19 13:21:39 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														ERR_FAIL_COND_V ( src_tangents . is_empty ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector < float >  tangents_v4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															int  max_idx  =  tangents_v3 . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															int  size4  =  src_tangents . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															tangents_v4 . resize ( size4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															float  * w4  =  tangents_v4 . ptrw ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  Vector3  * r3  =  tangents_v3 . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															const  float  * r4  =  src_tangents . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int  l  =  0 ;  l  <  size4  /  4 ;  l + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																if  ( l  <  max_idx )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w4 [ l  *  4  +  0 ]  =  r3 [ l ] . x  +  r4 [ l  *  4  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w4 [ l  *  4  +  1 ]  =  r3 [ l ] . y  +  r4 [ l  *  4  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w4 [ l  *  4  +  2 ]  =  r3 [ l ] . z  +  r4 [ l  *  4  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w4 [ l  *  4  +  0 ]  =  r4 [ l  *  4  +  0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w4 [ l  *  4  +  1 ]  =  r4 [ l  *  4  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																	w4 [ l  *  4  +  2 ]  =  r4 [ l  *  4  +  2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																w4 [ l  *  4  +  3 ]  =  r4 [ l  *  4  +  3 ] ;  //copy flip value
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														array_copy [ Mesh : : ARRAY_TANGENT ]  =  tangents_v4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Ref < SurfaceTool >  blend_surface_tool ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													blend_surface_tool . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													blend_surface_tool - > create_from_triangle_arrays ( array_copy ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( a . has ( " JOINTS_0 " )  & &  a . has ( " JOINTS_1 " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														blend_surface_tool - > set_skin_weight_count ( SurfaceTool : : SKIN_8_WEIGHTS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													blend_surface_tool - > index ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													if  ( generate_tangents )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														blend_surface_tool - > generate_tangents ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													array_copy  =  blend_surface_tool - > commit_to_arrays ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-24 17:15:23 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													// Enforce blend shape mask array format
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  l  =  0 ;  l  <  Mesh : : ARRAY_MAX ;  l + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( ! ( Mesh : : ARRAY_FORMAT_BLEND_SHAPE_MASK  &  ( 1ULL  < <  l ) ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-03-24 17:15:23 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															array_copy [ l ]  =  Variant ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													morphs . push_back ( array_copy ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Ref < Material >  mat ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											String  mat_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( ! p_state - > discard_meshes_and_materials )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( mesh_prim . has ( " material " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  material  =  mesh_prim [ " material " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													ERR_FAIL_INDEX_V ( material ,  p_state - > materials . size ( ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < Material >  mat3d  =  p_state - > materials [ material ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													ERR_FAIL_COND_V ( mat3d . is_null ( ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < BaseMaterial3D >  base_material  =  mat3d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( has_vertex_color  & &  base_material . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														base_material - > set_flag ( BaseMaterial3D : : FLAG_ALBEDO_FROM_VERTEX_COLOR ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mat  =  mat3d ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < StandardMaterial3D >  mat3d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mat3d . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( has_vertex_color )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														mat3d - > set_flag ( StandardMaterial3D : : FLAG_ALBEDO_FROM_VERTEX_COLOR ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mat  =  mat3d ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( mat . is_null ( ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												instance_materials . append ( mat ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												mat_name  =  mat - > get_name ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											import_mesh - > add_surface ( primitive ,  array ,  morphs , 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Dictionary ( ) ,  mat ,  mat_name ,  flags ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < float >  blend_weights ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										blend_weights . resize ( import_mesh - > get_blend_shape_count ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  weight_i  =  0 ;  weight_i  <  blend_weights . size ( ) ;  weight_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											blend_weights . write [ weight_i ]  =  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( mesh_dict . has ( " weights " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Array  & weights  =  mesh_dict [ " weights " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											for  ( int  j  =  0 ;  j  <  weights . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-28 11:51:48 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( j  > =  blend_weights . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												blend_weights . write [ j ]  =  weights [ j ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mesh - > set_blend_weights ( blend_weights ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										mesh - > set_instance_materials ( instance_materials ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										mesh - > set_mesh ( import_mesh ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > meshes . push_back ( mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total meshes:  "  +  itos ( p_state - > meshes . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 17:55:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : set_naming_version ( int  p_version )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_naming_version  =  p_version ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								int  GLTFDocument : : get_naming_version ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _naming_version ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : set_image_format ( const  String  & p_image_format )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_image_format  =  p_image_format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								String  GLTFDocument : : get_image_format ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _image_format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  GLTFDocument : : set_lossy_quality ( float  p_lossy_quality )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_lossy_quality  =  p_lossy_quality ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								float  GLTFDocument : : get_lossy_quality ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _lossy_quality ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : set_fallback_image_format ( const  String  & p_fallback_image_format )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_fallback_image_format  =  p_fallback_image_format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								String  GLTFDocument : : get_fallback_image_format ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _fallback_image_format ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  GLTFDocument : : set_fallback_image_quality ( float  p_fallback_image_quality )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_fallback_image_quality  =  p_fallback_image_quality ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								float  GLTFDocument : : get_fallback_image_quality ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _fallback_image_quality ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-18 14:42:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_images ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  images ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Check if any extension wants to be the image saver.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_image_save_extension  =  Ref < GLTFDocumentExtension > ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < String >  image_formats  =  ext - > get_saveable_image_formats ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( image_formats . has ( _image_format ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_image_save_extension  =  ext ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Serialize every image in the state's images array.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_state - > images . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  image_dict ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_state - > images [ i ] . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_PRINT ( " glTF export: Image Texture2D is null. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-18 14:42:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Ref < Image >  image  =  p_state - > images [ i ] - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( image . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_PRINT ( " glTF export: Image's image is null. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												String  image_name  =  p_state - > images [ i ] - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( image_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													image_name  =  itos ( i ) . pad_zeros ( 3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												image_name  =  _gen_unique_name ( p_state ,  image_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												image - > set_name ( image_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												image_dict  =  _serialize_image ( p_state ,  image ,  _image_format ,  _lossy_quality ,  _image_save_extension ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										images . push_back ( image_dict ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " Total images:  "  +  itos ( p_state - > images . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! images . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " images " ]  =  images ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Dictionary  GLTFDocument : : _serialize_image ( Ref < GLTFState >  p_state ,  Ref < Image >  p_image ,  const  String  & p_image_format ,  float  p_lossy_quality ,  Ref < GLTFDocumentExtension >  p_image_save_extension )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  image_dict ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_image - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_image - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( p_image - > is_compressed ( ) ,  image_dict ,  " glTF: Image was compressed, but could not be decompressed. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_state - > filename . to_lower ( ) . ends_with ( " gltf " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  relative_texture_dir  =  " textures " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  full_texture_dir  =  p_state - > base_path . path_join ( relative_texture_dir ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < DirAccess >  da  =  DirAccess : : open ( p_state - > base_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( da . is_null ( ) ,  image_dict ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! da - > dir_exists ( full_texture_dir ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											da - > make_dir ( full_texture_dir ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  image_file_name  =  p_image - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_image_save_extension . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_file_name  =  image_file_name  +  p_image_save_extension - > get_image_file_extension ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Error  err  =  p_image_save_extension - > save_image_at_path ( p_state ,  p_image ,  full_texture_dir . path_join ( image_file_name ) ,  p_image_format ,  p_lossy_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V_MSG ( err  ! =  OK ,  image_dict ,  " glTF: Failed to save image in ' "  +  p_image_format  +  " ' format as a separate file, error  "  +  itos ( err )  +  " . " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( p_image_format  = =  " PNG " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_file_name  =  image_file_name  +  " .png " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_image - > save_png ( full_texture_dir . path_join ( image_file_name ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( p_image_format  = =  " JPEG " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_file_name  =  image_file_name  +  " .jpg " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_image - > save_jpg ( full_texture_dir . path_join ( image_file_name ) ,  p_lossy_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V_MSG ( image_dict ,  " glTF: Unknown image format ' "  +  p_image_format  +  " '. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										image_dict [ " uri " ]  =  relative_texture_dir . path_join ( image_file_name ) . uri_encode ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFBufferViewIndex  bvi ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFBufferView >  bv ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bv . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  GLTFBufferIndex  bi  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bv - > buffer  =  bi ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_INDEX_V ( bi ,  p_state - > buffers . size ( ) ,  image_dict ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bv - > byte_offset  =  p_state - > buffers [ bi ] . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < uint8_t >  buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < ImageTexture >  img_tex  =  p_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( img_tex . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_image  =  img_tex - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Save in various image formats. Note that if the format is "None",
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// the state's images will be empty, so this code will not be reached.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( _image_save_extension . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer  =  _image_save_extension - > serialize_image_to_bytes ( p_state ,  p_image ,  image_dict ,  p_image_format ,  p_lossy_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( p_image_format  = =  " PNG " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer  =  p_image - > save_png_to_buffer ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_dict [ " mimeType " ]  =  " image/png " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( p_image_format  = =  " JPEG " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											buffer  =  p_image - > save_jpg_to_buffer ( p_lossy_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_dict [ " mimeType " ]  =  " image/jpeg " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V_MSG ( image_dict ,  " glTF: Unknown image format ' "  +  p_image_format  +  " '. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( buffer . is_empty ( ) ,  image_dict ,  " glTF: Failed to save image in ' "  +  p_image_format  +  " ' format. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bv - > byte_length  =  buffer . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffers . write [ bi ] . resize ( p_state - > buffers [ bi ] . size ( )  +  bv - > byte_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										memcpy ( & p_state - > buffers . write [ bi ] . write [ bv - > byte_offset ] ,  buffer . ptr ( ) ,  buffer . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( bv - > byte_offset  +  bv - > byte_length  >  p_state - > buffers [ bi ] . size ( ) ,  image_dict ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > buffer_views . push_back ( bv ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bvi  =  p_state - > buffer_views . size ( )  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										image_dict [ " bufferView " ]  =  bvi ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  image_dict ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-15 22:23:43 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Image >  GLTFDocument : : _parse_image_bytes_into_image ( Ref < GLTFState >  p_state ,  const  Vector < uint8_t >  & p_bytes ,  const  String  & p_mime_type ,  int  p_index ,  String  & r_file_extension )  {  
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Image >  r_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_image . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Check if any GLTFDocumentExtensions want to import this data as an image.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Error  err  =  ext - > parse_image_data ( p_state ,  p_bytes ,  p_mime_type ,  r_image ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_CONTINUE_MSG ( err  ! =  OK ,  " glTF: Encountered error  "  +  itos ( err )  +  "  when parsing image  "  +  itos ( p_index )  +  "  in file  "  +  p_state - > filename  +  " . Continuing. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! r_image - > is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-15 22:23:43 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											r_file_extension  =  ext - > get_image_file_extension ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  r_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// If no extension wanted to import this data as an image, try to load a PNG or JPEG.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// First we honor the mime types if they were defined.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_mime_type  = =  " image/png " )  {  // Load buffer as PNG.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_image - > load_png_from_buffer ( p_bytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-15 22:23:43 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										r_file_extension  =  " .png " ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( p_mime_type  = =  " image/jpeg " )  {  // Loader buffer as JPEG.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_image - > load_jpg_from_buffer ( p_bytes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-15 22:23:43 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										r_file_extension  =  " .jpg " ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// If we didn't pass the above tests, we attempt loading as PNG and then JPEG directly.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This covers URIs with base64-encoded data with application/* type but
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// no optional mimeType property, or bufferViews with a bogus mimeType
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// (e.g. `image/jpeg` but the data is actually PNG).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// That's not *exactly* what the spec mandates but this lets us be
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// lenient with bogus glb files which do exist in production.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_image - > is_empty ( ) )  {  // Try PNG first.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_image - > load_png_from_buffer ( p_bytes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_image - > is_empty ( ) )  {  // And then JPEG.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_image - > load_jpg_from_buffer ( p_bytes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// If it still can't be loaded, give up and insert an empty image as placeholder.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_image - > is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_PRINT ( vformat ( " glTF: Couldn't load image index '%d' with its given mimetype: %s. " ,  p_index ,  p_mime_type ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  r_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _parse_image_save_image ( Ref < GLTFState >  p_state ,  const  Vector < uint8_t >  & p_bytes ,  const  String  & p_resource_uri ,  const  String  & p_file_extension ,  int  p_index ,  Ref < Image >  p_image )  {  
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFState : : GLTFHandleBinary  handling  =  GLTFState : : GLTFHandleBinary ( p_state - > handle_binary_image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_image - > is_empty ( )  | |  handling  = =  GLTFState : : GLTFHandleBinary : : HANDLE_BINARY_DISCARD_TEXTURES )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > images . push_back ( Ref < Texture2D > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > source_images . push_back ( Ref < Image > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef TOOLS_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( Engine : : get_singleton ( ) - > is_editor_hint ( )  & &  handling  = =  GLTFState : : GLTFHandleBinary : : HANDLE_BINARY_EXTRACT_TEXTURES )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-30 02:36:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_state - > extract_path . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											WARN_PRINT ( " glTF: Couldn't extract image because the base and extract paths are empty. It will be loaded directly instead, uncompressed. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( p_state - > extract_path . begins_with ( " res://.godot/imported " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											WARN_PRINT ( vformat ( " glTF: Extract path is in the imported directory. Image index '%d' will be loaded directly, uncompressed. " ,  p_index ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-10 00:15:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_image - > get_name ( ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												WARN_PRINT ( vformat ( " glTF: Image index '%d' did not have a name. It will be automatically given a name based on its index. " ,  p_index ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_image - > set_name ( itos ( p_index ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											bool  must_write  =  true ;  // If the resource does not exist on the disk within res:// directory write it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  must_import  =  true ;  // Trigger import.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Vector < uint8_t >  img_data  =  p_image - > get_data ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  generator_parameters ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											String  file_path ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// If resource_uri is within res:// folder but outside of .godot/imported folder, use it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! p_resource_uri . is_empty ( )  & &  ! p_resource_uri . begins_with ( " res://.godot/imported " )  & &  ! p_resource_uri . begins_with ( " res://.. " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												file_path  =  p_resource_uri ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												must_import  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												must_write  =  ! FileAccess : : exists ( file_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Texture data has to be written to the res:// folder and imported.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												file_path  =  p_state - > get_extract_path ( ) . path_join ( p_state - > get_extract_prefix ( )  +  " _ "  +  p_image - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												file_path  + =  p_file_extension . is_empty ( )  ?  " .png "  :  p_file_extension ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( FileAccess : : exists ( file_path  +  " .import " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < ConfigFile >  config ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													config . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													config - > load ( file_path  +  " .import " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( config - > has_section_key ( " remap " ,  " generator_parameters " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														generator_parameters  =  ( Dictionary ) config - > get_value ( " remap " ,  " generator_parameters " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ! generator_parameters . has ( " md5 " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														must_write  =  false ;  // Didn't come from a gltf document; don't overwrite.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														must_import  =  false ;  // And don't import.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-12-25 00:58:38 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( must_write )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												String  existing_md5  =  generator_parameters [ " md5 " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												unsigned  char  md5_hash [ 16 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												CryptoCore : : md5 ( img_data . ptr ( ) ,  img_data . size ( ) ,  md5_hash ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  new_md5  =  String : : hex_encode_buffer ( md5_hash ,  16 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												generator_parameters [ " md5 " ]  =  new_md5 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( new_md5  = =  existing_md5 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													must_write  =  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													must_import  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( must_write )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-15 22:23:43 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_file_extension . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// If a file extension was not specified, save the image data to a PNG file.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													err  =  p_image - > save_png ( file_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_COND ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// If a file extension was specified, save the original bytes to a file with that extension.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < FileAccess >  file  =  FileAccess : : open ( file_path ,  FileAccess : : WRITE ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_COND ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													file - > store_buffer ( p_bytes ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													file - > close ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( must_import )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// ResourceLoader::import will crash if not is_editor_hint(), so this case is protected above and will fall through to uncompressed.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												HashMap < StringName ,  Variant >  custom_options ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												custom_options [ SNAME ( " mipmaps/generate " ) ]  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Will only use project settings defaults if custom_importer is empty.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												EditorFileSystem : : get_singleton ( ) - > update_file ( file_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												EditorFileSystem : : get_singleton ( ) - > reimport_append ( file_path ,  custom_options ,  String ( ) ,  generator_parameters ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < Texture2D >  saved_image  =  ResourceLoader : : load ( file_path ,  " Texture2D " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( saved_image . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > images . push_back ( saved_image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > source_images . push_back ( saved_image - > get_image ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-10 00:15:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												return ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												WARN_PRINT ( vformat ( " glTF: Image index '%d' with the name '%s' resolved to %s couldn't be imported. It will be loaded directly instead, uncompressed. " ,  p_index ,  p_image - > get_name ( ) ,  file_path ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif  // TOOLS_ENABLED
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( handling  = =  GLTFState : : GLTFHandleBinary : : HANDLE_BINARY_EMBED_AS_BASISU )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < PortableCompressedTexture2D >  tex ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										tex . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										tex - > set_name ( p_image - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										tex - > set_keep_compressed_buffer ( true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										tex - > create_from_image ( p_image ,  PortableCompressedTexture2D : : COMPRESSION_MODE_BASIS_UNIVERSAL ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > images . push_back ( tex ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > source_images . push_back ( p_image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This handles the case of HANDLE_BINARY_EMBED_AS_UNCOMPRESSED, and it also serves
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// as a fallback for HANDLE_BINARY_EXTRACT_TEXTURES when this is not the editor.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ImageTexture >  tex ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									tex . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									tex - > set_name ( p_image - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									tex - > set_image ( p_image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > images . push_back ( tex ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > source_images . push_back ( p_image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_images ( Ref < GLTFState >  p_state ,  const  String  & p_base_path )  {  
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_state . is_null ( ) ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " images " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Ref: https://github.com/KhronosGroup/glTF/blob/master/specification/2.0/README.md#images
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & images  =  p_state - > json [ " images " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-27 11:38:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									HashSet < String >  used_names ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  images . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Dictionary  & dict  =  images [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// glTF 2.0 supports PNG and JPEG types, which can be specified as (from spec):
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// "- a URI to an external file in one of the supported images formats, or
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//  - a URI with embedded base64-encoded data, or
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//  - a reference to a bufferView; in that case mimeType must be defined."
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Since mimeType is optional for external files and base64 data, we'll have to
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// fall back on letting Godot parse the data to figure out if it's PNG or JPEG.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// We'll assume that we use either URI or bufferView, so let's warn the user
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// if their image somehow uses both. And fail if it has neither.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_CONTINUE_MSG ( ! dict . has ( " uri " )  & &  ! dict . has ( " bufferView " ) ,  " Invalid image definition in glTF file, it should specify an 'uri' or 'bufferView'. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( dict . has ( " uri " )  & &  dict . has ( " bufferView " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-03 02:55:31 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											WARN_PRINT ( " Invalid image definition in glTF file using both 'uri' and 'bufferView'. 'uri' will take precedence. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										String  mime_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( dict . has ( " mimeType " ) )  {  // Should be "image/png", "image/jpeg", or something handled by an extension.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mime_type  =  dict [ " mimeType " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										String  image_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( dict . has ( " name " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_name  =  dict [ " name " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-27 11:38:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											image_name  =  image_name . get_file ( ) . get_basename ( ) . validate_filename ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( image_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_name  =  itos ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										while  ( used_names . has ( image_name ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											image_name  + =  " _ "  +  itos ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  resource_uri ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-01-27 11:38:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										used_names . insert ( image_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Load the image data. If we get a byte array, store here for later.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < uint8_t >  data ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( dict . has ( " uri " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											// Handles the first two bullet points from the spec (embedded data, or external file).
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											String  uri  =  dict [ " uri " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( uri . begins_with ( " data: " ) )  {  // Embedded data using base64.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												data  =  _parse_base64_uri ( uri ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// mimeType is optional, but if we have it defined in the URI, let's use it.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-12-05 17:56:08 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( mime_type . is_empty ( )  & &  uri . contains_char ( ' ; ' ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													// Trim "data:" prefix which is 5 characters long, and end at ";base64".
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mime_type  =  uri . substr ( 5 ,  uri . find ( " ;base64 " )  -  5 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  {  // Relative path to an external image file.
 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( p_base_path . is_empty ( ) ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-04-07 22:49:57 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												uri  =  uri . uri_file_decode ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-28 12:15:00 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												uri  =  p_base_path . path_join ( uri ) . replace_char ( ' \\ ' ,  ' / ' ) ;  // Fix for Windows.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												resource_uri  =  uri . simplify_path ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// ResourceLoader will rely on the file extension to use the relevant loader.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// The spec says that if mimeType is defined, it should take precedence (e.g.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// there could be a `.png` image which is actually JPEG), but there's no easy
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// API for that in Godot, so we'd have to load as a buffer (i.e. embedded in
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// the material), so we only do that only as fallback.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ResourceLoader : : exists ( resource_uri ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < Texture2D >  texture  =  ResourceLoader : : load ( resource_uri ,  " Texture2D " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-10 00:15:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( texture . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_state - > images . push_back ( texture ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_state - > source_images . push_back ( texture - > get_image ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// mimeType is optional, but if we have it in the file extension, let's use it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// If the mimeType does not match with the file extension, either it should be
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// specified in the file, or the GLTFDocumentExtension should handle it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( mime_type . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													mime_type  =  " image/ "  +  resource_uri . get_extension ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Fallback to loading as byte array. This enables us to support the
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// spec's requirement that we honor mimetype regardless of file URI.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												data  =  FileAccess : : get_file_as_bytes ( resource_uri ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-20 00:07:31 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( data . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													WARN_PRINT ( vformat ( " glTF: Image index '%d' couldn't be loaded as a buffer of MIME type '%s' from URI: %s because there was no data to load. Skipping it. " ,  i ,  mime_type ,  resource_uri ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_state - > images . push_back ( Ref < Texture2D > ( ) ) ;  // Placeholder to keep count.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_state - > source_images . push_back ( Ref < Image > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  if  ( dict . has ( " bufferView " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											// Handles the third bullet point from the spec (bufferView).
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND_V_MSG ( mime_type . is_empty ( ) ,  ERR_FILE_CORRUPT ,  vformat ( " glTF: Image index '%d' specifies 'bufferView' but no 'mimeType', which is invalid. " ,  i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  GLTFBufferViewIndex  bvi  =  dict [ " bufferView " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_INDEX_V ( bvi ,  p_state - > buffer_views . size ( ) ,  ERR_PARAMETER_RANGE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < GLTFBufferView >  bv  =  p_state - > buffer_views [ bvi ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											const  GLTFBufferIndex  bi  =  bv - > buffer ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_INDEX_V ( bi ,  p_state - > buffers . size ( ) ,  ERR_PARAMETER_RANGE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( bv - > byte_offset  +  bv - > byte_length  >  p_state - > buffers [ bi ] . size ( ) ,  ERR_FILE_CORRUPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  PackedByteArray  & buffer  =  p_state - > buffers [ bi ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											data  =  buffer . slice ( bv - > byte_offset ,  bv - > byte_offset  +  bv - > byte_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Done loading the image data bytes. Check that we actually got data to parse.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Note: There are paths above that return early, so this point might not be reached.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( data . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											WARN_PRINT ( vformat ( " glTF: Image index '%d' couldn't be loaded, no data found. Skipping it. " ,  i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > images . push_back ( Ref < Texture2D > ( ) ) ;  // Placeholder to keep count.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > source_images . push_back ( Ref < Image > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Parse the image data from bytes into an Image resource and save if needed.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-15 22:23:43 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										String  file_extension ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Image >  img  =  _parse_image_bytes_into_image ( p_state ,  data ,  mime_type ,  i ,  file_extension ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-27 11:38:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										img - > set_name ( image_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-29 21:33:00 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_parse_image_save_image ( p_state ,  data ,  resource_uri ,  file_extension ,  i ,  img ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total images:  "  +  itos ( p_state - > images . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_textures ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > textures . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Array  textures ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int32_t  i  =  0 ;  i  <  p_state - > textures . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  texture_dict ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFTexture >  gltf_texture  =  p_state - > textures [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _image_save_extension . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Error  err  =  _image_save_extension - > serialize_texture_json ( p_state ,  texture_dict ,  gltf_texture ,  _image_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// If a fallback image format was specified, serialize another image for it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Note: This must only be done after serializing other images to keep the indices of those consistent.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( _fallback_image_format  ! =  " None "  & &  p_state - > json . has ( " images " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Array  json_images  =  p_state - > json [ " images " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												texture_dict [ " source " ]  =  json_images . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Image >  image  =  p_state - > source_images [ gltf_texture - > get_src_image ( ) ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  fallback_name  =  _gen_unique_name ( p_state ,  image - > get_name ( )  +  " _fallback " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												image  =  image - > duplicate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												image - > set_name ( fallback_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_CONTINUE ( image . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( _fallback_image_format  = =  " PNG " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													image - > resize ( image - > get_width ( )  *  _fallback_image_quality ,  image - > get_height ( )  *  _fallback_image_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												json_images . push_back ( _serialize_image ( p_state ,  image ,  _fallback_image_format ,  _fallback_image_quality ,  nullptr ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( gltf_texture - > get_src_image ( )  = =  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											texture_dict [ " source " ]  =  gltf_texture - > get_src_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										GLTFTextureSamplerIndex  sampler_index  =  gltf_texture - > get_sampler ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( sampler_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											texture_dict [ " sampler " ]  =  sampler_index ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										textures . push_back ( texture_dict ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " textures " ]  =  textures ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_textures ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " textures " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & textures  =  p_state - > json [ " textures " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( GLTFTextureIndex  i  =  0 ;  i  <  textures . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Dictionary  & texture_dict  =  textures [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFTexture >  gltf_texture ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_texture . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Check if any GLTFDocumentExtensions want to handle this texture JSON.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Error  err  =  ext - > parse_texture_json ( p_state ,  texture_dict ,  gltf_texture ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE_MSG ( err  ! =  OK ,  " glTF: Encountered error  "  +  itos ( err )  +  "  when parsing texture JSON  "  +  String ( Variant ( texture_dict ) )  +  "  in file  "  +  p_state - > filename  +  " . Continuing. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( gltf_texture - > get_src_image ( )  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_texture - > get_src_image ( )  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// No extensions handled it, so use the base glTF source.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// This may be the fallback, or the only option anyway.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! texture_dict . has ( " source " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_texture - > set_src_image ( texture_dict [ " source " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_texture - > get_sampler ( )  = =  - 1  & &  texture_dict . has ( " sampler " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_texture - > set_sampler ( texture_dict [ " sampler " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > textures . push_back ( gltf_texture ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFTextureIndex  GLTFDocument : : _set_texture ( Ref < GLTFState >  p_state ,  Ref < Texture2D >  p_texture ,  StandardMaterial3D : : TextureFilter  p_filter_mode ,  bool  p_repeats )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_texture . is_null ( ) ,  - 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFTexture >  gltf_texture ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_texture . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-28 12:32:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_texture - > get_image ( ) . is_null ( ) ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFImageIndex  gltf_src_image_i  =  p_state - > images . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > images . push_back ( p_texture ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > source_images . push_back ( p_texture - > get_image ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									gltf_texture - > set_src_image ( gltf_src_image_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_texture - > set_sampler ( _set_sampler_for_mode ( p_state ,  p_filter_mode ,  p_repeats ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									GLTFTextureIndex  gltf_texture_i  =  p_state - > textures . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > textures . push_back ( gltf_texture ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  gltf_texture_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < Texture2D >  GLTFDocument : : _get_texture ( Ref < GLTFState >  p_state ,  const  GLTFTextureIndex  p_texture ,  int  p_texture_types )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_texture ,  p_state - > textures . size ( ) ,  Ref < Texture2D > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  GLTFImageIndex  image  =  p_state - > textures [ p_texture ] - > get_src_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( image ,  p_state - > images . size ( ) ,  Ref < Texture2D > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( GLTFState : : GLTFHandleBinary ( p_state - > handle_binary_image )  = =  GLTFState : : GLTFHandleBinary : : HANDLE_BINARY_EMBED_AS_BASISU )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-05 16:52:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_INDEX_V ( image ,  p_state - > source_images . size ( ) ,  Ref < Texture2D > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < PortableCompressedTexture2D >  portable_texture ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										portable_texture . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										portable_texture - > set_keep_compressed_buffer ( true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-05 16:52:51 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < Image >  new_img  =  p_state - > source_images [ image ] - > duplicate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( new_img . is_null ( ) ,  Ref < Texture2D > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										new_img - > generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_texture_types )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											portable_texture - > create_from_image ( new_img ,  PortableCompressedTexture2D : : COMPRESSION_MODE_BASIS_UNIVERSAL ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											portable_texture - > create_from_image ( new_img ,  PortableCompressedTexture2D : : COMPRESSION_MODE_BASIS_UNIVERSAL ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > images . write [ image ]  =  portable_texture ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-09 21:28:40 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > source_images . write [ image ]  =  new_img ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  p_state - > images [ image ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFTextureSamplerIndex  GLTFDocument : : _set_sampler_for_mode ( Ref < GLTFState >  p_state ,  StandardMaterial3D : : TextureFilter  p_filter_mode ,  bool  p_repeats )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_state - > texture_samplers . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_state - > texture_samplers [ i ] - > get_filter_mode ( )  = =  p_filter_mode )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFTextureSamplerIndex  gltf_sampler_i  =  p_state - > texture_samplers . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFTextureSampler >  gltf_sampler ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_sampler . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_sampler - > set_filter_mode ( p_filter_mode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_sampler - > set_wrap_mode ( p_repeats ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > texture_samplers . push_back ( gltf_sampler ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  gltf_sampler_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Ref < GLTFTextureSampler >  GLTFDocument : : _get_sampler_for_texture ( Ref < GLTFState >  p_state ,  const  GLTFTextureIndex  p_texture )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( p_texture ,  p_state - > textures . size ( ) ,  Ref < Texture2D > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  GLTFTextureSamplerIndex  sampler  =  p_state - > textures [ p_texture ] - > get_sampler ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( sampler  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  p_state - > default_texture_sampler ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_INDEX_V ( sampler ,  p_state - > texture_samplers . size ( ) ,  Ref < GLTFTextureSampler > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  p_state - > texture_samplers [ sampler ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_texture_samplers ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > texture_samplers . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Array  samplers ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int32_t  i  =  0 ;  i  <  p_state - > texture_samplers . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  d ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFTextureSampler >  s  =  p_state - > texture_samplers [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										d [ " magFilter " ]  =  s - > get_mag_filter ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " minFilter " ]  =  s - > get_min_filter ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " wrapS " ]  =  s - > get_wrap_s ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " wrapT " ]  =  s - > get_wrap_t ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										samplers . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " samplers " ]  =  samplers ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_texture_samplers ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > default_texture_sampler . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > default_texture_sampler - > set_min_filter ( GLTFTextureSampler : : FilterMode : : LINEAR_MIPMAP_LINEAR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > default_texture_sampler - > set_mag_filter ( GLTFTextureSampler : : FilterMode : : LINEAR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > default_texture_sampler - > set_wrap_s ( GLTFTextureSampler : : WrapMode : : REPEAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > default_texture_sampler - > set_wrap_t ( GLTFTextureSampler : : WrapMode : : REPEAT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " samplers " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & samplers  =  p_state - > json [ " samplers " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  samplers . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & d  =  samplers [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFTextureSampler >  sampler ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										sampler . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " minFilter " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_min_filter ( d [ " minFilter " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_min_filter ( GLTFTextureSampler : : FilterMode : : LINEAR_MIPMAP_LINEAR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " magFilter " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_mag_filter ( d [ " magFilter " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_mag_filter ( GLTFTextureSampler : : FilterMode : : LINEAR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " wrapS " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_wrap_s ( d [ " wrapS " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_wrap_s ( GLTFTextureSampler : : WrapMode : : DEFAULT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " wrapT " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_wrap_t ( d [ " wrapT " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											sampler - > set_wrap_t ( GLTFTextureSampler : : WrapMode : : DEFAULT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > texture_samplers . push_back ( sampler ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_materials ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  materials ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int32_t  i  =  0 ;  i  <  p_state - > materials . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  d ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < Material >  material  =  p_state - > materials [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( material . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											materials . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! material - > get_name ( ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											d [ " name " ]  =  _gen_unique_name ( p_state ,  material - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < BaseMaterial3D >  base_material  =  material ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( base_material . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											materials . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Dictionary  mr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Color  c  =  base_material - > get_albedo ( ) . srgb_to_linear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-22 22:53:26 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Array  arr  =  {  c . r ,  c . g ,  c . b ,  c . a  } ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mr [ " baseColorFactor " ]  =  arr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _image_format  ! =  " None " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Dictionary  bct ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < Texture2D >  albedo_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_ALBEDO ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFTextureIndex  gltf_texture_index  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( albedo_texture . is_valid ( )  & &  albedo_texture - > get_image ( ) . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												albedo_texture - > set_name ( material - > get_name ( )  +  " _albedo " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_texture_index  =  _set_texture ( p_state ,  albedo_texture ,  base_material - > get_texture_filter ( ) ,  base_material - > get_flag ( BaseMaterial3D : : FLAG_USE_TEXTURE_REPEAT ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( gltf_texture_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												bct [ " index " ]  =  gltf_texture_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  extensions  =  _serialize_texture_transform_uv1 ( material ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! extensions . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bct [ " extensions " ]  =  extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_state - > use_khr_texture_transform  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mr [ " baseColorTexture " ]  =  bct ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mr [ " metallicFactor " ]  =  base_material - > get_metallic ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mr [ " roughnessFactor " ]  =  base_material - > get_roughness ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _image_format  ! =  " None " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  has_roughness  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_ROUGHNESS ) . is_valid ( )  & &  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_ROUGHNESS ) - > get_image ( ) . is_valid ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  has_ao  =  base_material - > get_feature ( BaseMaterial3D : : FEATURE_AMBIENT_OCCLUSION )  & &  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_AMBIENT_OCCLUSION ) . is_valid ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  has_metalness  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_METALLIC ) . is_valid ( )  & &  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_METALLIC ) - > get_image ( ) . is_valid ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( has_ao  | |  has_roughness  | |  has_metalness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  mrt ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Texture2D >  roughness_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_ROUGHNESS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												BaseMaterial3D : : TextureChannel  roughness_channel  =  base_material - > get_roughness_texture_channel ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Texture2D >  metallic_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_METALLIC ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												BaseMaterial3D : : TextureChannel  metalness_channel  =  base_material - > get_metallic_texture_channel ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Texture2D >  ao_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_AMBIENT_OCCLUSION ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												BaseMaterial3D : : TextureChannel  ao_channel  =  base_material - > get_ao_texture_channel ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < ImageTexture >  orm_texture ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												orm_texture . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Image >  orm_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												orm_image . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int32_t  height  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int32_t  width  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Image >  ao_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( has_ao )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													height  =  ao_texture - > get_height ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													width  =  ao_texture - > get_width ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ao_image  =  ao_texture - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < ImageTexture >  img_tex  =  ao_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( img_tex . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ao_image  =  img_tex - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ao_image - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ao_image - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Ref < Image >  roughness_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( has_roughness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													height  =  roughness_texture - > get_height ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													width  =  roughness_texture - > get_width ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													roughness_image  =  roughness_texture - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < ImageTexture >  img_tex  =  roughness_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( img_tex . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														roughness_image  =  img_tex - > get_image ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( roughness_image - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														roughness_image - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Image >  metallness_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( has_metalness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													height  =  metallic_texture - > get_height ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													width  =  metallic_texture - > get_width ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													metallness_image  =  metallic_texture - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < ImageTexture >  img_tex  =  metallness_image ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( img_tex . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														metallness_image  =  img_tex - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( metallness_image - > is_compressed ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														metallness_image - > decompress ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Texture2D >  albedo_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_ALBEDO ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( albedo_texture . is_valid ( )  & &  albedo_texture - > get_image ( ) . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													height  =  albedo_texture - > get_height ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													width  =  albedo_texture - > get_width ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												orm_image - > initialize_data ( width ,  height ,  false ,  Image : : FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ao_image . is_valid ( )  & &  ao_image - > get_size ( )  ! =  Vector2 ( width ,  height ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ao_image - > resize ( width ,  height ,  Image : : INTERPOLATE_LANCZOS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( roughness_image . is_valid ( )  & &  roughness_image - > get_size ( )  ! =  Vector2 ( width ,  height ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													roughness_image - > resize ( width ,  height ,  Image : : INTERPOLATE_LANCZOS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( metallness_image . is_valid ( )  & &  metallness_image - > get_size ( )  ! =  Vector2 ( width ,  height ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													metallness_image - > resize ( width ,  height ,  Image : : INTERPOLATE_LANCZOS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int32_t  h  =  0 ;  h  <  height ;  h + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  w  =  0 ;  w  <  width ;  w + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Color  c  =  Color ( 1.0f ,  1.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( has_ao )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_RED  = =  ao_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . r  =  ao_image - > get_pixel ( w ,  h ) . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_GREEN  = =  ao_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . r  =  ao_image - > get_pixel ( w ,  h ) . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_BLUE  = =  ao_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . r  =  ao_image - > get_pixel ( w ,  h ) . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_ALPHA  = =  ao_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . r  =  ao_image - > get_pixel ( w ,  h ) . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( has_roughness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_RED  = =  roughness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . g  =  roughness_image - > get_pixel ( w ,  h ) . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_GREEN  = =  roughness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . g  =  roughness_image - > get_pixel ( w ,  h ) . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_BLUE  = =  roughness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . g  =  roughness_image - > get_pixel ( w ,  h ) . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_ALPHA  = =  roughness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . g  =  roughness_image - > get_pixel ( w ,  h ) . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( has_metalness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_RED  = =  metalness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . b  =  metallness_image - > get_pixel ( w ,  h ) . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_GREEN  = =  metalness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . b  =  metallness_image - > get_pixel ( w ,  h ) . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_BLUE  = =  metalness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . b  =  metallness_image - > get_pixel ( w ,  h ) . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( BaseMaterial3D : : TextureChannel : : TEXTURE_CHANNEL_ALPHA  = =  metalness_channel )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . b  =  metallness_image - > get_pixel ( w ,  h ) . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														orm_image - > set_pixel ( w ,  h ,  c ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												orm_image - > generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												orm_texture - > set_image ( orm_image ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												GLTFTextureIndex  orm_texture_index  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( has_ao  | |  has_roughness  | |  has_metalness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													orm_texture - > set_name ( material - > get_name ( )  +  " _orm " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													orm_texture_index  =  _set_texture ( p_state ,  orm_texture ,  base_material - > get_texture_filter ( ) ,  base_material - > get_flag ( BaseMaterial3D : : FLAG_USE_TEXTURE_REPEAT ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( has_ao )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Dictionary  occt ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													occt [ " index " ]  =  orm_texture_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													d [ " occlusionTexture " ]  =  occt ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( has_roughness  | |  has_metalness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mrt [ " index " ]  =  orm_texture_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Dictionary  extensions  =  _serialize_texture_transform_uv1 ( material ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ! extensions . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														mrt [ " extensions " ]  =  extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_state - > use_khr_texture_transform  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mr [ " metallicRoughnessTexture " ]  =  mrt ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										d [ " pbrMetallicRoughness " ]  =  mr ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( base_material - > get_feature ( BaseMaterial3D : : FEATURE_NORMAL_MAPPING )  & &  _image_format  ! =  " None " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Dictionary  nt ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < ImageTexture >  tex ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											tex . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											{ 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Ref < Texture2D >  normal_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_NORMAL ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-12-31 17:43:15 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( normal_texture . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Code for uncompressing RG normal maps
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < Image >  img  =  normal_texture - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( img . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Ref < ImageTexture >  img_tex  =  img ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( img_tex . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															img  =  img_tex - > get_image ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														img - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														img - > convert ( Image : : FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														for  ( int32_t  y  =  0 ;  y  <  img - > get_height ( ) ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															for  ( int32_t  x  =  0 ;  x  <  img - > get_width ( ) ;  x + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																Color  c  =  img - > get_pixel ( x ,  y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																Vector2  red_green  =  Vector2 ( c . r ,  c . g ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																red_green  =  red_green  *  Vector2 ( 2.0f ,  2.0f )  -  Vector2 ( 1.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																float  blue  =  1.0f  -  red_green . dot ( red_green ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																blue  =  MAX ( 0.0f ,  blue ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																c . b  =  Math : : sqrt ( blue ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																img - > set_pixel ( x ,  y ,  c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-04 01:49:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														tex - > set_image ( img ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFTextureIndex  gltf_texture_index  =  - 1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-28 12:32:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( tex . is_valid ( )  & &  tex - > get_image ( ) . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												tex - > set_name ( material - > get_name ( )  +  " _normal " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												gltf_texture_index  =  _set_texture ( p_state ,  tex ,  base_material - > get_texture_filter ( ) ,  base_material - > get_flag ( BaseMaterial3D : : FLAG_USE_TEXTURE_REPEAT ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											nt [ " scale " ]  =  base_material - > get_normal_scale ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( gltf_texture_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												nt [ " index " ]  =  gltf_texture_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												d [ " normalTexture " ]  =  nt ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( base_material - > get_feature ( BaseMaterial3D : : FEATURE_EMISSION ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Color  c  =  base_material - > get_emission ( ) . linear_to_srgb ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-03-22 22:53:26 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Array  arr  =  {  c . r ,  c . g ,  c . b  } ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											d [ " emissiveFactor " ]  =  arr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( base_material - > get_feature ( BaseMaterial3D : : FEATURE_EMISSION )  & &  _image_format  ! =  " None " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Dictionary  et ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Ref < Texture2D >  emission_texture  =  base_material - > get_texture ( BaseMaterial3D : : TEXTURE_EMISSION ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											GLTFTextureIndex  gltf_texture_index  =  - 1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-28 12:32:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( emission_texture . is_valid ( )  & &  emission_texture - > get_image ( ) . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												emission_texture - > set_name ( material - > get_name ( )  +  " _emission " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												gltf_texture_index  =  _set_texture ( p_state ,  emission_texture ,  base_material - > get_texture_filter ( ) ,  base_material - > get_flag ( BaseMaterial3D : : FLAG_USE_TEXTURE_REPEAT ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( gltf_texture_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												et [ " index " ]  =  gltf_texture_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												d [ " emissiveTexture " ]  =  et ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  bool  ds  =  base_material - > get_cull_mode ( )  = =  BaseMaterial3D : : CULL_DISABLED ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( ds )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " doubleSided " ]  =  ds ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( base_material - > get_transparency ( )  = =  BaseMaterial3D : : TRANSPARENCY_ALPHA_SCISSOR )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											d [ " alphaMode " ]  =  " MASK " ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											d [ " alphaCutoff " ]  =  base_material - > get_alpha_scissor_threshold ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( base_material - > get_transparency ( )  ! =  BaseMaterial3D : : TRANSPARENCY_DISABLED )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											d [ " alphaMode " ]  =  " BLEND " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-16 23:36:01 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-03-03 12:10:42 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( base_material - > get_shading_mode ( )  = =  BaseMaterial3D : : SHADING_MODE_UNSHADED )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  mat_unlit ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											extensions [ " KHR_materials_unlit " ]  =  mat_unlit ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > add_used_extension ( " KHR_materials_unlit " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-08 22:56:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( base_material - > get_feature ( BaseMaterial3D : : FEATURE_EMISSION )  & &  ! Math : : is_equal_approx ( base_material - > get_emission_energy_multiplier ( ) ,  1.0f ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  mat_emissive_strength ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mat_emissive_strength [ " emissiveStrength " ]  =  base_material - > get_emission_energy_multiplier ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											extensions [ " KHR_materials_emissive_strength " ]  =  mat_emissive_strength ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > add_used_extension ( " KHR_materials_emissive_strength " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-03-03 12:10:42 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										d [ " extensions " ]  =  extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_attach_meta_to_extras ( material ,  d ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										materials . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! materials . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " materials " ]  =  materials ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " Total materials:  "  +  itos ( p_state - > materials . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_materials ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " materials " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & materials  =  p_state - > json [ " materials " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( GLTFMaterialIndex  i  =  0 ;  i  <  materials . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Dictionary  & material_dict  =  materials [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < StandardMaterial3D >  material ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										material . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " name " )  & &  ! String ( material_dict [ " name " ] ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material - > set_name ( material_dict [ " name " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-24 00:29:20 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material - > set_name ( vformat ( " material_%s " ,  itos ( i ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  material_extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( material_dict . has ( " extensions " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material_extensions  =  material_dict [ " extensions " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-03-03 12:10:42 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_extensions . has ( " KHR_materials_unlit " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-03-03 12:10:42 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											material - > set_shading_mode ( BaseMaterial3D : : SHADING_MODE_UNSHADED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_extensions . has ( " KHR_materials_emissive_strength " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  emissive_strength  =  material_extensions [ " KHR_materials_emissive_strength " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 19:43:34 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( emissive_strength . has ( " emissiveStrength " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_emission_energy_multiplier ( emissive_strength [ " emissiveStrength " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_extensions . has ( " KHR_materials_pbrSpecularGlossiness " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											WARN_PRINT ( " Material uses a specular and glossiness workflow. Textures will be converted to roughness and metallic workflow, which may not be 100% accurate. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Dictionary  sgm  =  material_extensions [ " KHR_materials_pbrSpecularGlossiness " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < GLTFSpecGloss >  spec_gloss ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											spec_gloss . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( sgm . has ( " diffuseTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Dictionary  & diffuse_texture_dict  =  sgm [ " diffuseTexture " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( diffuse_texture_dict . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Ref < GLTFTextureSampler >  diffuse_sampler  =  _get_sampler_for_texture ( p_state ,  diffuse_texture_dict [ " index " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( diffuse_sampler . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														material - > set_texture_filter ( diffuse_sampler - > get_filter_mode ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														material - > set_flag ( BaseMaterial3D : : FLAG_USE_TEXTURE_REPEAT ,  diffuse_sampler - > get_wrap_mode ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Ref < Texture2D >  diffuse_texture  =  _get_texture ( p_state ,  diffuse_texture_dict [ " index " ] ,  TEXTURE_TYPE_GENERIC ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													if  ( diffuse_texture . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-28 12:32:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														spec_gloss - > diffuse_img  =  diffuse_texture - > get_image ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														material - > set_texture ( BaseMaterial3D : : TEXTURE_ALBEDO ,  diffuse_texture ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( sgm . has ( " diffuseFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Array  & arr  =  sgm [ " diffuseFactor " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( arr . size ( )  ! =  4 ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Color  c  =  Color ( arr [ 0 ] ,  arr [ 1 ] ,  arr [ 2 ] ,  arr [ 3 ] ) . linear_to_srgb ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												spec_gloss - > diffuse_factor  =  c ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_albedo ( spec_gloss - > diffuse_factor ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( sgm . has ( " specularFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Array  & arr  =  sgm [ " specularFactor " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( arr . size ( )  ! =  3 ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												spec_gloss - > specular_factor  =  Color ( arr [ 0 ] ,  arr [ 1 ] ,  arr [ 2 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( sgm . has ( " glossinessFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												spec_gloss - > gloss_factor  =  sgm [ " glossinessFactor " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_roughness ( 1.0f  -  CLAMP ( spec_gloss - > gloss_factor ,  0.0f ,  1.0f ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( sgm . has ( " specularGlossinessTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Dictionary  & spec_gloss_texture  =  sgm [ " specularGlossinessTexture " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( spec_gloss_texture . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													const  Ref < Texture2D >  orig_texture  =  _get_texture ( p_state ,  spec_gloss_texture [ " index " ] ,  TEXTURE_TYPE_GENERIC ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													if  ( orig_texture . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-28 12:32:17 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														spec_gloss - > spec_gloss_img  =  orig_texture - > get_image ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											spec_gloss_to_rough_metal ( spec_gloss ,  material ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  if  ( material_dict . has ( " pbrMetallicRoughness " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & mr  =  material_dict [ " pbrMetallicRoughness " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( mr . has ( " baseColorFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Array  & arr  =  mr [ " baseColorFactor " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( arr . size ( )  ! =  4 ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Color  c  =  Color ( arr [ 0 ] ,  arr [ 1 ] ,  arr [ 2 ] ,  arr [ 3 ] ) . linear_to_srgb ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												material - > set_albedo ( c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mr . has ( " baseColorTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Dictionary  & bct  =  mr [ " baseColorTexture " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( bct . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Ref < GLTFTextureSampler >  bct_sampler  =  _get_sampler_for_texture ( p_state ,  bct [ " index " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													material - > set_texture_filter ( bct_sampler - > get_filter_mode ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													material - > set_flag ( BaseMaterial3D : : FLAG_USE_TEXTURE_REPEAT ,  bct_sampler - > get_wrap_mode ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													material - > set_texture ( BaseMaterial3D : : TEXTURE_ALBEDO ,  _get_texture ( p_state ,  bct [ " index " ] ,  TEXTURE_TYPE_GENERIC ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! mr . has ( " baseColorFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													material - > set_albedo ( Color ( 1 ,  1 ,  1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_set_texture_transform_uv1 ( bct ,  material ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mr . has ( " metallicFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_metallic ( mr [ " metallicFactor " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_metallic ( 1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mr . has ( " roughnessFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_roughness ( mr [ " roughnessFactor " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_roughness ( 1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mr . has ( " metallicRoughnessTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Dictionary  & bct  =  mr [ " metallicRoughnessTexture " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( bct . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													const  Ref < Texture2D >  t  =  _get_texture ( p_state ,  bct [ " index " ] ,  TEXTURE_TYPE_GENERIC ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													material - > set_texture ( BaseMaterial3D : : TEXTURE_METALLIC ,  t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													material - > set_metallic_texture_channel ( BaseMaterial3D : : TEXTURE_CHANNEL_BLUE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													material - > set_texture ( BaseMaterial3D : : TEXTURE_ROUGHNESS ,  t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													material - > set_roughness_texture_channel ( BaseMaterial3D : : TEXTURE_CHANNEL_GREEN ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ! mr . has ( " metallicFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														material - > set_metallic ( 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( ! mr . has ( " roughnessFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														material - > set_roughness ( 1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " normalTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & bct  =  material_dict [ " normalTexture " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( bct . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												material - > set_texture ( BaseMaterial3D : : TEXTURE_NORMAL ,  _get_texture ( p_state ,  bct [ " index " ] ,  TEXTURE_TYPE_NORMAL ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												material - > set_feature ( BaseMaterial3D : : FEATURE_NORMAL_MAPPING ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( bct . has ( " scale " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_normal_scale ( bct [ " scale " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " occlusionTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & bct  =  material_dict [ " occlusionTexture " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( bct . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												material - > set_texture ( BaseMaterial3D : : TEXTURE_AMBIENT_OCCLUSION ,  _get_texture ( p_state ,  bct [ " index " ] ,  TEXTURE_TYPE_GENERIC ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												material - > set_ao_texture_channel ( BaseMaterial3D : : TEXTURE_CHANNEL_RED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_feature ( BaseMaterial3D : : FEATURE_AMBIENT_OCCLUSION ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " emissiveFactor " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Array  & arr  =  material_dict [ " emissiveFactor " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( arr . size ( )  ! =  3 ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  Color  c  =  Color ( arr [ 0 ] ,  arr [ 1 ] ,  arr [ 2 ] ) . linear_to_srgb ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											material - > set_feature ( BaseMaterial3D : : FEATURE_EMISSION ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material - > set_emission ( c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " emissiveTexture " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & bct  =  material_dict [ " emissiveTexture " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( bct . has ( " index " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-18 17:58:27 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												material - > set_texture ( BaseMaterial3D : : TEXTURE_EMISSION ,  _get_texture ( p_state ,  bct [ " index " ] ,  TEXTURE_TYPE_GENERIC ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												material - > set_feature ( BaseMaterial3D : : FEATURE_EMISSION ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_emission ( Color ( 0 ,  0 ,  0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " doubleSided " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  bool  ds  =  material_dict [ " doubleSided " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( ds )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_cull_mode ( BaseMaterial3D : : CULL_DISABLED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-06-23 14:01:07 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " alphaMode " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  String  & am  =  material_dict [ " alphaMode " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( am  = =  " BLEND " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_transparency ( BaseMaterial3D : : TRANSPARENCY_ALPHA_DEPTH_PRE_PASS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( am  = =  " MASK " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												material - > set_transparency ( BaseMaterial3D : : TRANSPARENCY_ALPHA_SCISSOR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2025-01-02 12:53:55 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( material_dict . has ( " alphaCutoff " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material - > set_alpha_scissor_threshold ( material_dict [ " alphaCutoff " ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material - > set_alpha_scissor_threshold ( 0.5f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( material_dict . has ( " extras " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_attach_extras_to_meta ( material_dict [ " extras " ] ,  material ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > materials . push_back ( material ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " Total materials:  "  +  itos ( p_state - > materials . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _set_texture_transform_uv1 ( const  Dictionary  & p_dict ,  Ref < BaseMaterial3D >  p_material )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_dict . has ( " extensions " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & extensions  =  p_dict [ " extensions " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( extensions . has ( " KHR_texture_transform " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_material . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Dictionary  & texture_transform  =  extensions [ " KHR_texture_transform " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Array  & offset_arr  =  texture_transform [ " offset " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( offset_arr . size ( )  = =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Vector3  offset_vector3  =  Vector3 ( offset_arr [ 0 ] ,  offset_arr [ 1 ] ,  0.0f ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_material - > set_uv1_offset ( offset_vector3 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  Array  & scale_arr  =  texture_transform [ " scale " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( scale_arr . size ( )  = =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Vector3  scale_vector3  =  Vector3 ( scale_arr [ 0 ] ,  scale_arr [ 1 ] ,  1.0f ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_material - > set_uv1_scale ( scale_vector3 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  GLTFDocument : : spec_gloss_to_rough_metal ( Ref < GLTFSpecGloss >  r_spec_gloss ,  Ref < BaseMaterial3D >  p_material )  {  
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( r_spec_gloss . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( r_spec_gloss - > spec_gloss_img . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_spec_gloss - > diffuse_img . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_material . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									bool  has_roughness  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  has_metal  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_material - > set_roughness ( 1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_material - > set_metallic ( 1.0f ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-22 20:06:19 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Image >  rm_img  =  Image : : create_empty ( r_spec_gloss - > spec_gloss_img - > get_width ( ) ,  r_spec_gloss - > spec_gloss_img - > get_height ( ) ,  false ,  Image : : FORMAT_RGBA8 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									r_spec_gloss - > spec_gloss_img - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( r_spec_gloss - > diffuse_img . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_spec_gloss - > diffuse_img - > decompress ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_spec_gloss - > diffuse_img - > resize ( r_spec_gloss - > spec_gloss_img - > get_width ( ) ,  r_spec_gloss - > spec_gloss_img - > get_height ( ) ,  Image : : INTERPOLATE_LANCZOS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										r_spec_gloss - > spec_gloss_img - > resize ( r_spec_gloss - > diffuse_img - > get_width ( ) ,  r_spec_gloss - > diffuse_img - > get_height ( ) ,  Image : : INTERPOLATE_LANCZOS ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  y  =  0 ;  y  <  r_spec_gloss - > spec_gloss_img - > get_height ( ) ;  y + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  x  =  0 ;  x  <  r_spec_gloss - > spec_gloss_img - > get_width ( ) ;  x + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  Color  specular_pixel  =  r_spec_gloss - > spec_gloss_img - > get_pixel ( x ,  y ) . srgb_to_linear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Color  specular  =  Color ( specular_pixel . r ,  specular_pixel . g ,  specular_pixel . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											specular  * =  r_spec_gloss - > specular_factor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Color  diffuse  =  Color ( 1.0f ,  1.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											diffuse  * =  r_spec_gloss - > diffuse_img - > get_pixel ( x ,  y ) . srgb_to_linear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											float  metallic  =  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Color  base_color ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											spec_gloss_to_metal_base_color ( specular ,  diffuse ,  base_color ,  metallic ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Color  mr  =  Color ( 1.0f ,  1.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mr . g  =  specular_pixel . a ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mr . b  =  metallic ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! Math : : is_equal_approx ( mr . g ,  1.0f ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												has_roughness  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-20 03:03:06 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( ! Math : : is_zero_approx ( mr . b ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												has_metal  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mr . g  * =  r_spec_gloss - > gloss_factor ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mr . g  =  1.0f  -  mr . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											rm_img - > set_pixel ( x ,  y ,  mr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( r_spec_gloss - > diffuse_img . is_valid ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 10:37:22 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												r_spec_gloss - > diffuse_img - > set_pixel ( x ,  y ,  base_color . linear_to_srgb ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									rm_img - > generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_spec_gloss - > diffuse_img - > generate_mipmaps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-04 01:49:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_material - > set_texture ( BaseMaterial3D : : TEXTURE_ALBEDO ,  ImageTexture : : create_from_image ( r_spec_gloss - > diffuse_img ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ImageTexture >  rm_image_texture  =  ImageTexture : : create_from_image ( rm_img ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( has_roughness )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_material - > set_texture ( BaseMaterial3D : : TEXTURE_ROUGHNESS ,  rm_image_texture ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_material - > set_roughness_texture_channel ( BaseMaterial3D : : TEXTURE_CHANNEL_GREEN ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( has_metal )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_material - > set_texture ( BaseMaterial3D : : TEXTURE_METALLIC ,  rm_image_texture ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_material - > set_metallic_texture_channel ( BaseMaterial3D : : TEXTURE_CHANNEL_BLUE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  GLTFDocument : : spec_gloss_to_metal_base_color ( const  Color  & p_specular_factor ,  const  Color  & p_diffuse ,  Color  & r_base_color ,  float  & r_metallic )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Color  DIELECTRIC_SPECULAR  =  Color ( 0.04f ,  0.04f ,  0.04f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Color  specular  =  Color ( p_specular_factor . r ,  p_specular_factor . g ,  p_specular_factor . b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  one_minus_specular_strength  =  1.0f  -  get_max_component ( specular ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  dielectric_specular_red  =  DIELECTRIC_SPECULAR . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									float  brightness_diffuse  =  get_perceived_brightness ( p_diffuse ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  brightness_specular  =  get_perceived_brightness ( specular ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_metallic  =  solve_metallic ( dielectric_specular_red ,  brightness_diffuse ,  brightness_specular ,  one_minus_specular_strength ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  one_minus_metallic  =  1.0f  -  r_metallic ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Color  base_color_from_diffuse  =  p_diffuse  *  ( one_minus_specular_strength  /  ( 1.0f  -  dielectric_specular_red )  /  MAX ( one_minus_metallic ,  CMP_EPSILON ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Color  base_color_from_specular  =  ( specular  -  ( DIELECTRIC_SPECULAR  *  ( one_minus_metallic ) ) )  *  ( 1.0f  /  MAX ( r_metallic ,  CMP_EPSILON ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_base_color . r  =  Math : : lerp ( base_color_from_diffuse . r ,  base_color_from_specular . r ,  r_metallic  *  r_metallic ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_base_color . g  =  Math : : lerp ( base_color_from_diffuse . g ,  base_color_from_specular . g ,  r_metallic  *  r_metallic ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_base_color . b  =  Math : : lerp ( base_color_from_diffuse . b ,  base_color_from_specular . b ,  r_metallic  *  r_metallic ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_base_color . a  =  p_diffuse . a ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-29 09:36:34 +05:45 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									r_base_color  =  r_base_color . clamp ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_skins ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " skins " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & skins  =  p_state - > json [ " skins " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Create the base skins, and mark nodes that are joints
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  skins . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & d  =  skins [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFSkin >  skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										skin . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( ! d . has ( " joints " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Array  & joints  =  d [ " joints " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " inverseBindMatrices " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											skin - > inverse_binds  =  _decode_accessor_as_xform ( p_state ,  d [ " inverseBindMatrices " ] ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( skin - > inverse_binds . size ( )  ! =  joints . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  joints . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  GLTFNodeIndex  node  =  joints [ j ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_INDEX_V ( node ,  p_state - > nodes . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											skin - > joints . push_back ( node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											skin - > joints_original . push_back ( node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > nodes . write [ node ] - > joint  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-24 00:29:20 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( d . has ( " name " )  & &  ! String ( d [ " name " ] ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											skin - > set_name ( d [ " name " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-24 00:29:20 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											skin - > set_name ( vformat ( " skin_%s " ,  itos ( i ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( d . has ( " skeleton " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											skin - > skin_root  =  d [ " skeleton " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > skins . push_back ( skin ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFSkinIndex  i  =  0 ;  i  <  p_state - > skins . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFSkin >  skin  =  p_state - > skins . write [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Expand the skin to capture all the extra non-joints that lie in between the actual joints,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// and expand the hierarchy to ensure multi-rooted trees lie on the same height level
 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( SkinTool : : _expand_skin ( p_state - > nodes ,  skin ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( SkinTool : : _verify_skin ( p_state - > nodes ,  skin ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total skins:  "  +  itos ( p_state - > skins . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_skins ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_remove_duplicate_skins ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Array  json_skins ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  skin_i  =  0 ;  skin_i  <  p_state - > skins . size ( ) ;  skin_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFSkin >  gltf_skin  =  p_state - > skins [ skin_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Dictionary  json_skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										json_skin [ " inverseBindMatrices " ]  =  _encode_accessor_as_xform ( p_state ,  gltf_skin - > inverse_binds ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										json_skin [ " joints " ]  =  gltf_skin - > get_joints ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										json_skin [ " name " ]  =  gltf_skin - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										json_skins . push_back ( json_skin ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > skins . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " skins " ]  =  json_skins ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _create_skins ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( GLTFSkinIndex  skin_i  =  0 ;  skin_i  <  p_state - > skins . size ( ) ;  + + skin_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFSkin >  gltf_skin  =  p_state - > skins . write [ skin_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Skin >  skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										skin . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Some skins don't have IBM's! What absolute monsters!
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  bool  has_ibms  =  ! gltf_skin - > inverse_binds . is_empty ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  joint_i  =  0 ;  joint_i  <  gltf_skin - > joints_original . size ( ) ;  + + joint_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFNodeIndex  node  =  gltf_skin - > joints_original [ joint_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											String  bone_name  =  p_state - > nodes [ node ] - > get_name ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Transform3D  xform ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											if  ( has_ibms )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												xform  =  gltf_skin - > inverse_binds [ joint_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_state - > use_named_skin_binds )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												skin - > add_named_bind ( bone_name ,  xform ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int32_t  bone_i  =  gltf_skin - > joint_i_to_bone_i [ joint_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skin - > add_bind ( bone_i ,  xform ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_skin - > godot_skin  =  skin ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Purge the duplicates!
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									_remove_duplicate_skins ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Create unique names now, after removing duplicates
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFSkinIndex  skin_i  =  0 ;  skin_i  <  p_state - > skins . size ( ) ;  + + skin_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Skin >  skin  =  p_state - > skins . write [ skin_i ] - > godot_skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( skin - > get_name ( ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											// Make a unique name, no gltf node represents this skin
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											skin - > set_name ( _gen_unique_name ( p_state ,  " Skin " ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								bool  GLTFDocument : : _skins_are_same ( const  Ref < Skin >  p_skin_a ,  const  Ref < Skin >  p_skin_b )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_skin_a - > get_bind_count ( )  ! =  p_skin_b - > get_bind_count ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_skin_a - > get_bind_count ( ) ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_skin_a - > get_bind_bone ( i )  ! =  p_skin_b - > get_bind_bone ( i ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											return  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_skin_a - > get_bind_name ( i )  ! =  p_skin_b - > get_bind_name ( i ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-20 20:26:11 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Transform3D  a_xform  =  p_skin_a - > get_bind_pose ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Transform3D  b_xform  =  p_skin_b - > get_bind_pose ( i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( a_xform  ! =  b_xform )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _remove_duplicate_skins ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_state - > skins . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  i  +  1 ;  j  <  p_state - > skins . size ( ) ;  + + j )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Ref < Skin >  skin_i  =  p_state - > skins [ i ] - > godot_skin ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Ref < Skin >  skin_j  =  p_state - > skins [ j ] - > godot_skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( _skins_are_same ( skin_i ,  skin_j ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// replace it and delete the old
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_state - > skins . write [ j ] - > godot_skin  =  skin_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_lights ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_state - > lights . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  lights ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFLightIndex  i  =  0 ;  i  <  p_state - > lights . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										lights . push_back ( p_state - > lights [ i ] - > to_dictionary ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  extensions ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > json . has ( " extensions " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										extensions  =  p_state - > json [ " extensions " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > json [ " extensions " ]  =  extensions ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  lights_punctual ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									extensions [ " KHR_lights_punctual " ]  =  lights_punctual ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									lights_punctual [ " lights " ]  =  lights ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total lights:  "  +  itos ( p_state - > lights . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_cameras ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  cameras ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									cameras . resize ( p_state - > cameras . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( GLTFCameraIndex  i  =  0 ;  i  <  p_state - > cameras . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										cameras [ i ]  =  p_state - > cameras [ i ] - > to_dictionary ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > cameras . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " cameras " ]  =  cameras ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total cameras:  "  +  itos ( p_state - > cameras . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_lights ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " extensions " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Dictionary  extensions  =  p_state - > json [ " extensions " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( ! extensions . has ( " KHR_lights_punctual " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  lights_punctual  =  extensions [ " KHR_lights_punctual " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! lights_punctual . has ( " lights " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Array  & lights  =  lights_punctual [ " lights " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( GLTFLightIndex  light_i  =  0 ;  light_i  <  lights . size ( ) ;  light_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-26 00:51:53 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFLight >  light  =  GLTFLight : : from_dictionary ( lights [ light_i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( light . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  Error : : ERR_PARSE_ERROR ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > lights . push_back ( light ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total lights:  "  +  itos ( p_state - > lights . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_cameras ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " cameras " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  cameras  =  p_state - > json [ " cameras " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( GLTFCameraIndex  i  =  0 ;  i  <  cameras . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > cameras . push_back ( GLTFCamera : : from_dictionary ( cameras [ i ] ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total cameras:  "  +  itos ( p_state - > cameras . size ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								String  GLTFDocument : : interpolation_to_string ( const  GLTFAnimation : : Interpolation  p_interp )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									String  interp  =  " LINEAR " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_interp  = =  GLTFAnimation : : INTERP_STEP )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										interp  =  " STEP " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( p_interp  = =  GLTFAnimation : : INTERP_LINEAR )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										interp  =  " LINEAR " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( p_interp  = =  GLTFAnimation : : INTERP_CATMULLROMSPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										interp  =  " CATMULLROMSPLINE " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( p_interp  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										interp  =  " CUBICSPLINE " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_animations ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > animation_players . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int32_t  player_i  =  0 ;  player_i  <  p_state - > animation_players . size ( ) ;  player_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										AnimationPlayer  * animation_player  =  p_state - > animation_players [ player_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										List < StringName >  animations ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										animation_player - > get_animation_list ( & animations ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-01 16:47:20 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( const  StringName  & animation_name  :  animations )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_convert_animation ( p_state ,  animation_player ,  animation_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Array  animations ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFAnimationIndex  animation_i  =  0 ;  animation_i  <  p_state - > animations . size ( ) ;  animation_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Dictionary  d ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFAnimation >  gltf_animation  =  p_state - > animations [ animation_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_animation - > is_empty_of_tracks ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-15 12:04:21 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! gltf_animation - > get_name ( ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											d [ " name " ]  =  gltf_animation - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Array  channels ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Array  samplers ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Serialize glTF node tracks with the vanilla glTF animation system.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( KeyValue < int ,  GLTFAnimation : : NodeTrack >  & track_i  :  gltf_animation - > get_node_tracks ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFAnimation : : NodeTrack  track  =  track_i . value ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-30 22:18:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( track . position_track . times . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												Dictionary  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " sampler " ]  =  samplers . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  s ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-08-30 22:18:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " interpolation " ]  =  interpolation_to_string ( track . position_track . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < double >  times  =  track . position_track . times ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " input " ]  =  _encode_accessor_as_floats ( p_state ,  times ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < Vector3 >  values  =  track . position_track . values ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " output " ]  =  _encode_accessor_as_vec3 ( p_state ,  values ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												samplers . push_back ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												target [ " path " ]  =  " translation " ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-09 14:13:42 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												target [ " node " ]  =  track_i . key ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " target " ]  =  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channels . push_back ( t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( track . rotation_track . times . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " sampler " ]  =  samplers . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  s ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												s [ " interpolation " ]  =  interpolation_to_string ( track . rotation_track . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < double >  times  =  track . rotation_track . times ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " input " ]  =  _encode_accessor_as_floats ( p_state ,  times ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < Quaternion >  values  =  track . rotation_track . values ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " output " ]  =  _encode_accessor_as_quaternions ( p_state ,  values ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												samplers . push_back ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												target [ " path " ]  =  " rotation " ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-09 14:13:42 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												target [ " node " ]  =  track_i . key ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " target " ]  =  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channels . push_back ( t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( track . scale_track . times . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " sampler " ]  =  samplers . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  s ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												s [ " interpolation " ]  =  interpolation_to_string ( track . scale_track . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < double >  times  =  track . scale_track . times ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " input " ]  =  _encode_accessor_as_floats ( p_state ,  times ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < Vector3 >  values  =  track . scale_track . values ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " output " ]  =  _encode_accessor_as_vec3 ( p_state ,  values ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												samplers . push_back ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												target [ " path " ]  =  " scale " ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-09 14:13:42 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												target [ " node " ]  =  track_i . key ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " target " ]  =  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channels . push_back ( t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( track . weight_tracks . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												double  length  =  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int32_t  track_idx  =  0 ;  track_idx  <  track . weight_tracks . size ( ) ;  track_idx + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int32_t  last_time_index  =  track . weight_tracks [ track_idx ] . times . size ( )  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													length  =  MAX ( length ,  track . weight_tracks [ track_idx ] . times [ last_time_index ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												Dictionary  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " sampler " ]  =  samplers . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  s ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < double >  times ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												{ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( time  > =  length )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															time  =  length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( int32_t  track_idx  =  0 ;  track_idx  <  track . weight_tracks . size ( ) ;  track_idx + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < real_t >  weight_track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													while  ( true )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-16 01:03:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														float  weight  =  _interpolate_track < real_t > ( track . weight_tracks [ track_idx ] . times , 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																track . weight_tracks [ track_idx ] . values , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																time , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																track . weight_tracks [ track_idx ] . interpolation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight_track . push_back ( weight ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( time  > =  length )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															time  =  length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track . weight_tracks . write [ track_idx ] . times  =  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track . weight_tracks . write [ track_idx ] . values  =  weight_track ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Vector < double >  all_track_times  =  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < double >  all_track_values ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												int32_t  values_size  =  track . weight_tracks [ 0 ] . values . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												int32_t  weight_tracks_size  =  track . weight_tracks . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												all_track_values . resize ( weight_tracks_size  *  values_size ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												for  ( int  k  =  0 ;  k  <  track . weight_tracks . size ( ) ;  k + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-16 01:03:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector < real_t >  wdata  =  track . weight_tracks [ k ] . values ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													for  ( int  l  =  0 ;  l  <  wdata . size ( ) ;  l + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														int32_t  index  =  l  *  weight_tracks_size  +  k ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_BREAK ( index  > =  all_track_values . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														all_track_values . write [ index ]  =  wdata . write [ l ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												s [ " interpolation " ]  =  interpolation_to_string ( track . weight_tracks [ track . weight_tracks . size ( )  -  1 ] . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												s [ " input " ]  =  _encode_accessor_as_floats ( p_state ,  all_track_times ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												s [ " output " ]  =  _encode_accessor_as_floats ( p_state ,  all_track_values ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												samplers . push_back ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												target [ " path " ]  =  " weights " ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-09 14:13:42 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												target [ " node " ]  =  track_i . key ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												t [ " target " ]  =  target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channels . push_back ( t ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! gltf_animation - > get_pointer_tracks ( ) . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Serialize glTF pointer tracks with the KHR_animation_pointer extension.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! p_state - > extensions_used . has ( " KHR_animation_pointer " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > extensions_used . push_back ( " KHR_animation_pointer " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( KeyValue < String ,  GLTFAnimation : : Channel < Variant > >  & pointer_track_iter  :  gltf_animation - > get_pointer_tracks ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  String  & json_pointer  =  pointer_track_iter . key ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  GLTFAnimation : : Channel < Variant >  & pointer_track  =  pointer_track_iter . value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Ref < GLTFObjectModelProperty >  & obj_model_prop  =  p_state - > object_model_properties [ json_pointer ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel [ " sampler " ]  =  samplers . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  channel_target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel_target [ " path " ]  =  " pointer " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  channel_target_ext ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  channel_target_ext_khr_anim_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel_target_ext_khr_anim_ptr [ " pointer " ]  =  json_pointer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel_target_ext [ " KHR_animation_pointer " ]  =  channel_target_ext_khr_anim_ptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel_target [ " extensions " ]  =  channel_target_ext ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel [ " target " ]  =  channel_target ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channels . push_back ( channel ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  sampler ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												sampler [ " input " ]  =  _encode_accessor_as_floats ( p_state ,  pointer_track . times ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												sampler [ " interpolation " ]  =  interpolation_to_string ( pointer_track . interpolation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												sampler [ " output " ]  =  _encode_accessor_as_variant ( p_state ,  pointer_track . values ,  obj_model_prop - > get_variant_type ( ) ,  obj_model_prop - > get_accessor_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												samplers . push_back ( sampler ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( channels . size ( )  & &  samplers . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " channels " ]  =  channels ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											d [ " samplers " ]  =  samplers ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											animations . push_back ( d ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! animations . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " animations " ]  =  animations ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total animations ' "  +  itos ( p_state - > animations . size ( ) )  +  " '. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_animations ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " animations " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Array  & animations  =  p_state - > json [ " animations " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFAnimationIndex  anim_index  =  0 ;  anim_index  <  animations . size ( ) ;  anim_index + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Dictionary  & anim_dict  =  animations [ anim_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFAnimation >  animation ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										animation . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! anim_dict . has ( " channels " )  | |  ! anim_dict . has ( " samplers " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Array  channels  =  anim_dict [ " channels " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Array  samplers  =  anim_dict [ " samplers " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( anim_dict . has ( " name " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  String  anim_name  =  anim_dict [ " name " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  String  anim_name_lower  =  anim_name . to_lower ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( anim_name_lower . begins_with ( " loop " )  | |  anim_name_lower . ends_with ( " loop " )  | |  anim_name_lower . begins_with ( " cycle " )  | |  anim_name_lower . ends_with ( " cycle " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												animation - > set_loop ( true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											animation - > set_original_name ( anim_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											animation - > set_name ( _gen_unique_animation_name ( p_state ,  anim_name ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  channel_index  =  0 ;  channel_index  <  channels . size ( ) ;  channel_index + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & anim_channel  =  channels [ channel_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V_MSG ( ! anim_channel . has ( " sampler " ) ,  ERR_PARSE_ERROR ,  " glTF: Animation channel missing required 'sampler' property. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V_MSG ( ! anim_channel . has ( " target " ) ,  ERR_PARSE_ERROR ,  " glTF: Animation channel missing required 'target' property. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Parse sampler.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  sampler_index  =  anim_channel [ " sampler " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_INDEX_V ( sampler_index ,  samplers . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & sampler_dict  =  samplers [ sampler_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! sampler_dict . has ( " input " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V ( ! sampler_dict . has ( " output " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  input_time_accessor_index  =  sampler_dict [ " input " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  output_value_accessor_index  =  sampler_dict [ " output " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											GLTFAnimation : : Interpolation  interp  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  output_count  =  1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( sampler_dict . has ( " interpolation " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  String  & in  =  sampler_dict [ " interpolation " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												if  ( in  = =  " STEP " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													interp  =  GLTFAnimation : : INTERP_STEP ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( in  = =  " LINEAR " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													interp  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( in  = =  " CATMULLROMSPLINE " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													interp  =  GLTFAnimation : : INTERP_CATMULLROMSPLINE ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													output_count  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( in  = =  " CUBICSPLINE " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													interp  =  GLTFAnimation : : INTERP_CUBIC_SPLINE ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													output_count  =  3 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  Vector < double >  times  =  _decode_accessor ( p_state ,  input_time_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Parse target.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Dictionary  & anim_target  =  anim_channel [ " target " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_V_MSG ( ! anim_target . has ( " path " ) ,  ERR_PARSE_ERROR ,  " glTF: Animation channel target missing required 'path' property. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											String  path  =  anim_target [ " path " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( path  = =  " pointer " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( ! anim_target . has ( " extensions " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  target_extensions  =  anim_target [ " extensions " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( ! target_extensions . has ( " KHR_animation_pointer " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Dictionary  khr_anim_ptr  =  target_extensions [ " KHR_animation_pointer " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( ! khr_anim_ptr . has ( " pointer " ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  anim_json_ptr  =  khr_anim_ptr [ " pointer " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												_parse_animation_pointer ( p_state ,  anim_json_ptr ,  animation ,  interp ,  times ,  output_value_accessor_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// If it's not a pointer, it's a regular animation channel from vanilla glTF (pos/rot/scale/weights).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! anim_target . has ( " node " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													WARN_PRINT ( " glTF: Animation channel target missing 'node' property. Ignoring this channel. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												GLTFNodeIndex  node  =  anim_target [ " node " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_FAIL_INDEX_V ( node ,  p_state - > nodes . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												GLTFAnimation : : NodeTrack  * track  =  nullptr ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( ! animation - > get_node_tracks ( ) . has ( node ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > get_node_tracks ( ) [ node ]  =  GLTFAnimation : : NodeTrack ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												track  =  & animation - > get_node_tracks ( ) [ node ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( path  = =  " translation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Vector < Vector3 >  positions  =  _decode_accessor_as_vec3 ( p_state ,  output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > position_track . interpolation  =  interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > position_track . times  =  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > position_track . values  =  positions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( path  = =  " rotation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Vector < Quaternion >  rotations  =  _decode_accessor_as_quaternion ( p_state ,  output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > rotation_track . interpolation  =  interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > rotation_track . times  =  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > rotation_track . values  =  rotations ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( path  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Vector < Vector3 >  scales  =  _decode_accessor_as_vec3 ( p_state ,  output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > scale_track . interpolation  =  interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > scale_track . times  =  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > scale_track . values  =  scales ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( path  = =  " weights " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  Vector < float >  weights  =  _decode_accessor_as_floats ( p_state ,  output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_INDEX_V ( p_state - > nodes [ node ] - > mesh ,  p_state - > meshes . size ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Ref < GLTFMesh >  mesh  =  p_state - > meshes [ p_state - > nodes [ node ] - > mesh ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  wc  =  mesh - > get_blend_weights ( ) . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_CONTINUE_MSG ( wc  = =  0 ,  " glTF: Animation tried to animate weights, but mesh has no weights. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													track - > weight_tracks . resize ( wc ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  expected_value_count  =  times . size ( )  *  output_count  *  wc ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_CONTINUE_MSG ( weights . size ( )  ! =  expected_value_count ,  " Invalid weight data, expected  "  +  itos ( expected_value_count )  +  "  weight values, got  "  +  itos ( weights . size ( ) )  +  "  instead. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  int  wlen  =  weights . size ( )  /  wc ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int  k  =  0 ;  k  <  wc ;  k + + )  {  //separate tracks, having them together is not such a good idea
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														GLTFAnimation : : Channel < real_t >  cf ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cf . interpolation  =  interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cf . times  =  Variant ( times ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector < real_t >  wdata ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														wdata . resize ( wlen ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														for  ( int  l  =  0 ;  l  <  wlen ;  l + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															wdata . write [ l ]  =  weights [ l  *  wc  +  k ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														cf . values  =  wdata ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														track - > weight_tracks . write [ k ]  =  cf ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													WARN_PRINT ( " Invalid path ' "  +  path  +  " '. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > animations . push_back ( animation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									print_verbose ( " glTF: Total animations ' "  +  itos ( p_state - > animations . size ( ) )  +  " '. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _parse_animation_pointer ( Ref < GLTFState >  p_state ,  const  String  & p_animation_json_pointer ,  const  Ref < GLTFAnimation >  p_gltf_animation ,  const  GLTFAnimation : : Interpolation  p_interp ,  const  Vector < double >  & p_times ,  const  int  p_output_value_accessor_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Special case: Convert TRS animation pointers to node track pos/rot/scale.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This is required to handle skeleton bones, and improves performance for regular nodes.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Mark this as unlikely because TRS animation pointers are not recommended,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// since vanilla glTF animations can already animate TRS properties directly.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// But having this code exist is required to be spec-compliant and handle all test files.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Note that TRS still needs to be handled in the general case as well, for KHR_interactivity.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  PackedStringArray  split  =  p_animation_json_pointer . split ( " / " ,  false ,  3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( unlikely ( split . size ( )  = =  3  & &  split [ 0 ]  = =  " nodes "  & &  ( split [ 2 ]  = =  " translation "  | |  split [ 2 ]  = =  " rotation "  | |  split [ 2 ]  = =  " scale "  | |  split [ 2 ]  = =  " matrix "  | |  split [ 2 ]  = =  " weights " ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  GLTFNodeIndex  node_index  =  split [ 1 ] . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										HashMap < int ,  GLTFAnimation : : NodeTrack >  & node_tracks  =  p_gltf_animation - > get_node_tracks ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! node_tracks . has ( node_index ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node_tracks [ node_index ]  =  GLTFAnimation : : NodeTrack ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFAnimation : : NodeTrack  * track  =  & node_tracks [ node_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( split [ 2 ]  = =  " translation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < Vector3 >  positions  =  _decode_accessor_as_vec3 ( p_state ,  p_output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > position_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > position_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > position_track . values  =  positions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( split [ 2 ]  = =  " rotation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < Quaternion >  rotations  =  _decode_accessor_as_quaternion ( p_state ,  p_output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > rotation_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > rotation_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > rotation_track . values  =  rotations ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( split [ 2 ]  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < Vector3 >  scales  =  _decode_accessor_as_vec3 ( p_state ,  p_output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > scale_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > scale_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > scale_track . values  =  scales ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( split [ 2 ]  = =  " matrix " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < Transform3D >  transforms  =  _decode_accessor_as_xform ( p_state ,  p_output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > position_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > position_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > position_track . values . resize ( transforms . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > rotation_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > rotation_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > rotation_track . values . resize ( transforms . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > scale_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > scale_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > scale_track . values . resize ( transforms . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  transforms . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												track - > position_track . values . write [ i ]  =  transforms [ i ] . get_origin ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												track - > rotation_track . values . write [ i ]  =  transforms [ i ] . basis . get_rotation_quaternion ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												track - > scale_track . values . write [ i ]  =  transforms [ i ] . basis . get_scale ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  {  // if (split[2] == "weights")
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < float >  accessor_weights  =  _decode_accessor_as_floats ( p_state ,  p_output_value_accessor_index ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  GLTFMeshIndex  mesh_index  =  p_state - > nodes [ node_index ] - > mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_INDEX ( mesh_index ,  p_state - > meshes . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Ref < GLTFMesh >  gltf_mesh  =  p_state - > meshes [ mesh_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Vector < float >  & blend_weights  =  gltf_mesh - > get_blend_weights ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  blend_weight_count  =  gltf_mesh - > get_blend_weights ( ) . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  anim_weights_size  =  accessor_weights . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// For example, if a mesh has 2 blend weights, and the accessor provides 10 values, then there are 5 frames of animation, each with 2 blend weights.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_COND_MSG ( blend_weight_count  = =  0  | |  ( ( anim_weights_size  %  blend_weight_count )  ! =  0 ) ,  " glTF: Cannot apply  "  +  itos ( accessor_weights . size ( ) )  +  "  weights to a mesh with  "  +  itos ( blend_weights . size ( ) )  +  "  blend weights. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  frame_count  =  anim_weights_size  /  blend_weight_count ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track - > weight_tracks . resize ( blend_weight_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  blend_weight_index  =  0 ;  blend_weight_index  <  blend_weight_count ;  blend_weight_index + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												GLTFAnimation : : Channel < real_t >  weight_track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												weight_track . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												weight_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												weight_track . values . resize ( frame_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  frame_index  =  0 ;  frame_index  <  frame_count ;  frame_index + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// For example, if a mesh has 2 blend weights, and the accessor provides 10 values,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// then the first frame has indices [0, 1], the second frame has [2, 3], and so on.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Here we process all frames of one blend weight, so we want [0, 2, 4, 6, 8] or [1, 3, 5, 7, 9].
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// For the fist one we calculate 0 * 2 + 0, 1 * 2 + 0, 2 * 2 + 0, etc, then for the second 0 * 2 + 1, 1 * 2 + 1, 2 * 2 + 1, etc.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weight_track . values . write [ frame_index ]  =  accessor_weights [ frame_index  *  blend_weight_count  +  blend_weight_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												track - > weight_tracks . write [ blend_weight_index ]  =  weight_track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// The special case was handled, return to skip the general case.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// General case: Convert animation pointers to Variant value pointer tracks.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFObjectModelProperty >  obj_model_prop  =  import_object_model_property ( p_state ,  p_animation_json_pointer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( obj_model_prop . is_null ( )  | |  ! obj_model_prop - > has_node_paths ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Exit quietly, `import_object_model_property` already prints a warning if the property is not found.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									HashMap < String ,  GLTFAnimation : : Channel < Variant > >  & anim_ptr_map  =  p_gltf_animation - > get_pointer_tracks ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									GLTFAnimation : : Channel < Variant >  channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									channel . interpolation  =  p_interp ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									channel . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									channel . values  =  _decode_accessor_as_variant ( p_state ,  p_output_value_accessor_index ,  obj_model_prop - > get_variant_type ( ) ,  obj_model_prop - > get_accessor_type ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									anim_ptr_map [ p_animation_json_pointer ]  =  channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _assign_node_names ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_state - > nodes . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										// Any joints get unique names generated when the skeleton is made, unique to the skeleton
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > skeleton  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 21:17:28 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										String  gltf_node_name  =  gltf_node - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( gltf_node_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 17:55:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( _naming_version  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( gltf_node - > mesh  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_node_name  =  _gen_unique_name ( p_state ,  " Mesh " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( gltf_node - > camera  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_node_name  =  _gen_unique_name ( p_state ,  " Camera3D " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_node_name  =  _gen_unique_name ( p_state ,  " Node " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 17:55:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( gltf_node - > mesh  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_node_name  =  " Mesh " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( gltf_node - > camera  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_node_name  =  " Camera " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_node_name  =  " Node " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 21:17:28 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										gltf_node - > set_name ( _gen_unique_name ( p_state ,  gltf_node_name ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								BoneAttachment3D  * GLTFDocument : : _generate_bone_attachment ( Ref < GLTFState >  p_state ,  Skeleton3D  * p_skeleton ,  const  GLTFNodeIndex  p_node_index ,  const  GLTFNodeIndex  p_bone_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  bone_node  =  p_state - > nodes [ p_bone_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									BoneAttachment3D  * bone_attachment  =  memnew ( BoneAttachment3D ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Creating bone attachment for:  "  +  gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! bone_node - > joint ,  nullptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bone_attachment - > set_bone_name ( bone_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  bone_attachment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFMeshIndex  GLTFDocument : : _convert_mesh_to_gltf ( Ref < GLTFState >  p_state ,  MeshInstance3D  * p_mesh_instance )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( p_mesh_instance ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-03 21:41:00 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( p_mesh_instance - > get_mesh ( ) . is_null ( ) ,  - 1 ,  " glTF: Tried to export a MeshInstance3D node named  "  +  p_mesh_instance - > get_name ( )  +  " , but it has no mesh. This node will be exported without a mesh. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Mesh >  mesh_resource  =  p_mesh_instance - > get_mesh ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( mesh_resource - > get_surface_count ( )  = =  0 ,  - 1 ,  " glTF: Tried to export a MeshInstance3D node named  "  +  p_mesh_instance - > get_name ( )  +  " , but its mesh has no surfaces. This node will be exported without a mesh. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-29 07:09:42 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									TypedArray < Material >  instance_materials ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  surface_i  =  0 ;  surface_i  <  mesh_resource - > get_surface_count ( ) ;  surface_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Material >  mat  =  p_mesh_instance - > get_active_material ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										instance_materials . append ( mat ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-03 21:41:00 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < ImporterMesh >  current_mesh  =  _mesh_to_importer_mesh ( mesh_resource ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Vector < float >  blend_weights ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-03 21:41:00 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int32_t  blend_count  =  mesh_resource - > get_blend_shape_count ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-20 21:39:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									blend_weights . resize ( blend_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  blend_i  =  0 ;  blend_i  <  blend_count ;  blend_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										blend_weights . write [ blend_i ]  =  0.0f ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-20 21:39:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Ref < GLTFMesh >  gltf_mesh ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-11-01 17:31:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh - > set_instance_materials ( instance_materials ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh - > set_mesh ( current_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									gltf_mesh - > set_blend_weights ( blend_weights ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFMeshIndex  mesh_i  =  p_state - > meshes . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > meshes . push_back ( gltf_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  mesh_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								ImporterMeshInstance3D  * GLTFDocument : : _generate_mesh_instance ( Ref < GLTFState >  p_state ,  const  GLTFNodeIndex  p_node_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( gltf_node - > mesh ,  p_state - > meshes . size ( ) ,  nullptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ImporterMeshInstance3D  * mi  =  memnew ( ImporterMeshInstance3D ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Creating mesh for:  "  +  gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > scene_mesh_instances . insert ( p_node_index ,  mi ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFMesh >  mesh  =  p_state - > meshes . write [ gltf_node - > mesh ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( mesh . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  mi ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < ImporterMesh >  import_mesh  =  mesh - > get_mesh ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( import_mesh . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  mi ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mi - > set_mesh ( import_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									import_mesh - > merge_meta_from ( * mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  mi ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Light3D  * GLTFDocument : : _generate_light ( Ref < GLTFState >  p_state ,  const  GLTFNodeIndex  p_node_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( gltf_node - > light ,  p_state - > lights . size ( ) ,  nullptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Creating light for:  "  +  gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFLight >  l  =  p_state - > lights [ gltf_node - > light ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-26 00:51:53 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  l - > to_node ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Camera3D  * GLTFDocument : : _generate_camera ( Ref < GLTFState >  p_state ,  const  GLTFNodeIndex  p_node_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( gltf_node - > camera ,  p_state - > cameras . size ( ) ,  nullptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Creating camera for:  "  +  gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFCamera >  c  =  p_state - > cameras [ gltf_node - > camera ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-13 16:27:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  c - > to_node ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFCameraIndex  GLTFDocument : : _convert_camera ( Ref < GLTFState >  p_state ,  Camera3D  * p_camera )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Converting camera:  "  +  p_camera - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-08-13 16:27:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFCamera >  c  =  GLTFCamera : : from_node ( p_camera ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFCameraIndex  camera_index  =  p_state - > cameras . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > cameras . push_back ( c ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  camera_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFLightIndex  GLTFDocument : : _convert_light ( Ref < GLTFState >  p_state ,  Light3D  * p_light )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Converting light:  "  +  p_light - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-26 00:51:53 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFLight >  l  =  GLTFLight : : from_node ( p_light ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFLightIndex  light_index  =  p_state - > lights . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > lights . push_back ( l ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  light_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_spatial ( Ref < GLTFState >  p_state ,  Node3D  * p_spatial ,  Ref < GLTFNode >  p_node )  {  
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_node - > transform  =  p_spatial - > get_transform ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Node3D  * GLTFDocument : : _generate_spatial ( Ref < GLTFState >  p_state ,  const  GLTFNodeIndex  p_node_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Node3D  * spatial  =  memnew ( Node3D ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									print_verbose ( " glTF: Converting spatial:  "  +  gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  spatial ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:16:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_scene_node ( Ref < GLTFState >  p_state ,  Node  * p_current ,  const  GLTFNodeIndex  p_gltf_parent ,  const  GLTFNodeIndex  p_gltf_root )  {  
						 
					
						
							
								
									
										
										
										
											2024-02-03 21:41:00 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# ifdef TOOLS_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( Engine : : get_singleton ( ) - > is_editor_hint ( )  & &  p_gltf_root  ! =  - 1  & &  p_current - > get_owner ( )  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										WARN_VERBOSE ( " glTF export warning: Node ' "  +  p_current - > get_name ( )  +  " ' has no owner. This is likely a temporary node generated by a @tool script. This would not be saved when saving the Godot scene, therefore it will not be exported to glTF. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# endif  // TOOLS_ENABLED
  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_node . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_current - > has_method ( " is_visible " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bool  visible  =  p_current - > call ( " is_visible " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! visible  & &  _visibility_mode  = =  VISIBILITY_MODE_EXCLUDE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_node - > visible  =  visible ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_node - > set_original_name ( p_current - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_node - > set_name ( _gen_unique_name ( p_state ,  p_current - > get_name ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-02 01:28:07 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_node - > merge_meta_from ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( Object : : cast_to < Node3D > ( p_current ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Node3D  * spatial  =  Object : : cast_to < Node3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_spatial ( p_state ,  spatial ,  gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( Object : : cast_to < MeshInstance3D > ( p_current ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MeshInstance3D  * mi  =  Object : : cast_to < MeshInstance3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_mesh_instance_to_gltf ( mi ,  p_state ,  gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < BoneAttachment3D > ( p_current ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										BoneAttachment3D  * bone  =  Object : : cast_to < BoneAttachment3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_bone_attachment_to_gltf ( bone ,  p_state ,  p_gltf_parent ,  p_gltf_root ,  gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < Skeleton3D > ( p_current ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Skeleton3D  * skel  =  Object : : cast_to < Skeleton3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_skeleton_to_gltf ( skel ,  p_state ,  p_gltf_parent ,  p_gltf_root ,  gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										// We ignore the Godot Engine node that is the skeleton.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < MultiMeshInstance3D > ( p_current ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MultiMeshInstance3D  * multi  =  Object : : cast_to < MultiMeshInstance3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_multi_mesh_instance_to_gltf ( multi ,  p_gltf_parent ,  p_gltf_root ,  gltf_node ,  p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-22 16:52:32 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# ifdef MODULE_CSG_ENABLED 
  
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < CSGShape3D > ( p_current ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										CSGShape3D  * shape  =  Object : : cast_to < CSGShape3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( shape - > get_parent ( )  & &  shape - > is_root_shape ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_convert_csg_shape_to_gltf ( shape ,  p_gltf_parent ,  gltf_node ,  p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-22 16:52:32 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif  // MODULE_CSG_ENABLED
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# ifdef MODULE_GRIDMAP_ENABLED 
  
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < GridMap > ( p_current ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										GridMap  * gridmap  =  Object : : cast_to < GridMap > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_grid_map_to_gltf ( gridmap ,  p_gltf_parent ,  p_gltf_root ,  gltf_node ,  p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-22 16:52:32 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif  // MODULE_GRIDMAP_ENABLED
  
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < Camera3D > ( p_current ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Camera3D  * camera  =  Object : : cast_to < Camera3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_camera_to_gltf ( camera ,  p_state ,  gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < Light3D > ( p_current ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Light3D  * light  =  Object : : cast_to < Light3D > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_light_to_gltf ( light ,  p_state ,  gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  if  ( Object : : cast_to < AnimationPlayer > ( p_current ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										AnimationPlayer  * animation_player  =  Object : : cast_to < AnimationPlayer > ( p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > animation_players . push_back ( animation_player ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-05-25 12:30:42 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( animation_player - > get_child_count ( )  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_node - > set_parent ( - 2 ) ;  // Don't export AnimationPlayer nodes as glTF nodes (unless they have children).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ext - > convert_scene_node ( p_state ,  gltf_node ,  p_current ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-02 01:28:07 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFNodeIndex  current_node_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( gltf_node - > get_parent ( )  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										current_node_i  =  p_state - > append_gltf_node ( gltf_node ,  p_current ,  p_gltf_parent ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( gltf_node - > get_parent ( )  <  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										current_node_i  =  p_state - > nodes . size ( )  -  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										while  ( gltf_node  ! =  p_state - > nodes [ current_node_i ] )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											current_node_i - - ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-02 01:28:07 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  GLTFNodeIndex  gltf_root  =  ( p_gltf_root  = =  - 1 )  ?  current_node_i  :  p_gltf_root ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( int  node_i  =  0 ;  node_i  <  p_current - > get_child_count ( ) ;  node_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_scene_node ( p_state ,  p_current - > get_child ( node_i ) ,  current_node_i ,  gltf_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_csg_shape_to_gltf ( CSGShape3D  * p_current ,  GLTFNodeIndex  p_gltf_parent ,  Ref < GLTFNode >  p_gltf_node ,  Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2024-12-04 13:28:07 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# ifndef MODULE_CSG_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_MSG ( " csg module is disabled. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# else 
  
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									CSGShape3D  * csg  =  p_current ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-15 23:47:24 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									csg - > update_shape ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Array  meshes  =  csg - > get_meshes ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( meshes . size ( )  ! =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ImporterMesh >  mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									{ 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-29 07:09:42 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < ArrayMesh >  csg_mesh  =  csg - > get_meshes ( ) [ 1 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int32_t  surface_i  =  0 ;  surface_i  <  csg_mesh - > get_surface_count ( ) ;  surface_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Array  array  =  csg_mesh - > surface_get_arrays ( surface_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-29 07:09:42 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < Material >  mat ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < Material >  mat_override  =  csg - > get_material_override ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mat_override . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mat  =  mat_override ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < Material >  mat_surface_override  =  csg_mesh - > surface_get_material ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mat_surface_override . is_valid ( )  & &  mat . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mat  =  mat_surface_override ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											String  mat_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mat . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mat_name  =  mat - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Assign default material when no material is assigned.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-09 15:21:41 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												mat . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-29 07:09:42 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mesh - > add_surface ( csg_mesh - > surface_get_primitive_type ( surface_i ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													array ,  csg_mesh - > surface_get_blend_shape_arrays ( surface_i ) ,  csg_mesh - > surface_get_lods ( surface_i ) ,  mat , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													mat_name ,  csg_mesh - > surface_get_format ( surface_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Ref < GLTFMesh >  gltf_mesh ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-11 00:01:25 +05:30 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh - > set_mesh ( mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh - > set_original_name ( csg - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFMeshIndex  mesh_i  =  p_state - > meshes . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > meshes . push_back ( gltf_mesh ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_gltf_node - > mesh  =  mesh_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-29 07:09:42 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_gltf_node - > transform  =  csg - > get_transform ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_gltf_node - > set_original_name ( csg - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_gltf_node - > set_name ( _gen_unique_name ( p_state ,  csg - > get_name ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-22 16:52:32 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif  // MODULE_CSG_ENABLED
  
						 
					
						
							
								
									
										
										
										
											2024-12-04 13:28:07 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_camera_to_gltf ( Camera3D  * camera ,  Ref < GLTFState >  p_state ,  Ref < GLTFNode >  p_gltf_node )  {  
						 
					
						
							
								
									
										
										
										
											2023-09-09 17:40:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_NULL ( camera ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFCameraIndex  camera_index  =  _convert_camera ( p_state ,  camera ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( camera_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_gltf_node - > camera  =  camera_index ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_light_to_gltf ( Light3D  * light ,  Ref < GLTFState >  p_state ,  Ref < GLTFNode >  p_gltf_node )  {  
						 
					
						
							
								
									
										
										
										
											2023-09-09 17:40:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_NULL ( light ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFLightIndex  light_index  =  _convert_light ( p_state ,  light ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( light_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_gltf_node - > light  =  light_index ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_grid_map_to_gltf ( GridMap  * p_grid_map ,  GLTFNodeIndex  p_parent_node_index ,  GLTFNodeIndex  p_root_node_index ,  Ref < GLTFNode >  p_gltf_node ,  Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2024-12-04 13:28:07 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# ifndef MODULE_GRIDMAP_ENABLED 
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_MSG ( " gridmap module is disabled. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								# else 
  
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Array  cells  =  p_grid_map - > get_used_cells ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  k  =  0 ;  k  <  cells . size ( ) ;  k + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFNode  * new_gltf_node  =  memnew ( GLTFNode ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_gltf_node - > children . push_back ( p_state - > nodes . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > nodes . push_back ( new_gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Vector3  cell_location  =  cells [ k ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										int32_t  cell  =  p_grid_map - > get_cell_item ( 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												Vector3 ( cell_location . x ,  cell_location . y ,  cell_location . z ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Transform3D  cell_xform ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-26 23:44:36 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										cell_xform . basis  =  p_grid_map - > get_basis_with_orthogonal_index ( 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_grid_map - > get_cell_item_orientation ( 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														Vector3 ( cell_location . x ,  cell_location . y ,  cell_location . z ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										cell_xform . basis . scale ( Vector3 ( p_grid_map - > get_cell_scale ( ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_grid_map - > get_cell_scale ( ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_grid_map - > get_cell_scale ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-08-20 18:39:05 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										cell_xform . set_origin ( p_grid_map - > map_to_local ( 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												Vector3 ( cell_location . x ,  cell_location . y ,  cell_location . z ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFMesh >  gltf_mesh ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										gltf_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-02-20 21:39:11 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										gltf_mesh - > set_mesh ( _mesh_to_importer_mesh ( p_grid_map - > get_mesh_library ( ) - > get_item_mesh ( cell ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										gltf_mesh - > set_original_name ( p_grid_map - > get_mesh_library ( ) - > get_item_name ( cell ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > mesh  =  p_state - > meshes . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > meshes . push_back ( gltf_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > transform  =  cell_xform  *  p_grid_map - > get_transform ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > set_original_name ( p_grid_map - > get_mesh_library ( ) - > get_item_name ( cell ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > set_name ( _gen_unique_name ( p_state ,  p_grid_map - > get_mesh_library ( ) - > get_item_name ( cell ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-22 16:52:32 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								# endif  // MODULE_GRIDMAP_ENABLED
  
						 
					
						
							
								
									
										
										
										
											2024-12-04 13:28:07 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_multi_mesh_instance_to_gltf (  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										MultiMeshInstance3D  * p_multi_mesh_instance , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFNodeIndex  p_parent_node_index , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFNodeIndex  p_root_node_index , 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFNode >  p_gltf_node ,  Ref < GLTFState >  p_state )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-09 17:40:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_NULL ( p_multi_mesh_instance ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < MultiMesh >  multi_mesh  =  p_multi_mesh_instance - > get_multimesh ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( multi_mesh . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFMesh >  gltf_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Mesh >  mesh  =  multi_mesh - > get_mesh ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( mesh . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh - > set_original_name ( multi_mesh - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_mesh - > set_name ( multi_mesh - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ImporterMesh >  importer_mesh ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									importer_mesh . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < ArrayMesh >  array_mesh  =  multi_mesh - > get_mesh ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( array_mesh . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										importer_mesh - > set_blend_shape_mode ( array_mesh - > get_blend_shape_mode ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  blend_i  =  0 ;  blend_i  <  array_mesh - > get_blend_shape_count ( ) ;  blend_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											importer_mesh - > add_blend_shape ( array_mesh - > get_blend_shape_name ( blend_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  surface_i  =  0 ;  surface_i  <  mesh - > get_surface_count ( ) ;  surface_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Material >  mat  =  mesh - > surface_get_material ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  material_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( mat . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											material_name  =  mat - > get_name ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Array  blend_arrays ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( array_mesh . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											blend_arrays  =  array_mesh - > surface_get_blend_shape_arrays ( surface_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										importer_mesh - > add_surface ( mesh - > surface_get_primitive_type ( surface_i ) ,  mesh - > surface_get_arrays ( surface_i ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												blend_arrays ,  mesh - > surface_get_lods ( surface_i ) ,  mat ,  material_name ,  mesh - > surface_get_format ( surface_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_mesh - > set_mesh ( importer_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFMeshIndex  mesh_index  =  p_state - > meshes . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > meshes . push_back ( gltf_mesh ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int32_t  instance_i  =  0 ;  instance_i  <  multi_mesh - > get_instance_count ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											instance_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Transform3D  transform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( multi_mesh - > get_transform_format ( )  = =  MultiMesh : : TRANSFORM_2D )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Transform2D  xform_2d  =  multi_mesh - > get_instance_transform_2d ( instance_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											transform . origin  = 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector3 ( xform_2d . get_origin ( ) . x ,  0 ,  xform_2d . get_origin ( ) . y ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											real_t  rotation  =  xform_2d . get_rotation ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Quaternion  quaternion ( Vector3 ( 0 ,  1 ,  0 ) ,  rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Size2  scale  =  xform_2d . get_scale ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											transform . basis . set_quaternion_scale ( quaternion , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector3 ( scale . x ,  0 ,  scale . y ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											transform  =  p_multi_mesh_instance - > get_transform ( )  *  transform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( multi_mesh - > get_transform_format ( )  = =  MultiMesh : : TRANSFORM_3D )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											transform  =  p_multi_mesh_instance - > get_transform ( )  * 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-28 15:19:35 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													multi_mesh - > get_instance_transform ( instance_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  new_gltf_node ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										new_gltf_node . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										new_gltf_node - > mesh  =  mesh_index ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > transform  =  transform ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > set_original_name ( p_multi_mesh_instance - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										new_gltf_node - > set_name ( _gen_unique_name ( p_state ,  p_multi_mesh_instance - > get_name ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_gltf_node - > children . push_back ( p_state - > nodes . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > nodes . push_back ( new_gltf_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_skeleton_to_gltf ( Skeleton3D  * p_skeleton3d ,  Ref < GLTFState >  p_state ,  GLTFNodeIndex  p_parent_node_index ,  GLTFNodeIndex  p_root_node_index ,  Ref < GLTFNode >  p_gltf_node )  {  
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Skeleton3D  * skeleton  =  p_skeleton3d ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFSkeleton >  gltf_skeleton ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_skeleton . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// GLTFSkeleton is only used to hold internal p_state data. It will not be written to the document.
 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									//
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									gltf_skeleton - > godot_skeleton  =  skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFSkeletonIndex  skeleton_i  =  p_state - > skeletons . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > skeleton3d_to_gltf_skeleton [ skeleton - > get_instance_id ( ) ]  =  skeleton_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > skeletons . push_back ( gltf_skeleton ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BoneId  bone_count  =  skeleton - > get_bone_count ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( BoneId  bone_i  =  0 ;  bone_i  <  bone_count ;  bone_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  joint_node ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										joint_node . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Note that we cannot use _gen_unique_bone_name here, because glTF spec requires all node
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// names to be unique regardless of whether or not they are used as joints.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										joint_node - > set_original_name ( skeleton - > get_bone_name ( bone_i ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										joint_node - > set_name ( _gen_unique_name ( p_state ,  skeleton - > get_bone_name ( bone_i ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										joint_node - > transform  =  skeleton - > get_bone_pose ( bone_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										joint_node - > joint  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-30 22:40:11 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_skeleton3d - > has_bone_meta ( bone_i ,  " extras " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											joint_node - > set_meta ( " extras " ,  p_skeleton3d - > get_bone_meta ( bone_i ,  " extras " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										GLTFNodeIndex  current_node_i  =  p_state - > nodes . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > scene_nodes . insert ( current_node_i ,  skeleton ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > nodes . push_back ( joint_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_skeleton - > joints . push_back ( current_node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( skeleton - > get_bone_parent ( bone_i )  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_skeleton - > roots . push_back ( current_node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										gltf_skeleton - > godot_bone_node . insert ( bone_i ,  current_node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( BoneId  bone_i  =  0 ;  bone_i  <  bone_count ;  bone_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFNodeIndex  current_node_i  =  gltf_skeleton - > godot_bone_node [ bone_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										BoneId  parent_bone_id  =  skeleton - > get_bone_parent ( bone_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( parent_bone_id  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_parent_node_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_state - > nodes . write [ current_node_i ] - > parent  =  p_parent_node_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > nodes . write [ p_parent_node_index ] - > children . push_back ( current_node_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFNodeIndex  parent_node_i  =  gltf_skeleton - > godot_bone_node [ parent_bone_id ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > nodes . write [ current_node_i ] - > parent  =  parent_node_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_state - > nodes . write [ parent_node_i ] - > children . push_back ( current_node_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Remove placeholder skeleton3d node by not creating the gltf node
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Skins are per mesh
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  node_i  =  0 ;  node_i  <  skeleton - > get_child_count ( ) ;  node_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_scene_node ( p_state ,  skeleton - > get_child ( node_i ) ,  p_parent_node_index ,  p_root_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_bone_attachment_to_gltf ( BoneAttachment3D  * p_bone_attachment ,  Ref < GLTFState >  p_state ,  GLTFNodeIndex  p_parent_node_index ,  GLTFNodeIndex  p_root_node_index ,  Ref < GLTFNode >  p_gltf_node )  {  
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Skeleton3D  * skeleton ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Note that relative transforms to external skeletons and pose overrides are not supported.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_bone_attachment - > get_use_external_skeleton ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										skeleton  =  Object : : cast_to < Skeleton3D > ( p_bone_attachment - > get_node_or_null ( p_bone_attachment - > get_external_skeleton ( ) ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										skeleton  =  Object : : cast_to < Skeleton3D > ( p_bone_attachment - > get_parent ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									GLTFSkeletonIndex  skel_gltf_i  =  - 1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( skeleton  ! =  nullptr  & &  p_state - > skeleton3d_to_gltf_skeleton . has ( skeleton - > get_instance_id ( ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										skel_gltf_i  =  p_state - > skeleton3d_to_gltf_skeleton [ skeleton - > get_instance_id ( ) ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  bone_idx  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( skeleton  ! =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bone_idx  =  p_bone_attachment - > get_bone_idx ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( bone_idx  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bone_idx  =  skeleton - > find_bone ( p_bone_attachment - > get_bone_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									GLTFNodeIndex  par_node_index  =  p_parent_node_index ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( skeleton  ! =  nullptr  & &  bone_idx  ! =  - 1  & &  skel_gltf_i  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < GLTFSkeleton >  gltf_skeleton  =  p_state - > skeletons . write [ skel_gltf_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										gltf_skeleton - > bone_attachments . push_back ( p_bone_attachment ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										par_node_index  =  gltf_skeleton - > joints [ bone_idx ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  node_i  =  0 ;  node_i  <  p_bone_attachment - > get_child_count ( ) ;  node_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_convert_scene_node ( p_state ,  p_bone_attachment - > get_child ( node_i ) ,  par_node_index ,  p_root_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_mesh_instance_to_gltf ( MeshInstance3D  * p_scene_parent ,  Ref < GLTFState >  p_state ,  Ref < GLTFNode >  p_gltf_node )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									GLTFMeshIndex  gltf_mesh_index  =  _convert_mesh_to_gltf ( p_state ,  p_scene_parent ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( gltf_mesh_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_gltf_node - > mesh  =  gltf_mesh_index ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _generate_scene_node ( Ref < GLTFState >  p_state ,  const  GLTFNodeIndex  p_node_index ,  Node  * p_scene_parent ,  Node  * p_scene_root )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( gltf_node - > skeleton  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_generate_skeleton_bone_node ( p_state ,  p_node_index ,  p_scene_parent ,  p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Node3D  * current_node  =  nullptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Is our parent a skeleton
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Skeleton3D  * active_skeleton  =  Object : : cast_to < Skeleton3D > ( p_scene_parent ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  bool  non_bone_parented_to_skeleton  =  active_skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// skinned meshes must not be placed in a bone attachment.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( non_bone_parented_to_skeleton  & &  gltf_node - > skin  <  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Bone Attachment - Parent Case
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										BoneAttachment3D  * bone_attachment  =  _generate_bone_attachment ( p_state ,  active_skeleton ,  p_node_index ,  gltf_node - > parent ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_scene_parent - > add_child ( bone_attachment ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-28 05:32:32 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Find the correct bone_idx so we can properly serialize it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										bone_attachment - > set_bone_idx ( active_skeleton - > find_bone ( gltf_node - > get_name ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										bone_attachment - > set_owner ( p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// There is no gltf_node that represent this, so just directly create a unique name
 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 09:14:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										bone_attachment - > set_name ( gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// We change the scene_parent to our bone attachment now. We do not set current_node because we want to make the node
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// and attach it to the bone_attachment
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_scene_parent  =  bone_attachment ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Check if any GLTFDocumentExtension classes want to generate a node for us.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										current_node  =  ext - > generate_scene_node ( p_state ,  gltf_node ,  p_scene_parent ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( current_node )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-06 15:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// If none of our GLTFDocumentExtension classes generated us a node, we generate one.
 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-06 15:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! current_node )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_node - > skin  > =  0  & &  gltf_node - > mesh  > =  0  & &  ! gltf_node - > children . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// glTF specifies that skinned meshes should ignore their node transforms,
 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-05 12:19:22 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// only being controlled by the skeleton, so Godot will reparent a skinned
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// mesh to its skeleton. However, we still need to ensure any child nodes
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// keep their place in the tree, so if there are any child nodes, the skinned
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// mesh must not be the base node, so generate an empty spatial base.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node  =  _generate_spatial ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Node3D  * mesh_inst  =  _generate_mesh_instance ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mesh_inst - > set_name ( gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											current_node - > add_child ( mesh_inst ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( gltf_node - > mesh  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node  =  _generate_mesh_instance ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  if  ( gltf_node - > camera  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node  =  _generate_camera ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  if  ( gltf_node - > light  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node  =  _generate_light ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node  =  _generate_spatial ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 21:59:39 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  gltf_node_name  =  gltf_node - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! gltf_node_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										current_node - > set_name ( gltf_node_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									current_node - > set_visible ( gltf_node - > visible ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 22:36:57 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Note: p_scene_parent and p_scene_root must either both be null or both be valid.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_scene_root  = =  nullptr )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// If the root node argument is null, this is the root node.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_scene_root  =  current_node ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-04 02:23:01 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// If multiple nodes were generated under the root node, ensure they have the owner set.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( unlikely ( current_node - > get_child_count ( )  >  0 ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Array  args ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											args . append ( p_scene_root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  current_node - > get_child_count ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Node  * child  =  current_node - > get_child ( i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												child - > propagate_call ( StringName ( " set_owner " ) ,  args ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 22:36:57 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Add the node we generated and set the owner to the scene root.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_scene_parent - > add_child ( current_node ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Array  args ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										args . append ( p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										current_node - > propagate_call ( StringName ( " set_owner " ) ,  args ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										current_node - > set_transform ( gltf_node - > transform ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-01-11 20:47:31 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									current_node - > merge_meta_from ( * gltf_node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > scene_nodes . insert ( p_node_index ,  current_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  gltf_node - > children . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_generate_scene_node ( p_state ,  gltf_node - > children [ i ] ,  current_node ,  p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _generate_skeleton_bone_node ( Ref < GLTFState >  p_state ,  const  GLTFNodeIndex  p_node_index ,  Node  * p_scene_parent ,  Node  * p_scene_root )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_node_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Node3D  * current_node  =  nullptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Skeleton3D  * skeleton  =  p_state - > skeletons [ gltf_node - > skeleton ] - > godot_skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// In this case, this node is already a bone in skeleton.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  bool  is_skinned_mesh  =  ( gltf_node - > skin  > =  0  & &  gltf_node - > mesh  > =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  bool  requires_extra_node  =  ( gltf_node - > mesh  > =  0  | |  gltf_node - > camera  > =  0  | |  gltf_node - > light  > =  0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Skeleton3D  * active_skeleton  =  Object : : cast_to < Skeleton3D > ( p_scene_parent ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( active_skeleton  ! =  skeleton )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( active_skeleton )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// Should no longer be possible.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_PRINT ( vformat ( " glTF: Generating scene detected direct parented Skeletons at node %d " ,  p_node_index ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											BoneAttachment3D  * bone_attachment  =  _generate_bone_attachment ( p_state ,  active_skeleton ,  p_node_index ,  gltf_node - > parent ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_scene_parent - > add_child ( bone_attachment ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bone_attachment - > set_owner ( p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// There is no gltf_node that represent this, so just directly create a unique name
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											bone_attachment - > set_name ( _gen_unique_name ( p_state ,  " BoneAttachment3D " ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// We change the scene_parent to our bone attachment now. We do not set current_node because we want to make the node
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// and attach it to the bone_attachment
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_scene_parent  =  bone_attachment ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( skeleton - > get_parent ( )  = =  nullptr )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-04 02:47:44 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_scene_root )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_scene_parent - > add_child ( skeleton ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skeleton - > set_owner ( p_scene_root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_scene_parent  =  skeleton ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_scene_root  =  skeleton ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									active_skeleton  =  skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									current_node  =  active_skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-17 04:11:16 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( active_skeleton )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_scene_parent  =  active_skeleton ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( requires_extra_node )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										current_node  =  nullptr ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// skinned meshes must not be placed in a bone attachment.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! is_skinned_mesh )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Bone Attachment - Same Node Case
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											BoneAttachment3D  * bone_attachment  =  _generate_bone_attachment ( p_state ,  active_skeleton ,  p_node_index ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_scene_parent - > add_child ( bone_attachment ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-28 05:32:32 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Find the correct bone_idx so we can properly serialize it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bone_attachment - > set_bone_idx ( active_skeleton - > find_bone ( gltf_node - > get_name ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											bone_attachment - > set_owner ( p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// There is no gltf_node that represent this, so just directly create a unique name
 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 09:14:07 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											bone_attachment - > set_name ( gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// We change the scene_parent to our bone attachment now. We do not set current_node because we want to make the node
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// and attach it to the bone_attachment
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_scene_parent  =  bone_attachment ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Check if any GLTFDocumentExtension classes want to generate a node for us.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node  =  ext - > generate_scene_node ( p_state ,  gltf_node ,  p_scene_parent ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( current_node )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// If none of our GLTFDocumentExtension classes generated us a node, we generate one.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! current_node )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( gltf_node - > mesh  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												current_node  =  _generate_mesh_instance ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( gltf_node - > camera  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												current_node  =  _generate_camera ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( gltf_node - > light  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												current_node  =  _generate_light ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												current_node  =  _generate_spatial ( p_state ,  p_node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Add the node we generated and set the owner to the scene root.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_scene_parent - > add_child ( current_node ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( current_node  ! =  p_scene_root )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Array  args ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											args . append ( p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 17:48:06 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											current_node - > propagate_call ( StringName ( " set_owner " ) ,  args ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Do not set transform here. Transform is already applied to our bone.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										current_node - > set_name ( gltf_node - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > scene_nodes . insert ( p_node_index ,  current_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  gltf_node - > children . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 22:06:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										_generate_scene_node ( p_state ,  gltf_node - > children [ i ] ,  active_skeleton ,  p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								template  < typename  T >  
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:39:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								struct  SceneFormatImporterGLTFInterpolate  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									T  lerp ( const  T  & a ,  const  T  & b ,  float  c )  const  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  a  +  ( b  -  a )  *  c ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									T  catmull_rom ( const  T  & p0 ,  const  T  & p1 ,  const  T  & p2 ,  const  T  & p3 ,  float  t )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  float  t2  =  t  *  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  float  t3  =  t2  *  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  0.5f  *  ( ( 2.0f  *  p1 )  +  ( - p0  +  p2 )  *  t  +  ( 2.0f  *  p0  -  5.0f  *  p1  +  4.0f  *  p2  -  p3 )  *  t2  +  ( - p0  +  3.0f  *  p1  -  3.0f  *  p2  +  p3 )  *  t3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									T  hermite ( T  start ,  T  tan_start ,  T  end ,  T  tan_end ,  float  t )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										/* Formula from the glTF 2.0 specification. */ 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										const  real_t  t2  =  t  *  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  real_t  t3  =  t2  *  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  real_t  h00  =  2.0  *  t3  -  3.0  *  t2  +  1.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  real_t  h10  =  t3  -  2.0  *  t2  +  t ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  real_t  h01  =  - 2.0  *  t3  +  3.0  *  t2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  real_t  h11  =  t3  -  t2 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  start  *  h00  +  tan_start  *  h10  +  end  *  h01  +  tan_end  *  h11 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								// thank you for existing, partial specialization
  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								template  < >  
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:39:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								struct  SceneFormatImporterGLTFInterpolate < Quaternion >  {  
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Quaternion  lerp ( const  Quaternion  & a ,  const  Quaternion  & b ,  const  float  c )  const  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-17 17:30:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( ! a . is_normalized ( ) ,  Quaternion ( ) ,  vformat ( " The quaternion  \" a \"  %s must be normalized. " ,  a ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( ! b . is_normalized ( ) ,  Quaternion ( ) ,  vformat ( " The quaternion  \" b \"  %s must be normalized. " ,  b ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  a . slerp ( b ,  c ) . normalized ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Quaternion  catmull_rom ( const  Quaternion  & p0 ,  const  Quaternion  & p1 ,  const  Quaternion  & p2 ,  const  Quaternion  & p3 ,  const  float  c )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-17 17:30:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( ! p1 . is_normalized ( ) ,  Quaternion ( ) ,  vformat ( " The quaternion  \" p1 \"  (%s) must be normalized. " ,  p1 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( ! p2 . is_normalized ( ) ,  Quaternion ( ) ,  vformat ( " The quaternion  \" p2 \"  (%s) must be normalized. " ,  p2 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  p1 . slerp ( p2 ,  c ) . normalized ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Quaternion  hermite ( const  Quaternion  start ,  const  Quaternion  tan_start ,  const  Quaternion  end ,  const  Quaternion  tan_end ,  const  float  t )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-01-17 17:30:04 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( ! start . is_normalized ( ) ,  Quaternion ( ) ,  vformat ( " The start quaternion %s must be normalized. " ,  start ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V_MSG ( ! end . is_normalized ( ) ,  Quaternion ( ) ,  vformat ( " The end quaternion %s must be normalized. " ,  end ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  start . slerp ( end ,  t ) . normalized ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								} ;  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								template  < typename  T >  
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								T  GLTFDocument : : _interpolate_track ( const  Vector < double >  & p_times ,  const  Vector < T >  & p_values ,  const  float  p_time ,  const  GLTFAnimation : : Interpolation  p_interp )  {  
						 
					
						
							
								
									
										
										
										
											2024-01-19 13:21:39 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_values . is_empty ( ) ,  T ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_times . size ( )  ! =  ( p_values . size ( )  /  ( p_interp  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE  ?  3  :  1 ) ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-07-29 22:56:19 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_PRINT_ONCE ( " The interpolated values are not corresponding to its times. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  p_values [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									//could use binary search, worth it?
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  idx  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_times [ i ]  >  p_time )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										idx + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-03-28 15:39:24 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									SceneFormatImporterGLTFInterpolate < T >  interp ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									switch  ( p_interp )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAnimation : : INTERP_LINEAR :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( idx  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( idx  > =  p_times . size ( )  -  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ p_times . size ( )  -  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  float  c  =  ( p_time  -  p_times [ idx ] )  /  ( p_times [ idx  +  1 ]  -  p_times [ idx ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  interp . lerp ( p_values [ idx ] ,  p_values [ idx  +  1 ] ,  c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAnimation : : INTERP_STEP :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( idx  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( idx  > =  p_times . size ( )  -  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ p_times . size ( )  -  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  p_values [ idx ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAnimation : : INTERP_CATMULLROMSPLINE :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( idx  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ 1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( idx  > =  p_times . size ( )  -  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ 1  +  p_times . size ( )  -  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  float  c  =  ( p_time  -  p_times [ idx ] )  /  ( p_times [ idx  +  1 ]  -  p_times [ idx ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  interp . catmull_rom ( p_values [ idx  -  1 ] ,  p_values [ idx ] ,  p_values [ idx  +  1 ] ,  p_values [ idx  +  3 ] ,  c ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										case  GLTFAnimation : : INTERP_CUBIC_SPLINE :  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( idx  = =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ 1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( idx  > =  p_times . size ( )  -  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  p_values [ ( p_times . size ( )  -  1 )  *  3  +  1 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  float  td  =  ( p_times [ idx  +  1 ]  -  p_times [ idx ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  float  c  =  ( p_time  -  p_times [ idx ] )  /  td ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-11-18 17:40:56 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  T  & from  =  p_values [ idx  *  3  +  1 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  T  tan_from  =  td  *  p_values [ idx  *  3  +  2 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-11-18 17:40:56 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  T  & to  =  p_values [ idx  *  3  +  4 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  T  tan_to  =  td  *  p_values [ idx  *  3  +  3 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-25 17:01:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											return  interp . hermite ( from ,  tan_from ,  to ,  tan_to ,  c ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_V ( p_values [ 0 ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:19:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								NodePath  GLTFDocument : : _find_material_node_path ( Ref < GLTFState >  p_state ,  Ref < Material >  p_material )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  mesh_index  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFMesh >  gltf_mesh  :  p_state - > meshes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										TypedArray < Material >  materials  =  gltf_mesh - > get_instance_materials ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  mat_index  =  0 ;  mat_index  <  materials . size ( ) ;  mat_index + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( materials [ mat_index ]  = =  p_material )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( Ref < GLTFNode >  gltf_node  :  p_state - > nodes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( gltf_node - > mesh  = =  mesh_index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														NodePath  node_path  =  gltf_node - > get_scene_node_path ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// Example: MyNode:mesh:surface_0/material:albedo_color, so we want the mesh:surface_0/material part.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector < StringName >  subpath ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														subpath . append ( " mesh " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														subpath . append ( " surface_ "  +  itos ( mat_index )  +  " /material " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														return  NodePath ( node_path . get_names ( ) ,  subpath ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										mesh_index + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  NodePath ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Ref < GLTFObjectModelProperty >  GLTFDocument : : import_object_model_property ( Ref < GLTFState >  p_state ,  const  String  & p_json_pointer )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_state - > object_model_properties . has ( p_json_pointer ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  p_state - > object_model_properties [ p_json_pointer ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFObjectModelProperty >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Split the JSON pointer into its components.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  PackedStringArray  split  =  p_json_pointer . split ( " / " ,  false ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( split . size ( )  <  3 ,  ret ,  " glTF: Cannot use JSON pointer ' "  +  p_json_pointer  +  " ' because it does not contain enough elements. The only animatable properties are at least 3 levels deep (ex: '/nodes/0/translation' or '/materials/0/emissiveFactor'). " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret - > set_json_pointers ( {  split  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Partial paths are passed to GLTFDocumentExtension classes if GLTFDocument cannot handle a given JSON pointer.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									TypedArray < NodePath >  partial_paths ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Note: This might not be an integer, but in that case, we don't use this value anyway.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int  top_level_index  =  split [ 1 ] . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// For JSON pointers present in the core glTF Object Model, hard-code them in GLTFDocument.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// https://github.com/KhronosGroup/glTF/blob/main/specification/2.0/ObjectModel.adoc
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( split [ 0 ]  = =  " nodes " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_INDEX_V_MSG ( top_level_index ,  p_state - > nodes . size ( ) ,  ret ,  vformat ( " glTF: Unable to find node %d for JSON pointer '%s'. " ,  top_level_index ,  p_json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  pointed_gltf_node  =  p_state - > nodes [ top_level_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										NodePath  node_path  =  pointed_gltf_node - > get_scene_node_path ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										partial_paths . append ( node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Check if it's something we should be able to handle.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  String  & node_prop  =  split [ 2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( node_prop  = =  " translation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > append_path_to_property ( node_path ,  " position " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( node_prop  = =  " rotation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > append_path_to_property ( node_path ,  " quaternion " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : QUATERNION ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( node_prop  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > append_path_to_property ( node_path ,  " scale " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( node_prop  = =  " matrix " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > append_path_to_property ( node_path ,  " transform " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : TRANSFORM3D ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4X4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( node_prop  = =  " globalMatrix " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > append_path_to_property ( node_path ,  " global_transform " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : TRANSFORM3D ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4X4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( node_prop  = =  " weights " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( split . size ( )  >  3 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  String  & weight_index_string  =  split [ 3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > append_path_to_property ( node_path ,  " blend_shapes/morph_ "  +  weight_index_string ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Else, Godot's MeshInstance3D does not expose the blend shape weights as one property.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// But that's fine, we handle this case in _parse_animation_pointer instead.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( split [ 0 ]  = =  " cameras " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  String  & camera_prop  =  split [ 2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFNode >  gltf_node  :  p_state - > nodes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( gltf_node - > camera  = =  top_level_index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												NodePath  node_path  =  gltf_node - > get_scene_node_path ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												partial_paths . append ( node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Check if it's something we should be able to handle.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( camera_prop  = =  " orthographic "  | |  camera_prop  = =  " perspective " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_FAIL_COND_V ( split . size ( )  <  4 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  String  & sub_prop  =  split [ 3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( sub_prop  = =  " xmag "  | |  sub_prop  = =  " ymag " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( node_path ,  " size " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( sub_prop  = =  " yfov " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( node_path ,  " fov " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														GLTFCamera : : set_fov_conversion_expressions ( ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( sub_prop  = =  " zfar " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( node_path ,  " far " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( sub_prop  = =  " znear " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( node_path ,  " near " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( split [ 0 ]  = =  " materials " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_INDEX_V_MSG ( top_level_index ,  p_state - > materials . size ( ) ,  ret ,  vformat ( " glTF: Unable to find material %d for JSON pointer '%s'. " ,  top_level_index ,  p_json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < Material >  pointed_material  =  p_state - > materials [ top_level_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										NodePath  mat_path  =  _find_material_node_path ( p_state ,  pointed_material ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( mat_path . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											WARN_PRINT ( vformat ( " glTF: Unable to find a path to the material %d for JSON pointer '%s'. This is likely bad data but it's also possible this is intentional. Continuing anyway. " ,  top_level_index ,  p_json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											partial_paths . append ( mat_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  String  & mat_prop  =  split [ 2 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mat_prop  = =  " alphaCutoff " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > append_path_to_property ( mat_path ,  " alpha_scissor_threshold " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( mat_prop  = =  " emissiveFactor " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > append_path_to_property ( mat_path ,  " emission " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : COLOR ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( mat_prop  = =  " extensions " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( split . size ( )  <  5 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  String  & ext_name  =  split [ 3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  String  & ext_prop  =  split [ 4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ext_name  = =  " KHR_materials_emissive_strength "  & &  ext_prop  = =  " emissiveStrength " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > append_path_to_property ( mat_path ,  " emission_energy_multiplier " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_FAIL_COND_V ( split . size ( )  <  4 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  String  & sub_prop  =  split [ 3 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( mat_prop  = =  " normalTexture " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( sub_prop  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( mat_path ,  " normal_scale " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( mat_prop  = =  " occlusionTexture " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( sub_prop  = =  " strength " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														// This is the closest thing Godot has to an occlusion strength property.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( mat_path ,  " ao_light_affect " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( mat_prop  = =  " pbrMetallicRoughness " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( sub_prop  = =  " baseColorFactor " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( mat_path ,  " albedo_color " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > set_types ( Variant : : COLOR ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( sub_prop  = =  " metallicFactor " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( mat_path ,  " metallic " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( sub_prop  = =  " roughnessFactor " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( mat_path ,  " roughness " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( sub_prop  = =  " baseColorTexture " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_V ( split . size ( )  <  6 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  String  & tex_ext_dict  =  split [ 4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  String  & tex_ext_name  =  split [ 5 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  String  & tex_ext_prop  =  split [ 6 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( tex_ext_dict  = =  " extensions "  & &  tex_ext_name  = =  " KHR_texture_transform " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															// Godot only supports UVs for the whole material, not per texture.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															// We treat the albedo texture as the main texture, and import as UV1.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															// Godot does not support texture rotation, only offset and scale.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															if  ( tex_ext_prop  = =  " offset " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																ret - > append_path_to_property ( mat_path ,  " uv1_offset " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( tex_ext_prop  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																ret - > append_path_to_property ( mat_path ,  " uv1_scale " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( split [ 0 ]  = =  " meshes " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFNode >  gltf_node  :  p_state - > nodes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( gltf_node - > mesh  = =  top_level_index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												NodePath  node_path  =  gltf_node - > get_scene_node_path ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < StringName >  subpath ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												subpath . append ( " mesh " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												partial_paths . append ( NodePath ( node_path . get_names ( ) ,  subpath ,  false ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( split [ 0 ]  = =  " extensions " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( split [ 1 ]  = =  " KHR_lights_punctual "  & &  split [ 2 ]  = =  " lights "  & &  split . size ( )  >  4 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  light_index  =  split [ 3 ] . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_INDEX_V_MSG ( light_index ,  p_state - > lights . size ( ) ,  ret ,  vformat ( " glTF: Unable to find light %d for JSON pointer '%s'. " ,  light_index ,  p_json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  String  & light_prop  =  split [ 4 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Ref < GLTFLight >  pointed_light  =  p_state - > lights [ light_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( Ref < GLTFNode >  gltf_node  :  p_state - > nodes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( gltf_node - > light  = =  light_index )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													NodePath  node_path  =  gltf_node - > get_scene_node_path ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													partial_paths . append ( node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Check if it's something we should be able to handle.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( light_prop  = =  " color " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( node_path ,  " light_color " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > set_types ( Variant : : COLOR ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( light_prop  = =  " intensity " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ret - > append_path_to_property ( node_path ,  " light_energy " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( light_prop  = =  " range " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  String  & light_type  =  p_state - > lights [ light_index ] - > light_type ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( light_type  = =  " spot " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															ret - > append_path_to_property ( node_path ,  " spot_range " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															ret - > append_path_to_property ( node_path ,  " omni_range " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  if  ( light_prop  = =  " spot " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_V ( split . size ( )  <  6 ,  ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														const  String  & sub_prop  =  split [ 5 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( sub_prop  = =  " innerConeAngle " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															ret - > append_path_to_property ( node_path ,  " spot_angle_attenuation " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															GLTFLight : : set_cone_inner_attenuation_conversion_expressions ( ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  if  ( sub_prop  = =  " outerConeAngle " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															ret - > append_path_to_property ( node_path ,  " spot_angle " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Additional JSON pointers can be added by GLTFDocumentExtension classes.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// We only need this if no mapping has been found yet from GLTFDocument's internal code.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// When available, we pass the partial paths to the extension to help it generate the full path.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// For example, for `/nodes/3/extensions/MY_ext/prop`, we pass a NodePath that leads to node 3,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// so the GLTFDocumentExtension class only needs to resolve the last `MY_ext/prop` part of the path.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// It should check `split.size() > 4 and split[0] == "nodes" and split[2] == "extensions" and split[3] == "MY_ext"`
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// at the start of the function to check if this JSON pointer applies to it, then it can handle `split[4]`.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! ret - > has_node_paths ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFDocumentExtension >  ext  :  all_document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret  =  ext - > import_object_model_property ( p_state ,  split ,  partial_paths ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ret . is_valid ( )  & &  ret - > has_node_paths ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! ret - > has_json_pointers ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_json_pointers ( {  split  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ret . is_null ( )  | |  ! ret - > has_node_paths ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( split . has ( " KHR_texture_transform " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												WARN_VERBOSE ( vformat ( " glTF: Texture transforms are only supported per material in Godot. All KHR_texture_transform properties will be ignored except for the albedo texture. Ignoring JSON pointer '%s'. " ,  p_json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												WARN_PRINT ( vformat ( " glTF: Animation contained JSON pointer '%s' which could not be resolved. This property will not be animated. " ,  p_json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > object_model_properties [ p_json_pointer ]  =  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Ref < GLTFObjectModelProperty >  GLTFDocument : : export_object_model_property ( Ref < GLTFState >  p_state ,  const  NodePath  & p_node_path ,  const  Node  * p_godot_node ,  GLTFNodeIndex  p_gltf_node_index )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFObjectModelProperty >  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Object  * target_object  =  p_godot_node ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < StringName >  subpath  =  p_node_path . get_subnames ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( subpath . is_empty ( ) ,  ret ,  " glTF: Cannot export empty property. No property was specified in the NodePath:  "  +  p_node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  target_prop_depth  =  0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( StringName  subname  :  subpath )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Variant  target_property  =  target_object - > get ( subname ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( target_property . get_type ( )  = =  Variant : : OBJECT )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											target_object  =  target_property ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( target_object )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												target_prop_depth + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  String  & target_prop  =  subpath [ target_prop_depth ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ret - > set_node_paths ( {  p_node_path  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < PackedStringArray >  split_json_pointers ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									PackedStringArray  split_json_pointer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( Object : : cast_to < BaseMaterial3D > ( target_object ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  p_state - > materials . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_state - > materials [ i ] . ptr ( )  = =  target_object )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " materials " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( itos ( i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( target_prop  = =  " alpha_scissor_threshold " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " alphaCutoff " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " emission " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " emissiveFactor " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : COLOR ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " emission_energy_multiplier " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " extensions " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " KHR_materials_emissive_strength " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " emissiveStrength " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " normal_scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " normalTexture " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " scale " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " ao_light_affect " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " occlusionTexture " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " strength " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " albedo_color " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " pbrMetallicRoughness " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " baseColorFactor " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : COLOR ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " metallic " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " pbrMetallicRoughness " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " metallicFactor " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " roughness " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " pbrMetallicRoughness " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " roughnessFactor " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  if  ( target_prop  = =  " uv1_offset "  | |  target_prop  = =  " uv1_scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " pbrMetallicRoughness " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " baseColorTexture " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " extensions " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . append ( " KHR_texture_transform " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( target_prop  = =  " uv1_offset " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														split_json_pointer . append ( " offset " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														split_json_pointer . append ( " scale " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT2 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													split_json_pointer . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Properties directly on Godot nodes.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ p_gltf_node_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( Object : : cast_to < Camera3D > ( target_object )  & &  gltf_node - > camera  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " cameras " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( itos ( gltf_node - > camera ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Camera3D  * camera_node  =  Object : : cast_to < Camera3D > ( target_object ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Camera3D : : ProjectionType  projection_type  =  camera_node - > get_projection ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( projection_type  = =  Camera3D : : PROJECTION_PERSPECTIVE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " perspective " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " orthographic " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( target_prop  = =  " size " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												PackedStringArray  xmag  =  split_json_pointer . duplicate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												xmag . append ( " xmag " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointers . append ( xmag ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " ymag " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " fov " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " yfov " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												GLTFCamera : : set_fov_conversion_expressions ( ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " far " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " zfar " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " near " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " znear " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( Object : : cast_to < Light3D > ( target_object )  & &  gltf_node - > light  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " extensions " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " KHR_lights_punctual " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " lights " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( itos ( gltf_node - > light ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret - > set_types ( Variant : : FLOAT ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( target_prop  = =  " light_color " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " color " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : COLOR ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " light_energy " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " intensity " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " spot_range " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " range " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " omni_range " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " range " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " spot_angle " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " spot " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " outerConeAngle " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " spot_angle_attenuation " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " spot " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " innerConeAngle " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												GLTFLight : : set_cone_inner_attenuation_conversion_expressions ( ret ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( Object : : cast_to < MeshInstance3D > ( target_object )  & &  target_prop . begins_with ( " blend_shapes/morph_ " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  String  & weight_index_string  =  target_prop . trim_prefix ( " blend_shapes/morph_ " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " nodes " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( itos ( p_gltf_node_index ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " weights " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( weight_index_string ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Transform properties. Check for all 3D nodes if we haven't resolved the JSON pointer yet.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Note: Do not put this in an `else`, because otherwise this will not be reached.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( split_json_pointer . is_empty ( )  & &  Object : : cast_to < Node3D > ( target_object ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( " nodes " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											split_json_pointer . append ( itos ( p_gltf_node_index ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( target_prop  = =  " position " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " translation " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " quaternion " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Note: Only Quaternion rotation can be converted from Godot in this mapping.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// Struct methods like from_euler are not accessible from the Expression class. :(
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " rotation " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : QUATERNION ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " scale " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : VECTOR3 ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT3 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " transform " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " matrix " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : TRANSFORM3D ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4X4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( target_prop  = =  " global_transform " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . append ( " globalMatrix " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ret - > set_types ( Variant : : TRANSFORM3D ,  GLTFObjectModelProperty : : GLTF_OBJECT_MODEL_TYPE_FLOAT4X4 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												split_json_pointer . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Additional JSON pointers can be added by GLTFDocumentExtension classes.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// We only need this if no mapping has been found yet from GLTFDocument's internal code.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// We pass as many pieces of information as we can to the extension to give it lots of context.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( split_json_pointer . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFDocumentExtension >  ext  :  all_document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ret  =  ext - > export_object_model_property ( p_state ,  p_node_path ,  p_godot_node ,  p_gltf_node_index ,  target_object ,  target_prop_depth ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ret . is_valid ( )  & &  ret - > has_json_pointers ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( ! ret - > has_node_paths ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ret - > set_node_paths ( {  p_node_path  } ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// GLTFDocument's internal code found a mapping, so set it and return it.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										split_json_pointers . append ( split_json_pointer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ret - > set_json_pointers ( split_json_pointers ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _import_animation ( Ref < GLTFState >  p_state ,  AnimationPlayer  * p_animation_player ,  const  GLTFAnimationIndex  p_index ,  const  bool  p_trimming ,  const  bool  p_remove_immutable_tracks )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND ( p_state . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Node  * scene_root  =  p_animation_player - > get_parent ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL ( scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFAnimation >  anim  =  p_state - > animations [ p_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  anim_name  =  anim - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( anim_name . is_empty ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										// No node represent these, and they are not in the hierarchy, so just make a unique name
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										anim_name  =  _gen_unique_name ( p_state ,  " Animation " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < Animation >  animation ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									animation . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									animation - > set_name ( anim_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									animation - > set_step ( 1.0  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( anim - > get_loop ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-15 22:25:00 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										animation - > set_loop_mode ( Animation : : LOOP_LINEAR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-04-10 11:21:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									double  anim_start  =  p_trimming  ?  Math : : INF  :  0.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									double  anim_end  =  0.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( const  KeyValue < int ,  GLTFAnimation : : NodeTrack >  & track_i  :  anim - > get_node_tracks ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  GLTFAnimation : : NodeTrack  & track  =  track_i . value ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//need to find the path: for skeletons, weight tracks will affect the mesh
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										NodePath  node_path ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//for skeletons, transform tracks always affect bones
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										NodePath  transform_node_path ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										//for meshes, especially skinned meshes, there are cases where it will be added as a child
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										NodePath  mesh_instance_node_path ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-08-09 14:13:42 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										GLTFNodeIndex  node_index  =  track_i . key ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  Ref < GLTFNode >  gltf_node  =  p_state - > nodes [ track_i . key ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										HashMap < GLTFNodeIndex ,  Node  * > : : Iterator  node_element  =  p_state - > scene_nodes . find ( node_index ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_CONTINUE_MSG ( ! node_element ,  vformat ( " Unable to find node %d for animation. " ,  node_index ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										node_path  =  scene_root - > get_path_to ( node_element - > value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										HashMap < GLTFNodeIndex ,  ImporterMeshInstance3D  * > : : Iterator  mesh_instance_element  =  p_state - > scene_mesh_instances . find ( node_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( mesh_instance_element )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mesh_instance_node_path  =  scene_root - > get_path_to ( mesh_instance_element - > value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mesh_instance_node_path  =  node_path ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( gltf_node - > skeleton  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  Skeleton3D  * sk  =  p_state - > skeletons [ gltf_node - > skeleton ] - > godot_skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-09-09 17:40:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_NULL ( sk ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  String  path  =  p_animation_player - > get_parent ( ) - > get_path_to ( sk ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											const  String  bone  =  gltf_node - > get_name ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											transform_node_path  =  path  +  " : "  +  bone ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											transform_node_path  =  node_path ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_trimming )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . rotation_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_start  =  MIN ( anim_start ,  track . rotation_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  track . rotation_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . position_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_start  =  MIN ( anim_start ,  track . position_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  track . position_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . scale_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_start  =  MIN ( anim_start ,  track . scale_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  track . scale_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . weight_tracks . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  track . weight_tracks [ i ] . times . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													anim_start  =  MIN ( anim_start ,  track . weight_tracks [ i ] . times [ j ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													anim_end  =  MAX ( anim_end ,  track . weight_tracks [ i ] . times [ j ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// If you don't use trimming and the first key time is not at 0.0, fake keys will be inserted.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . rotation_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  track . rotation_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . position_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  track . position_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . scale_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  track . scale_track . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  track . weight_tracks . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  track . weight_tracks [ i ] . times . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													anim_end  =  MAX ( anim_end ,  track . weight_tracks [ i ] . times [ j ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-05-21 00:03:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Animated TRS properties will not affect a skinned mesh.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  bool  transform_affects_skinned_mesh_instance  =  gltf_node - > skeleton  <  0  & &  gltf_node - > skin  > =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-30 22:18:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ( track . rotation_track . values . size ( )  | |  track . position_track . values . size ( )  | |  track . scale_track . values . size ( ) )  & &  ! transform_affects_skinned_mesh_instance )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											//make transform track
 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  base_idx  =  animation - > get_track_count ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  position_idx  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  rotation_idx  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int  scale_idx  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( track . position_track . values . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												bool  is_default  =  true ;  //discard the track if all it contains is default values
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_remove_immutable_tracks )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector3  base_pos  =  gltf_node - > get_position ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  track . position_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-20 16:56:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														int  value_index  =  track . position_track . interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE  ?  ( 1  +  i  *  3 )  :  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_MSG ( value_index  > =  track . position_track . values . size ( ) ,  " Animation sampler output accessor with 'CUBICSPLINE' interpolation doesn't have enough elements. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  value  =  track . position_track . values [ value_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( ! value . is_equal_approx ( base_pos ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															is_default  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( ! p_remove_immutable_tracks  | |  ! is_default )  { 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													position_idx  =  base_idx ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > add_track ( Animation : : TYPE_POSITION_3D ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > track_set_path ( position_idx ,  transform_node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > track_set_imported ( position_idx ,  true ) ;  //helps merging later
 
							 
						 
					
						
							
								
									
										
										
										
											2023-12-11 01:59:22 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( track . position_track . interpolation  = =  GLTFAnimation : : INTERP_STEP )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														animation - > track_set_interpolation_type ( position_idx ,  Animation : : InterpolationType : : INTERPOLATION_NEAREST ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													base_idx + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( track . rotation_track . values . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												bool  is_default  =  true ;  //discard the track if all it contains is default values
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_remove_immutable_tracks )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Quaternion  base_rot  =  gltf_node - > get_rotation ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  track . rotation_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-20 16:56:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														int  value_index  =  track . rotation_track . interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE  ?  ( 1  +  i  *  3 )  :  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_MSG ( value_index  > =  track . rotation_track . values . size ( ) ,  " Animation sampler output accessor with 'CUBICSPLINE' interpolation doesn't have enough elements. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Quaternion  value  =  track . rotation_track . values [ value_index ] . normalized ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( ! value . is_equal_approx ( base_rot ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															is_default  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( ! p_remove_immutable_tracks  | |  ! is_default )  { 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													rotation_idx  =  base_idx ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > add_track ( Animation : : TYPE_ROTATION_3D ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > track_set_path ( rotation_idx ,  transform_node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > track_set_imported ( rotation_idx ,  true ) ;  //helps merging later
 
							 
						 
					
						
							
								
									
										
										
										
											2023-12-11 01:59:22 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( track . rotation_track . interpolation  = =  GLTFAnimation : : INTERP_STEP )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														animation - > track_set_interpolation_type ( rotation_idx ,  Animation : : InterpolationType : : INTERPOLATION_NEAREST ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													base_idx + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( track . scale_track . values . size ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												bool  is_default  =  true ;  //discard the track if all it contains is default values
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_remove_immutable_tracks )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Vector3  base_scale  =  gltf_node - > get_scale ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int  i  =  0 ;  i  <  track . scale_track . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-20 16:56:49 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														int  value_index  =  track . scale_track . interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE  ?  ( 1  +  i  *  3 )  :  i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_FAIL_COND_MSG ( value_index  > =  track . scale_track . values . size ( ) ,  " Animation sampler output accessor with 'CUBICSPLINE' interpolation doesn't have enough elements. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  value  =  track . scale_track . values [ value_index ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														if  ( ! value . is_equal_approx ( base_scale ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															is_default  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( ! p_remove_immutable_tracks  | |  ! is_default )  { 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													scale_idx  =  base_idx ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > add_track ( Animation : : TYPE_SCALE_3D ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > track_set_path ( scale_idx ,  transform_node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													animation - > track_set_imported ( scale_idx ,  true ) ;  //helps merging later
 
							 
						 
					
						
							
								
									
										
										
										
											2023-12-11 01:59:22 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( track . scale_track . interpolation  = =  GLTFAnimation : : INTERP_STEP )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														animation - > track_set_interpolation_type ( scale_idx ,  Animation : : InterpolationType : : INTERPOLATION_NEAREST ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													base_idx + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											double  time  =  anim_start ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector3  base_pos ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											Quaternion  base_rot ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Vector3  base_scale  =  Vector3 ( 1 ,  1 ,  1 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( rotation_idx  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												base_rot  =  gltf_node - > get_rotation ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( position_idx  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												base_pos  =  gltf_node - > get_position ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( scale_idx  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												base_scale  =  gltf_node - > get_scale ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  pos  =  base_pos ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Quaternion  rot  =  base_rot ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												Vector3  scale  =  base_scale ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( position_idx  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-30 22:18:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													pos  =  _interpolate_track < Vector3 > ( track . position_track . times ,  track . position_track . values ,  time ,  track . position_track . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													animation - > position_track_insert_key ( position_idx ,  time  -  anim_start ,  pos ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( rotation_idx  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 07:02:02 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													rot  =  _interpolate_track < Quaternion > ( track . rotation_track . times ,  track . rotation_track . values ,  time ,  track . rotation_track . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													animation - > rotation_track_insert_key ( rotation_idx ,  time  -  anim_start ,  rot ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( scale_idx  > =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													scale  =  _interpolate_track < Vector3 > ( track . scale_track . times ,  track . scale_track . values ,  time ,  track . scale_track . interpolation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													animation - > scale_track_insert_key ( scale_idx ,  time  -  anim_start ,  scale ) ; 
							 
						 
					
						
							
								
									
										
										
											
												Remove animation 3D transform track, replace by loc/rot/scale tracks.
* `Animation.TYPE_TRANSFORM3D` track is gone.
* Added POSITION_3D, ROTATION_3D, SCALE_3D tracks.
* GLTF2, Collada, FBX importers will only import the track types found.
* Skeleton3D bone poses are now Pos/Rot/Scale, pose matrix removed.
* AnimationPlayer and AnimationTree animate these tracks separately, only when found.
* Removed BakeReset code, is useless with these changes.
This is the first in a series of commits designed to make the animation system in Godot more useful, which includes:
* Better compatibility with Autodesk products
* Better reusability of animations across models (including retargeting).
* Proper animation compression.
* etc.
*Note* GLTF2 animation saving went broken with this PR, needs to be fixed in a subsequent one.
											 
										 
										
											2021-10-11 19:20:58 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												time  + =  increment ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													last  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													time  =  anim_end ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  track . weight_tracks . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE ( gltf_node - > mesh  <  0  | |  gltf_node - > mesh  > =  p_state - > meshes . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < GLTFMesh >  mesh  =  p_state - > meshes [ gltf_node - > mesh ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( mesh . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( mesh - > get_mesh ( ) . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( mesh - > get_mesh ( ) - > get_mesh ( ) . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  String  blend_path  =  String ( mesh_instance_node_path )  +  " : "  +  String ( mesh - > get_mesh ( ) - > get_blend_shape_name ( i ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  track_idx  =  animation - > get_track_count ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-15 19:04:35 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											animation - > add_track ( Animation : : TYPE_BLEND_SHAPE ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											animation - > track_set_path ( track_idx ,  blend_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-23 07:40:06 +00:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											animation - > track_set_imported ( track_idx ,  true ) ;  //helps merging later
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Only LINEAR and STEP (NEAREST) can be supported out of the box by Godot's Animation,
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// the other modes have to be baked.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFAnimation : : Interpolation  gltf_interp  =  track . weight_tracks [ i ] . interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( gltf_interp  = =  GLTFAnimation : : INTERP_LINEAR  | |  gltf_interp  = =  GLTFAnimation : : INTERP_STEP )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												animation - > track_set_interpolation_type ( track_idx ,  gltf_interp  = =  GLTFAnimation : : INTERP_STEP  ?  Animation : : INTERPOLATION_NEAREST  :  Animation : : INTERPOLATION_LINEAR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  j  =  0 ;  j  <  track . weight_tracks [ i ] . times . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  float  t  =  track . weight_tracks [ i ] . times [ j ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  float  attribs  =  track . weight_tracks [ i ] . values [ j ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-15 19:04:35 -03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													animation - > blend_shape_track_insert_key ( track_idx ,  t ,  attribs ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-18 01:50:28 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												double  time  =  0.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												while  ( true )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-16 01:03:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													real_t  blend  =  _interpolate_track < real_t > ( track . weight_tracks [ i ] . times ,  track . weight_tracks [ i ] . values ,  time ,  gltf_interp ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													animation - > blend_shape_track_insert_key ( track_idx ,  time  -  anim_start ,  blend ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													time  + =  increment ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														last  =  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														time  =  anim_end ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( const  KeyValue < String ,  GLTFAnimation : : Channel < Variant > >  & track_iter  :  anim - > get_pointer_tracks ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Determine the property to animate.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  String  json_pointer  =  track_iter . key ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Ref < GLTFObjectModelProperty >  prop  =  import_object_model_property ( p_state ,  json_pointer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND ( prop . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Adjust the animation duration to encompass all keyframes.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  GLTFAnimation : : Channel < Variant >  & channel  =  track_iter . value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE_MSG ( channel . times . size ( )  ! =  channel . values . size ( ) ,  vformat ( " glTF: Animation pointer '%s' has mismatched keyframe times and values. " ,  json_pointer ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( p_trimming )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  channel . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_start  =  MIN ( anim_start ,  channel . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  channel . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  channel . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												anim_end  =  MAX ( anim_end ,  channel . times [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Begin converting the glTF animation to a Godot animation.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Ref < Expression >  gltf_to_godot_expr  =  prop - > get_gltf_to_godot_expression ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  bool  is_gltf_to_godot_expr_valid  =  gltf_to_godot_expr . is_valid ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( const  NodePath  node_path  :  prop - > get_node_paths ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// If using an expression, determine the base instance to pass to the expression.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Object  * base_instance  =  nullptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( is_gltf_to_godot_expr_valid )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Resource >  resource ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < StringName >  leftover_subpath ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												base_instance  =  scene_root - > get_node_and_resource ( node_path ,  resource ,  leftover_subpath ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( resource . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													base_instance  =  resource . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Add a track and insert all keys and values.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int  track_index  =  animation - > get_track_count ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											animation - > add_track ( Animation : : TYPE_VALUE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											animation - > track_set_interpolation_type ( track_index ,  GLTFAnimation : : gltf_to_godot_interpolation ( channel . interpolation ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											animation - > track_set_path ( track_index ,  node_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int  i  =  0 ;  i  <  channel . times . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  double  time  =  channel . times [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Variant  value  =  channel . values [ i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( is_gltf_to_godot_expr_valid )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Array  inputs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													inputs . append ( value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													value  =  gltf_to_godot_expr - > execute ( inputs ,  base_instance ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												animation - > track_insert_key ( track_index ,  time ,  value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									animation - > set_length ( anim_end  -  anim_start ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-07 13:49:28 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < AnimationLibrary >  library ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_animation_player - > has_animation_library ( " " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-07 13:49:28 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										library . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_animation_player - > add_animation_library ( " " ,  library ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-07 13:49:28 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										library  =  p_animation_player - > get_animation_library ( " " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-07 13:49:28 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-29 12:53:28 +03:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									library - > add_animation ( anim_name ,  animation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_mesh_instances ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( GLTFNodeIndex  mi_node_i  =  0 ;  mi_node_i  <  p_state - > nodes . size ( ) ;  + + mi_node_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  node  =  p_state - > nodes [ mi_node_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( node - > mesh  <  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										HashMap < GLTFNodeIndex ,  Node  * > : : Iterator  mi_element  =  p_state - > scene_nodes . find ( mi_node_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( ! mi_element )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2022-05-13 15:04:37 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										MeshInstance3D  * mi  =  Object : : cast_to < MeshInstance3D > ( mi_element - > value ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( ! mi )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-12 17:37:03 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										node - > transform  =  mi - > get_transform ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Node  * skel_node  =  mi - > get_node_or_null ( mi - > get_skeleton_path ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Skeleton3D  * godot_skeleton  =  Object : : cast_to < Skeleton3D > ( skel_node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! godot_skeleton  | |  godot_skeleton - > get_bone_count ( )  = =  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// At this point in the code, we know we have a Skeleton3D with at least one bone.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Ref < Skin >  skin  =  mi - > get_skin ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFSkin >  gltf_skin ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										gltf_skin . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Array  json_joints ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_state - > skeleton3d_to_gltf_skeleton . has ( godot_skeleton - > get_instance_id ( ) ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// This is a skinned mesh. If the mesh has no ARRAY_WEIGHTS or ARRAY_BONES, it will be invisible.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  GLTFSkeletonIndex  skeleton_gltf_i  =  p_state - > skeleton3d_to_gltf_skeleton [ godot_skeleton - > get_instance_id ( ) ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < GLTFSkeleton >  gltf_skeleton  =  p_state - > skeletons [ skeleton_gltf_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											int  bone_cnt  =  godot_skeleton - > get_bone_count ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_FAIL_COND ( bone_cnt  ! =  gltf_skeleton - > joints . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-11-22 22:40:47 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ObjectID  gltf_skin_key ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( skin . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_skin_key  =  skin - > get_instance_id ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ObjectID  gltf_skel_key  =  godot_skeleton - > get_instance_id ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFSkinIndex  skin_gltf_i  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFNodeIndex  root_gltf_i  =  - 1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! gltf_skeleton - > roots . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												root_gltf_i  =  gltf_skeleton - > roots [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											if  ( p_state - > skin_and_skeleton3d_to_gltf_skin . has ( gltf_skin_key )  & &  p_state - > skin_and_skeleton3d_to_gltf_skin [ gltf_skin_key ] . has ( gltf_skel_key ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												skin_gltf_i  =  p_state - > skin_and_skeleton3d_to_gltf_skin [ gltf_skin_key ] [ gltf_skel_key ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( skin . is_null ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// Note that gltf_skin_key should remain null, so these can share a reference.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													skin  =  godot_skeleton - > create_skin_from_rest_transforms ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_skin . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_skin - > godot_skin  =  skin ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_skin - > set_name ( skin - > get_name ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_skin - > skeleton  =  skeleton_gltf_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												gltf_skin - > skin_root  =  root_gltf_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												//gltf_state->godot_to_gltf_node[skel_node]
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												HashMap < StringName ,  int >  bone_name_to_idx ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  bone_i  =  0 ;  bone_i  <  bone_cnt ;  bone_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													bone_name_to_idx [ godot_skeleton - > get_bone_name ( bone_i ) ]  =  bone_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												for  ( int  bind_i  =  0 ,  cnt  =  skin - > get_bind_count ( ) ;  bind_i  <  cnt ;  bind_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													int  bone_i  =  skin - > get_bind_bone ( bind_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Transform3D  bind_pose  =  skin - > get_bind_pose ( bind_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													StringName  bind_name  =  skin - > get_bind_name ( bind_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( bind_name  ! =  StringName ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														bone_i  =  bone_name_to_idx [ bind_name ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													ERR_CONTINUE ( bone_i  <  0  | |  bone_i  > =  bone_cnt ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( bind_name  = =  StringName ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														bind_name  =  godot_skeleton - > get_bone_name ( bone_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													GLTFNodeIndex  skeleton_bone_i  =  gltf_skeleton - > joints [ bone_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_skin - > joints_original . push_back ( skeleton_bone_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_skin - > joints . push_back ( skeleton_bone_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_skin - > inverse_binds . push_back ( bind_pose ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-05-27 03:08:44 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( godot_skeleton - > get_bone_parent ( bone_i )  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														gltf_skin - > roots . push_back ( skeleton_bone_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_skin - > joint_i_to_bone_i [ bind_i ]  =  bone_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_skin - > joint_i_to_name [ bind_i ]  =  bind_name ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												skin_gltf_i  =  p_state - > skins . size ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > skins . push_back ( gltf_skin ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > skin_and_skeleton3d_to_gltf_skin [ gltf_skin_key ] [ gltf_skel_key ]  =  skin_gltf_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											node - > skin  =  skin_gltf_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node - > skeleton  =  skeleton_gltf_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								float  GLTFDocument : : solve_metallic ( float  p_dielectric_specular ,  float  p_diffuse ,  float  p_specular ,  float  p_one_minus_specular_strength )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_specular  < =  p_dielectric_specular )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										return  0.0f ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  a  =  p_dielectric_specular ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  float  b  =  p_diffuse  *  p_one_minus_specular_strength  /  ( 1.0f  -  p_dielectric_specular )  +  p_specular  -  2.0f  *  p_dielectric_specular ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  c  =  p_dielectric_specular  -  p_specular ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									const  float  D  =  b  *  b  -  4.0f  *  a  *  c ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  CLAMP ( ( - b  +  Math : : sqrt ( D ) )  /  ( 2.0f  *  a ) ,  0.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								float  GLTFDocument : : get_perceived_brightness ( const  Color  p_color )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Color  coeff  =  Color ( R_BRIGHTNESS_COEFF ,  G_BRIGHTNESS_COEFF ,  B_BRIGHTNESS_COEFF ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Color  value  =  coeff  *  ( p_color  *  p_color ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  r  =  value . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  g  =  value . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  b  =  value . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  Math : : sqrt ( r  +  g  +  b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								float  GLTFDocument : : get_max_component ( const  Color  & p_color )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  r  =  p_color . r ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  g  =  p_color . g ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  float  b  =  p_color . b ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  MAX ( MAX ( r ,  g ) ,  b ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-02-04 02:47:44 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _process_mesh_instances ( Ref < GLTFState >  p_state ,  Node  * p_scene_root )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFNodeIndex  node_i  =  0 ;  node_i  <  p_state - > nodes . size ( ) ;  + + node_i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFNode >  node  =  p_state - > nodes [ node_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( node - > skin  > =  0  & &  node - > mesh  > =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  GLTFSkinIndex  skin_i  =  node - > skin ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-01-26 22:41:58 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ImporterMeshInstance3D  * mi  =  nullptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											HashMap < GLTFNodeIndex ,  ImporterMeshInstance3D  * > : : Iterator  mi_element  =  p_state - > scene_mesh_instances . find ( node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( mi_element )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mi  =  mi_element - > value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												HashMap < GLTFNodeIndex ,  Node  * > : : Iterator  si_element  =  p_state - > scene_nodes . find ( node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_CONTINUE_MSG ( ! si_element ,  vformat ( " Unable to find node %d " ,  node_i ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												mi  =  Object : : cast_to < ImporterMeshInstance3D > ( si_element - > value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												ERR_CONTINUE_MSG ( mi  = =  nullptr ,  vformat ( " Unable to cast node %d of type %s to ImporterMeshInstance3D " ,  node_i ,  si_element - > value - > get_class_name ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  GLTFSkeletonIndex  skel_i  =  p_state - > skins . write [ node - > skin ] - > skeleton ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < GLTFSkeleton >  gltf_skeleton  =  p_state - > skeletons . write [ skel_i ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											Skeleton3D  * skeleton  =  gltf_skeleton - > godot_skeleton ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-05-20 19:12:16 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE_MSG ( skeleton  = =  nullptr ,  vformat ( " Unable to find Skeleton for node %d skin %d " ,  node_i ,  skin_i ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											mi - > get_parent ( ) - > remove_child ( mi ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-13 12:45:55 +08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mi - > set_owner ( nullptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-21 16:46:07 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											skeleton - > add_child ( mi ,  true ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-04 02:47:44 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mi - > set_owner ( p_scene_root ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mi - > set_skin ( p_state - > skins . write [ skin_i ] - > godot_skin ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											mi - > set_skeleton_path ( mi - > get_path_to ( skeleton ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-10-17 01:08:21 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											mi - > set_transform ( Transform3D ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								GLTFNodeIndex  GLTFDocument : : _node_and_or_bone_to_gltf_node_index ( Ref < GLTFState >  p_state ,  const  Vector < StringName >  & p_node_subpath ,  const  Node  * p_godot_node )  {  
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									const  Skeleton3D  * skeleton  =  Object : : cast_to < Skeleton3D > ( p_godot_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( skeleton  & &  p_node_subpath . size ( )  = =  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Special case: Handle skeleton bone TRS tracks. They use the format `A/B/C/Skeleton3D:bone_name`.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// We have a Skeleton3D, check if it has a bone with the same name as this subpath.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  String  & bone_name  =  p_node_subpath [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  int32_t  bone_index  =  skeleton - > find_bone ( bone_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( bone_index  ! =  - 1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// A bone was found! But we still need to figure out which glTF node it corresponds to.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( GLTFSkeletonIndex  skeleton_i  =  0 ;  skeleton_i  <  p_state - > skeletons . size ( ) ;  skeleton_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												const  Ref < GLTFSkeleton >  & skeleton_gltf  =  p_state - > skeletons [ skeleton_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( skeleton  = =  skeleton_gltf - > godot_skeleton )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													GLTFNodeIndex  node_i  =  skeleton_gltf - > godot_bone_node [ bone_index ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													return  node_i ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_V_MSG ( - 1 ,  vformat ( " glTF: Found a bone %s in a Skeleton3D that wasn't in the GLTFState. Ensure that all nodes referenced by the AnimationPlayer are in the scene you are exporting. " ,  bone_name ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// General case: Not a skeleton bone, usually this means a normal node, or it could be the Skeleton3D itself.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( const  KeyValue < GLTFNodeIndex ,  Node  * >  & scene_node_i  :  p_state - > scene_nodes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( scene_node_i . value  = =  p_godot_node )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  scene_node_i . key ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_V_MSG ( - 1 ,  vformat ( " glTF: A node was animated, but it wasn't found in the GLTFState. Ensure that all nodes referenced by the AnimationPlayer are in the scene you are exporting. " ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								bool  GLTFDocument : : _convert_animation_node_track ( Ref < GLTFState >  p_state ,  GLTFAnimation : : NodeTrack  & p_gltf_node_track ,  const  Ref < Animation >  & p_godot_animation ,  int32_t  p_godot_anim_track_index ,  Vector < double >  & p_times )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									GLTFAnimation : : Interpolation  gltf_interpolation  =  GLTFAnimation : : godot_to_gltf_interpolation ( p_godot_animation ,  p_godot_anim_track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Animation : : TrackType  track_type  =  p_godot_animation - > track_get_type ( p_godot_anim_track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int32_t  key_count  =  p_godot_animation - > track_get_key_count ( p_godot_anim_track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  NodePath  node_path  =  p_godot_animation - > track_get_path ( p_godot_anim_track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  Vector < StringName >  subpath  =  node_path . get_subnames ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									double  anim_end  =  p_godot_animation - > get_length ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-13 02:18:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( track_type  = =  Animation : : TYPE_SCALE_3D )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_gltf_node_track . scale_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . scale_track . values . clear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  scale ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  p_godot_animation - > try_scale_track_interpolate ( p_godot_anim_track_index ,  time ,  & scale ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . values . push_back ( scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_gltf_node_track . scale_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . scale_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . scale_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  scale ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  p_godot_animation - > scale_track_get_key ( p_godot_anim_track_index ,  key_i ,  & scale ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . values . write [ key_i ]  =  scale ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-13 02:18:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( track_type  = =  Animation : : TYPE_POSITION_3D )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_gltf_node_track . position_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . position_track . values . clear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  scale ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  p_godot_animation - > try_position_track_interpolate ( p_godot_anim_track_index ,  time ,  & scale ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . values . push_back ( scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_gltf_node_track . position_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . position_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . position_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector3  position ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  p_godot_animation - > position_track_get_key ( p_godot_anim_track_index ,  key_i ,  & position ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . values . write [ key_i ]  =  position ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-13 02:18:43 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( track_type  = =  Animation : : TYPE_ROTATION_3D )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_gltf_node_track . rotation_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . rotation_track . values . clear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Quaternion  rotation ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  p_godot_animation - > try_rotation_track_interpolate ( p_godot_anim_track_index ,  time ,  & rotation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . values . push_back ( rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_gltf_node_track . rotation_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . rotation_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											p_gltf_node_track . rotation_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Quaternion  rotation ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												Error  err  =  p_godot_animation - > rotation_track_get_key ( p_godot_anim_track_index ,  key_i ,  & rotation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . values . write [ key_i ]  =  rotation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( subpath . size ( )  >  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  StringName  & node_prop  =  subpath [ 0 ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( track_type  = =  Animation : : TYPE_VALUE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( node_prop  = =  " position " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . values . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  position ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Error  err  =  p_godot_animation - > try_position_track_interpolate ( p_godot_anim_track_index ,  time ,  & position ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . position_track . values . push_back ( position ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . position_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  position  =  p_godot_animation - > track_get_key_value ( p_godot_anim_track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . position_track . values . write [ key_i ]  =  position ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( node_prop  = =  " rotation "  | |  node_prop  = =  " rotation_degrees "  | |  node_prop  = =  " quaternion " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . values . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Quaternion  rotation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Error  err  =  p_godot_animation - > try_rotation_track_interpolate ( p_godot_anim_track_index ,  time ,  & rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . rotation_track . values . push_back ( rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . rotation_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Quaternion  rotation_quaternion ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( node_prop  = =  " quaternion " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															rotation_quaternion  =  p_godot_animation - > track_get_key_value ( p_godot_anim_track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															Vector3  rotation_euler  =  p_godot_animation - > track_get_key_value ( p_godot_anim_track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															if  ( node_prop  = =  " rotation_degrees " )  { 
							 
						 
					
						
							
								
									
										
										
										
											2025-04-10 11:21:05 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
																rotation_euler  * =  Math : : TAU  /  360.0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															rotation_quaternion  =  Quaternion : : from_euler ( rotation_euler ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . rotation_track . values . write [ key_i ]  =  rotation_quaternion ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( node_prop  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . values . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  scale ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Error  err  =  p_godot_animation - > try_scale_track_interpolate ( p_godot_anim_track_index ,  time ,  & scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . values . push_back ( scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  scale_track  =  p_godot_animation - > track_get_key_value ( p_godot_anim_track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . values . write [ key_i ]  =  scale_track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( node_prop  = =  " transform " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . position_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . rotation_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . times  =  p_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_gltf_node_track . scale_track . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( gltf_interpolation  = =  GLTFAnimation : : INTERP_CUBIC_SPLINE )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													gltf_interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . values . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . values . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . times . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . values . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													// CATMULLROMSPLINE or CUBIC_SPLINE have to be baked, apologies.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													const  double  increment  =  1.0  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													double  time  =  0.0 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													bool  last  =  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  position ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Quaternion  rotation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  scale ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Error  err  =  p_godot_animation - > try_position_track_interpolate ( p_godot_anim_track_index ,  time ,  & position ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														err  =  p_godot_animation - > try_rotation_track_interpolate ( p_godot_anim_track_index ,  time ,  & rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														err  =  p_godot_animation - > try_scale_track_interpolate ( p_godot_anim_track_index ,  time ,  & scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . position_track . values . push_back ( position ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . position_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . rotation_track . values . push_back ( rotation ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . rotation_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . values . push_back ( scale ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . times . push_back ( time ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( last )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														time  + =  increment ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( time  > =  anim_end )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															last  =  true ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															time  =  anim_end ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Transform3D  transform  =  p_godot_animation - > track_get_key_value ( p_godot_anim_track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . position_track . values . write [ key_i ]  =  transform . get_origin ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . rotation_track . values . write [ key_i ]  =  transform . basis . get_rotation_quaternion ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . values . write [ key_i ]  =  transform . basis . get_scale ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												// This is a Value track animating a property, but not a TRS property, so it can't be converted into a node track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  false ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  if  ( track_type  = =  Animation : : TYPE_BEZIER )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  int32_t  keys  =  anim_end  *  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( node_prop  = =  " scale " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_gltf_node_track . scale_track . times . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < double >  new_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													new_times . resize ( keys ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														new_times . write [ key_i ]  =  key_i  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . times  =  new_times ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_gltf_node_track . scale_track . values . resize ( keys ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . values . write [ key_i ]  =  Vector3 ( 1.0f ,  1.0f ,  1.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														Vector3  bezier_track  =  p_gltf_node_track . scale_track . values [ key_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( subpath . size ( )  = =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															if  ( subpath [ 1 ]  = =  StringName ( " x " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																bezier_track . x  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( subpath [ 1 ]  = =  StringName ( " y " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																bezier_track . y  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															}  else  if  ( subpath [ 1 ]  = =  StringName ( " z " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
																bezier_track . z  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														p_gltf_node_track . scale_track . values . write [ key_i ]  =  bezier_track ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  if  ( node_prop  = =  " position " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_gltf_node_track . position_track . times . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < double >  new_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													new_times . resize ( keys ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														new_times . write [ key_i ]  =  key_i  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . times  =  new_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . values . resize ( keys ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector3  bezier_track  =  p_gltf_node_track . position_track . values [ key_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( subpath . size ( )  = =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( subpath [ 1 ]  = =  StringName ( " x " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . x  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  if  ( subpath [ 1 ]  = =  StringName ( " y " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . y  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  if  ( subpath [ 1 ]  = =  StringName ( " z " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . z  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . position_track . values . write [ key_i ]  =  bezier_track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											}  else  if  ( node_prop  = =  " quaternion " )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( p_gltf_node_track . rotation_track . times . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Vector < double >  new_times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													new_times . resize ( keys ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														new_times . write [ key_i ]  =  key_i  /  p_state - > get_bake_fps ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . times  =  new_times ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . values . resize ( keys ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( int32_t  key_i  =  0 ;  key_i  <  keys ;  key_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													Quaternion  bezier_track  =  p_gltf_node_track . rotation_track . values [ key_i ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													if  ( subpath . size ( )  = =  2 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														if  ( subpath [ 1 ]  = =  StringName ( " x " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . x  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  if  ( subpath [ 1 ]  = =  StringName ( " y " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . y  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  if  ( subpath [ 1 ]  = =  StringName ( " z " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . z  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														}  else  if  ( subpath [ 1 ]  = =  StringName ( " w " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
															bezier_track . w  =  p_godot_animation - > bezier_track_interpolate ( p_godot_anim_track_index ,  key_i  /  p_state - > get_bake_fps ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													p_gltf_node_track . rotation_track . values . write [ key_i ]  =  bezier_track ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												// This is a Bezier track animating a property, but not a TRS property, so it can't be converted into a node track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												return  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-02-03 18:06:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// This property track isn't a Value track or Bezier track, so it can't be converted into a node track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// This isn't a TRS track or a property track, so it can't be converted into a node track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  false ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// If we reached this point, the track was some kind of TRS track and was successfully converted.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// All failure paths should return false before this point to indicate this
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// isn't a node track so it can be handled by KHR_animation_pointer instead.
 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  true ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _convert_animation ( Ref < GLTFState >  p_state ,  AnimationPlayer  * p_animation_player ,  const  String  & p_animation_track_name )  {  
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < Animation >  animation  =  p_animation_player - > get_animation ( p_animation_track_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Ref < GLTFAnimation >  gltf_animation ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-06-17 16:03:09 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_animation . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_animation - > set_original_name ( p_animation_track_name ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									gltf_animation - > set_name ( _gen_unique_name ( p_state ,  p_animation_track_name ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									HashMap < int ,  GLTFAnimation : : NodeTrack >  & node_tracks  =  gltf_animation - > get_node_tracks ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( int32_t  track_index  =  0 ;  track_index  <  animation - > get_track_count ( ) ;  track_index + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! animation - > track_is_enabled ( track_index ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// Get the Godot node and the glTF node index for the animation track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  NodePath  track_path  =  animation - > track_get_path ( track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Node  * anim_player_parent  =  p_animation_player - > get_parent ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Node  * animated_node  =  anim_player_parent - > get_node_or_null ( track_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE_MSG ( ! animated_node ,  " glTF: Cannot get node for animated track using path:  "  +  String ( track_path ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  GLTFAnimation : : Interpolation  gltf_interpolation  =  GLTFAnimation : : godot_to_gltf_interpolation ( animation ,  track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// First, check if it's a Blend Shape track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( animation - > track_get_type ( track_index )  = =  Animation : : TYPE_BLEND_SHAPE )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 02:02:03 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											const  MeshInstance3D  * mesh_instance  =  Object : : cast_to < MeshInstance3D > ( animated_node ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE_MSG ( ! mesh_instance ,  " glTF: Animation had a Blend Shape track, but the node wasn't a MeshInstance3D. Ignoring this track. " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < Mesh >  mesh  =  mesh_instance - > get_mesh ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_CONTINUE ( mesh . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											int32_t  mesh_index  =  - 1 ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( const  KeyValue < GLTFNodeIndex ,  Node  * >  & mesh_track_i  :  p_state - > scene_nodes )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												if  ( mesh_track_i . value  = =  animated_node )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-08-09 14:13:42 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													mesh_index  =  mesh_track_i . key ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( mesh_index  = =  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											GLTFAnimation : : NodeTrack  track  =  node_tracks . has ( mesh_index )  ?  node_tracks [ mesh_index ]  :  GLTFAnimation : : NodeTrack ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( ! node_tracks . has ( mesh_index ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												for  ( int32_t  shape_i  =  0 ;  shape_i  <  mesh - > get_blend_shape_count ( ) ;  shape_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													String  shape_name  =  mesh - > get_blend_shape_name ( shape_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													NodePath  shape_path  =  NodePath ( track_path . get_names ( ) ,  {  shape_name  } ,  false ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-16 10:04:09 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													int32_t  shape_track_i  =  animation - > find_track ( shape_path ,  Animation : : TYPE_BLEND_SHAPE ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													if  ( shape_track_i  = =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-16 01:03:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														GLTFAnimation : : Channel < real_t >  weight ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
														weight . interpolation  =  GLTFAnimation : : INTERP_LINEAR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight . times . push_back ( 0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight . times . push_back ( 0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight . values . push_back ( 0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight . values . push_back ( 0.0f ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														track . weight_tracks . push_back ( weight ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
														continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													int32_t  key_count  =  animation - > track_get_key_count ( shape_track_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-16 01:03:50 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													GLTFAnimation : : Channel < real_t >  weight ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													weight . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													weight . times . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  time_i  =  0 ;  time_i  <  key_count ;  time_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight . times . write [ time_i ]  =  animation - > track_get_key_time ( shape_track_i ,  time_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													weight . values . resize ( key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													for  ( int32_t  value_i  =  0 ;  value_i  <  key_count ;  value_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
														weight . values . write [ value_i ]  =  animation - > track_get_key_value ( shape_track_i ,  value_i ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
													} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-03 18:00:59 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
													track . weight_tracks . push_back ( weight ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												node_tracks [ mesh_index ]  =  track ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// If it's not a Blend Shape track, it must either be a TRS track, a property Value track, or something we can't handle.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// For the cases we can handle, we will need to know the glTF node index, glTF interpolation, and the times of the track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  Vector < StringName >  subnames  =  track_path . get_subnames ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  GLTFNodeIndex  node_i  =  _node_and_or_bone_to_gltf_node_index ( p_state ,  subnames ,  animated_node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE_MSG ( node_i  = =  - 1 ,  " glTF: Cannot get glTF node index for animated track using path:  "  +  String ( track_path ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  int  anim_key_count  =  animation - > track_get_key_count ( track_index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < double >  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										times . resize ( anim_key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  key_i  =  0 ;  key_i  <  anim_key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											times . write [ key_i ]  =  animation - > track_get_key_time ( track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Try converting the track to a TRS glTF node track. This will only succeed if the Godot animation is a TRS track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  HashMap < int ,  GLTFAnimation : : NodeTrack > : : Iterator  node_track_iter  =  node_tracks . find ( node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										GLTFAnimation : : NodeTrack  track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( node_track_iter )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											track  =  node_track_iter - > value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( _convert_animation_node_track ( p_state ,  track ,  animation ,  track_index ,  times ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// If the track was successfully converted, save it and continue to the next track.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											node_tracks [ node_i ]  =  track ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											continue ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										// If the track wasn't a TRS track or Blend Shape track, it might be a Value track animating a property.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Then this is something that we need to handle with KHR_animation_pointer.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Ref < GLTFObjectModelProperty >  obj_model_prop  =  export_object_model_property ( p_state ,  track_path ,  animated_node ,  node_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( obj_model_prop . is_valid ( )  & &  obj_model_prop - > has_json_pointers ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Insert the property track into the KHR_animation_pointer pointer tracks.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFAnimation : : Channel < Variant >  channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											channel . interpolation  =  gltf_interpolation ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											channel . times  =  times ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											channel . values . resize ( anim_key_count ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// If using an expression, determine the base instance to pass to the expression.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  Ref < Expression >  godot_to_gltf_expr  =  obj_model_prop - > get_godot_to_gltf_expression ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											const  bool  is_godot_to_gltf_expr_valid  =  godot_to_gltf_expr . is_valid ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Object  * base_instance  =  nullptr ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( is_godot_to_gltf_expr_valid )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Ref < Resource >  resource ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Vector < StringName >  leftover_subpath ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												base_instance  =  anim_player_parent - > get_node_and_resource ( track_path ,  resource ,  leftover_subpath ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( resource . is_valid ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													base_instance  =  resource . ptr ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Convert the Godot animation values into glTF animation values (still Variant).
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( int32_t  key_i  =  0 ;  key_i  <  anim_key_count ;  key_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Variant  value  =  animation - > track_get_key_value ( track_index ,  key_i ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( is_godot_to_gltf_expr_valid )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													Array  inputs ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													inputs . append ( value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													value  =  godot_to_gltf_expr - > execute ( inputs ,  base_instance ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												channel . values . write [ key_i ]  =  value ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											// Use the JSON pointer to insert the property track into the pointer tracks. There will usually be just one JSON pointer.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											HashMap < String ,  GLTFAnimation : : Channel < Variant > >  & pointer_tracks  =  gltf_animation - > get_pointer_tracks ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Vector < PackedStringArray >  split_json_pointers  =  obj_model_prop - > get_json_pointers ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											for  ( const  PackedStringArray  & split_json_pointer  :  split_json_pointers )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												String  json_pointer_str  =  " / "  +  String ( " / " ) . join ( split_json_pointer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												p_state - > object_model_properties [ json_pointer_str ]  =  obj_model_prop ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												pointer_tracks [ json_pointer_str ]  =  channel ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! gltf_animation - > is_empty_of_tracks ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > animations . push_back ( gltf_animation ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse ( Ref < GLTFState >  p_state ,  String  p_path ,  Ref < FileAccess >  p_file )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Error  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_file . is_null ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										return  FAILED ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_file - > seek ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									uint32_t  magic  =  p_file - > get_32 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									if  ( magic  = =  0x46546C67 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//binary file
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										//text file
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_file - > seek ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  _parse_glb ( p_file ,  p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											return  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_file - > seek ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  text  =  p_file - > get_as_utf8_string ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										JSON  json ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  json . parse ( text ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_err_print_error ( " " ,  " " ,  json . get_error_line ( ) ,  json . get_error_message ( ) . utf8 ( ) . get_data ( ) ,  false ,  ERR_HANDLER_SCRIPT ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										p_state - > json  =  json . get_data ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-10 00:18:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_asset_header ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									document_extensions . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  all_document_extensions )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  ext - > import_preflight ( p_state ,  p_state - > json [ " extensionsUsed " ] ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( err  = =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											document_extensions . push_back ( ext ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-04-05 14:09:59 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_gltf_state ( p_state ,  p_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Dictionary  _serialize_texture_transform_uv ( Vector2  p_offset ,  Vector2  p_scale )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  texture_transform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  is_offset  =  p_offset  ! =  Vector2 ( 0.0 ,  0.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( is_offset )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Array  offset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										offset . resize ( 2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										offset [ 0 ]  =  p_offset . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										offset [ 1 ]  =  p_offset . y ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										texture_transform [ " offset " ]  =  offset ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									bool  is_scaled  =  p_scale  ! =  Vector2 ( 1.0 ,  1.0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( is_scaled )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										Array  scale ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										scale . resize ( 2 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										scale [ 0 ]  =  p_scale . x ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										scale [ 1 ]  =  p_scale . y ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										texture_transform [ " scale " ]  =  scale ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  extension ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Note: Godot doesn't support texture rotation.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( is_offset  | |  is_scaled )  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										extension [ " KHR_texture_transform " ]  =  texture_transform ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  extension ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Dictionary  GLTFDocument : : _serialize_texture_transform_uv1 ( Ref < BaseMaterial3D >  p_material )  {  
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_material . is_null ( ) ,  Dictionary ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector3  offset  =  p_material - > get_uv1_offset ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  scale  =  p_material - > get_uv1_scale ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _serialize_texture_transform_uv ( Vector2 ( offset . x ,  offset . y ) ,  Vector2 ( scale . x ,  scale . y ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-07-23 18:52:46 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Dictionary  GLTFDocument : : _serialize_texture_transform_uv2 ( Ref < BaseMaterial3D >  p_material )  {  
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_material . is_null ( ) ,  Dictionary ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-23 15:29:01 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Vector3  offset  =  p_material - > get_uv2_offset ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector3  scale  =  p_material - > get_uv2_scale ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _serialize_texture_transform_uv ( Vector2 ( offset . x ,  offset . y ) ,  Vector2 ( scale . x ,  scale . y ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-10 00:18:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_asset_header ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									const  String  version  =  " 2.0 " ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-16 17:16:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > major_version  =  version . get_slicec ( ' . ' ,  0 ) . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > minor_version  =  version . get_slicec ( ' . ' ,  1 ) . to_int ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Dictionary  asset ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									asset [ " version " ]  =  version ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-10 00:18:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > copyright . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										asset [ " copyright " ]  =  p_state - > copyright ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-03 22:27:29 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  hash  =  String ( GODOT_VERSION_HASH ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									asset [ " generator " ]  =  String ( GODOT_VERSION_FULL_NAME )  +  String ( " @ " )  +  ( hash . is_empty ( )  ?  String ( " unknown " )  :  hash ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > json [ " asset " ]  =  asset ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! asset . has ( " version " ) ,  Error : : FAILED ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( ! p_state - > json . has ( " asset " ) ,  Error : : FAILED ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _serialize_file ( Ref < GLTFState >  p_state ,  const  String  p_path )  {  
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									Error  err  =  FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_path . to_lower ( ) . ends_with ( " glb " ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _encode_buffer_glb ( p_state ,  p_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < FileAccess >  file  =  FileAccess : : open ( p_path ,  FileAccess : : WRITE ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( file . is_null ( ) ,  FAILED ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										String  json  =  Variant ( p_state - > json ) . to_json_string ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  uint32_t  magic  =  0x46546C67 ;  // GLTF
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  int32_t  header_size  =  12 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  int32_t  chunk_header_size  =  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										CharString  cs  =  json . utf8 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  uint32_t  text_data_length  =  cs . length ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  uint32_t  text_chunk_length  =  ( ( text_data_length  +  3 )  &  ( ~ 3 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										const  uint32_t  text_chunk_type  =  0x4E4F534A ;  //JSON
 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										uint32_t  binary_data_length  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_state - > buffers . size ( )  >  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											binary_data_length  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										const  uint32_t  binary_chunk_length  =  ( ( binary_data_length  +  3 )  &  ( ~ 3 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  uint32_t  binary_chunk_type  =  0x004E4942 ;  //BIN
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										file - > create ( FileAccess : : ACCESS_RESOURCES ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_32 ( magic ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_32 ( p_state - > major_version ) ;  // version
 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										uint32_t  total_length  =  header_size  +  chunk_header_size  +  text_chunk_length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( binary_chunk_length )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											total_length  + =  chunk_header_size  +  binary_chunk_length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_32 ( total_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Write the JSON text chunk.
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										file - > store_32 ( text_chunk_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_32 ( text_chunk_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_buffer ( ( uint8_t  * ) & cs [ 0 ] ,  cs . length ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( uint32_t  pad_i  =  text_data_length ;  pad_i  <  text_chunk_length ;  pad_i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											file - > store_8 ( '   ' ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										// Write a single binary chunk.
 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										if  ( binary_chunk_length )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											file - > store_32 ( binary_chunk_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											file - > store_32 ( binary_chunk_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											file - > store_buffer ( p_state - > buffers [ 0 ] . ptr ( ) ,  binary_data_length ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											for  ( uint32_t  pad_i  =  binary_data_length ;  pad_i  <  binary_chunk_length ;  pad_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												file - > store_8 ( 0 ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-25 20:14:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _encode_buffer_bins ( p_state ,  p_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										Ref < FileAccess >  file  =  FileAccess : : open ( p_path ,  FileAccess : : WRITE ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( file . is_null ( ) ,  FAILED ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										file - > create ( FileAccess : : ACCESS_RESOURCES ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										String  json  =  Variant ( p_state - > json ) . to_json_string ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										file - > store_string ( json ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2020-12-21 07:39:32 -08:00 
										
									 
								 
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2021-09-10 00:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  GLTFDocument : : _bind_methods ( )  {  
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( ROOT_NODE_MODE_SINGLE_ROOT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( ROOT_NODE_MODE_KEEP_ROOT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( ROOT_NODE_MODE_MULTI_ROOT ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( VISIBILITY_MODE_INCLUDE_REQUIRED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( VISIBILITY_MODE_INCLUDE_OPTIONAL ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									BIND_ENUM_CONSTANT ( VISIBILITY_MODE_EXCLUDE ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_image_format " ,  " image_format " ) ,  & GLTFDocument : : set_image_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_image_format " ) ,  & GLTFDocument : : get_image_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_lossy_quality " ,  " lossy_quality " ) ,  & GLTFDocument : : set_lossy_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_lossy_quality " ) ,  & GLTFDocument : : get_lossy_quality ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_fallback_image_format " ,  " fallback_image_format " ) ,  & GLTFDocument : : set_fallback_image_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_fallback_image_format " ) ,  & GLTFDocument : : get_fallback_image_format ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_fallback_image_quality " ,  " fallback_image_quality " ) ,  & GLTFDocument : : set_fallback_image_quality ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_fallback_image_quality " ) ,  & GLTFDocument : : get_fallback_image_quality ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_root_node_mode " ,  " root_node_mode " ) ,  & GLTFDocument : : set_root_node_mode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_root_node_mode " ) ,  & GLTFDocument : : get_root_node_mode ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " set_visibility_mode " ,  " visibility_mode " ) ,  & GLTFDocument : : set_visibility_mode ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " get_visibility_mode " ) ,  & GLTFDocument : : get_visibility_mode ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-15 04:14:52 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " append_from_file " ,  " path " ,  " state " ,  " flags " ,  " base_path " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : append_from_file ,  DEFVAL ( 0 ) ,  DEFVAL ( String ( ) ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " append_from_buffer " ,  " bytes " ,  " base_path " ,  " state " ,  " flags " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : append_from_buffer ,  DEFVAL ( 0 ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " append_from_scene " ,  " node " ,  " state " ,  " flags " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : append_from_scene ,  DEFVAL ( 0 ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-01-30 08:49:55 +09:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " generate_scene " ,  " state " ,  " bake_fps " ,  " trimming " ,  " remove_immutable_tracks " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : generate_scene ,  DEFVAL ( 30 ) ,  DEFVAL ( false ) ,  DEFVAL ( true ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " generate_buffer " ,  " state " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : generate_buffer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_method ( D_METHOD ( " write_to_filesystem " ,  " state " ,  " path " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : write_to_filesystem ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : STRING ,  " image_format " ) ,  " set_image_format " ,  " get_image_format " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " lossy_quality " ) ,  " set_lossy_quality " ,  " get_lossy_quality " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-29 15:36:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : STRING ,  " fallback_image_format " ) ,  " set_fallback_image_format " ,  " get_fallback_image_format " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : FLOAT ,  " fallback_image_quality " ) ,  " set_fallback_image_quality " ,  " get_fallback_image_quality " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 22:36:57 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : INT ,  " root_node_mode " ) ,  " set_root_node_mode " ,  " get_root_node_mode " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ADD_PROPERTY ( PropertyInfo ( Variant : : INT ,  " visibility_mode " ) ,  " set_visibility_mode " ,  " get_visibility_mode " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-16 01:03:49 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:19:12 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " GLTFDocument " ,  D_METHOD ( " import_object_model_property " ,  " state " ,  " json_pointer " ) ,  & GLTFDocument : : import_object_model_property ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " GLTFDocument " ,  D_METHOD ( " export_object_model_property " ,  " state " ,  " node_path " ,  " godot_node " ,  " gltf_node_index " ) ,  & GLTFDocument : : export_object_model_property ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " GLTFDocument " ,  D_METHOD ( " register_gltf_document_extension " ,  " extension " ,  " first_priority " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : register_gltf_document_extension ,  DEFVAL ( false ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-22 21:07:56 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " GLTFDocument " ,  D_METHOD ( " unregister_gltf_document_extension " ,  " extension " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : unregister_gltf_document_extension ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-28 17:46:01 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ClassDB : : bind_static_method ( " GLTFDocument " ,  D_METHOD ( " get_supported_gltf_extensions " ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											& GLTFDocument : : get_supported_gltf_extensions ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-10 00:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2025-01-08 11:56:49 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : _build_parent_hierarchy ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2021-09-10 00:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// build the hierarchy
 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( GLTFNodeIndex  node_i  =  0 ;  node_i  <  p_state - > nodes . size ( ) ;  node_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  j  =  0 ;  j  <  p_state - > nodes [ node_i ] - > children . size ( ) ;  j + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											GLTFNodeIndex  child_i  =  p_state - > nodes [ node_i ] - > children [ j ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_FAIL_INDEX ( child_i ,  p_state - > nodes . size ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( p_state - > nodes . write [ child_i ] - > parent  ! =  - 1 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-10 00:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
												continue ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											p_state - > nodes . write [ child_i ] - > parent  =  node_i ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-10 00:54:10 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Ref < GLTFDocumentExtension > >  GLTFDocument : : all_document_extensions ;  
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : register_gltf_document_extension ( Ref < GLTFDocumentExtension >  p_extension ,  bool  p_first_priority )  {  
						 
					
						
							
								
									
										
										
										
											2024-05-06 16:20:20 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! all_document_extensions . has ( p_extension ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( p_first_priority )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											all_document_extensions . insert ( 0 ,  p_extension ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											all_document_extensions . push_back ( p_extension ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-11-22 21:07:56 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : unregister_gltf_document_extension ( Ref < GLTFDocumentExtension >  p_extension )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									all_document_extensions . erase ( p_extension ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : unregister_all_gltf_document_extensions ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									all_document_extensions . clear ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-09-20 18:24:31 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-09-26 12:01:26 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < Ref < GLTFDocumentExtension > >  GLTFDocument : : get_all_gltf_document_extensions ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  all_document_extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-08-28 17:46:01 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Vector < String >  GLTFDocument : : get_supported_gltf_extensions ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									HashSet < String >  set  =  get_supported_gltf_extensions_hashset ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Vector < String >  vec ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( const  String  & s  :  set )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										vec . append ( s ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									vec . sort ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  vec ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								HashSet < String >  GLTFDocument : : get_supported_gltf_extensions_hashset ( )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									HashSet < String >  supported_extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// If the extension is supported directly in GLTFDocument, list it here.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Other built-in extensions are supported by GLTFDocumentExtension classes.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									supported_extensions . insert ( " GODOT_single_root " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-04 00:37:44 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_animation_pointer " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-28 17:46:01 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_lights_punctual " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_materials_emissive_strength " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_materials_pbrSpecularGlossiness " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_materials_unlit " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_node_visibility " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-28 17:46:01 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									supported_extensions . insert ( " KHR_texture_transform " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  all_document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < String >  ext_supported_extensions  =  ext - > get_supported_extensions ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  ext_supported_extensions . size ( ) ;  + + i )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											supported_extensions . insert ( ext_supported_extensions [ i ] ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  supported_extensions ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								PackedByteArray  GLTFDocument : : _serialize_glb_buffer ( Ref < GLTFState >  p_state ,  Error  * r_err )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  _encode_buffer_glb ( p_state ,  " " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( r_err )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										* r_err  =  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  PackedByteArray ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  json  =  Variant ( p_state - > json ) . to_json_string ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint32_t  magic  =  0x46546C67 ;  // GLTF
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int32_t  header_size  =  12 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int32_t  chunk_header_size  =  8 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									CharString  cs  =  json . utf8 ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-12-01 11:05:53 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									int32_t  padding  =  ( chunk_header_size  +  cs . length ( ) )  %  4 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint32_t  text_chunk_length  =  cs . length ( )  +  padding ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  uint32_t  text_chunk_type  =  0x4E4F534A ;  //JSON
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int32_t  binary_data_length  =  0 ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-09 22:23:16 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > buffers . size ( )  >  0 )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										binary_data_length  =  p_state - > buffers [ 0 ] . size ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int32_t  binary_chunk_length  =  binary_data_length ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  int32_t  binary_chunk_type  =  0x004E4942 ;  //BIN
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < StreamPeerBuffer >  buffer ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buffer . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buffer - > put_32 ( magic ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									buffer - > put_32 ( p_state - > major_version ) ;  // version
 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									buffer - > put_32 ( header_size  +  chunk_header_size  +  text_chunk_length  +  chunk_header_size  +  binary_data_length ) ;  // length
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buffer - > put_32 ( text_chunk_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buffer - > put_32 ( text_chunk_type ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									buffer - > put_data ( ( uint8_t  * ) & cs [ 0 ] ,  cs . length ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-12-01 11:05:53 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  padding ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffer - > put_8 ( '   ' ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( binary_chunk_length )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffer - > put_32 ( binary_chunk_length ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										buffer - > put_32 ( binary_chunk_type ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										buffer - > put_data ( p_state - > buffers [ 0 ] . ptr ( ) ,  binary_data_length ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  buffer - > get_data_array ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 21:59:39 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Node  * GLTFDocument : : _generate_scene_node_tree ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2023-08-20 15:21:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Generate the skeletons and skins (if any).
 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									HashMap < ObjectID ,  SkinSkeletonIndex >  skeleton_map ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  SkinTool : : _create_skeletons ( p_state - > unique_names ,  p_state - > skins ,  p_state - > nodes , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											skeleton_map ,  p_state - > skeletons ,  p_state - > scene_nodes ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( err  ! =  OK ,  nullptr ,  " glTF: Failed to create skeletons. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-20 15:21:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _create_skins ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( err  ! =  OK ,  nullptr ,  " glTF: Failed to create skins. " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-02 03:27:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Run pre-generate for each extension, in case an extension needs to do something before generating the scene.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  ext - > import_pre_generate ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-20 15:21:12 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Generate the node tree.
 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 22:36:57 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Node  * single_root ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( p_state - > extensions_used . has ( " GODOT_single_root " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_generate_scene_node ( p_state ,  0 ,  nullptr ,  nullptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										single_root  =  p_state - > scene_nodes [ 0 ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-04-17 04:11:16 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( single_root  & &  single_root - > get_owner ( )  & &  single_root - > get_owner ( )  ! =  single_root )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											single_root  =  single_root - > get_owner ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-22 22:36:57 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										single_root  =  memnew ( Node3D ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int32_t  root_i  =  0 ;  root_i  <  p_state - > root_nodes . size ( ) ;  root_i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_generate_scene_node ( p_state ,  p_state - > root_nodes [ root_i ] ,  single_root ,  single_root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 21:59:39 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Assign the scene name and single root name to each other
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// if one is missing, or do nothing if both are already set.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( unlikely ( p_state - > scene_name . is_empty ( ) ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > scene_name  =  single_root - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  if  ( single_root - > get_name ( )  = =  StringName ( ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2023-10-31 17:55:15 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										if  ( _naming_version  = =  0 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											single_root - > set_name ( p_state - > scene_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											single_root - > set_name ( _gen_unique_name ( p_state ,  p_state - > scene_name ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-21 21:59:39 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  single_root ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-07-10 00:18:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_asset_header ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! p_state - > json . has ( " asset " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  ERR_PARSE_ERROR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Dictionary  asset  =  p_state - > json [ " asset " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! asset . has ( " version " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  ERR_PARSE_ERROR ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									String  version  =  asset [ " version " ] ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-11-16 17:16:07 +01:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > major_version  =  version . get_slicec ( ' . ' ,  0 ) . to_int ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									p_state - > minor_version  =  version . get_slicec ( ' . ' ,  1 ) . to_int ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-07-10 00:18:55 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( asset . has ( " copyright " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > copyright  =  asset [ " copyright " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_gltf_state ( Ref < GLTFState >  p_state ,  const  String  & p_search_path )  {  
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									/* PARSE EXTENSIONS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_gltf_extensions ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									/* PARSE SCENE */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_scenes ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE NODES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_nodes ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE BUFFERS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_buffers ( p_state ,  p_search_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE BUFFER VIEWS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_buffer_views ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE ACCESSORS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_accessors ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( ! p_state - > discard_meshes_and_materials )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										/* PARSE IMAGES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _parse_images ( p_state ,  p_search_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										/* PARSE TEXTURE SAMPLERS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _parse_texture_samplers ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-04 10:49:42 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										/* PARSE TEXTURES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _parse_textures ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										/* PARSE TEXTURES */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  _parse_materials ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-04-13 05:14:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE SKINS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_skins ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* DETERMINE SKELETONS */ 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-25 00:36:39 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  SkinTool : : _determine_skeletons ( p_state - > skins ,  p_state - > nodes ,  p_state - > skeletons ,  p_state - > get_import_as_skeleton_bones ( )  ?  p_state - > root_nodes  :  Vector < GLTFNodeIndex > ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-07-10 01:26:35 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* ASSIGN SCENE NODE NAMES */ 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// This must be run AFTER determining skeletons, and BEFORE parsing animations.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_assign_node_names ( p_state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE MESHES (we have enough info now) */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_meshes ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE LIGHTS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_lights ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE CAMERAS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_cameras ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									/* PARSE ANIMATIONS */ 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse_animations ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								PackedByteArray  GLTFDocument : : generate_buffer ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFState >  state  =  p_state ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( state . is_null ( ) ,  PackedByteArray ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// For buffers, set the state filename to an empty string, but
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// don't touch the base path, in case the user set it manually.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > filename  =  " " ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  _serialize ( state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  PackedByteArray ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									PackedByteArray  bytes  =  _serialize_glb_buffer ( state ,  & err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  bytes ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Error  GLTFDocument : : write_to_filesystem ( Ref < GLTFState >  p_state ,  const  String  & p_path )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFState >  state  =  p_state ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( state . is_null ( ) ,  ERR_INVALID_PARAMETER ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-30 02:36:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									state - > set_base_path ( p_path . get_base_dir ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									state - > filename  =  p_path . get_file ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  _serialize ( state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  err ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									err  =  _serialize_file ( state ,  p_path ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( err  ! =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										return  Error : : FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Node  * GLTFDocument : : generate_scene ( Ref < GLTFState >  p_state ,  float  p_bake_fps ,  bool  p_trimming ,  bool  p_remove_immutable_tracks )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFState >  state  =  p_state ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( state . is_null ( ) ,  nullptr ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_INDEX_V ( 0 ,  state - > root_nodes . size ( ) ,  nullptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									p_state - > set_bake_fps ( p_bake_fps ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Node  * root  =  _generate_scene_node_tree ( state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( root ,  nullptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_process_mesh_instances ( state ,  root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( state - > get_create_animations ( )  & &  state - > animations . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										AnimationPlayer  * ap  =  memnew ( AnimationPlayer ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										root - > add_child ( ap ,  true ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ap - > set_owner ( root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  state - > animations . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-05-23 08:40:26 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											_import_animation ( state ,  ap ,  i ,  p_trimming ,  p_remove_immutable_tracks ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( KeyValue < GLTFNodeIndex ,  Node  * >  E  :  state - > scene_nodes )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ! E . value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Dictionary  node_json ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											if  ( state - > json . has ( " nodes " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												Array  nodes  =  state - > json [ " nodes " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												if  ( 0  < =  E . key  & &  E . key  <  nodes . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
													node_json  =  nodes [ E . key ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
												} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											Ref < GLTFNode >  gltf_node  =  state - > nodes [ E . key ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											err  =  ext - > import_node ( p_state ,  gltf_node ,  node_json ,  E . value ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-09 23:53:58 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ImporterMeshInstance3D  * root_importer_mesh  =  Object : : cast_to < ImporterMeshInstance3D > ( root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( unlikely ( root_importer_mesh ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										root  =  GLTFDocumentExtensionConvertImporterMesh : : convert_importer_mesh_instance_3d ( root_importer_mesh ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										memdelete ( root_importer_mesh ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  ext - > import_post ( p_state ,  root ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( root ,  nullptr ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  root ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Error  GLTFDocument : : append_from_scene ( Node  * p_node ,  Ref < GLTFState >  p_state ,  uint32_t  p_flags )  {  
						 
					
						
							
								
									
										
										
										
											2024-04-10 17:05:54 -04:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_NULL_V ( p_node ,  FAILED ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFState >  state  =  p_state ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( state . is_null ( ) ,  FAILED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > use_named_skin_binds  =  p_flags  &  GLTF_IMPORT_USE_NAMED_SKIN_BINDS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > discard_meshes_and_materials  =  p_flags  &  GLTF_IMPORT_DISCARD_MESHES_AND_MATERIALS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > force_generate_tangents  =  p_flags  &  GLTF_IMPORT_GENERATE_TANGENT_ARRAYS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > force_disable_compression  =  p_flags  &  GLTF_IMPORT_FORCE_DISABLE_MESH_COMPRESSION ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( ! state - > buffers . size ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										state - > buffers . push_back ( Vector < uint8_t > ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Perform export preflight for document extensions. Only extensions that
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// return OK will be used for the rest of the export steps.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									document_extensions . clear ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  all_document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Error  err  =  ext - > export_preflight ( state ,  p_node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( err  = =  OK )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											document_extensions . push_back ( ext ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// Add the root node(s) and their descendants to the state.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( _root_node_mode  = =  RootNodeMode : : ROOT_NODE_MODE_MULTI_ROOT )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										const  int  child_count  =  p_node - > get_child_count ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-27 22:02:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										for  ( int  i  =  0 ;  i  <  child_count ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											_convert_scene_node ( state ,  p_node - > get_child ( i ) ,  - 1 ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2025-03-27 22:02:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										state - > scene_name  =  p_node - > get_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( _root_node_mode  = =  RootNodeMode : : ROOT_NODE_MODE_SINGLE_ROOT )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											state - > extensions_used . append ( " GODOT_single_root " ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										_convert_scene_node ( state ,  p_node ,  - 1 ,  - 1 ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-09-02 03:27:06 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// Run post-convert for each extension, in case an extension needs to do something after converting the scene.
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Error  err  =  ext - > export_post_convert ( p_state ,  p_node ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( err  ! =  OK ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								Error  GLTFDocument : : append_from_buffer ( PackedByteArray  p_bytes ,  String  p_base_path ,  Ref < GLTFState >  p_state ,  uint32_t  p_flags )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < GLTFState >  state  =  p_state ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( state . is_null ( ) ,  FAILED ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									// TODO Add missing texture and missing .bin file paths to r_missing_deps 2021-09-10 fire
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Error  err  =  FAILED ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > use_named_skin_binds  =  p_flags  &  GLTF_IMPORT_USE_NAMED_SKIN_BINDS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > discard_meshes_and_materials  =  p_flags  &  GLTF_IMPORT_DISCARD_MESHES_AND_MATERIALS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > force_generate_tangents  =  p_flags  &  GLTF_IMPORT_GENERATE_TANGENT_ARRAYS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > force_disable_compression  =  p_flags  &  GLTF_IMPORT_FORCE_DISABLE_MESH_COMPRESSION ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									Ref < FileAccessMemory >  file_access ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									file_access . instantiate ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									file_access - > open_custom ( p_bytes . ptr ( ) ,  p_bytes . size ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-30 02:36:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									state - > set_base_path ( p_base_path . get_base_dir ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse ( p_state ,  state - > base_path ,  file_access ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										err  =  ext - > import_post_parse ( state ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : append_from_file ( String  p_path ,  Ref < GLTFState >  p_state ,  uint32_t  p_flags ,  String  p_base_path )  {  
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < GLTFState >  state  =  p_state ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									// TODO Add missing texture and missing .bin file paths to r_missing_deps 2021-09-10 fire
 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( state  = =  Ref < GLTFState > ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										state . instantiate ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-30 02:36:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									state - > set_filename ( p_path . get_file ( ) . get_basename ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									state - > use_named_skin_binds  =  p_flags  &  GLTF_IMPORT_USE_NAMED_SKIN_BINDS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > discard_meshes_and_materials  =  p_flags  &  GLTF_IMPORT_DISCARD_MESHES_AND_MATERIALS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > force_generate_tangents  =  p_flags  &  GLTF_IMPORT_GENERATE_TANGENT_ARRAYS ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									state - > force_disable_compression  =  p_flags  &  GLTF_IMPORT_FORCE_DISABLE_MESH_COMPRESSION ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-29 21:04:32 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  err ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Ref < FileAccess >  file  =  FileAccess : : open ( p_path ,  FileAccess : : READ ,  & err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-30 23:42:10 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V_MSG ( err  ! =  OK ,  err ,  vformat ( R " (Can't open file at path  " % s " ) " ,  p_path ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( file . is_null ( ) ,  ERR_FILE_CANT_OPEN ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-12-13 21:34:18 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									String  base_path  =  p_base_path ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									if  ( base_path . is_empty ( ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										base_path  =  p_path . get_base_dir ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-10-30 02:36:47 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									state - > set_base_path ( base_path ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									err  =  _parse ( p_state ,  base_path ,  file ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( Ref < GLTFDocumentExtension >  ext  :  document_extensions )  { 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_CONTINUE ( ext . is_null ( ) ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2023-08-03 01:18:45 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										err  =  ext - > import_post_parse ( p_state ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-04-09 02:35:50 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
										ERR_FAIL_COND_V ( err  ! =  OK ,  err ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2021-10-19 09:06:23 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								Error  GLTFDocument : : _parse_gltf_extensions ( Ref < GLTFState >  p_state )  {  
						 
					
						
							
								
									
										
										
										
											2024-07-26 11:52:26 +02:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									ERR_FAIL_COND_V ( p_state . is_null ( ) ,  ERR_PARSE_ERROR ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > json . has ( " extensionsUsed " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < String >  ext_array  =  p_state - > json [ " extensionsUsed " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > extensions_used  =  ext_array ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:06:23 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									if  ( p_state - > json . has ( " extensionsRequired " ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										Vector < String >  ext_array  =  p_state - > json [ " extensionsRequired " ] ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										p_state - > extensions_required  =  ext_array ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-17 22:06:23 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-28 17:46:01 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									HashSet < String >  supported_extensions  =  get_supported_gltf_extensions_hashset ( ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-11-22 09:29:56 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									Error  ret  =  OK ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-12-10 15:05:13 -06:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
									for  ( int  i  =  0 ;  i  <  p_state - > extensions_required . size ( ) ;  i + + )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! supported_extensions . has ( p_state - > extensions_required [ i ] ) )  { 
							 
						 
					
						
							
								
									
										
										
										
											2024-08-15 18:07:30 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ERR_PRINT ( " glTF: Can't import file ' "  +  p_state - > filename  +  " ', required extension ' "  +  String ( p_state - > extensions_required [ i ] )  +  " ' is not supported. Are you missing a GLTFDocumentExtension plugin? " ) ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-09-18 20:35:13 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
											ret  =  ERR_UNAVAILABLE ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  ret ; 
							 
						 
					
						
							
								
									
										
										
										
											2022-01-07 19:01:09 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2023-07-22 22:36:57 -05:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								void  GLTFDocument : : set_root_node_mode ( GLTFDocument : : RootNodeMode  p_root_node_mode )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_root_node_mode  =  p_root_node_mode ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								GLTFDocument : : RootNodeMode  GLTFDocument : : get_root_node_mode ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _root_node_mode ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-06-28 14:06:29 -07:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								void  GLTFDocument : : set_visibility_mode ( VisibilityMode  p_visibility_mode )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									_visibility_mode  =  p_visibility_mode ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								GLTFDocument : : VisibilityMode  GLTFDocument : : get_visibility_mode ( )  const  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  _visibility_mode ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2024-02-16 05:25:15 -08:00 
										
									 
								 
							 
							
								
									
										 
								
							 
							
								 
							
							
								String  GLTFDocument : : _gen_unique_name_static ( HashSet < String >  & r_unique_names ,  const  String  & p_name )  {  
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									const  String  s_name  =  p_name . validate_node_name ( ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									String  u_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									int  index  =  1 ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									while  ( true )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										u_name  =  s_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( index  >  1 )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											u_name  + =  itos ( index ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										if  ( ! r_unique_names . has ( u_name ) )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
											break ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
										index + + ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									r_unique_names . insert ( u_name ) ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
									return  u_name ; 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							
							
								}