diff --git a/scene/main/node.cpp b/scene/main/node.cpp index 5db915c58a86..25d48a476a5d 100644 --- a/scene/main/node.cpp +++ b/scene/main/node.cpp @@ -2951,6 +2951,10 @@ Node *Node::duplicate(int p_flags) const { ERR_FAIL_NULL_V_MSG(dupe, nullptr, "Failed to duplicate node."); + if (p_flags & DUPLICATE_SCRIPTS) { + _duplicate_scripts(this, dupe); + } + _duplicate_properties(this, this, dupe, p_flags); if (p_flags & DUPLICATE_SIGNALS) { @@ -2971,6 +2975,10 @@ Node *Node::duplicate_from_editor(HashMap &r_duplimap, con ERR_FAIL_NULL_V_MSG(dupe, nullptr, "Failed to duplicate node."); + if (flags & DUPLICATE_SCRIPTS) { + _duplicate_scripts(this, dupe); + } + _duplicate_properties(this, this, dupe, flags); // This is used by SceneTreeDock's paste functionality. When pasting to foreign scene, resources are duplicated. @@ -3043,6 +3051,20 @@ void Node::_emit_editor_state_changed() { } #endif +void Node::_duplicate_scripts(const Node *p_original, Node *p_copy) const { + bool is_valid = false; + Variant scr = p_original->get(CoreStringName(script), &is_valid); + if (is_valid) { + p_copy->set(CoreStringName(script), scr); + } + + for (int i = 0; i < p_original->get_child_count(false); i++) { + Node *copy_child = p_copy->get_child(i, false); + ERR_FAIL_NULL_MSG(copy_child, "Child node disappeared while duplicating."); + _duplicate_scripts(p_original->get_child(i, false), copy_child); + } +} + // Duplicate node's properties. // This has to be called after nodes have been duplicated since there might be properties // of type Node that can be updated properly only if duplicated node tree is complete. @@ -3050,13 +3072,6 @@ void Node::_duplicate_properties(const Node *p_root, const Node *p_original, Nod List props; p_original->get_property_list(&props); const StringName &script_property_name = CoreStringName(script); - if (p_flags & DUPLICATE_SCRIPTS) { - bool is_valid = false; - Variant scr = p_original->get(script_property_name, &is_valid); - if (is_valid) { - p_copy->set(script_property_name, scr); - } - } for (const PropertyInfo &E : props) { if (!(E.usage & PROPERTY_USAGE_STORAGE)) { continue; diff --git a/scene/main/node.h b/scene/main/node.h index 974a6b5b54df..b791cef9c549 100644 --- a/scene/main/node.h +++ b/scene/main/node.h @@ -315,6 +315,7 @@ class Node : public Object { void _propagate_translation_domain_dirty(); Array _get_node_and_resource(const NodePath &p_path); + void _duplicate_scripts(const Node *p_original, Node *p_copy) const; void _duplicate_properties(const Node *p_root, const Node *p_original, Node *p_copy, int p_flags) const; void _duplicate_signals(const Node *p_original, Node *p_copy) const; Node *_duplicate(int p_flags, HashMap *r_duplimap = nullptr) const;