diff options
-rw-r--r-- | doc/classes/EditorImportPlugin.xml | 3 | ||||
-rw-r--r-- | editor/editor_file_system.cpp | 62 | ||||
-rw-r--r-- | editor/editor_file_system.h | 4 | ||||
-rw-r--r-- | editor/import/editor_import_plugin.cpp | 10 | ||||
-rw-r--r-- | editor/import/editor_import_plugin.h | 4 | ||||
-rw-r--r-- | modules/gltf/gltf_document.cpp | 63 |
6 files changed, 68 insertions, 78 deletions
diff --git a/doc/classes/EditorImportPlugin.xml b/doc/classes/EditorImportPlugin.xml index 1d6a642ab2..66b61f187e 100644 --- a/doc/classes/EditorImportPlugin.xml +++ b/doc/classes/EditorImportPlugin.xml @@ -232,8 +232,9 @@ <param index="0" name="path" type="String" /> <param index="1" name="custom_options" type="Dictionary" default="{}" /> <param index="2" name="custom_importer" type="String" default="""" /> + <param index="3" name="generator_parameters" type="Variant" default="null" /> <description> - This function can only be called during the [method _import] callback and it allows manually importing resources from it. This is useful when the imported file generates external resources that require importing (as example, images). Custom parameters for the ".import" file can be passed via the [param custom_options]. Additionally, in cases where multiple importers can handle a file, the [param custom_importer] ca be specified to force a specific one. This function performs a resource import and returns immediately with a success or error code. + This function can only be called during the [method _import] callback and it allows manually importing resources from it. This is useful when the imported file generates external resources that require importing (as example, images). Custom parameters for the ".import" file can be passed via the [param custom_options]. Additionally, in cases where multiple importers can handle a file, the [param custom_importer] ca be specified to force a specific one. This function performs a resource import and returns immediately with a success or error code. [param generator_parameters] defines optional extra metadata which will be stored as [code]generator_parameters[/code] in the [code]remap[/code] section of the [code].import[/code] file, for example to store a md5 hash of the source data. </description> </method> </methods> diff --git a/editor/editor_file_system.cpp b/editor/editor_file_system.cpp index dc594e1e9b..ec1ef8a6bc 100644 --- a/editor/editor_file_system.cpp +++ b/editor/editor_file_system.cpp @@ -1900,7 +1900,7 @@ Error EditorFileSystem::_reimport_group(const String &p_group_file, const Vector return err; } -Error EditorFileSystem::_reimport_file(const String &p_file, const HashMap<StringName, Variant> *p_custom_options, const String &p_custom_importer) { +Error EditorFileSystem::_reimport_file(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer, Variant *p_generator_parameters) { EditorFileSystemDirectory *fs = nullptr; int cpos = -1; bool found = _find_file(p_file, &fs, cpos); @@ -1908,46 +1908,48 @@ Error EditorFileSystem::_reimport_file(const String &p_file, const HashMap<Strin //try to obtain existing params - HashMap<StringName, Variant> params; + HashMap<StringName, Variant> params = p_custom_options; String importer_name; //empty by default though if (!p_custom_importer.is_empty()) { importer_name = p_custom_importer; } - if (p_custom_options != nullptr) { - params = *p_custom_options; - } ResourceUID::ID uid = ResourceUID::INVALID_ID; - Variant gen_params; + Variant generator_parameters; + if (p_generator_parameters) { + generator_parameters = *p_generator_parameters; + } if (FileAccess::exists(p_file + ".import")) { //use existing - if (p_custom_options == nullptr) { - Ref<ConfigFile> cf; - cf.instantiate(); - Error err = cf->load(p_file + ".import"); - if (err == OK) { - if (cf->has_section("params")) { - List<String> sk; - cf->get_section_keys("params", &sk); - for (const String &E : sk) { + Ref<ConfigFile> cf; + cf.instantiate(); + Error err = cf->load(p_file + ".import"); + if (err == OK) { + if (cf->has_section("params")) { + List<String> sk; + cf->get_section_keys("params", &sk); + for (const String &E : sk) { + if (!params.has(E)) { params[E] = cf->get_value("params", E); } } + } - if (cf->has_section("remap")) { - if (p_custom_importer.is_empty()) { - importer_name = cf->get_value("remap", "importer"); - } + if (cf->has_section("remap")) { + if (p_custom_importer.is_empty()) { + importer_name = cf->get_value("remap", "importer"); + } - if (cf->has_section_key("remap", "uid")) { - String uidt = cf->get_value("remap", "uid"); - uid = ResourceUID::get_singleton()->text_to_id(uidt); - } + if (cf->has_section_key("remap", "uid")) { + String uidt = cf->get_value("remap", "uid"); + uid = ResourceUID::get_singleton()->text_to_id(uidt); + } - if (cf->has_section_key("remap", "gen_params")) { - gen_params = cf->get_value("remap", "gen_params"); + if (!p_generator_parameters) { + if (cf->has_section_key("remap", "generator_parameters")) { + generator_parameters = cf->get_value("remap", "generator_parameters"); } } } @@ -2061,8 +2063,8 @@ Error EditorFileSystem::_reimport_file(const String &p_file, const HashMap<Strin f->store_line("metadata=" + meta.get_construct_string()); } - if (gen_params != Variant()) { - f->store_line("gen_params=" + gen_params.get_construct_string()); + if (generator_parameters != Variant()) { + f->store_line("generator_parameters=" + generator_parameters.get_construct_string()); } f->store_line(""); @@ -2164,7 +2166,7 @@ void EditorFileSystem::_find_group_files(EditorFileSystemDirectory *efd, HashMap } void EditorFileSystem::reimport_file_with_custom_parameters(const String &p_file, const String &p_importer, const HashMap<StringName, Variant> &p_custom_params) { - _reimport_file(p_file, &p_custom_params, p_importer); + _reimport_file(p_file, p_custom_params, p_importer); } void EditorFileSystem::_reimport_thread(uint32_t p_index, ImportThreadData *p_import_data) { @@ -2301,9 +2303,9 @@ void EditorFileSystem::reimport_files(const Vector<String> &p_files) { emit_signal(SNAME("resources_reimported"), reloads); } -Error EditorFileSystem::reimport_append(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer) { +Error EditorFileSystem::reimport_append(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer, Variant p_generator_parameters) { ERR_FAIL_COND_V_MSG(!importing, ERR_INVALID_PARAMETER, "Can only append files to import during a current reimport process."); - return _reimport_file(p_file, &p_custom_options, p_custom_importer); + return _reimport_file(p_file, p_custom_options, p_custom_importer, &p_generator_parameters); } Error EditorFileSystem::_resource_import(const String &p_path) { diff --git a/editor/editor_file_system.h b/editor/editor_file_system.h index 79101813ac..0d558c84c5 100644 --- a/editor/editor_file_system.h +++ b/editor/editor_file_system.h @@ -242,7 +242,7 @@ class EditorFileSystem : public Node { void _update_extensions(); - Error _reimport_file(const String &p_file, const HashMap<StringName, Variant> *p_custom_options = nullptr, const String &p_custom_importer = String()); + Error _reimport_file(const String &p_file, const HashMap<StringName, Variant> &p_custom_options = HashMap<StringName, Variant>(), const String &p_custom_importer = String(), Variant *generator_parameters = nullptr); Error _reimport_group(const String &p_group_file, const Vector<String> &p_files); bool _test_for_reimport(const String &p_path, bool p_only_imported_files); @@ -315,7 +315,7 @@ public: EditorFileSystemDirectory *find_file(const String &p_file, int *r_index) const; void reimport_files(const Vector<String> &p_files); - Error reimport_append(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer = String()); + Error reimport_append(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer, Variant p_generator_parameters); void reimport_file_with_custom_parameters(const String &p_file, const String &p_importer, const HashMap<StringName, Variant> &p_custom_params); diff --git a/editor/import/editor_import_plugin.cpp b/editor/import/editor_import_plugin.cpp index 7de79881d0..7afce116b8 100644 --- a/editor/import/editor_import_plugin.cpp +++ b/editor/import/editor_import_plugin.cpp @@ -186,18 +186,18 @@ Error EditorImportPlugin::import(const String &p_source_file, const String &p_sa ERR_FAIL_V_MSG(ERR_METHOD_NOT_FOUND, "Unimplemented _import in add-on."); } -Error EditorImportPlugin::_append_import_external_resource(const String &p_file, const Dictionary &p_custom_options, const String &p_custom_importer) { +Error EditorImportPlugin::_append_import_external_resource(const String &p_file, const Dictionary &p_custom_options, const String &p_custom_importer, Variant p_generator_parameters) { HashMap<StringName, Variant> options; List<Variant> keys; p_custom_options.get_key_list(&keys); for (const Variant &K : keys) { options.insert(K, p_custom_options[K]); } - return append_import_external_resource(p_file, options, p_custom_importer); + return append_import_external_resource(p_file, options, p_custom_importer, p_generator_parameters); } -Error EditorImportPlugin::append_import_external_resource(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer) { - return EditorFileSystem::get_singleton()->reimport_append(p_file, p_custom_options, p_custom_importer); +Error EditorImportPlugin::append_import_external_resource(const String &p_file, const HashMap<StringName, Variant> &p_custom_options, const String &p_custom_importer, Variant p_generator_parameters) { + return EditorFileSystem::get_singleton()->reimport_append(p_file, p_custom_options, p_custom_importer, p_generator_parameters); } void EditorImportPlugin::_bind_methods() { @@ -213,5 +213,5 @@ void EditorImportPlugin::_bind_methods() { GDVIRTUAL_BIND(_get_import_order) GDVIRTUAL_BIND(_get_option_visibility, "path", "option_name", "options") GDVIRTUAL_BIND(_import, "source_file", "save_path", "options", "platform_variants", "gen_files"); - ClassDB::bind_method(D_METHOD("append_import_external_resource", "path", "custom_options", "custom_importer"), &EditorImportPlugin::_append_import_external_resource, DEFVAL(Dictionary()), DEFVAL(String())); + ClassDB::bind_method(D_METHOD("append_import_external_resource", "path", "custom_options", "custom_importer", "generator_parameters"), &EditorImportPlugin::_append_import_external_resource, DEFVAL(Dictionary()), DEFVAL(String()), DEFVAL(Variant())); } diff --git a/editor/import/editor_import_plugin.h b/editor/import/editor_import_plugin.h index 448659d4e3..fb164c7f15 100644 --- a/editor/import/editor_import_plugin.h +++ b/editor/import/editor_import_plugin.h @@ -53,7 +53,7 @@ protected: GDVIRTUAL3RC(bool, _get_option_visibility, String, StringName, Dictionary) GDVIRTUAL5RC(Error, _import, String, String, Dictionary, TypedArray<String>, TypedArray<String>) - Error _append_import_external_resource(const String &p_file, const Dictionary &p_custom_options = Dictionary(), const String &p_custom_importer = String()); + Error _append_import_external_resource(const String &p_file, const Dictionary &p_custom_options = Dictionary(), const String &p_custom_importer = String(), Variant p_generator_parameters = Variant()); public: EditorImportPlugin(); @@ -69,7 +69,7 @@ public: virtual void get_import_options(const String &p_path, List<ImportOption> *r_options, int p_preset) const override; virtual bool get_option_visibility(const String &p_path, const String &p_option, const HashMap<StringName, Variant> &p_options) const override; virtual Error import(const String &p_source_file, const String &p_save_path, const HashMap<StringName, Variant> &p_options, List<String> *r_platform_variants, List<String> *r_gen_files, Variant *r_metadata = nullptr) override; - Error append_import_external_resource(const String &p_file, const HashMap<StringName, Variant> &p_custom_options = HashMap<StringName, Variant>(), const String &p_custom_importer = String()); + Error append_import_external_resource(const String &p_file, const HashMap<StringName, Variant> &p_custom_options = HashMap<StringName, Variant>(), const String &p_custom_importer = String(), Variant p_generator_parameters = Variant()); }; #endif // EDITOR_IMPORT_PLUGIN_H diff --git a/modules/gltf/gltf_document.cpp b/modules/gltf/gltf_document.cpp index 1a09b5bdcc..bd3ee1881f 100644 --- a/modules/gltf/gltf_document.cpp +++ b/modules/gltf/gltf_document.cpp @@ -54,6 +54,9 @@ #include "modules/modules_enabled.gen.h" // For csg, gridmap. +#ifdef TOOLS_ENABLED +#include "editor/editor_file_system.h" +#endif #ifdef MODULE_CSG_ENABLED #include "modules/csg/csg_shape.h" #endif // MODULE_CSG_ENABLED @@ -3232,54 +3235,38 @@ Error GLTFDocument::_parse_images(Ref<GLTFState> p_state, const String &p_base_p p_state->source_images.push_back(Ref<Image>()); } else { Error err = OK; - bool must_import = false; + bool must_import = true; + Vector<uint8_t> img_data = img->get_data(); + Dictionary generator_parameters; String file_path = p_state->get_base_path() + "/" + p_state->filename.get_basename() + "_" + img->get_name() + ".png"; - if (!FileAccess::exists(file_path + ".import")) { + if (FileAccess::exists(file_path + ".import")) { Ref<ConfigFile> config; config.instantiate(); - config->set_value("remap", "importer", "texture"); - config->set_value("remap", "type", "Texture2D"); - // Currently, it will likely use project defaults of Detect 3D, so textures will be reimported again. - if (!config->has_section_key("params", "mipmaps/generate")) { - config->set_value("params", "mipmaps/generate", true); + config->load(file_path + ".import"); + if (config->has_section_key("remap", "generator_parameters")) { + generator_parameters = (Dictionary)config->get_value("remap", "generator_parameters"); } - - if (ProjectSettings::get_singleton()->has_setting("importer_defaults/texture")) { - //use defaults if exist - Dictionary importer_defaults = GLOBAL_GET("importer_defaults/texture"); - List<Variant> importer_def_keys; - importer_defaults.get_key_list(&importer_def_keys); - for (const Variant &key : importer_def_keys) { - if (!config->has_section_key("params", (String)key)) { - config->set_value("params", (String)key, importer_defaults[key]); - } - } + if (!generator_parameters.has("md5")) { + must_import = false; // Didn't come form a gltf document; don't overwrite. } - err = config->save(file_path + ".import"); - ERR_FAIL_COND_V(err != OK, err); - must_import = true; - } - Vector<uint8_t> png_buffer = img->save_png_to_buffer(); - if (ResourceLoader::exists(file_path)) { - Ref<FileAccess> file = FileAccess::open(file_path, FileAccess::READ, &err); - if (err == OK && file.is_valid()) { - Vector<uint8_t> orig_png_buffer = file->get_buffer(file->get_length()); - if (png_buffer != orig_png_buffer) { - must_import = true; - } + 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) { + must_import = false; } - } else { - must_import = true; } if (must_import) { - Ref<FileAccess> file = FileAccess::open(file_path, FileAccess::WRITE, &err); + err = img->save_png(file_path); ERR_FAIL_COND_V(err != OK, err); - ERR_FAIL_COND_V(file.is_null(), FAILED); - file->store_buffer(png_buffer); - file->flush(); - file.unref(); // ResourceLoader::import will crash if not is_editor_hint(), so this case is protected above and will fall through to uncompressed. - ResourceLoader::import(file_path); + HashMap<StringName, Variant> custom_options; + custom_options[SNAME("mipmaps/generate")] = true; + // Will only use project settings defaults if custom_importer is empty. + 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()) { |