summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRémi Verschelde <rverschelde@gmail.com>2022-10-31 10:46:08 +0100
committerRémi Verschelde <rverschelde@gmail.com>2022-10-31 10:46:08 +0100
commitfa732117548068a06fe064ef715aadf1c3d02087 (patch)
treed09ced939ed47db582c0232daad31664f0d8fea5
parentb43cc96535a41e51aa400156e96cdc22888828e1 (diff)
parent809dad907a82e49173d8d417c8215d328568aa31 (diff)
Merge pull request #65118 from Mickeon/editor-remote-tree-buttons
Add a few buttons in Remote Scene Tree
-rw-r--r--editor/debugger/editor_debugger_node.cpp19
-rw-r--r--editor/debugger/editor_debugger_node.h1
-rw-r--r--editor/debugger/editor_debugger_tree.cpp32
-rw-r--r--editor/debugger/editor_debugger_tree.h5
-rw-r--r--editor/scene_tree_dock.cpp2
-rw-r--r--scene/debugger/scene_debugger.cpp42
-rw-r--r--scene/debugger/scene_debugger.h13
7 files changed, 103 insertions, 11 deletions
diff --git a/editor/debugger/editor_debugger_node.cpp b/editor/debugger/editor_debugger_node.cpp
index 06b73cf296..ecd8fcb2ba 100644
--- a/editor/debugger/editor_debugger_node.cpp
+++ b/editor/debugger/editor_debugger_node.cpp
@@ -77,6 +77,7 @@ EditorDebuggerNode::EditorDebuggerNode() {
remote_scene_tree = memnew(EditorDebuggerTree);
remote_scene_tree->connect("object_selected", callable_mp(this, &EditorDebuggerNode::_remote_object_requested));
remote_scene_tree->connect("save_node", callable_mp(this, &EditorDebuggerNode::_save_node_requested));
+ remote_scene_tree->connect("button_clicked", callable_mp(this, &EditorDebuggerNode::_remote_tree_button_pressed));
SceneTreeDock::get_singleton()->add_remote_tree_editor(remote_scene_tree);
SceneTreeDock::get_singleton()->connect("remote_tree_selected", callable_mp(this, &EditorDebuggerNode::request_remote_tree));
@@ -573,6 +574,24 @@ void EditorDebuggerNode::_remote_tree_updated(int p_debugger) {
remote_scene_tree->update_scene_tree(get_current_debugger()->get_remote_tree(), p_debugger);
}
+void EditorDebuggerNode::_remote_tree_button_pressed(Object *p_item, int p_column, int p_id, MouseButton p_button) {
+ if (p_button != MouseButton::LEFT) {
+ return;
+ }
+
+ TreeItem *item = Object::cast_to<TreeItem>(p_item);
+ ERR_FAIL_COND(!item);
+
+ if (p_id == EditorDebuggerTree::BUTTON_SUBSCENE) {
+ remote_scene_tree->emit_signal(SNAME("open"), item->get_meta("scene_file_path"));
+ } else if (p_id == EditorDebuggerTree::BUTTON_VISIBILITY) {
+ ObjectID obj_id = item->get_metadata(0);
+ ERR_FAIL_COND(obj_id.is_null());
+ get_current_debugger()->update_remote_object(obj_id, "visible", !item->get_meta("visible"));
+ get_current_debugger()->request_remote_tree();
+ }
+}
+
void EditorDebuggerNode::_remote_object_updated(ObjectID p_id, int p_debugger) {
if (p_debugger != tabs->get_current_tab()) {
return;
diff --git a/editor/debugger/editor_debugger_node.h b/editor/debugger/editor_debugger_node.h
index e79e60b180..305f18a652 100644
--- a/editor/debugger/editor_debugger_node.h
+++ b/editor/debugger/editor_debugger_node.h
@@ -129,6 +129,7 @@ protected:
void _debugger_wants_stop(int p_id);
void _debugger_changed(int p_tab);
void _remote_tree_updated(int p_debugger);
+ void _remote_tree_button_pressed(Object *p_item, int p_column, int p_id, MouseButton p_button);
void _remote_object_updated(ObjectID p_id, int p_debugger);
void _remote_object_property_updated(ObjectID p_id, const String &p_property, int p_debugger);
void _remote_object_requested(ObjectID p_id, int p_debugger);
diff --git a/editor/debugger/editor_debugger_tree.cpp b/editor/debugger/editor_debugger_tree.cpp
index 76efcd7190..4168efda26 100644
--- a/editor/debugger/editor_debugger_tree.cpp
+++ b/editor/debugger/editor_debugger_tree.cpp
@@ -65,6 +65,7 @@ void EditorDebuggerTree::_notification(int p_what) {
void EditorDebuggerTree::_bind_methods() {
ADD_SIGNAL(MethodInfo("object_selected", PropertyInfo(Variant::INT, "object_id"), PropertyInfo(Variant::INT, "debugger")));
ADD_SIGNAL(MethodInfo("save_node", PropertyInfo(Variant::INT, "object_id"), PropertyInfo(Variant::STRING, "filename"), PropertyInfo(Variant::INT, "debugger")));
+ ADD_SIGNAL(MethodInfo("open"));
}
void EditorDebuggerTree::_scene_tree_selected() {
@@ -162,7 +163,7 @@ void EditorDebuggerTree::update_scene_tree(const SceneDebuggerTree *p_tree, int
}
item->set_metadata(0, node.id);
- // Set current item as collapsed if necessary (root is never collapsed)
+ // Set current item as collapsed if necessary (root is never collapsed).
if (parent) {
if (!unfold_cache.has(node.id)) {
item->set_collapsed(true);
@@ -178,7 +179,7 @@ void EditorDebuggerTree::update_scene_tree(const SceneDebuggerTree *p_tree, int
}
} else { // Must use path
if (last_path == _get_path(item)) {
- updating_scene_tree = false; // Force emission of new selection
+ updating_scene_tree = false; // Force emission of new selection.
item->select(0);
if (filter_changed) {
scroll_item = item;
@@ -187,6 +188,33 @@ void EditorDebuggerTree::update_scene_tree(const SceneDebuggerTree *p_tree, int
}
}
+ // Add buttons.
+ const Color remote_button_color = Color(1, 1, 1, 0.8);
+ if (!node.scene_file_path.is_empty()) {
+ String node_scene_file_path = node.scene_file_path;
+ Ref<Texture2D> button_icon = get_theme_icon(SNAME("InstanceOptions"), SNAME("EditorIcons"));
+ String tooltip = vformat(TTR("This node has been instantiated from a PackedScene file:\n%s\nClick to open the original file in the Editor."), node_scene_file_path);
+
+ item->set_meta("scene_file_path", node_scene_file_path);
+ item->add_button(0, button_icon, BUTTON_SUBSCENE, false, tooltip);
+ item->set_button_color(0, item->get_button_count(0) - 1, remote_button_color);
+ }
+
+ if (node.view_flags & SceneDebuggerTree::RemoteNode::VIEW_HAS_VISIBLE_METHOD) {
+ bool node_visible = node.view_flags & SceneDebuggerTree::RemoteNode::VIEW_VISIBLE;
+ bool node_visible_in_tree = node.view_flags & SceneDebuggerTree::RemoteNode::VIEW_VISIBLE_IN_TREE;
+ Ref<Texture2D> button_icon = get_theme_icon(node_visible ? SNAME("GuiVisibilityVisible") : SNAME("GuiVisibilityHidden"), SNAME("EditorIcons"));
+ String tooltip = TTR("Toggle Visibility");
+
+ item->set_meta("visible", node_visible);
+ item->add_button(0, button_icon, BUTTON_VISIBILITY, false, tooltip);
+ if (ClassDB::is_parent_class(node.type_name, "CanvasItem") || ClassDB::is_parent_class(node.type_name, "Node3D")) {
+ item->set_button_color(0, item->get_button_count(0) - 1, node_visible_in_tree ? remote_button_color : Color(1, 1, 1, 0.6));
+ } else {
+ item->set_button_color(0, item->get_button_count(0) - 1, remote_button_color);
+ }
+ }
+
// Add in front of the parents stack if children are expected.
if (node.child_count) {
parents.push_front(Pair<TreeItem *, int>(item, node.child_count));
diff --git a/editor/debugger/editor_debugger_tree.h b/editor/debugger/editor_debugger_tree.h
index 5af3a0d84a..6d590cdb7a 100644
--- a/editor/debugger/editor_debugger_tree.h
+++ b/editor/debugger/editor_debugger_tree.h
@@ -65,6 +65,11 @@ protected:
void _notification(int p_what);
public:
+ enum Button {
+ BUTTON_SUBSCENE = 0,
+ BUTTON_VISIBILITY = 1,
+ };
+
virtual Variant get_drag_data(const Point2 &p_point) override;
String get_selected_path();
diff --git a/editor/scene_tree_dock.cpp b/editor/scene_tree_dock.cpp
index ee358a8064..27943b6077 100644
--- a/editor/scene_tree_dock.cpp
+++ b/editor/scene_tree_dock.cpp
@@ -1401,6 +1401,7 @@ void SceneTreeDock::_node_replace_owner(Node *p_base, Node *p_node, Node *p_root
void SceneTreeDock::_load_request(const String &p_path) {
EditorNode::get_singleton()->open_request(p_path);
+ _local_tree_selected();
}
void SceneTreeDock::_script_open_request(const Ref<Script> &p_script) {
@@ -3218,6 +3219,7 @@ void SceneTreeDock::add_remote_tree_editor(Control *p_remote) {
add_child(p_remote);
remote_tree = p_remote;
remote_tree->hide();
+ remote_tree->connect("open", callable_mp(this, &SceneTreeDock::_load_request));
}
void SceneTreeDock::show_remote_tree() {
diff --git a/scene/debugger/scene_debugger.cpp b/scene/debugger/scene_debugger.cpp
index bfc3c25fe6..b4bdda9ecb 100644
--- a/scene/debugger/scene_debugger.cpp
+++ b/scene/debugger/scene_debugger.cpp
@@ -548,14 +548,36 @@ SceneDebuggerTree::SceneDebuggerTree(Node *p_root) {
// Flatten tree into list, depth first, use stack to avoid recursion.
List<Node *> stack;
stack.push_back(p_root);
+ bool is_root = true;
+ const StringName &is_visible_sn = SNAME("is_visible");
+ const StringName &is_visible_in_tree_sn = SNAME("is_visible_in_tree");
while (stack.size()) {
Node *n = stack[0];
stack.pop_front();
+
int count = n->get_child_count();
- nodes.push_back(RemoteNode(count, n->get_name(), n->get_class(), n->get_instance_id()));
for (int i = 0; i < count; i++) {
stack.push_front(n->get_child(count - i - 1));
}
+
+ int view_flags = 0;
+ if (is_root) {
+ // Prevent root window visibility from being changed.
+ is_root = false;
+ } else if (n->has_method(is_visible_sn)) {
+ const Variant visible = n->call(is_visible_sn);
+ if (visible.get_type() == Variant::BOOL) {
+ view_flags = RemoteNode::VIEW_HAS_VISIBLE_METHOD;
+ view_flags |= uint8_t(visible) * RemoteNode::VIEW_VISIBLE;
+ }
+ if (n->has_method(is_visible_in_tree_sn)) {
+ const Variant visible_in_tree = n->call(is_visible_in_tree_sn);
+ if (visible_in_tree.get_type() == Variant::BOOL) {
+ view_flags |= uint8_t(visible_in_tree) * RemoteNode::VIEW_VISIBLE_IN_TREE;
+ }
+ }
+ }
+ nodes.push_back(RemoteNode(count, n->get_name(), n->get_class(), n->get_instance_id(), n->get_scene_file_path(), view_flags));
}
}
@@ -565,19 +587,23 @@ void SceneDebuggerTree::serialize(Array &p_arr) {
p_arr.push_back(n.name);
p_arr.push_back(n.type_name);
p_arr.push_back(n.id);
+ p_arr.push_back(n.scene_file_path);
+ p_arr.push_back(n.view_flags);
}
}
void SceneDebuggerTree::deserialize(const Array &p_arr) {
int idx = 0;
while (p_arr.size() > idx) {
- ERR_FAIL_COND(p_arr.size() < 4);
- CHECK_TYPE(p_arr[idx], INT);
- CHECK_TYPE(p_arr[idx + 1], STRING);
- CHECK_TYPE(p_arr[idx + 2], STRING);
- CHECK_TYPE(p_arr[idx + 3], INT);
- nodes.push_back(RemoteNode(p_arr[idx], p_arr[idx + 1], p_arr[idx + 2], p_arr[idx + 3]));
- idx += 4;
+ ERR_FAIL_COND(p_arr.size() < 6);
+ CHECK_TYPE(p_arr[idx], INT); // child_count.
+ CHECK_TYPE(p_arr[idx + 1], STRING); // name.
+ CHECK_TYPE(p_arr[idx + 2], STRING); // type_name.
+ CHECK_TYPE(p_arr[idx + 3], INT); // id.
+ CHECK_TYPE(p_arr[idx + 4], STRING); // scene_file_path.
+ CHECK_TYPE(p_arr[idx + 5], INT); // view_flags.
+ nodes.push_back(RemoteNode(p_arr[idx], p_arr[idx + 1], p_arr[idx + 2], p_arr[idx + 3], p_arr[idx + 4], p_arr[idx + 5]));
+ idx += 6;
}
}
diff --git a/scene/debugger/scene_debugger.h b/scene/debugger/scene_debugger.h
index 911363f45d..fe35446aae 100644
--- a/scene/debugger/scene_debugger.h
+++ b/scene/debugger/scene_debugger.h
@@ -110,12 +110,23 @@ public:
String name;
String type_name;
ObjectID id;
+ String scene_file_path;
+ uint8_t view_flags = 0;
- RemoteNode(int p_child, const String &p_name, const String &p_type, ObjectID p_id) {
+ enum ViewFlags {
+ VIEW_HAS_VISIBLE_METHOD = 1 << 1,
+ VIEW_VISIBLE = 1 << 2,
+ VIEW_VISIBLE_IN_TREE = 1 << 3,
+ };
+
+ RemoteNode(int p_child, const String &p_name, const String &p_type, ObjectID p_id, const String p_scene_file_path, int p_view_flags) {
child_count = p_child;
name = p_name;
type_name = p_type;
id = p_id;
+
+ scene_file_path = p_scene_file_path;
+ view_flags = p_view_flags;
}
RemoteNode() {}