diff options
Diffstat (limited to 'editor/scene_tree_dock.cpp')
-rw-r--r-- | editor/scene_tree_dock.cpp | 219 |
1 files changed, 84 insertions, 135 deletions
diff --git a/editor/scene_tree_dock.cpp b/editor/scene_tree_dock.cpp index 816156ef00..4d5d467857 100644 --- a/editor/scene_tree_dock.cpp +++ b/editor/scene_tree_dock.cpp @@ -290,6 +290,7 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) { if (!scene) { EditorNode::get_singleton()->new_inherited_scene(); + break; } file->set_mode(EditorFileDialog::MODE_OPEN_FILE); @@ -443,8 +444,8 @@ void SceneTreeDock::_tool_selected(int p_tool, bool p_confirm_override) { List<Node *> owned; node->get_owned_by(node->get_owner(), &owned); - Map<Node *, Node *> duplimap; - Node *dup = _duplicate(node, duplimap); + Map<const Node *, Node *> duplimap; + Node *dup = node->duplicate_from_editor(duplimap); ERR_CONTINUE(!dup); @@ -745,6 +746,10 @@ void SceneTreeDock::_notification(int p_what) { canvas_item_plugin->get_canvas_item_editor()->connect("item_group_status_changed", scene_tree, "_update_tree"); scene_tree->connect("node_changed", canvas_item_plugin->get_canvas_item_editor()->get_viewport_control(), "update"); } + + SpatialEditorPlugin *spatial_editor_plugin = Object::cast_to<SpatialEditorPlugin>(editor_data->get_editor("3D")); + spatial_editor_plugin->get_spatial_editor()->connect("item_lock_status_changed", scene_tree, "_update_tree"); + button_add->set_icon(get_icon("Add", "EditorIcons")); button_instance->set_icon(get_icon("Instance", "EditorIcons")); button_create_script->set_icon(get_icon("ScriptCreate", "EditorIcons")); @@ -821,82 +826,6 @@ void SceneTreeDock::_node_renamed() { _node_selected(); } -Node *SceneTreeDock::_duplicate(Node *p_node, Map<Node *, Node *> &duplimap) { - - Node *node = NULL; - - if (p_node->get_filename() != "") { //an instance - - Ref<PackedScene> sd = ResourceLoader::load(p_node->get_filename()); - ERR_FAIL_COND_V(!sd.is_valid(), NULL); - node = sd->instance(PackedScene::GEN_EDIT_STATE_INSTANCE); - ERR_FAIL_COND_V(!node, NULL); - node->set_scene_instance_load_placeholder(p_node->get_scene_instance_load_placeholder()); - } else { - Object *obj = ClassDB::instance(p_node->get_class()); - ERR_FAIL_COND_V(!obj, NULL); - node = Object::cast_to<Node>(obj); - if (!node) - memdelete(obj); - ERR_FAIL_COND_V(!node, NULL); - } - - List<PropertyInfo> plist; - - p_node->get_property_list(&plist); - - for (List<PropertyInfo>::Element *E = plist.front(); E; E = E->next()) { - - if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) - continue; - String name = E->get().name; - Variant value = p_node->get(name); - // Duplicate dictionaries and arrays, mainly needed for __meta__ - if (value.get_type() == Variant::DICTIONARY) { - value = Dictionary(value).copy(); - } else if (value.get_type() == Variant::ARRAY) { - value = Array(value).duplicate(); - } - node->set(name, value); - } - - List<Connection> conns; - p_node->get_all_signal_connections(&conns); - for (List<Connection>::Element *E = conns.front(); E; E = E->next()) { - if (E->get().flags & CONNECT_PERSIST) { - node->connect(E->get().signal, E->get().target, E->get().method, E->get().binds, E->get().flags); - } - } - - List<Node::GroupInfo> group_info; - p_node->get_groups(&group_info); - for (List<Node::GroupInfo>::Element *E = group_info.front(); E; E = E->next()) { - - if (E->get().persistent) - node->add_to_group(E->get().name, true); - } - - node->set_name(p_node->get_name()); - duplimap[p_node] = node; - - for (int i = 0; i < p_node->get_child_count(); i++) { - - Node *child = p_node->get_child(i); - if (p_node->get_owner() != child->get_owner()) - continue; //don't bother with not in-scene nodes. - - Node *dup = _duplicate(child, duplimap); - if (!dup) { - memdelete(node); - return NULL; - } - - node->add_child(dup); - } - - return node; -} - void SceneTreeDock::_set_owners(Node *p_owner, const Array &p_nodes) { for (int i = 0; i < p_nodes.size(); i++) { @@ -1058,7 +987,7 @@ void SceneTreeDock::perform_node_renames(Node *p_base, List<Pair<NodePath, NodeP //will be renamed NodePath rel_path = new_root_path.rel_path_to(E->get().second); - NodePath new_path = NodePath(rel_path.get_names(), track_np.get_subnames(), false, track_np.get_property()); + NodePath new_path = NodePath(rel_path.get_names(), track_np.get_subnames(), false); if (new_path == track_np) continue; //bleh editor_data->get_undo_redo().add_do_method(anim.ptr(), "track_set_path", i, new_path); @@ -1430,7 +1359,7 @@ void SceneTreeDock::_create() { editor_data->get_undo_redo().commit_action(); editor->push_item(c); - + editor_selection->clear(); if (Object::cast_to<Control>(c)) { //make editor more comfortable, so some controls don't appear super shrunk Control *ct = Object::cast_to<Control>(c); @@ -1444,75 +1373,81 @@ void SceneTreeDock::_create() { } } else if (current_option == TOOL_REPLACE) { - Node *n = scene_tree->get_selected(); - ERR_FAIL_COND(!n); + List<Node *> selection = editor_selection->get_selected_node_list(); + ERR_FAIL_COND(selection.size() <= 0); + for (List<Node *>::Element *E = selection.front(); E; E = E->next()) { + Node *n = E->get(); + ERR_FAIL_COND(!n); - Object *c = create_dialog->instance_selected(); + Object *c = create_dialog->instance_selected(); - ERR_FAIL_COND(!c); - Node *newnode = Object::cast_to<Node>(c); - ERR_FAIL_COND(!newnode); + ERR_FAIL_COND(!c); + Node *newnode = Object::cast_to<Node>(c); + ERR_FAIL_COND(!newnode); - List<PropertyInfo> pinfo; - n->get_property_list(&pinfo); + List<PropertyInfo> pinfo; + n->get_property_list(&pinfo); - for (List<PropertyInfo>::Element *E = pinfo.front(); E; E = E->next()) { - if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) - continue; - newnode->set(E->get().name, n->get(E->get().name)); - } + for (List<PropertyInfo>::Element *E = pinfo.front(); E; E = E->next()) { + if (!(E->get().usage & PROPERTY_USAGE_STORAGE)) + continue; + if (E->get().name == "__meta__") + continue; + newnode->set(E->get().name, n->get(E->get().name)); + } - editor->push_item(NULL); + editor->push_item(NULL); - //reconnect signals - List<MethodInfo> sl; + //reconnect signals + List<MethodInfo> sl; - n->get_signal_list(&sl); - for (List<MethodInfo>::Element *E = sl.front(); E; E = E->next()) { + n->get_signal_list(&sl); + for (List<MethodInfo>::Element *E = sl.front(); E; E = E->next()) { - List<Object::Connection> cl; - n->get_signal_connection_list(E->get().name, &cl); + List<Object::Connection> cl; + n->get_signal_connection_list(E->get().name, &cl); - for (List<Object::Connection>::Element *F = cl.front(); F; F = F->next()) { + for (List<Object::Connection>::Element *F = cl.front(); F; F = F->next()) { - Object::Connection &c = F->get(); - if (!(c.flags & Object::CONNECT_PERSIST)) - continue; - newnode->connect(c.signal, c.target, c.method, varray(), Object::CONNECT_PERSIST); + Object::Connection &c = F->get(); + if (!(c.flags & Object::CONNECT_PERSIST)) + continue; + newnode->connect(c.signal, c.target, c.method, varray(), Object::CONNECT_PERSIST); + } } - } - String newname = n->get_name(); + String newname = n->get_name(); - List<Node *> to_erase; - for (int i = 0; i < n->get_child_count(); i++) { - if (n->get_child(i)->get_owner() == NULL && n->is_owned_by_parent()) { - to_erase.push_back(n->get_child(i)); + List<Node *> to_erase; + for (int i = 0; i < n->get_child_count(); i++) { + if (n->get_child(i)->get_owner() == NULL && n->is_owned_by_parent()) { + to_erase.push_back(n->get_child(i)); + } } - } - n->replace_by(newnode, true); + n->replace_by(newnode, true); - if (n == edited_scene) { - edited_scene = newnode; - editor->set_edited_scene(newnode); - newnode->set_editable_instances(n->get_editable_instances()); - } + if (n == edited_scene) { + edited_scene = newnode; + editor->set_edited_scene(newnode); + newnode->set_editable_instances(n->get_editable_instances()); + } - //small hack to make collisionshapes and other kind of nodes to work - for (int i = 0; i < newnode->get_child_count(); i++) { - Node *c = newnode->get_child(i); - c->call("set_transform", c->call("get_transform")); - } - editor_data->get_undo_redo().clear_history(); - newnode->set_name(newname); + //small hack to make collisionshapes and other kind of nodes to work + for (int i = 0; i < newnode->get_child_count(); i++) { + Node *c = newnode->get_child(i); + c->call("set_transform", c->call("get_transform")); + } + editor_data->get_undo_redo().clear_history(); + newnode->set_name(newname); - editor->push_item(newnode); + editor->push_item(newnode); - memdelete(n); + memdelete(n); - while (to_erase.front()) { - memdelete(to_erase.front()->get()); - to_erase.pop_front(); + while (to_erase.front()) { + memdelete(to_erase.front()->get()); + to_erase.pop_front(); + } } } } @@ -1806,13 +1741,12 @@ void SceneTreeDock::_tree_rmb(const Vector2 &p_menu_pos) { menu->add_icon_shortcut(get_icon("Add", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/add_child_node"), TOOL_NEW); menu->add_icon_shortcut(get_icon("Instance", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/instance_scene"), TOOL_INSTANCE); menu->add_separator(); - menu->add_icon_shortcut(get_icon("Reload", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/change_node_type"), TOOL_REPLACE); - menu->add_separator(); menu->add_icon_shortcut(get_icon("ScriptCreate", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/attach_script"), TOOL_ATTACH_SCRIPT); menu->add_icon_shortcut(get_icon("ScriptRemove", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/clear_script"), TOOL_CLEAR_SCRIPT); menu->add_separator(); } - + menu->add_icon_shortcut(get_icon("Reload", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/change_node_type"), TOOL_REPLACE); + menu->add_separator(); menu->add_icon_shortcut(get_icon("MoveUp", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/move_up"), TOOL_MOVE_UP); menu->add_icon_shortcut(get_icon("MoveDown", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/move_down"), TOOL_MOVE_DOWN); menu->add_icon_shortcut(get_icon("Duplicate", "EditorIcons"), ED_GET_SHORTCUT("scene_tree/duplicate"), TOOL_DUPLICATE); @@ -1897,16 +1831,24 @@ void SceneTreeDock::add_remote_tree_editor(Control *p_remote) { void SceneTreeDock::show_remote_tree() { - button_hb->show(); _remote_tree_selected(); } void SceneTreeDock::hide_remote_tree() { - button_hb->hide(); _local_tree_selected(); } +void SceneTreeDock::show_tab_buttons() { + + button_hb->show(); +} + +void SceneTreeDock::hide_tab_buttons() { + + button_hb->hide(); +} + void SceneTreeDock::_remote_tree_selected() { scene_tree->hide(); @@ -1914,6 +1856,8 @@ void SceneTreeDock::_remote_tree_selected() { remote_tree->show(); edit_remote->set_pressed(true); edit_local->set_pressed(false); + + emit_signal("remote_tree_selected"); } void SceneTreeDock::_local_tree_selected() { @@ -1923,6 +1867,8 @@ void SceneTreeDock::_local_tree_selected() { remote_tree->hide(); edit_remote->set_pressed(false); edit_local->set_pressed(true); + + _node_selected(); } void SceneTreeDock::_bind_methods() { @@ -1954,10 +1900,13 @@ void SceneTreeDock::_bind_methods() { ClassDB::bind_method(D_METHOD("_local_tree_selected"), &SceneTreeDock::_local_tree_selected); ClassDB::bind_method(D_METHOD("instance"), &SceneTreeDock::instance); + + ADD_SIGNAL(MethodInfo("remote_tree_selected")); } SceneTreeDock::SceneTreeDock(EditorNode *p_editor, Node *p_scene_root, EditorSelection *p_editor_selection, EditorData &p_editor_data) { + set_name("Scene"); editor = p_editor; edited_scene = NULL; editor_data = &p_editor_data; |