Browse Source

Merge pull request #53813 from reduz/editor-import-plugins

Rémi Verschelde 3 years ago
parent
commit
55c71ba1a3

+ 21 - 7
doc/classes/EditorPlugin.xml

@@ -381,7 +381,7 @@
 			<argument index="0" name="importer" type="EditorImportPlugin" />
 			<argument index="0" name="importer" type="EditorImportPlugin" />
 			<description>
 			<description>
 				Registers a new [EditorImportPlugin]. Import plugins are used to import custom and unsupported assets as a custom [Resource] type.
 				Registers a new [EditorImportPlugin]. Import plugins are used to import custom and unsupported assets as a custom [Resource] type.
-				[b]Note:[/b] If you want to import custom 3D asset formats use [method add_scene_import_plugin] instead.
+				[b]Note:[/b] If you want to import custom 3D asset formats use [method add_scene_format_importer_plugin] instead.
 				See [method add_inspector_plugin] for an example of how to register a plugin.
 				See [method add_inspector_plugin] for an example of how to register a plugin.
 			</description>
 			</description>
 		</method>
 		</method>
@@ -405,11 +405,18 @@
 				[/codeblocks]
 				[/codeblocks]
 			</description>
 			</description>
 		</method>
 		</method>
-		<method name="add_scene_import_plugin">
+		<method name="add_scene_format_importer_plugin">
 			<return type="void" />
 			<return type="void" />
-			<argument index="0" name="scene_importer" type="EditorSceneImporter" />
+			<argument index="0" name="scene_format_importer" type="EditorSceneFormatImporter" />
 			<description>
 			<description>
-				Registers a new [EditorSceneImporter]. Scene importers are used to import custom 3D asset formats as scenes.
+				Registers a new [EditorSceneFormatImporter]. Scene importers are used to import custom 3D asset formats as scenes.
+			</description>
+		</method>
+		<method name="add_scene_post_import_plugin">
+			<return type="void" />
+			<argument index="0" name="scene_import_plugin" type="EditorScenePostImportPlugin" />
+			<description>
+				Add a [EditorScenePostImportPlugin]. These plugins allow customizing the import process of 3D assets by adding new options to the import dialogs.
 			</description>
 			</description>
 		</method>
 		</method>
 		<method name="add_spatial_gizmo_plugin">
 		<method name="add_spatial_gizmo_plugin">
@@ -553,11 +560,18 @@
 				Removes an inspector plugin registered by [method add_import_plugin]
 				Removes an inspector plugin registered by [method add_import_plugin]
 			</description>
 			</description>
 		</method>
 		</method>
-		<method name="remove_scene_import_plugin">
+		<method name="remove_scene_format_importer_plugin">
+			<return type="void" />
+			<argument index="0" name="scene_format_importer" type="EditorSceneFormatImporter" />
+			<description>
+				Removes a scene format importer registered by [method add_scene_format_importer_plugin].
+			</description>
+		</method>
+		<method name="remove_scene_post_import_plugin">
 			<return type="void" />
 			<return type="void" />
-			<argument index="0" name="scene_importer" type="EditorSceneImporter" />
+			<argument index="0" name="scene_import_plugin" type="EditorScenePostImportPlugin" />
 			<description>
 			<description>
-				Removes a scene importer registered by [method add_scene_import_plugin].
+				Remove the [EditorScenePostImportPlugin], added with [method add_scene_post_import_plugin].
 			</description>
 			</description>
 		</method>
 		</method>
 		<method name="remove_spatial_gizmo_plugin">
 		<method name="remove_spatial_gizmo_plugin">

+ 1 - 1
doc/classes/EditorSceneImporter.xml → doc/classes/EditorSceneFormatImporter.xml

@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="UTF-8" ?>
 <?xml version="1.0" encoding="UTF-8" ?>
-<class name="EditorSceneImporter" inherits="RefCounted" version="4.0">
+<class name="EditorSceneFormatImporter" inherits="RefCounted" version="4.0">
 	<brief_description>
 	<brief_description>
 		Imports scenes from third-parties' 3D files.
 		Imports scenes from third-parties' 3D files.
 	</brief_description>
 	</brief_description>

+ 1 - 1
modules/fbx/doc_classes/EditorSceneImporterFBX.xml → doc/classes/EditorSceneFormatImporterFBX.xml

@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="UTF-8" ?>
 <?xml version="1.0" encoding="UTF-8" ?>
-<class name="EditorSceneImporterFBX" inherits="EditorSceneImporter" version="4.0">
+<class name="EditorSceneFormatImporterFBX" inherits="EditorSceneFormatImporter" version="4.0">
 	<brief_description>
 	<brief_description>
 		FBX 3D asset importer.
 		FBX 3D asset importer.
 	</brief_description>
 	</brief_description>

+ 1 - 1
modules/gltf/doc_classes/EditorSceneImporterGLTF.xml → doc/classes/EditorSceneFormatImporterGLTF.xml

@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="UTF-8" ?>
 <?xml version="1.0" encoding="UTF-8" ?>
-<class name="EditorSceneImporterGLTF" inherits="EditorSceneImporter" version="4.0">
+<class name="EditorSceneFormatImporterGLTF" inherits="EditorSceneFormatImporter" version="4.0">
 	<brief_description>
 	<brief_description>
 	</brief_description>
 	</brief_description>
 	<description>
 	<description>

+ 116 - 0
doc/classes/EditorScenePostImportPlugin.xml

@@ -0,0 +1,116 @@
+<?xml version="1.0" encoding="UTF-8" ?>
+<class name="EditorScenePostImportPlugin" inherits="RefCounted" version="4.0">
+	<brief_description>
+		Plugin to control and modifying the process of importing a scene.
+	</brief_description>
+	<description>
+		This plugin type exists to modify the process of importing scenes, allowing to change the content as well as add importer options at every stage of the process.
+	</description>
+	<tutorials>
+	</tutorials>
+	<methods>
+		<method name="_get_import_options" qualifiers="virtual">
+			<return type="void" />
+			<description>
+				Override to add general import options. These will appear in the main import dock on the editor. Add options via [method add_import_option] and [method add_import_option_advanced].
+			</description>
+		</method>
+		<method name="_get_internal_import_options" qualifiers="virtual">
+			<return type="void" />
+			<argument index="0" name="category" type="int" />
+			<description>
+				Override to add internal import options. These will appear in the 3D scene import dialog. Add options via [method add_import_option] and [method add_import_option_advanced].
+			</description>
+		</method>
+		<method name="_get_internal_option_update_view_required" qualifiers="virtual const">
+			<return type="Variant" />
+			<argument index="0" name="category" type="int" />
+			<argument index="1" name="option" type="String" />
+			<description>
+				Return true whether updating the 3D view of the import dialog needs to be updated if an option has changed.
+			</description>
+		</method>
+		<method name="_get_internal_option_visibility" qualifiers="virtual const">
+			<return type="Variant" />
+			<argument index="0" name="category" type="int" />
+			<argument index="1" name="option" type="String" />
+			<description>
+				Return true or false whether a given option should be visible. Return null to ignore.
+			</description>
+		</method>
+		<method name="_get_option_visibility" qualifiers="virtual const">
+			<return type="Variant" />
+			<argument index="0" name="option" type="String" />
+			<description>
+				Return true or false whether a given option should be visible. Return null to ignore.
+			</description>
+		</method>
+		<method name="_internal_process" qualifiers="virtual">
+			<return type="void" />
+			<argument index="0" name="category" type="int" />
+			<argument index="1" name="base_node" type="Node" />
+			<argument index="2" name="node" type="Node" />
+			<argument index="3" name="resource" type="Resource" />
+			<description>
+				Process a specific node or resource for a given category.
+			</description>
+		</method>
+		<method name="_post_process" qualifiers="virtual">
+			<return type="void" />
+			<argument index="0" name="scene" type="Node" />
+			<description>
+				Post process the scene. This function is called after the final scene has been configured.
+			</description>
+		</method>
+		<method name="_pre_process" qualifiers="virtual">
+			<return type="void" />
+			<argument index="0" name="scene" type="Node" />
+			<description>
+				Pre Process the scene. This function is called right after the scene format loader loaded the scene and no changes have been made.
+			</description>
+		</method>
+		<method name="add_import_option">
+			<return type="void" />
+			<argument index="0" name="name" type="String" />
+			<argument index="1" name="value" type="Variant" />
+			<description>
+				Add a specific import option (name and default value only). This function can only be called from [method _get_import_options] and [method _get_internal_import_options].
+			</description>
+		</method>
+		<method name="add_import_option_advanced">
+			<return type="void" />
+			<argument index="0" name="type" type="int" enum="Variant.Type" />
+			<argument index="1" name="name" type="String" />
+			<argument index="2" name="default_value" type="Variant" />
+			<argument index="3" name="hint" type="int" enum="PropertyHint" default="0" />
+			<argument index="4" name="hint_string" type="String" default="&quot;&quot;" />
+			<argument index="5" name="usage_flags" type="int" default="7" />
+			<description>
+				Add a specific import option. This function can only be called from [method _get_import_options] and [method _get_internal_import_options].
+			</description>
+		</method>
+		<method name="get_option_value" qualifiers="const">
+			<return type="Variant" />
+			<argument index="0" name="name" type="StringName" />
+			<description>
+				Query the value of an option. This function can only be called from those querying visibility, or processing.
+			</description>
+		</method>
+	</methods>
+	<constants>
+		<constant name="INTERNAL_IMPORT_CATEGORY_NODE" value="0" enum="InternalImportCategory">
+		</constant>
+		<constant name="INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE" value="1" enum="InternalImportCategory">
+		</constant>
+		<constant name="INTERNAL_IMPORT_CATEGORY_MESH" value="2" enum="InternalImportCategory">
+		</constant>
+		<constant name="INTERNAL_IMPORT_CATEGORY_MATERIAL" value="3" enum="InternalImportCategory">
+		</constant>
+		<constant name="INTERNAL_IMPORT_CATEGORY_ANIMATION" value="4" enum="InternalImportCategory">
+		</constant>
+		<constant name="INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE" value="5" enum="InternalImportCategory">
+		</constant>
+		<constant name="INTERNAL_IMPORT_CATEGORY_MAX" value="6" enum="InternalImportCategory">
+		</constant>
+	</constants>
+</class>

+ 4 - 3
editor/editor_node.cpp

@@ -3848,7 +3848,8 @@ void EditorNode::register_editor_types() {
 	GDREGISTER_VIRTUAL_CLASS(EditorInterface);
 	GDREGISTER_VIRTUAL_CLASS(EditorInterface);
 	GDREGISTER_CLASS(EditorExportPlugin);
 	GDREGISTER_CLASS(EditorExportPlugin);
 	GDREGISTER_CLASS(EditorResourceConversionPlugin);
 	GDREGISTER_CLASS(EditorResourceConversionPlugin);
-	GDREGISTER_CLASS(EditorSceneImporter);
+	GDREGISTER_CLASS(EditorSceneFormatImporter);
+	GDREGISTER_CLASS(EditorScenePostImportPlugin);
 	GDREGISTER_CLASS(EditorInspector);
 	GDREGISTER_CLASS(EditorInspector);
 	GDREGISTER_CLASS(EditorInspectorPlugin);
 	GDREGISTER_CLASS(EditorInspectorPlugin);
 	GDREGISTER_CLASS(EditorProperty);
 	GDREGISTER_CLASS(EditorProperty);
@@ -5935,7 +5936,7 @@ EditorNode::EditorNode() {
 		ResourceFormatImporter::get_singleton()->add_importer(import_scene);
 		ResourceFormatImporter::get_singleton()->add_importer(import_scene);
 
 
 		{
 		{
-			Ref<EditorSceneImporterCollada> import_collada;
+			Ref<EditorSceneFormatImporterCollada> import_collada;
 			import_collada.instantiate();
 			import_collada.instantiate();
 			import_scene->add_importer(import_collada);
 			import_scene->add_importer(import_collada);
 
 
@@ -5943,7 +5944,7 @@ EditorNode::EditorNode() {
 			import_obj2.instantiate();
 			import_obj2.instantiate();
 			import_scene->add_importer(import_obj2);
 			import_scene->add_importer(import_obj2);
 
 
-			Ref<EditorSceneImporterESCN> import_escn;
+			Ref<EditorSceneFormatImporterESCN> import_escn;
 			import_escn.instantiate();
 			import_escn.instantiate();
 			import_scene->add_importer(import_escn);
 			import_scene->add_importer(import_escn);
 		}
 		}

+ 13 - 4
editor/editor_plugin.cpp

@@ -762,16 +762,23 @@ void EditorPlugin::remove_inspector_plugin(const Ref<EditorInspectorPlugin> &p_p
 	EditorInspector::remove_inspector_plugin(p_plugin);
 	EditorInspector::remove_inspector_plugin(p_plugin);
 }
 }
 
 
-void EditorPlugin::add_scene_import_plugin(const Ref<EditorSceneImporter> &p_importer) {
+void EditorPlugin::add_scene_format_importer_plugin(const Ref<EditorSceneFormatImporter> &p_importer) {
 	ERR_FAIL_COND(!p_importer.is_valid());
 	ERR_FAIL_COND(!p_importer.is_valid());
 	ResourceImporterScene::get_singleton()->add_importer(p_importer);
 	ResourceImporterScene::get_singleton()->add_importer(p_importer);
 }
 }
 
 
-void EditorPlugin::remove_scene_import_plugin(const Ref<EditorSceneImporter> &p_importer) {
+void EditorPlugin::remove_scene_format_importer_plugin(const Ref<EditorSceneFormatImporter> &p_importer) {
 	ERR_FAIL_COND(!p_importer.is_valid());
 	ERR_FAIL_COND(!p_importer.is_valid());
 	ResourceImporterScene::get_singleton()->remove_importer(p_importer);
 	ResourceImporterScene::get_singleton()->remove_importer(p_importer);
 }
 }
 
 
+void EditorPlugin::add_scene_post_import_plugin(const Ref<EditorScenePostImportPlugin> &p_plugin) {
+	ResourceImporterScene::get_singleton()->add_post_importer_plugin(p_plugin);
+}
+void EditorPlugin::remove_scene_post_import_plugin(const Ref<EditorScenePostImportPlugin> &p_plugin) {
+	ResourceImporterScene::get_singleton()->remove_post_importer_plugin(p_plugin);
+}
+
 int find(const PackedStringArray &a, const String &v) {
 int find(const PackedStringArray &a, const String &v) {
 	const String *r = a.ptr();
 	const String *r = a.ptr();
 	for (int j = 0; j < a.size(); ++j) {
 	for (int j = 0; j < a.size(); ++j) {
@@ -879,8 +886,10 @@ void EditorPlugin::_bind_methods() {
 	ClassDB::bind_method(D_METHOD("remove_translation_parser_plugin", "parser"), &EditorPlugin::remove_translation_parser_plugin);
 	ClassDB::bind_method(D_METHOD("remove_translation_parser_plugin", "parser"), &EditorPlugin::remove_translation_parser_plugin);
 	ClassDB::bind_method(D_METHOD("add_import_plugin", "importer"), &EditorPlugin::add_import_plugin);
 	ClassDB::bind_method(D_METHOD("add_import_plugin", "importer"), &EditorPlugin::add_import_plugin);
 	ClassDB::bind_method(D_METHOD("remove_import_plugin", "importer"), &EditorPlugin::remove_import_plugin);
 	ClassDB::bind_method(D_METHOD("remove_import_plugin", "importer"), &EditorPlugin::remove_import_plugin);
-	ClassDB::bind_method(D_METHOD("add_scene_import_plugin", "scene_importer"), &EditorPlugin::add_scene_import_plugin);
-	ClassDB::bind_method(D_METHOD("remove_scene_import_plugin", "scene_importer"), &EditorPlugin::remove_scene_import_plugin);
+	ClassDB::bind_method(D_METHOD("add_scene_format_importer_plugin", "scene_format_importer"), &EditorPlugin::add_scene_format_importer_plugin);
+	ClassDB::bind_method(D_METHOD("remove_scene_format_importer_plugin", "scene_format_importer"), &EditorPlugin::remove_scene_format_importer_plugin);
+	ClassDB::bind_method(D_METHOD("add_scene_post_import_plugin", "scene_import_plugin"), &EditorPlugin::add_scene_post_import_plugin);
+	ClassDB::bind_method(D_METHOD("remove_scene_post_import_plugin", "scene_import_plugin"), &EditorPlugin::remove_scene_post_import_plugin);
 	ClassDB::bind_method(D_METHOD("add_export_plugin", "plugin"), &EditorPlugin::add_export_plugin);
 	ClassDB::bind_method(D_METHOD("add_export_plugin", "plugin"), &EditorPlugin::add_export_plugin);
 	ClassDB::bind_method(D_METHOD("remove_export_plugin", "plugin"), &EditorPlugin::remove_export_plugin);
 	ClassDB::bind_method(D_METHOD("remove_export_plugin", "plugin"), &EditorPlugin::remove_export_plugin);
 	ClassDB::bind_method(D_METHOD("add_spatial_gizmo_plugin", "plugin"), &EditorPlugin::add_spatial_gizmo_plugin);
 	ClassDB::bind_method(D_METHOD("add_spatial_gizmo_plugin", "plugin"), &EditorPlugin::add_spatial_gizmo_plugin);

+ 5 - 2
editor/editor_plugin.h

@@ -288,8 +288,11 @@ public:
 	void add_inspector_plugin(const Ref<EditorInspectorPlugin> &p_plugin);
 	void add_inspector_plugin(const Ref<EditorInspectorPlugin> &p_plugin);
 	void remove_inspector_plugin(const Ref<EditorInspectorPlugin> &p_plugin);
 	void remove_inspector_plugin(const Ref<EditorInspectorPlugin> &p_plugin);
 
 
-	void add_scene_import_plugin(const Ref<EditorSceneImporter> &p_importer);
-	void remove_scene_import_plugin(const Ref<EditorSceneImporter> &p_importer);
+	void add_scene_format_importer_plugin(const Ref<EditorSceneFormatImporter> &p_importer);
+	void remove_scene_format_importer_plugin(const Ref<EditorSceneFormatImporter> &p_importer);
+
+	void add_scene_post_import_plugin(const Ref<EditorScenePostImportPlugin> &p_importer);
+	void remove_scene_post_import_plugin(const Ref<EditorScenePostImportPlugin> &p_importer);
 
 
 	void add_autoload_singleton(const String &p_name, const String &p_path);
 	void add_autoload_singleton(const String &p_name, const String &p_path);
 	void remove_autoload_singleton(const String &p_name);
 	void remove_autoload_singleton(const String &p_name);

+ 7 - 7
editor/import/editor_import_collada.cpp

@@ -1748,15 +1748,15 @@ void ColladaImport::create_animation(int p_clip, bool p_import_value_tracks) {
 /*************************************** SCENE ***********************************/
 /*************************************** SCENE ***********************************/
 /*********************************************************************************/
 /*********************************************************************************/
 
 
-uint32_t EditorSceneImporterCollada::get_import_flags() const {
+uint32_t EditorSceneFormatImporterCollada::get_import_flags() const {
 	return IMPORT_SCENE | IMPORT_ANIMATION;
 	return IMPORT_SCENE | IMPORT_ANIMATION;
 }
 }
 
 
-void EditorSceneImporterCollada::get_extensions(List<String> *r_extensions) const {
+void EditorSceneFormatImporterCollada::get_extensions(List<String> *r_extensions) const {
 	r_extensions->push_back("dae");
 	r_extensions->push_back("dae");
 }
 }
 
 
-Node *EditorSceneImporterCollada::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err) {
+Node *EditorSceneFormatImporterCollada::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err) {
 	if (r_err) {
 	if (r_err) {
 		*r_err = OK;
 		*r_err = OK;
 	}
 	}
@@ -1769,7 +1769,7 @@ Node *EditorSceneImporterCollada::import_scene(const String &p_path, uint32_t p_
 	state.use_mesh_builtin_materials = true;
 	state.use_mesh_builtin_materials = true;
 	state.bake_fps = p_bake_fps;
 	state.bake_fps = p_bake_fps;
 
 
-	Error err = state.load(p_path, flags, p_flags & EditorSceneImporter::IMPORT_GENERATE_TANGENT_ARRAYS, false);
+	Error err = state.load(p_path, flags, p_flags & EditorSceneFormatImporter::IMPORT_GENERATE_TANGENT_ARRAYS, false);
 
 
 	if (r_err) {
 	if (r_err) {
 		*r_err = err;
 		*r_err = err;
@@ -1812,12 +1812,12 @@ Node *EditorSceneImporterCollada::import_scene(const String &p_path, uint32_t p_
 	return state.scene;
 	return state.scene;
 }
 }
 
 
-Ref<Animation> EditorSceneImporterCollada::import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) {
+Ref<Animation> EditorSceneFormatImporterCollada::import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) {
 	ColladaImport state;
 	ColladaImport state;
 
 
 	state.use_mesh_builtin_materials = false;
 	state.use_mesh_builtin_materials = false;
 
 
-	Error err = state.load(p_path, Collada::IMPORT_FLAG_ANIMATION, p_flags & EditorSceneImporter::IMPORT_GENERATE_TANGENT_ARRAYS);
+	Error err = state.load(p_path, Collada::IMPORT_FLAG_ANIMATION, p_flags & EditorSceneFormatImporter::IMPORT_GENERATE_TANGENT_ARRAYS);
 	ERR_FAIL_COND_V_MSG(err != OK, RES(), "Cannot load animation from file '" + p_path + "'.");
 	ERR_FAIL_COND_V_MSG(err != OK, RES(), "Cannot load animation from file '" + p_path + "'.");
 
 
 	state.create_animations(true);
 	state.create_animations(true);
@@ -1833,5 +1833,5 @@ Ref<Animation> EditorSceneImporterCollada::import_animation(const String &p_path
 	return anim;
 	return anim;
 }
 }
 
 
-EditorSceneImporterCollada::EditorSceneImporterCollada() {
+EditorSceneFormatImporterCollada::EditorSceneFormatImporterCollada() {
 }
 }

+ 3 - 3
editor/import/editor_import_collada.h

@@ -33,8 +33,8 @@
 
 
 #include "editor/import/resource_importer_scene.h"
 #include "editor/import/resource_importer_scene.h"
 
 
-class EditorSceneImporterCollada : public EditorSceneImporter {
-	GDCLASS(EditorSceneImporterCollada, EditorSceneImporter);
+class EditorSceneFormatImporterCollada : public EditorSceneFormatImporter {
+	GDCLASS(EditorSceneFormatImporterCollada, EditorSceneFormatImporter);
 
 
 public:
 public:
 	virtual uint32_t get_import_flags() const override;
 	virtual uint32_t get_import_flags() const override;
@@ -42,7 +42,7 @@ public:
 	virtual Node *import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps = nullptr, Error *r_err = nullptr) override;
 	virtual Node *import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps = nullptr, Error *r_err = nullptr) override;
 	virtual Ref<Animation> import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) override;
 	virtual Ref<Animation> import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) override;
 
 
-	EditorSceneImporterCollada();
+	EditorSceneFormatImporterCollada();
 };
 };
 
 
 #endif
 #endif

+ 2 - 2
editor/import/resource_importer_obj.h

@@ -33,8 +33,8 @@
 
 
 #include "resource_importer_scene.h"
 #include "resource_importer_scene.h"
 
 
-class EditorOBJImporter : public EditorSceneImporter {
-	GDCLASS(EditorOBJImporter, EditorSceneImporter);
+class EditorOBJImporter : public EditorSceneFormatImporter {
+	GDCLASS(EditorOBJImporter, EditorSceneFormatImporter);
 
 
 public:
 public:
 	virtual uint32_t get_import_flags() const override;
 	virtual uint32_t get_import_flags() const override;

+ 224 - 28
editor/import/resource_importer_scene.cpp

@@ -52,7 +52,7 @@
 #include "scene/resources/surface_tool.h"
 #include "scene/resources/surface_tool.h"
 #include "scene/resources/world_boundary_shape_3d.h"
 #include "scene/resources/world_boundary_shape_3d.h"
 
 
-uint32_t EditorSceneImporter::get_import_flags() const {
+uint32_t EditorSceneFormatImporter::get_import_flags() const {
 	int ret;
 	int ret;
 	if (GDVIRTUAL_CALL(_get_import_flags, ret)) {
 	if (GDVIRTUAL_CALL(_get_import_flags, ret)) {
 		return ret;
 		return ret;
@@ -61,7 +61,7 @@ uint32_t EditorSceneImporter::get_import_flags() const {
 	ERR_FAIL_V(0);
 	ERR_FAIL_V(0);
 }
 }
 
 
-void EditorSceneImporter::get_extensions(List<String> *r_extensions) const {
+void EditorSceneFormatImporter::get_extensions(List<String> *r_extensions) const {
 	Vector<String> arr;
 	Vector<String> arr;
 	if (GDVIRTUAL_CALL(_get_extensions, arr)) {
 	if (GDVIRTUAL_CALL(_get_extensions, arr)) {
 		for (int i = 0; i < arr.size(); i++) {
 		for (int i = 0; i < arr.size(); i++) {
@@ -73,7 +73,7 @@ void EditorSceneImporter::get_extensions(List<String> *r_extensions) const {
 	ERR_FAIL();
 	ERR_FAIL();
 }
 }
 
 
-Node *EditorSceneImporter::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err) {
+Node *EditorSceneFormatImporter::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err) {
 	Object *ret;
 	Object *ret;
 	if (GDVIRTUAL_CALL(_import_scene, p_path, p_flags, p_bake_fps, ret)) {
 	if (GDVIRTUAL_CALL(_import_scene, p_path, p_flags, p_bake_fps, ret)) {
 		return Object::cast_to<Node>(ret);
 		return Object::cast_to<Node>(ret);
@@ -82,7 +82,7 @@ Node *EditorSceneImporter::import_scene(const String &p_path, uint32_t p_flags,
 	ERR_FAIL_V(nullptr);
 	ERR_FAIL_V(nullptr);
 }
 }
 
 
-Ref<Animation> EditorSceneImporter::import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) {
+Ref<Animation> EditorSceneFormatImporter::import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) {
 	Ref<Animation> ret;
 	Ref<Animation> ret;
 	if (GDVIRTUAL_CALL(_import_animation, p_path, p_flags, p_bake_fps, ret)) {
 	if (GDVIRTUAL_CALL(_import_animation, p_path, p_flags, p_bake_fps, ret)) {
 		return ret;
 		return ret;
@@ -94,17 +94,17 @@ Ref<Animation> EditorSceneImporter::import_animation(const String &p_path, uint3
 //for documenters, these functions are useful when an importer calls an external conversion helper (like, fbx2gltf),
 //for documenters, these functions are useful when an importer calls an external conversion helper (like, fbx2gltf),
 //and you want to load the resulting file
 //and you want to load the resulting file
 
 
-Node *EditorSceneImporter::import_scene_from_other_importer(const String &p_path, uint32_t p_flags, int p_bake_fps) {
+Node *EditorSceneFormatImporter::import_scene_from_other_importer(const String &p_path, uint32_t p_flags, int p_bake_fps) {
 	return ResourceImporterScene::get_singleton()->import_scene_from_other_importer(this, p_path, p_flags, p_bake_fps);
 	return ResourceImporterScene::get_singleton()->import_scene_from_other_importer(this, p_path, p_flags, p_bake_fps);
 }
 }
 
 
-Ref<Animation> EditorSceneImporter::import_animation_from_other_importer(const String &p_path, uint32_t p_flags, int p_bake_fps) {
+Ref<Animation> EditorSceneFormatImporter::import_animation_from_other_importer(const String &p_path, uint32_t p_flags, int p_bake_fps) {
 	return ResourceImporterScene::get_singleton()->import_animation_from_other_importer(this, p_path, p_flags, p_bake_fps);
 	return ResourceImporterScene::get_singleton()->import_animation_from_other_importer(this, p_path, p_flags, p_bake_fps);
 }
 }
 
 
-void EditorSceneImporter::_bind_methods() {
-	ClassDB::bind_method(D_METHOD("import_scene_from_other_importer", "path", "flags", "bake_fps"), &EditorSceneImporter::import_scene_from_other_importer);
-	ClassDB::bind_method(D_METHOD("import_animation_from_other_importer", "path", "flags", "bake_fps"), &EditorSceneImporter::import_animation_from_other_importer);
+void EditorSceneFormatImporter::_bind_methods() {
+	ClassDB::bind_method(D_METHOD("import_scene_from_other_importer", "path", "flags", "bake_fps"), &EditorSceneFormatImporter::import_scene_from_other_importer);
+	ClassDB::bind_method(D_METHOD("import_animation_from_other_importer", "path", "flags", "bake_fps"), &EditorSceneFormatImporter::import_animation_from_other_importer);
 
 
 	GDVIRTUAL_BIND(_get_import_flags);
 	GDVIRTUAL_BIND(_get_import_flags);
 	GDVIRTUAL_BIND(_get_extensions);
 	GDVIRTUAL_BIND(_get_extensions);
@@ -144,6 +144,105 @@ void EditorScenePostImport::init(const String &p_source_file) {
 EditorScenePostImport::EditorScenePostImport() {
 EditorScenePostImport::EditorScenePostImport() {
 }
 }
 
 
+///////////////////////////////////////////////////////
+
+Variant EditorScenePostImportPlugin::get_option_value(const StringName &p_name) const {
+	ERR_FAIL_COND_V_MSG(current_options == nullptr && current_options_dict == nullptr, Variant(), "get_option_value called from a function where option values are not available.");
+	ERR_FAIL_COND_V_MSG(current_options && !current_options->has(p_name), Variant(), "get_option_value called with unexisting option argument: " + String(p_name));
+	ERR_FAIL_COND_V_MSG(current_options_dict && !current_options_dict->has(p_name), Variant(), "get_option_value called with unexisting option argument: " + String(p_name));
+	if (current_options) {
+		(*current_options)[p_name];
+	}
+	if (current_options_dict) {
+		(*current_options_dict)[p_name];
+	}
+	return Variant();
+}
+void EditorScenePostImportPlugin::add_import_option(const String &p_name, Variant p_default_value) {
+	ERR_FAIL_COND_MSG(current_option_list == nullptr, "add_import_option() can only be called from get_import_options()");
+	add_import_option_advanced(p_default_value.get_type(), p_name, p_default_value);
+}
+void EditorScenePostImportPlugin::add_import_option_advanced(Variant::Type p_type, const String &p_name, Variant p_default_value, PropertyHint p_hint, const String &p_hint_string, int p_usage_flags) {
+	ERR_FAIL_COND_MSG(current_option_list == nullptr, "add_import_option_advanced() can only be called from get_import_options()");
+	current_option_list->push_back(ResourceImporter::ImportOption(PropertyInfo(p_type, p_name, p_hint, p_hint_string, p_usage_flags), p_default_value));
+}
+
+void EditorScenePostImportPlugin::get_internal_import_options(InternalImportCategory p_category, List<ResourceImporter::ImportOption> *r_options) {
+	current_option_list = r_options;
+	GDVIRTUAL_CALL(_get_internal_import_options, p_category);
+	current_option_list = nullptr;
+}
+Variant EditorScenePostImportPlugin::get_internal_option_visibility(InternalImportCategory p_category, const String &p_option, const Map<StringName, Variant> &p_options) const {
+	current_options = &p_options;
+	Variant ret;
+	GDVIRTUAL_CALL(_get_internal_option_visibility, p_category, p_option, ret);
+	current_options = nullptr;
+	return ret;
+}
+Variant EditorScenePostImportPlugin::get_internal_option_update_view_required(InternalImportCategory p_category, const String &p_option, const Map<StringName, Variant> &p_options) const {
+	current_options = &p_options;
+	Variant ret;
+	GDVIRTUAL_CALL(_get_internal_option_update_view_required, p_category, p_option, ret);
+	current_options = nullptr;
+	return ret;
+}
+
+void EditorScenePostImportPlugin::internal_process(InternalImportCategory p_category, Node *p_base_scene, Node *p_node, RES p_resource, const Dictionary &p_options) {
+	current_options_dict = &p_options;
+	GDVIRTUAL_CALL(_internal_process, p_category, p_base_scene, p_node, p_resource);
+	current_options_dict = nullptr;
+}
+
+void EditorScenePostImportPlugin::get_import_options(List<ResourceImporter::ImportOption> *r_options) {
+	current_option_list = r_options;
+	GDVIRTUAL_CALL(_get_import_options);
+	current_option_list = nullptr;
+}
+Variant EditorScenePostImportPlugin::get_option_visibility(const String &p_option, const Map<StringName, Variant> &p_options) const {
+	current_options = &p_options;
+	Variant ret;
+	GDVIRTUAL_CALL(_get_option_visibility, p_option, ret);
+	current_options = nullptr;
+	return ret;
+}
+
+void EditorScenePostImportPlugin::pre_process(Node *p_scene, const Map<StringName, Variant> &p_options) {
+	current_options = &p_options;
+	GDVIRTUAL_CALL(_pre_process, p_scene);
+	current_options = nullptr;
+}
+void EditorScenePostImportPlugin::post_process(Node *p_scene, const Map<StringName, Variant> &p_options) {
+	current_options = &p_options;
+	GDVIRTUAL_CALL(_post_process, p_scene);
+	current_options = nullptr;
+}
+
+void EditorScenePostImportPlugin::_bind_methods() {
+	ClassDB::bind_method(D_METHOD("get_option_value", "name"), &EditorScenePostImportPlugin::get_option_value);
+
+	ClassDB::bind_method(D_METHOD("add_import_option", "name", "value"), &EditorScenePostImportPlugin::add_import_option);
+	ClassDB::bind_method(D_METHOD("add_import_option_advanced", "type", "name", "default_value", "hint", "hint_string", "usage_flags"), &EditorScenePostImportPlugin::add_import_option_advanced, DEFVAL(PROPERTY_HINT_NONE), DEFVAL(""), DEFVAL(PROPERTY_USAGE_DEFAULT));
+
+	GDVIRTUAL_BIND(_get_internal_import_options, "category");
+	GDVIRTUAL_BIND(_get_internal_option_visibility, "category", "option");
+	GDVIRTUAL_BIND(_get_internal_option_update_view_required, "category", "option");
+	GDVIRTUAL_BIND(_internal_process, "category", "base_node", "node", "resource");
+	GDVIRTUAL_BIND(_get_import_options);
+	GDVIRTUAL_BIND(_get_option_visibility, "option");
+	GDVIRTUAL_BIND(_pre_process, "scene");
+	GDVIRTUAL_BIND(_post_process, "scene");
+
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_NODE);
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE);
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_MESH);
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_MATERIAL);
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_ANIMATION);
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE);
+	BIND_ENUM_CONSTANT(INTERNAL_IMPORT_CATEGORY_MAX);
+}
+
+/////////////////////////////////////////////////////////
+
 String ResourceImporterScene::get_importer_name() const {
 String ResourceImporterScene::get_importer_name() const {
 	return "scene";
 	return "scene";
 }
 }
@@ -153,7 +252,7 @@ String ResourceImporterScene::get_visible_name() const {
 }
 }
 
 
 void ResourceImporterScene::get_recognized_extensions(List<String> *p_extensions) const {
 void ResourceImporterScene::get_recognized_extensions(List<String> *p_extensions) const {
-	for (Set<Ref<EditorSceneImporter>>::Element *E = importers.front(); E; E = E->next()) {
+	for (Set<Ref<EditorSceneFormatImporter>>::Element *E = importers.front(); E; E = E->next()) {
 		E->get()->get_extensions(p_extensions);
 		E->get()->get_extensions(p_extensions);
 	}
 	}
 }
 }
@@ -181,6 +280,13 @@ bool ResourceImporterScene::get_option_visibility(const String &p_option, const
 		return false;
 		return false;
 	}
 	}
 
 
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		Variant ret = post_importer_plugins.write[i]->get_option_visibility(p_option, p_options);
+		if (ret.get_type() == Variant::BOOL) {
+			return ret;
+		}
+	}
+
 	return true;
 	return true;
 }
 }
 
 
@@ -547,6 +653,26 @@ Node *ResourceImporterScene::_post_fix_node(Node *p_node, Node *p_root, Map<Ref<
 		return nullptr;
 		return nullptr;
 	}
 	}
 
 
+	{
+		ObjectID node_id = p_node->get_instance_id();
+		for (int i = 0; i < post_importer_plugins.size(); i++) {
+			post_importer_plugins.write[i]->internal_process(EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_NODE, p_root, p_node, RES(), node_settings);
+			if (ObjectDB::get_instance(node_id) == nullptr) { //may have been erased, so do not continue
+				break;
+			}
+		}
+	}
+
+	if (Object::cast_to<ImporterMeshInstance3D>(p_node)) {
+		ObjectID node_id = p_node->get_instance_id();
+		for (int i = 0; i < post_importer_plugins.size(); i++) {
+			post_importer_plugins.write[i]->internal_process(EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE, p_root, p_node, RES(), node_settings);
+			if (ObjectDB::get_instance(node_id) == nullptr) { //may have been erased, so do not continue
+				break;
+			}
+		}
+	}
+
 	if (Object::cast_to<ImporterMeshInstance3D>(p_node)) {
 	if (Object::cast_to<ImporterMeshInstance3D>(p_node)) {
 		ImporterMeshInstance3D *mi = Object::cast_to<ImporterMeshInstance3D>(p_node);
 		ImporterMeshInstance3D *mi = Object::cast_to<ImporterMeshInstance3D>(p_node);
 
 
@@ -566,6 +692,11 @@ Node *ResourceImporterScene::_post_fix_node(Node *p_node, Node *p_root, Map<Ref<
 
 
 						if (mat_id != String() && p_material_data.has(mat_id)) {
 						if (mat_id != String() && p_material_data.has(mat_id)) {
 							Dictionary matdata = p_material_data[mat_id];
 							Dictionary matdata = p_material_data[mat_id];
+
+							for (int j = 0; j < post_importer_plugins.size(); j++) {
+								post_importer_plugins.write[j]->internal_process(EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MATERIAL, p_root, p_node, mat, matdata);
+							}
+
 							if (matdata.has("use_external/enabled") && bool(matdata["use_external/enabled"]) && matdata.has("use_external/path")) {
 							if (matdata.has("use_external/enabled") && bool(matdata["use_external/enabled"]) && matdata.has("use_external/path")) {
 								String path = matdata["use_external/path"];
 								String path = matdata["use_external/path"];
 								Ref<Material> external_mat = ResourceLoader::load(path);
 								Ref<Material> external_mat = ResourceLoader::load(path);
@@ -715,6 +846,10 @@ Node *ResourceImporterScene::_post_fix_node(Node *p_node, Node *p_root, Map<Ref<
 			}
 			}
 		}
 		}
 
 
+		for (int i = 0; i < post_importer_plugins.size(); i++) {
+			post_importer_plugins.write[i]->internal_process(EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE, p_root, p_node, RES(), node_settings);
+		}
+
 		bool use_optimizer = node_settings["optimizer/enabled"];
 		bool use_optimizer = node_settings["optimizer/enabled"];
 		float anim_optimizer_linerr = node_settings["optimizer/max_linear_error"];
 		float anim_optimizer_linerr = node_settings["optimizer/max_linear_error"];
 		float anim_optimizer_angerr = node_settings["optimizer/max_angular_error"];
 		float anim_optimizer_angerr = node_settings["optimizer/max_angular_error"];
@@ -790,6 +925,31 @@ Node *ResourceImporterScene::_post_fix_node(Node *p_node, Node *p_root, Map<Ref<
 				_optimize_track_usage(ap, import_tracks_mode);
 				_optimize_track_usage(ap, import_tracks_mode);
 			}
 			}
 		}
 		}
+
+		if (post_importer_plugins.size()) {
+			List<StringName> anims;
+			ap->get_animation_list(&anims);
+			for (const StringName &name : anims) {
+				if (p_animation_data.has(name)) {
+					Ref<Animation> anim = ap->get_animation(name);
+					Dictionary anim_settings = p_animation_data[name];
+					{
+						//fill with default values
+						List<ImportOption> iopts;
+						get_internal_import_options(INTERNAL_IMPORT_CATEGORY_ANIMATION, &iopts);
+						for (const ImportOption &F : iopts) {
+							if (!anim_settings.has(F.option.name)) {
+								anim_settings[F.option.name] = F.default_value;
+							}
+						}
+					}
+
+					for (int i = 0; i < post_importer_plugins.size(); i++) {
+						post_importer_plugins.write[i]->internal_process(EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_ANIMATION, p_root, p_node, anim, node_settings);
+					}
+				}
+			}
+		}
 	}
 	}
 
 
 	return p_node;
 	return p_node;
@@ -1052,6 +1212,10 @@ void ResourceImporterScene::get_internal_import_options(InternalImportCategory p
 		default: {
 		default: {
 		}
 		}
 	}
 	}
+
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		post_importer_plugins.write[i]->get_internal_import_options(EditorScenePostImportPlugin::InternalImportCategory(p_category), r_options);
+	}
 }
 }
 
 
 bool ResourceImporterScene::get_internal_option_visibility(InternalImportCategory p_category, const String &p_option, const Map<StringName, Variant> &p_options) const {
 bool ResourceImporterScene::get_internal_option_visibility(InternalImportCategory p_category, const String &p_option, const Map<StringName, Variant> &p_options) const {
@@ -1154,6 +1318,13 @@ bool ResourceImporterScene::get_internal_option_visibility(InternalImportCategor
 		}
 		}
 	}
 	}
 
 
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		Variant ret = post_importer_plugins.write[i]->get_internal_option_visibility(EditorScenePostImportPlugin::InternalImportCategory(p_category), p_option, p_options);
+		if (ret.get_type() == Variant::BOOL) {
+			return ret;
+		}
+	}
+
 	return true;
 	return true;
 }
 }
 
 
@@ -1181,6 +1352,14 @@ bool ResourceImporterScene::get_internal_option_update_view_required(InternalImp
 		default: {
 		default: {
 		}
 		}
 	}
 	}
+
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		Variant ret = post_importer_plugins.write[i]->get_internal_option_update_view_required(EditorScenePostImportPlugin::InternalImportCategory(p_category), p_option, p_options);
+		if (ret.get_type() == Variant::BOOL) {
+			return ret;
+		}
+	}
+
 	return false;
 	return false;
 }
 }
 
 
@@ -1212,6 +1391,10 @@ void ResourceImporterScene::get_import_options(List<ImportOption> *r_options, in
 	r_options->push_back(ImportOption(PropertyInfo(Variant::STRING, "import_script/path", PROPERTY_HINT_FILE, script_ext_hint), ""));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::STRING, "import_script/path", PROPERTY_HINT_FILE, script_ext_hint), ""));
 
 
 	r_options->push_back(ImportOption(PropertyInfo(Variant::DICTIONARY, "_subresources", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR), Dictionary()));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::DICTIONARY, "_subresources", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR), Dictionary()));
+
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		post_importer_plugins.write[i]->get_import_options(r_options);
+	}
 }
 }
 
 
 void ResourceImporterScene::_replace_owner(Node *p_node, Node *p_scene, Node *p_new_owner) {
 void ResourceImporterScene::_replace_owner(Node *p_node, Node *p_scene, Node *p_new_owner) {
@@ -1225,11 +1408,11 @@ void ResourceImporterScene::_replace_owner(Node *p_node, Node *p_scene, Node *p_
 	}
 	}
 }
 }
 
 
-Node *ResourceImporterScene::import_scene_from_other_importer(EditorSceneImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps) {
-	Ref<EditorSceneImporter> importer;
+Node *ResourceImporterScene::import_scene_from_other_importer(EditorSceneFormatImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps) {
+	Ref<EditorSceneFormatImporter> importer;
 	String ext = p_path.get_extension().to_lower();
 	String ext = p_path.get_extension().to_lower();
 
 
-	for (Set<Ref<EditorSceneImporter>>::Element *E = importers.front(); E; E = E->next()) {
+	for (Set<Ref<EditorSceneFormatImporter>>::Element *E = importers.front(); E; E = E->next()) {
 		if (E->get().ptr() == p_exception) {
 		if (E->get().ptr() == p_exception) {
 			continue;
 			continue;
 		}
 		}
@@ -1255,11 +1438,11 @@ Node *ResourceImporterScene::import_scene_from_other_importer(EditorSceneImporte
 	return importer->import_scene(p_path, p_flags, p_bake_fps, &missing, &err);
 	return importer->import_scene(p_path, p_flags, p_bake_fps, &missing, &err);
 }
 }
 
 
-Ref<Animation> ResourceImporterScene::import_animation_from_other_importer(EditorSceneImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps) {
-	Ref<EditorSceneImporter> importer;
+Ref<Animation> ResourceImporterScene::import_animation_from_other_importer(EditorSceneFormatImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps) {
+	Ref<EditorSceneFormatImporter> importer;
 	String ext = p_path.get_extension().to_lower();
 	String ext = p_path.get_extension().to_lower();
 
 
-	for (Set<Ref<EditorSceneImporter>>::Element *E = importers.front(); E; E = E->next()) {
+	for (Set<Ref<EditorSceneFormatImporter>>::Element *E = importers.front(); E; E = E->next()) {
 		if (E->get().ptr() == p_exception) {
 		if (E->get().ptr() == p_exception) {
 			continue;
 			continue;
 		}
 		}
@@ -1356,6 +1539,10 @@ void ResourceImporterScene::_generate_meshes(Node *p_node, const Dictionary &p_m
 							save_to_file = "";
 							save_to_file = "";
 						}
 						}
 					}
 					}
+
+					for (int i = 0; i < post_importer_plugins.size(); i++) {
+						post_importer_plugins.write[i]->internal_process(EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MESH, nullptr, src_mesh_node, src_mesh_node->get_mesh(), mesh_settings);
+					}
 				}
 				}
 
 
 				if (generate_lods) {
 				if (generate_lods) {
@@ -1592,13 +1779,13 @@ void ResourceImporterScene::_optimize_track_usage(AnimationPlayer *p_player, Ani
 }
 }
 
 
 Node *ResourceImporterScene::pre_import(const String &p_source_file) {
 Node *ResourceImporterScene::pre_import(const String &p_source_file) {
-	Ref<EditorSceneImporter> importer;
+	Ref<EditorSceneFormatImporter> importer;
 	String ext = p_source_file.get_extension().to_lower();
 	String ext = p_source_file.get_extension().to_lower();
 
 
 	EditorProgress progress("pre-import", TTR("Pre-Import Scene"), 0);
 	EditorProgress progress("pre-import", TTR("Pre-Import Scene"), 0);
 	progress.step(TTR("Importing Scene..."), 0);
 	progress.step(TTR("Importing Scene..."), 0);
 
 
-	for (Set<Ref<EditorSceneImporter>>::Element *E = importers.front(); E; E = E->next()) {
+	for (Set<Ref<EditorSceneFormatImporter>>::Element *E = importers.front(); E; E = E->next()) {
 		List<String> extensions;
 		List<String> extensions;
 		E->get()->get_extensions(&extensions);
 		E->get()->get_extensions(&extensions);
 
 
@@ -1617,7 +1804,7 @@ Node *ResourceImporterScene::pre_import(const String &p_source_file) {
 	ERR_FAIL_COND_V(!importer.is_valid(), nullptr);
 	ERR_FAIL_COND_V(!importer.is_valid(), nullptr);
 
 
 	Error err = OK;
 	Error err = OK;
-	Node *scene = importer->import_scene(p_source_file, EditorSceneImporter::IMPORT_ANIMATION | EditorSceneImporter::IMPORT_GENERATE_TANGENT_ARRAYS, 15, nullptr, &err);
+	Node *scene = importer->import_scene(p_source_file, EditorSceneFormatImporter::IMPORT_ANIMATION | EditorSceneFormatImporter::IMPORT_GENERATE_TANGENT_ARRAYS, 15, nullptr, &err);
 	if (!scene || err != OK) {
 	if (!scene || err != OK) {
 		return nullptr;
 		return nullptr;
 	}
 	}
@@ -1632,13 +1819,13 @@ Node *ResourceImporterScene::pre_import(const String &p_source_file) {
 Error ResourceImporterScene::import(const String &p_source_file, const String &p_save_path, const Map<StringName, Variant> &p_options, List<String> *r_platform_variants, List<String> *r_gen_files, Variant *r_metadata) {
 Error ResourceImporterScene::import(const String &p_source_file, const String &p_save_path, const Map<StringName, Variant> &p_options, List<String> *r_platform_variants, List<String> *r_gen_files, Variant *r_metadata) {
 	const String &src_path = p_source_file;
 	const String &src_path = p_source_file;
 
 
-	Ref<EditorSceneImporter> importer;
+	Ref<EditorSceneFormatImporter> importer;
 	String ext = src_path.get_extension().to_lower();
 	String ext = src_path.get_extension().to_lower();
 
 
 	EditorProgress progress("import", TTR("Import Scene"), 104);
 	EditorProgress progress("import", TTR("Import Scene"), 104);
 	progress.step(TTR("Importing Scene..."), 0);
 	progress.step(TTR("Importing Scene..."), 0);
 
 
-	for (Set<Ref<EditorSceneImporter>>::Element *E = importers.front(); E; E = E->next()) {
+	for (Set<Ref<EditorSceneFormatImporter>>::Element *E = importers.front(); E; E = E->next()) {
 		List<String> extensions;
 		List<String> extensions;
 		E->get()->get_extensions(&extensions);
 		E->get()->get_extensions(&extensions);
 
 
@@ -1661,16 +1848,16 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p
 	int import_flags = 0;
 	int import_flags = 0;
 
 
 	if (bool(p_options["animation/import"])) {
 	if (bool(p_options["animation/import"])) {
-		import_flags |= EditorSceneImporter::IMPORT_ANIMATION;
+		import_flags |= EditorSceneFormatImporter::IMPORT_ANIMATION;
 	}
 	}
 
 
 	if (bool(p_options["skins/use_named_skins"])) {
 	if (bool(p_options["skins/use_named_skins"])) {
-		import_flags |= EditorSceneImporter::IMPORT_USE_NAMED_SKIN_BINDS;
+		import_flags |= EditorSceneFormatImporter::IMPORT_USE_NAMED_SKIN_BINDS;
 	}
 	}
 
 
 	bool ensure_tangents = p_options["meshes/ensure_tangents"];
 	bool ensure_tangents = p_options["meshes/ensure_tangents"];
 	if (ensure_tangents) {
 	if (ensure_tangents) {
-		import_flags |= EditorSceneImporter::IMPORT_GENERATE_TANGENT_ARRAYS;
+		import_flags |= EditorSceneFormatImporter::IMPORT_GENERATE_TANGENT_ARRAYS;
 	}
 	}
 
 
 	Error err = OK;
 	Error err = OK;
@@ -1701,6 +1888,11 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p
 	Map<Ref<ImporterMesh>, Vector<Ref<Shape3D>>> collision_map;
 	Map<Ref<ImporterMesh>, Vector<Ref<Shape3D>>> collision_map;
 
 
 	_pre_fix_node(scene, scene, collision_map);
 	_pre_fix_node(scene, scene, collision_map);
+
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		post_importer_plugins.write[i]->pre_process(scene, p_options);
+	}
+
 	_post_fix_node(scene, scene, collision_map, scanned_meshes, node_data, material_data, animation_data, fps);
 	_post_fix_node(scene, scene, collision_map, scanned_meshes, node_data, material_data, animation_data, fps);
 
 
 	String root_type = p_options["nodes/root_type"];
 	String root_type = p_options["nodes/root_type"];
@@ -1804,6 +1996,10 @@ Error ResourceImporterScene::import(const String &p_source_file, const String &p
 		}
 		}
 	}
 	}
 
 
+	for (int i = 0; i < post_importer_plugins.size(); i++) {
+		post_importer_plugins.write[i]->post_process(scene, p_options);
+	}
+
 	progress.step(TTR("Saving..."), 104);
 	progress.step(TTR("Saving..."), 104);
 
 
 	Ref<PackedScene> packer = memnew(PackedScene);
 	Ref<PackedScene> packer = memnew(PackedScene);
@@ -1835,15 +2031,15 @@ ResourceImporterScene::ResourceImporterScene() {
 
 
 ///////////////////////////////////////
 ///////////////////////////////////////
 
 
-uint32_t EditorSceneImporterESCN::get_import_flags() const {
+uint32_t EditorSceneFormatImporterESCN::get_import_flags() const {
 	return IMPORT_SCENE;
 	return IMPORT_SCENE;
 }
 }
 
 
-void EditorSceneImporterESCN::get_extensions(List<String> *r_extensions) const {
+void EditorSceneFormatImporterESCN::get_extensions(List<String> *r_extensions) const {
 	r_extensions->push_back("escn");
 	r_extensions->push_back("escn");
 }
 }
 
 
-Node *EditorSceneImporterESCN::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err) {
+Node *EditorSceneFormatImporterESCN::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err) {
 	Error error;
 	Error error;
 	Ref<PackedScene> ps = ResourceFormatLoaderText::singleton->load(p_path, p_path, &error);
 	Ref<PackedScene> ps = ResourceFormatLoaderText::singleton->load(p_path, p_path, &error);
 	ERR_FAIL_COND_V_MSG(!ps.is_valid(), nullptr, "Cannot load scene as text resource from path '" + p_path + "'.");
 	ERR_FAIL_COND_V_MSG(!ps.is_valid(), nullptr, "Cannot load scene as text resource from path '" + p_path + "'.");
@@ -1854,6 +2050,6 @@ Node *EditorSceneImporterESCN::import_scene(const String &p_path, uint32_t p_fla
 	return scene;
 	return scene;
 }
 }
 
 
-Ref<Animation> EditorSceneImporterESCN::import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) {
+Ref<Animation> EditorSceneFormatImporterESCN::import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps) {
 	ERR_FAIL_V(Ref<Animation>());
 	ERR_FAIL_V(Ref<Animation>());
 }
 }

+ 77 - 18
editor/import/resource_importer_scene.h

@@ -42,8 +42,8 @@ class Material;
 class AnimationPlayer;
 class AnimationPlayer;
 
 
 class ImporterMesh;
 class ImporterMesh;
-class EditorSceneImporter : public RefCounted {
-	GDCLASS(EditorSceneImporter, RefCounted);
+class EditorSceneFormatImporter : public RefCounted {
+	GDCLASS(EditorSceneFormatImporter, RefCounted);
 
 
 protected:
 protected:
 	static void _bind_methods();
 	static void _bind_methods();
@@ -70,7 +70,7 @@ public:
 	virtual Node *import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err = nullptr);
 	virtual Node *import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps, List<String> *r_missing_deps, Error *r_err = nullptr);
 	virtual Ref<Animation> import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps);
 	virtual Ref<Animation> import_animation(const String &p_path, uint32_t p_flags, int p_bake_fps);
 
 
-	EditorSceneImporter() {}
+	EditorSceneFormatImporter() {}
 };
 };
 
 
 class EditorScenePostImport : public RefCounted {
 class EditorScenePostImport : public RefCounted {
@@ -90,10 +90,64 @@ public:
 	EditorScenePostImport();
 	EditorScenePostImport();
 };
 };
 
 
+class EditorScenePostImportPlugin : public RefCounted {
+	GDCLASS(EditorScenePostImportPlugin, RefCounted);
+
+public:
+	enum InternalImportCategory {
+		INTERNAL_IMPORT_CATEGORY_NODE,
+		INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE,
+		INTERNAL_IMPORT_CATEGORY_MESH,
+		INTERNAL_IMPORT_CATEGORY_MATERIAL,
+		INTERNAL_IMPORT_CATEGORY_ANIMATION,
+		INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE,
+		INTERNAL_IMPORT_CATEGORY_MAX
+	};
+
+private:
+	mutable const Map<StringName, Variant> *current_options = nullptr;
+	mutable const Dictionary *current_options_dict = nullptr;
+	List<ResourceImporter::ImportOption> *current_option_list = nullptr;
+	InternalImportCategory current_category = INTERNAL_IMPORT_CATEGORY_MAX;
+
+protected:
+	GDVIRTUAL1(_get_internal_import_options, int)
+	GDVIRTUAL2RC(Variant, _get_internal_option_visibility, int, String)
+	GDVIRTUAL2RC(Variant, _get_internal_option_update_view_required, int, String)
+	GDVIRTUAL4(_internal_process, int, Node *, Node *, RES)
+	GDVIRTUAL0(_get_import_options)
+	GDVIRTUAL1RC(Variant, _get_option_visibility, String)
+	GDVIRTUAL1(_pre_process, Node *)
+	GDVIRTUAL1(_post_process, Node *)
+
+	static void _bind_methods();
+
+public:
+	Variant get_option_value(const StringName &p_name) const;
+	void add_import_option(const String &p_name, Variant p_default_value);
+	void add_import_option_advanced(Variant::Type p_type, const String &p_name, Variant p_default_value, PropertyHint p_hint = PROPERTY_HINT_NONE, const String &p_hint_string = String(), int p_usage_flags = PROPERTY_USAGE_DEFAULT);
+
+	virtual void get_internal_import_options(InternalImportCategory p_category, List<ResourceImporter::ImportOption> *r_options);
+	virtual Variant get_internal_option_visibility(InternalImportCategory p_category, const String &p_option, const Map<StringName, Variant> &p_options) const;
+	virtual Variant get_internal_option_update_view_required(InternalImportCategory p_category, const String &p_option, const Map<StringName, Variant> &p_options) const;
+
+	virtual void internal_process(InternalImportCategory p_category, Node *p_base_scene, Node *p_node, RES p_resource, const Dictionary &p_options);
+
+	virtual void get_import_options(List<ResourceImporter::ImportOption> *r_options);
+	virtual Variant get_option_visibility(const String &p_option, const Map<StringName, Variant> &p_options) const;
+
+	virtual void pre_process(Node *p_scene, const Map<StringName, Variant> &p_options);
+	virtual void post_process(Node *p_scene, const Map<StringName, Variant> &p_options);
+
+	EditorScenePostImportPlugin() {}
+};
+
+VARIANT_ENUM_CAST(EditorScenePostImportPlugin::InternalImportCategory)
+
 class ResourceImporterScene : public ResourceImporter {
 class ResourceImporterScene : public ResourceImporter {
 	GDCLASS(ResourceImporterScene, ResourceImporter);
 	GDCLASS(ResourceImporterScene, ResourceImporter);
 
 
-	Set<Ref<EditorSceneImporter>> importers;
+	Set<Ref<EditorSceneFormatImporter>> importers;
 
 
 	static ResourceImporterScene *singleton;
 	static ResourceImporterScene *singleton;
 
 
@@ -158,13 +212,18 @@ class ResourceImporterScene : public ResourceImporter {
 
 
 	void _optimize_track_usage(AnimationPlayer *p_player, AnimationImportTracks *p_track_actions);
 	void _optimize_track_usage(AnimationPlayer *p_player, AnimationImportTracks *p_track_actions);
 
 
+	mutable Vector<Ref<EditorScenePostImportPlugin>> post_importer_plugins;
+
 public:
 public:
 	static ResourceImporterScene *get_singleton() { return singleton; }
 	static ResourceImporterScene *get_singleton() { return singleton; }
 
 
-	const Set<Ref<EditorSceneImporter>> &get_importers() const { return importers; }
+	void add_post_importer_plugin(const Ref<EditorScenePostImportPlugin> &p_plugin) { post_importer_plugins.push_back(p_plugin); }
+	void remove_post_importer_plugin(const Ref<EditorScenePostImportPlugin> &p_plugin) { post_importer_plugins.erase(p_plugin); }
 
 
-	void add_importer(Ref<EditorSceneImporter> p_importer) { importers.insert(p_importer); }
-	void remove_importer(Ref<EditorSceneImporter> p_importer) { importers.erase(p_importer); }
+	const Set<Ref<EditorSceneFormatImporter>> &get_importers() const { return importers; }
+
+	void add_importer(Ref<EditorSceneFormatImporter> p_importer) { importers.insert(p_importer); }
+	void remove_importer(Ref<EditorSceneFormatImporter> p_importer) { importers.erase(p_importer); }
 
 
 	virtual String get_importer_name() const override;
 	virtual String get_importer_name() const override;
 	virtual String get_visible_name() const override;
 	virtual String get_visible_name() const override;
@@ -177,13 +236,13 @@ public:
 	virtual String get_preset_name(int p_idx) const override;
 	virtual String get_preset_name(int p_idx) const override;
 
 
 	enum InternalImportCategory {
 	enum InternalImportCategory {
-		INTERNAL_IMPORT_CATEGORY_NODE,
-		INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE,
-		INTERNAL_IMPORT_CATEGORY_MESH,
-		INTERNAL_IMPORT_CATEGORY_MATERIAL,
-		INTERNAL_IMPORT_CATEGORY_ANIMATION,
-		INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE,
-		INTERNAL_IMPORT_CATEGORY_MAX
+		INTERNAL_IMPORT_CATEGORY_NODE = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_NODE,
+		INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MESH_3D_NODE,
+		INTERNAL_IMPORT_CATEGORY_MESH = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MESH,
+		INTERNAL_IMPORT_CATEGORY_MATERIAL = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MATERIAL,
+		INTERNAL_IMPORT_CATEGORY_ANIMATION = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_ANIMATION,
+		INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_ANIMATION_NODE,
+		INTERNAL_IMPORT_CATEGORY_MAX = EditorScenePostImportPlugin::INTERNAL_IMPORT_CATEGORY_MAX
 	};
 	};
 
 
 	void get_internal_import_options(InternalImportCategory p_category, List<ImportOption> *r_options) const;
 	void get_internal_import_options(InternalImportCategory p_category, List<ImportOption> *r_options) const;
@@ -205,8 +264,8 @@ public:
 	Node *pre_import(const String &p_source_file);
 	Node *pre_import(const String &p_source_file);
 	virtual Error import(const String &p_source_file, const String &p_save_path, const Map<StringName, Variant> &p_options, List<String> *r_platform_variants, List<String> *r_gen_files = nullptr, Variant *r_metadata = nullptr) override;
 	virtual Error import(const String &p_source_file, const String &p_save_path, const Map<StringName, Variant> &p_options, List<String> *r_platform_variants, List<String> *r_gen_files = nullptr, Variant *r_metadata = nullptr) override;
 
 
-	Node *import_scene_from_other_importer(EditorSceneImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps);
-	Ref<Animation> import_animation_from_other_importer(EditorSceneImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps);
+	Node *import_scene_from_other_importer(EditorSceneFormatImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps);
+	Ref<Animation> import_animation_from_other_importer(EditorSceneFormatImporter *p_exception, const String &p_path, uint32_t p_flags, int p_bake_fps);
 
 
 	virtual bool has_advanced_options() const override;
 	virtual bool has_advanced_options() const override;
 	virtual void show_advanced_options(const String &p_path) override;
 	virtual void show_advanced_options(const String &p_path) override;
@@ -222,8 +281,8 @@ public:
 	static Transform3D get_collision_shapes_transform(const M &p_options);
 	static Transform3D get_collision_shapes_transform(const M &p_options);
 };
 };
 
 
-class EditorSceneImporterESCN : public EditorSceneImporter {
-	GDCLASS(EditorSceneImporterESCN, EditorSceneImporter);
+class EditorSceneFormatImporterESCN : public EditorSceneFormatImporter {
+	GDCLASS(EditorSceneFormatImporterESCN, EditorSceneFormatImporter);
 
 
 public:
 public:
 	virtual uint32_t get_import_flags() const override;
 	virtual uint32_t get_import_flags() const override;

+ 11 - 11
modules/fbx/editor_scene_importer_fbx.cpp

@@ -56,7 +56,7 @@
 
 
 #include <string>
 #include <string>
 
 
-void EditorSceneImporterFBX::get_extensions(List<String> *r_extensions) const {
+void EditorSceneFormatImporterFBX::get_extensions(List<String> *r_extensions) const {
 	// register FBX as the one and only format for FBX importing
 	// register FBX as the one and only format for FBX importing
 	const String import_setting_string = "filesystem/import/fbx/";
 	const String import_setting_string = "filesystem/import/fbx/";
 	const String fbx_str = "fbx";
 	const String fbx_str = "fbx";
@@ -65,7 +65,7 @@ void EditorSceneImporterFBX::get_extensions(List<String> *r_extensions) const {
 	_register_project_setting_import(fbx_str, import_setting_string, exts, r_extensions, true);
 	_register_project_setting_import(fbx_str, import_setting_string, exts, r_extensions, true);
 }
 }
 
 
-void EditorSceneImporterFBX::_register_project_setting_import(const String generic,
+void EditorSceneFormatImporterFBX::_register_project_setting_import(const String generic,
 		const String import_setting_string,
 		const String import_setting_string,
 		const Vector<String> &exts,
 		const Vector<String> &exts,
 		List<String> *r_extensions,
 		List<String> *r_extensions,
@@ -79,11 +79,11 @@ void EditorSceneImporterFBX::_register_project_setting_import(const String gener
 	}
 	}
 }
 }
 
 
-uint32_t EditorSceneImporterFBX::get_import_flags() const {
+uint32_t EditorSceneFormatImporterFBX::get_import_flags() const {
 	return IMPORT_SCENE;
 	return IMPORT_SCENE;
 }
 }
 
 
-Node3D *EditorSceneImporterFBX::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps,
+Node3D *EditorSceneFormatImporterFBX::import_scene(const String &p_path, uint32_t p_flags, int p_bake_fps,
 		List<String> *r_missing_deps, Error *r_err) {
 		List<String> *r_missing_deps, Error *r_err) {
 	// done for performance when re-importing lots of files when testing importer in verbose only!
 	// done for performance when re-importing lots of files when testing importer in verbose only!
 	if (OS::get_singleton()->is_stdout_verbose()) {
 	if (OS::get_singleton()->is_stdout_verbose()) {
@@ -232,7 +232,7 @@ Node3D *EditorSceneImporterFBX::import_scene(const String &p_path, uint32_t p_fl
 }
 }
 
 
 template <class T>
 template <class T>
-struct EditorSceneImporterAssetImportInterpolate {
+struct EditorSceneFormatImporterAssetImportInterpolate {
 	T lerp(const T &a, const T &b, float c) const {
 	T lerp(const T &a, const T &b, float c) const {
 		return a + (b - a) * c;
 		return a + (b - a) * c;
 	}
 	}
@@ -258,7 +258,7 @@ struct EditorSceneImporterAssetImportInterpolate {
 
 
 //thank you for existing, partial specialization
 //thank you for existing, partial specialization
 template <>
 template <>
-struct EditorSceneImporterAssetImportInterpolate<Quaternion> {
+struct EditorSceneFormatImporterAssetImportInterpolate<Quaternion> {
 	Quaternion lerp(const Quaternion &a, const Quaternion &b, float c) const {
 	Quaternion lerp(const Quaternion &a, const Quaternion &b, float c) const {
 		ERR_FAIL_COND_V(!a.is_normalized(), Quaternion());
 		ERR_FAIL_COND_V(!a.is_normalized(), Quaternion());
 		ERR_FAIL_COND_V(!b.is_normalized(), Quaternion());
 		ERR_FAIL_COND_V(!b.is_normalized(), Quaternion());
@@ -282,7 +282,7 @@ struct EditorSceneImporterAssetImportInterpolate<Quaternion> {
 };
 };
 
 
 template <class T>
 template <class T>
-T EditorSceneImporterFBX::_interpolate_track(const Vector<float> &p_times, const Vector<T> &p_values, float p_time,
+T EditorSceneFormatImporterFBX::_interpolate_track(const Vector<float> &p_times, const Vector<T> &p_values, float p_time,
 		AssetImportAnimation::Interpolation p_interp) {
 		AssetImportAnimation::Interpolation p_interp) {
 	//could use binary search, worth it?
 	//could use binary search, worth it?
 	int idx = -1;
 	int idx = -1;
@@ -293,7 +293,7 @@ T EditorSceneImporterFBX::_interpolate_track(const Vector<float> &p_times, const
 		idx++;
 		idx++;
 	}
 	}
 
 
-	EditorSceneImporterAssetImportInterpolate<T> interp;
+	EditorSceneFormatImporterAssetImportInterpolate<T> interp;
 
 
 	switch (p_interp) {
 	switch (p_interp) {
 		case AssetImportAnimation::INTERP_LINEAR: {
 		case AssetImportAnimation::INTERP_LINEAR: {
@@ -352,7 +352,7 @@ T EditorSceneImporterFBX::_interpolate_track(const Vector<float> &p_times, const
 	ERR_FAIL_V(p_values[0]);
 	ERR_FAIL_V(p_values[0]);
 }
 }
 
 
-Node3D *EditorSceneImporterFBX::_generate_scene(
+Node3D *EditorSceneFormatImporterFBX::_generate_scene(
 		const String &p_path,
 		const String &p_path,
 		const FBXDocParser::Document *p_document,
 		const FBXDocParser::Document *p_document,
 		const uint32_t p_flags,
 		const uint32_t p_flags,
@@ -1294,7 +1294,7 @@ Node3D *EditorSceneImporterFBX::_generate_scene(
 	return scene_root;
 	return scene_root;
 }
 }
 
 
-void EditorSceneImporterFBX::BuildDocumentBones(Ref<FBXBone> p_parent_bone,
+void EditorSceneFormatImporterFBX::BuildDocumentBones(Ref<FBXBone> p_parent_bone,
 		ImportState &state, const FBXDocParser::Document *p_doc,
 		ImportState &state, const FBXDocParser::Document *p_doc,
 		uint64_t p_id) {
 		uint64_t p_id) {
 	const std::vector<const FBXDocParser::Connection *> &conns = p_doc->GetConnectionsByDestinationSequenced(p_id, "Model");
 	const std::vector<const FBXDocParser::Connection *> &conns = p_doc->GetConnectionsByDestinationSequenced(p_id, "Model");
@@ -1383,7 +1383,7 @@ void EditorSceneImporterFBX::BuildDocumentBones(Ref<FBXBone> p_parent_bone,
 	}
 	}
 }
 }
 
 
-void EditorSceneImporterFBX::BuildDocumentNodes(
+void EditorSceneFormatImporterFBX::BuildDocumentNodes(
 		Ref<PivotTransform> parent_transform,
 		Ref<PivotTransform> parent_transform,
 		ImportState &state,
 		ImportState &state,
 		const FBXDocParser::Document *p_doc,
 		const FBXDocParser::Document *p_doc,

+ 4 - 4
modules/fbx/editor_scene_importer_fbx.h

@@ -57,9 +57,9 @@
 
 
 #define CONVERT_FBX_TIME(time) static_cast<double>(time) / 46186158000LL
 #define CONVERT_FBX_TIME(time) static_cast<double>(time) / 46186158000LL
 
 
-class EditorSceneImporterFBX : public EditorSceneImporter {
+class EditorSceneFormatImporterFBX : public EditorSceneFormatImporter {
 private:
 private:
-	GDCLASS(EditorSceneImporterFBX, EditorSceneImporter);
+	GDCLASS(EditorSceneFormatImporterFBX, EditorSceneFormatImporter);
 
 
 	struct AssetImportAnimation {
 	struct AssetImportAnimation {
 		enum Interpolation {
 		enum Interpolation {
@@ -122,8 +122,8 @@ private:
 	void _register_project_setting_import(const String generic, const String import_setting_string, const Vector<String> &exts, List<String> *r_extensions, const bool p_enabled) const;
 	void _register_project_setting_import(const String generic, const String import_setting_string, const Vector<String> &exts, List<String> *r_extensions, const bool p_enabled) const;
 
 
 public:
 public:
-	EditorSceneImporterFBX() {}
-	~EditorSceneImporterFBX() {}
+	EditorSceneFormatImporterFBX() {}
+	~EditorSceneFormatImporterFBX() {}
 
 
 	virtual void get_extensions(List<String> *r_extensions) const override;
 	virtual void get_extensions(List<String> *r_extensions) const override;
 	virtual uint32_t get_import_flags() const override;
 	virtual uint32_t get_import_flags() const override;

+ 2 - 2
modules/fbx/register_types.cpp

@@ -35,7 +35,7 @@
 
 
 #ifdef TOOLS_ENABLED
 #ifdef TOOLS_ENABLED
 static void _editor_init() {
 static void _editor_init() {
-	Ref<EditorSceneImporterFBX> import_fbx;
+	Ref<EditorSceneFormatImporterFBX> import_fbx;
 	import_fbx.instantiate();
 	import_fbx.instantiate();
 	ResourceImporterScene::get_singleton()->add_importer(import_fbx);
 	ResourceImporterScene::get_singleton()->add_importer(import_fbx);
 }
 }
@@ -46,7 +46,7 @@ void register_fbx_types() {
 	ClassDB::APIType prev_api = ClassDB::get_current_api();
 	ClassDB::APIType prev_api = ClassDB::get_current_api();
 	ClassDB::set_current_api(ClassDB::API_EDITOR);
 	ClassDB::set_current_api(ClassDB::API_EDITOR);
 
 
-	GDREGISTER_CLASS(EditorSceneImporterFBX);
+	GDREGISTER_CLASS(EditorSceneFormatImporterFBX);
 
 
 	ClassDB::set_current_api(prev_api);
 	ClassDB::set_current_api(prev_api);
 
 

+ 4 - 4
modules/gltf/editor_scene_importer_gltf.cpp

@@ -38,16 +38,16 @@
 #include "scene/animation/animation_player.h"
 #include "scene/animation/animation_player.h"
 #include "scene/resources/animation.h"
 #include "scene/resources/animation.h"
 
 
-uint32_t EditorSceneImporterGLTF::get_import_flags() const {
+uint32_t EditorSceneFormatImporterGLTF::get_import_flags() const {
 	return ImportFlags::IMPORT_SCENE | ImportFlags::IMPORT_ANIMATION;
 	return ImportFlags::IMPORT_SCENE | ImportFlags::IMPORT_ANIMATION;
 }
 }
 
 
-void EditorSceneImporterGLTF::get_extensions(List<String> *r_extensions) const {
+void EditorSceneFormatImporterGLTF::get_extensions(List<String> *r_extensions) const {
 	r_extensions->push_back("gltf");
 	r_extensions->push_back("gltf");
 	r_extensions->push_back("glb");
 	r_extensions->push_back("glb");
 }
 }
 
 
-Node *EditorSceneImporterGLTF::import_scene(const String &p_path,
+Node *EditorSceneFormatImporterGLTF::import_scene(const String &p_path,
 		uint32_t p_flags, int p_bake_fps,
 		uint32_t p_flags, int p_bake_fps,
 		List<String> *r_missing_deps,
 		List<String> *r_missing_deps,
 		Error *r_err) {
 		Error *r_err) {
@@ -56,7 +56,7 @@ Node *EditorSceneImporterGLTF::import_scene(const String &p_path,
 	return doc->import_scene_gltf(p_path, p_flags, p_bake_fps, Ref<GLTFState>(), r_missing_deps, r_err);
 	return doc->import_scene_gltf(p_path, p_flags, p_bake_fps, Ref<GLTFState>(), r_missing_deps, r_err);
 }
 }
 
 
-Ref<Animation> EditorSceneImporterGLTF::import_animation(const String &p_path,
+Ref<Animation> EditorSceneFormatImporterGLTF::import_animation(const String &p_path,
 		uint32_t p_flags,
 		uint32_t p_flags,
 		int p_bake_fps) {
 		int p_bake_fps) {
 	return Ref<Animation>();
 	return Ref<Animation>();

+ 2 - 2
modules/gltf/editor_scene_importer_gltf.h

@@ -41,8 +41,8 @@
 
 
 class Animation;
 class Animation;
 
 
-class EditorSceneImporterGLTF : public EditorSceneImporter {
-	GDCLASS(EditorSceneImporterGLTF, EditorSceneImporter);
+class EditorSceneFormatImporterGLTF : public EditorSceneFormatImporter {
+	GDCLASS(EditorSceneFormatImporterGLTF, EditorSceneFormatImporter);
 
 
 public:
 public:
 	virtual uint32_t get_import_flags() const override;
 	virtual uint32_t get_import_flags() const override;

+ 4 - 4
modules/gltf/gltf_document.cpp

@@ -5684,7 +5684,7 @@ void GLTFDocument::_generate_skeleton_bone_node(Ref<GLTFState> state, Node *scen
 }
 }
 
 
 template <class T>
 template <class T>
-struct EditorSceneImporterGLTFInterpolate {
+struct EditorSceneFormatImporterGLTFInterpolate {
 	T lerp(const T &a, const T &b, float c) const {
 	T lerp(const T &a, const T &b, float c) const {
 		return a + (b - a) * c;
 		return a + (b - a) * c;
 	}
 	}
@@ -5710,7 +5710,7 @@ struct EditorSceneImporterGLTFInterpolate {
 
 
 // thank you for existing, partial specialization
 // thank you for existing, partial specialization
 template <>
 template <>
-struct EditorSceneImporterGLTFInterpolate<Quaternion> {
+struct EditorSceneFormatImporterGLTFInterpolate<Quaternion> {
 	Quaternion lerp(const Quaternion &a, const Quaternion &b, const float c) const {
 	Quaternion lerp(const Quaternion &a, const Quaternion &b, const float c) const {
 		ERR_FAIL_COND_V_MSG(!a.is_normalized(), Quaternion(), "The quaternion \"a\" must be normalized.");
 		ERR_FAIL_COND_V_MSG(!a.is_normalized(), Quaternion(), "The quaternion \"a\" must be normalized.");
 		ERR_FAIL_COND_V_MSG(!b.is_normalized(), Quaternion(), "The quaternion \"b\" must be normalized.");
 		ERR_FAIL_COND_V_MSG(!b.is_normalized(), Quaternion(), "The quaternion \"b\" must be normalized.");
@@ -5749,7 +5749,7 @@ T GLTFDocument::_interpolate_track(const Vector<float> &p_times, const Vector<T>
 		idx++;
 		idx++;
 	}
 	}
 
 
-	EditorSceneImporterGLTFInterpolate<T> interp;
+	EditorSceneFormatImporterGLTFInterpolate<T> interp;
 
 
 	switch (p_interp) {
 	switch (p_interp) {
 		case GLTFAnimation::INTERP_LINEAR: {
 		case GLTFAnimation::INTERP_LINEAR: {
@@ -6833,7 +6833,7 @@ Node *GLTFDocument::import_scene_gltf(const String &p_path, uint32_t p_flags, in
 		r_state.instantiate();
 		r_state.instantiate();
 	}
 	}
 	r_state->use_named_skin_binds =
 	r_state->use_named_skin_binds =
-			p_flags & EditorSceneImporter::IMPORT_USE_NAMED_SKIN_BINDS;
+			p_flags & EditorSceneFormatImporter::IMPORT_USE_NAMED_SKIN_BINDS;
 
 
 	Ref<GLTFDocument> gltf_document;
 	Ref<GLTFDocument> gltf_document;
 	gltf_document.instantiate();
 	gltf_document.instantiate();

+ 2 - 2
modules/gltf/register_types.cpp

@@ -52,7 +52,7 @@
 #ifndef _3D_DISABLED
 #ifndef _3D_DISABLED
 #ifdef TOOLS_ENABLED
 #ifdef TOOLS_ENABLED
 static void _editor_init() {
 static void _editor_init() {
-	Ref<EditorSceneImporterGLTF> import_gltf;
+	Ref<EditorSceneFormatImporterGLTF> import_gltf;
 	import_gltf.instantiate();
 	import_gltf.instantiate();
 	ResourceImporterScene::get_singleton()->add_importer(import_gltf);
 	ResourceImporterScene::get_singleton()->add_importer(import_gltf);
 }
 }
@@ -64,7 +64,7 @@ void register_gltf_types() {
 #ifdef TOOLS_ENABLED
 #ifdef TOOLS_ENABLED
 	ClassDB::APIType prev_api = ClassDB::get_current_api();
 	ClassDB::APIType prev_api = ClassDB::get_current_api();
 	ClassDB::set_current_api(ClassDB::API_EDITOR);
 	ClassDB::set_current_api(ClassDB::API_EDITOR);
-	GDREGISTER_CLASS(EditorSceneImporterGLTF);
+	GDREGISTER_CLASS(EditorSceneFormatImporterGLTF);
 	GDREGISTER_CLASS(GLTFMesh);
 	GDREGISTER_CLASS(GLTFMesh);
 	EditorPlugins::add_by_type<SceneExporterGLTFPlugin>();
 	EditorPlugins::add_by_type<SceneExporterGLTFPlugin>();
 	ClassDB::set_current_api(prev_api);
 	ClassDB::set_current_api(prev_api);

+ 3 - 3
scene/resources/importer_mesh.cpp

@@ -997,7 +997,7 @@ Ref<NavigationMesh> ImporterMesh::create_navigation_mesh() {
 
 
 extern bool (*array_mesh_lightmap_unwrap_callback)(float p_texel_size, const float *p_vertices, const float *p_normals, int p_vertex_count, const int *p_indices, int p_index_count, const uint8_t *p_cache_data, bool *r_use_cache, uint8_t **r_mesh_cache, int *r_mesh_cache_size, float **r_uv, int **r_vertex, int *r_vertex_count, int **r_index, int *r_index_count, int *r_size_hint_x, int *r_size_hint_y);
 extern bool (*array_mesh_lightmap_unwrap_callback)(float p_texel_size, const float *p_vertices, const float *p_normals, int p_vertex_count, const int *p_indices, int p_index_count, const uint8_t *p_cache_data, bool *r_use_cache, uint8_t **r_mesh_cache, int *r_mesh_cache_size, float **r_uv, int **r_vertex, int *r_vertex_count, int **r_index, int *r_index_count, int *r_size_hint_x, int *r_size_hint_y);
 
 
-struct EditorSceneImporterMeshLightmapSurface {
+struct EditorSceneFormatImporterMeshLightmapSurface {
 	Ref<Material> material;
 	Ref<Material> material;
 	LocalVector<SurfaceTool::Vertex> vertices;
 	LocalVector<SurfaceTool::Vertex> vertices;
 	Mesh::PrimitiveType primitive = Mesh::PrimitiveType::PRIMITIVE_MAX;
 	Mesh::PrimitiveType primitive = Mesh::PrimitiveType::PRIMITIVE_MAX;
@@ -1015,7 +1015,7 @@ Error ImporterMesh::lightmap_unwrap_cached(const Transform3D &p_base_transform,
 	LocalVector<float> uv;
 	LocalVector<float> uv;
 	LocalVector<Pair<int, int>> uv_indices;
 	LocalVector<Pair<int, int>> uv_indices;
 
 
-	Vector<EditorSceneImporterMeshLightmapSurface> lightmap_surfaces;
+	Vector<EditorSceneFormatImporterMeshLightmapSurface> lightmap_surfaces;
 
 
 	// Keep only the scale
 	// Keep only the scale
 	Basis basis = p_base_transform.get_basis();
 	Basis basis = p_base_transform.get_basis();
@@ -1027,7 +1027,7 @@ Error ImporterMesh::lightmap_unwrap_cached(const Transform3D &p_base_transform,
 	Basis normal_basis = transform.basis.inverse().transposed();
 	Basis normal_basis = transform.basis.inverse().transposed();
 
 
 	for (int i = 0; i < get_surface_count(); i++) {
 	for (int i = 0; i < get_surface_count(); i++) {
-		EditorSceneImporterMeshLightmapSurface s;
+		EditorSceneFormatImporterMeshLightmapSurface s;
 		s.primitive = get_surface_primitive_type(i);
 		s.primitive = get_surface_primitive_type(i);
 
 
 		ERR_FAIL_COND_V_MSG(s.primitive != Mesh::PRIMITIVE_TRIANGLES, ERR_UNAVAILABLE, "Only triangles are supported for lightmap unwrap.");
 		ERR_FAIL_COND_V_MSG(s.primitive != Mesh::PRIMITIVE_TRIANGLES, ERR_UNAVAILABLE, "Only triangles are supported for lightmap unwrap.");