diff --git a/editor/editor_properties.cpp b/editor/editor_properties.cpp index 44dfed8c7e6..04a019a4079 100644 --- a/editor/editor_properties.cpp +++ b/editor/editor_properties.cpp @@ -2759,48 +2759,17 @@ void EditorPropertyNodePath::_set_read_only(bool p_read_only) { clear->set_disabled(p_read_only); }; -String EditorPropertyNodePath::_get_meta_pointer_property() const { - ERR_FAIL_COND_V(!pointer_mode, String()); - return SceneState::get_meta_pointer_property(get_edited_property()); -} - Variant EditorPropertyNodePath::_get_cache_value(const StringName &p_prop, bool &r_valid) const { if (p_prop == get_edited_property()) { r_valid = true; - return const_cast(this)->get_edited_object()->get(pointer_mode ? StringName(_get_meta_pointer_property()) : get_edited_property(), &r_valid); + return const_cast(this)->get_edited_object()->get(get_edited_property(), &r_valid); } return Variant(); } -StringName EditorPropertyNodePath::_get_revert_property() const { - if (pointer_mode) { - return _get_meta_pointer_property(); - } else { - return get_edited_property(); - } -} - void EditorPropertyNodePath::_node_selected(const NodePath &p_path) { NodePath path = p_path; - Node *base_node = nullptr; - - if (!use_path_from_scene_root) { - base_node = Object::cast_to(get_edited_object()); - - if (!base_node) { - //try a base node within history - if (EditorNode::get_singleton()->get_editor_selection_history()->get_path_size() > 0) { - Object *base = ObjectDB::get_instance(EditorNode::get_singleton()->get_editor_selection_history()->get_path_object(0)); - if (base) { - base_node = Object::cast_to(base); - } - } - } - } - - if (!base_node && get_edited_object()->has_method("get_root_path")) { - base_node = Object::cast_to(get_edited_object()->call("get_root_path")); - } + Node *base_node = get_base_node(); if (!base_node && Object::cast_to(get_edited_object())) { Node *to_node = get_node(p_path); @@ -2811,8 +2780,13 @@ void EditorPropertyNodePath::_node_selected(const NodePath &p_path) { if (base_node) { // for AnimationTrackKeyEdit path = base_node->get_path().rel_path_to(p_path); } - if (pointer_mode && base_node) { - emit_changed(_get_meta_pointer_property(), path); + + if (editing_node) { + if (!base_node) { + emit_changed(get_edited_property(), get_tree()->get_edited_scene_root()->get_node(path)); + } else { + emit_changed(get_edited_property(), base_node->get_node(path)); + } } else { emit_changed(get_edited_property(), path); } @@ -2831,11 +2805,7 @@ void EditorPropertyNodePath::_node_assign() { } void EditorPropertyNodePath::_node_clear() { - if (pointer_mode) { - emit_changed(_get_meta_pointer_property(), NodePath()); - } else { - emit_changed(get_edited_property(), NodePath()); - } + emit_changed(get_edited_property(), NodePath()); update_property(); } @@ -2882,9 +2852,20 @@ bool EditorPropertyNodePath::is_drop_valid(const Dictionary &p_drag_data) const } void EditorPropertyNodePath::update_property() { + Node *base_node = get_base_node(); + NodePath p; - if (pointer_mode) { - p = get_edited_object()->get(_get_meta_pointer_property()); + Variant val = get_edited_object()->get(get_edited_property()); + Node *n = Object::cast_to(val); + if (n) { + if (!n->is_inside_tree()) { + return; + } + if (base_node) { + p = base_node->get_path_to(n); + } else { + p = get_tree()->get_edited_scene_root()->get_path_to(n); + } } else { p = get_edited_property_value(); } @@ -2898,15 +2879,6 @@ void EditorPropertyNodePath::update_property() { } assign->set_flat(true); - Node *base_node = nullptr; - if (base_hint != NodePath()) { - if (get_tree()->get_root()->has_node(base_hint)) { - base_node = get_tree()->get_root()->get_node(base_hint); - } - } else { - base_node = Object::cast_to(get_edited_object()); - } - if (!base_node || !base_node->has_node(p)) { assign->set_icon(Ref()); assign->set_text(p); @@ -2926,10 +2898,10 @@ void EditorPropertyNodePath::update_property() { assign->set_icon(EditorNode::get_singleton()->get_object_icon(target_node, "Node")); } -void EditorPropertyNodePath::setup(const NodePath &p_base_hint, Vector p_valid_types, bool p_use_path_from_scene_root, bool p_pointer_mode) { - pointer_mode = p_pointer_mode; +void EditorPropertyNodePath::setup(const NodePath &p_base_hint, Vector p_valid_types, bool p_use_path_from_scene_root, bool p_editing_node) { base_hint = p_base_hint; valid_types = p_valid_types; + editing_node = p_editing_node; use_path_from_scene_root = p_use_path_from_scene_root; } @@ -2945,6 +2917,35 @@ void EditorPropertyNodePath::_notification(int p_what) { void EditorPropertyNodePath::_bind_methods() { } +Node *EditorPropertyNodePath::get_base_node() { + if (!base_hint.is_empty() && get_tree()->get_root()->has_node(base_hint)) { + return get_tree()->get_root()->get_node(base_hint); + } + + Node *base_node = Object::cast_to(get_edited_object()); + + if (!base_node) { + base_node = Object::cast_to(InspectorDock::get_inspector_singleton()->get_edited_object()); + } + if (!base_node) { + // Try a base node within history. + if (EditorNode::get_singleton()->get_editor_selection_history()->get_path_size() > 0) { + Object *base = ObjectDB::get_instance(EditorNode::get_singleton()->get_editor_selection_history()->get_path_object(0)); + if (base) { + base_node = Object::cast_to(base); + } + } + } + if (use_path_from_scene_root) { + if (get_edited_object()->has_method("get_root_path")) { + base_node = Object::cast_to(get_edited_object()->call("get_root_path")); + } else { + base_node = get_tree()->get_edited_scene_root(); + } + } + + return base_node; +} EditorPropertyNodePath::EditorPropertyNodePath() { HBoxContainer *hbc = memnew(HBoxContainer); diff --git a/editor/editor_properties.h b/editor/editor_properties.h index 1505d77de1d..33e325bd42c 100644 --- a/editor/editor_properties.h +++ b/editor/editor_properties.h @@ -654,20 +654,19 @@ class EditorPropertyNodePath : public EditorProperty { SceneTreeDialog *scene_tree = nullptr; NodePath base_hint; bool use_path_from_scene_root = false; - bool pointer_mode = false; + bool editing_node = false; Vector valid_types; void _node_selected(const NodePath &p_path); void _node_assign(); void _node_clear(); + Node *get_base_node(); bool can_drop_data_fw(const Point2 &p_point, const Variant &p_data, Control *p_from) const; void drop_data_fw(const Point2 &p_point, const Variant &p_data, Control *p_from); bool is_drop_valid(const Dictionary &p_drag_data) const; - String _get_meta_pointer_property() const; virtual Variant _get_cache_value(const StringName &p_prop, bool &r_valid) const override; - virtual StringName _get_revert_property() const override; protected: virtual void _set_read_only(bool p_read_only) override; @@ -676,7 +675,7 @@ protected: public: virtual void update_property() override; - void setup(const NodePath &p_base_hint, Vector p_valid_types, bool p_use_path_from_scene_root = true, bool p_pointer_mode = false); + void setup(const NodePath &p_base_hint, Vector p_valid_types, bool p_use_path_from_scene_root = true, bool p_editing_node = false); EditorPropertyNodePath(); }; diff --git a/editor/editor_properties_array_dict.cpp b/editor/editor_properties_array_dict.cpp index 88e62b700e3..1a8d677a007 100644 --- a/editor/editor_properties_array_dict.cpp +++ b/editor/editor_properties_array_dict.cpp @@ -44,7 +44,7 @@ bool EditorPropertyArrayObject::_set(const StringName &p_name, const Variant &p_value) { String name = p_name; - if (!name.begins_with("indices") && !name.begins_with(PackedScene::META_POINTER_PROPERTY_BASE + "indices")) { + if (!name.begins_with("indices")) { return false; } @@ -62,7 +62,7 @@ bool EditorPropertyArrayObject::_set(const StringName &p_name, const Variant &p_ bool EditorPropertyArrayObject::_get(const StringName &p_name, Variant &r_ret) const { String name = p_name; - if (!name.begins_with("indices") && !name.begins_with(PackedScene::META_POINTER_PROPERTY_BASE + "indices")) { + if (!name.begins_with("indices")) { return false; } @@ -193,7 +193,7 @@ void EditorPropertyArray::initialize_array(Variant &p_array) { } void EditorPropertyArray::_property_changed(const String &p_property, Variant p_value, const String &p_name, bool p_changing) { - if (!p_property.begins_with("indices") && !p_property.begins_with(PackedScene::META_POINTER_PROPERTY_BASE + "indices")) { + if (!p_property.begins_with("indices")) { return; } @@ -204,18 +204,7 @@ void EditorPropertyArray::_property_changed(const String &p_property, Variant p_ index = p_property.get_slice("/", 1).to_int(); } - Variant array; - const Variant &original_array = object->get_array(); - - if (original_array.get_type() == Variant::ARRAY) { - // Needed to preserve type of TypedArrays in meta pointer properties. - Array temp; - temp.assign(original_array.duplicate()); - array = temp; - } else { - array = original_array.duplicate(); - } - + Variant array = object->get_array().duplicate(); array.set(index, p_value); object->set_array(array); emit_changed(get_edited_property(), array, "", true); diff --git a/scene/resources/packed_scene.cpp b/scene/resources/packed_scene.cpp index 1cb7c9e574f..4d690bd3b1c 100644 --- a/scene/resources/packed_scene.cpp +++ b/scene/resources/packed_scene.cpp @@ -45,8 +45,6 @@ #define PACKED_SCENE_VERSION 3 -const String PackedScene::META_POINTER_PROPERTY_BASE = "metadata/_editor_prop_ptr_"; - bool SceneState::can_instantiate() const { return nodes.size() > 0; } @@ -246,13 +244,14 @@ Node *SceneState::instantiate(GenEditState p_edit_state) const { const Variant &prop_variant = props[nprops[j].value]; if (prop_variant.get_type() == Variant::ARRAY) { - if (Engine::get_singleton()->is_editor_hint()) { - // If editor, simply set the original array of NodePaths. - node->set(prop_name, prop_variant); - continue; - } - const Array &array = prop_variant; + if (Engine::get_singleton()->is_editor_hint()) { + if (array.get_typed_builtin() == Variant::NODE_PATH) { + // If editor, simply set the original array of NodePaths. + node->set(prop_name, prop_variant); + continue; + } + } for (int k = 0; k < array.size(); k++) { DeferredNodePathProperties dnp; dnp.path = array[k]; @@ -263,16 +262,12 @@ Node *SceneState::instantiate(GenEditState p_edit_state) const { } } else { - node->set(PackedScene::META_POINTER_PROPERTY_BASE + String(prop_name), prop_variant); - - if (!Engine::get_singleton()->is_editor_hint()) { - // If not editor, do an actual deferred sed of the property path. - DeferredNodePathProperties dnp; - dnp.path = prop_variant; - dnp.base = node; - dnp.property = prop_name; - deferred_node_paths.push_back(dnp); - } + // Do an actual deferred set of the property path. + DeferredNodePathProperties dnp; + dnp.path = prop_variant; + dnp.base = node; + dnp.property = prop_name; + deferred_node_paths.push_back(dnp); } continue; } @@ -626,9 +621,6 @@ Error SceneState::_parse_node(Node *p_owner, Node *p_node, int p_parent_idx, Has if (E.name == META_PROPERTY_MISSING_RESOURCES) { continue; // Ignore this property when packing. } - if (E.name.begins_with(PackedScene::META_POINTER_PROPERTY_BASE)) { - continue; // do not save. - } // If instance or inheriting, not saving if property requested so. if (!states_stack.is_empty()) { @@ -642,11 +634,15 @@ Error SceneState::_parse_node(Node *p_owner, Node *p_node, int p_parent_idx, Has bool use_deferred_node_path_bit = false; if (E.type == Variant::OBJECT && E.hint == PROPERTY_HINT_NODE_TYPE) { - value = p_node->get(PackedScene::META_POINTER_PROPERTY_BASE + E.name); + if (value.get_type() == Variant::OBJECT) { + if (Node *n = Object::cast_to(value)) { + value = p_node->get_path_to(n); + } + use_deferred_node_path_bit = true; + } if (value.get_type() != Variant::NODE_PATH) { continue; //was never set, ignore. } - use_deferred_node_path_bit = true; } else if (E.type == Variant::OBJECT && missing_resource_properties.has(E.name)) { // Was this missing resource overridden? If so do not save the old value. Ref ures = value; @@ -665,7 +661,22 @@ Error SceneState::_parse_node(Node *p_owner, Node *p_node, int p_parent_idx, Has } Variant::Type subtype = Variant::Type(subtype_string.to_int()); - use_deferred_node_path_bit = subtype == Variant::OBJECT && subtype_hint == PROPERTY_HINT_NODE_TYPE; + if (subtype == Variant::OBJECT && subtype_hint == PROPERTY_HINT_NODE_TYPE) { + use_deferred_node_path_bit = true; + Array array = value; + Array new_array; + for (int i = 0; i < array.size(); i++) { + Variant elem = array[i]; + if (elem.get_type() == Variant::OBJECT) { + if (Node *n = Object::cast_to(elem)) { + new_array.push_back(p_node->get_path_to(n)); + continue; + } + } + new_array.push_back(elem); + } + value = new_array; + } } } @@ -1791,10 +1802,6 @@ void SceneState::add_editable_instance(const NodePath &p_path) { editable_instances.push_back(p_path); } -String SceneState::get_meta_pointer_property(const String &p_property) { - return PackedScene::META_POINTER_PROPERTY_BASE + p_property; -} - Vector SceneState::_get_node_groups(int p_idx) const { Vector groups = get_node_groups(p_idx); Vector ret; diff --git a/scene/resources/packed_scene.h b/scene/resources/packed_scene.h index 1967deab367..5c53ffdb456 100644 --- a/scene/resources/packed_scene.h +++ b/scene/resources/packed_scene.h @@ -221,8 +221,6 @@ protected: virtual void reset_state() override; public: - static const String META_POINTER_PROPERTY_BASE; - enum GenEditState { GEN_EDIT_STATE_DISABLED, GEN_EDIT_STATE_INSTANCE,