Skip to content

Commit

Permalink
Allow multiple contextual editors opened at once
Browse files Browse the repository at this point in the history
  • Loading branch information
KoBeWi committed Mar 18, 2021
1 parent d0f0fdb commit d627bd7
Show file tree
Hide file tree
Showing 6 changed files with 149 additions and 64 deletions.
133 changes: 98 additions & 35 deletions editor/editor_node.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1888,8 +1888,8 @@ bool EditorNode::item_has_editor(Object *p_object) {
return editor_data.get_subeditors(p_object).size() > 0;
}

void EditorNode::edit_item_resource(RES p_resource) {
edit_item(p_resource.ptr());
void EditorNode::edit_item_resource(RES p_resource, Object *p_owner) {
edit_item(p_resource.ptr(), p_owner);
}

bool EditorNode::_is_class_editor_disabled_by_feature_profile(const StringName &p_class) {
Expand All @@ -1913,7 +1913,7 @@ bool EditorNode::_is_class_editor_disabled_by_feature_profile(const StringName &
return false;
}

void EditorNode::edit_item(Object *p_object) {
void EditorNode::edit_item(Object *p_object, Object *p_owner) {
Vector<EditorPlugin *> sub_plugins;

if (p_object) {
Expand All @@ -1923,11 +1923,22 @@ void EditorNode::edit_item(Object *p_object) {
sub_plugins = editor_data.get_subeditors(p_object);
}

if (!sub_plugins.is_empty()) {
Vector<EditorPluginList::ActiveEditor> sub_editors;
for (int i = 0; i < sub_plugins.size(); i++) {
EditorPluginList::ActiveEditor item;
item.plugin = sub_plugins[i];
item.owner = p_owner->get_instance_id();
sub_editors.append(item);
}

sub_editors.append_array(editor_plugins_over->get_plugins_list());
editor_plugins_over->verify_top_editors(sub_editors);

if (!sub_editors.is_empty()) {
bool same = true;
if (sub_plugins.size() == editor_plugins_over->get_plugins_list().size()) {
for (int i = 0; i < sub_plugins.size(); i++) {
if (sub_plugins[i] != editor_plugins_over->get_plugins_list()[i]) {
if (sub_editors.size() == editor_plugins_over->get_plugins_list().size()) {
for (int i = 0; i < sub_editors.size(); i++) {
if (sub_editors[i].plugin != editor_plugins_over->get_plugins_list()[i].plugin) {
same = false;
}
}
Expand All @@ -1936,12 +1947,12 @@ void EditorNode::edit_item(Object *p_object) {
}
if (!same) {
_display_top_editors(false);
_set_top_editors(sub_plugins);
editor_plugins_over->set_plugins_list(sub_editors);
}
_set_editing_top_editors(p_object);
_display_top_editors(true);
} else {
hide_top_editors();
hide_unused_editors();
}
}

Expand Down Expand Up @@ -1979,20 +1990,20 @@ void EditorNode::_save_default_environment() {
}
}

void EditorNode::hide_top_editors() {
_display_top_editors(false);

editor_plugins_over->clear();
void EditorNode::hide_unused_editors() {
Vector<EditorPluginList::ActiveEditor> prev_editors(editor_plugins_over->get_plugins_list());
editor_plugins_over->verify_top_editors(editor_plugins_over->get_plugins_list());
for (int i = 0; i < prev_editors.size(); i++) {
if (!editor_plugins_over->get_plugins_list().has(prev_editors[i])) {
prev_editors[i].plugin->make_visible(false);
}
}
}

void EditorNode::_display_top_editors(bool p_display) {
editor_plugins_over->make_visible(p_display);
}

void EditorNode::_set_top_editors(Vector<EditorPlugin *> p_editor_plugins_over) {
editor_plugins_over->set_plugins_list(p_editor_plugins_over);
}

void EditorNode::_set_editing_top_editors(Object *p_current_object) {
editor_plugins_over->edit(p_current_object);
}
Expand Down Expand Up @@ -2182,14 +2193,25 @@ void EditorNode::_edit_current() {
sub_plugins = editor_data.get_subeditors(current_obj);
}

if (!sub_plugins.is_empty()) {
Vector<EditorPluginList::ActiveEditor> sub_editors;
for (int i = 0; i < sub_plugins.size(); i++) {
EditorPluginList::ActiveEditor item;
item.plugin = sub_plugins[i];
item.owner = current_obj->get_instance_id();
sub_editors.append(item);
}

sub_editors.append_array(editor_plugins_over->get_plugins_list());
editor_plugins_over->verify_top_editors(sub_editors);

if (!sub_editors.is_empty()) {
_display_top_editors(false);

_set_top_editors(sub_plugins);
editor_plugins_over->set_plugins_list(sub_editors);
_set_editing_top_editors(current_obj);
_display_top_editors(true);
} else if (!editor_plugins_over->get_plugins_list().is_empty()) {
hide_top_editors();
hide_unused_editors();
}
}

Expand Down Expand Up @@ -3085,10 +3107,11 @@ void EditorNode::remove_editor_plugin(EditorPlugin *p_editor, bool p_config_chan
if (p_config_changed) {
p_editor->disable_plugin();
}
singleton->editor_plugins_over->get_plugins_list().erase(p_editor);

singleton->editor_plugins_over->remove_plugin(p_editor, nullptr);
singleton->remove_child(p_editor);
singleton->editor_data.remove_editor_plugin(p_editor);
singleton->get_editor_plugins_force_input_forwarding()->remove_plugin(p_editor);
singleton->get_editor_plugins_force_input_forwarding()->remove_plugin(p_editor, nullptr);
}

void EditorNode::_update_addon_config() {
Expand Down Expand Up @@ -7001,23 +7024,51 @@ EditorNode::~EditorNode() {
* EDITOR PLUGIN LIST
*/

void EditorPluginList::verify_top_editors(Vector<ActiveEditor> &p_editors) {
int i = 0;
while (i < p_editors.size()) {
bool discard = true;
Object *owner = ObjectDB::get_instance(p_editors[i].owner);

if (discard) {
EditorPropertyResource *property = Object::cast_to<EditorPropertyResource>(owner);
if (property) {
discard = !property->is_visible_in_tree() || !property->get_edited_object()->editor_is_section_unfolded(property->get_edited_property());
}
}

if (discard) {
Node *node = Object::cast_to<Node>(owner);
if (node) {
discard = (EditorNode::get_singleton()->get_scene_tree_dock()->get_last_pushed_item() != node);
}
}

if (discard) {
p_editors.remove(i);
} else {
i++;
}
}
}

void EditorPluginList::make_visible(bool p_visible) {
for (int i = 0; i < plugins_list.size(); i++) {
plugins_list[i]->make_visible(p_visible);
plugins_list[i].plugin->make_visible(p_visible);
}
}

void EditorPluginList::edit(Object *p_object) {
for (int i = 0; i < plugins_list.size(); i++) {
plugins_list[i]->edit(p_object);
plugins_list[i].plugin->edit(p_object);
}
}

bool EditorPluginList::forward_gui_input(const Ref<InputEvent> &p_event) {
bool discard = false;

for (int i = 0; i < plugins_list.size(); i++) {
if (plugins_list[i]->forward_canvas_gui_input(p_event)) {
if (plugins_list[i].plugin->forward_canvas_gui_input(p_event)) {
discard = true;
}
}
Expand All @@ -7029,11 +7080,11 @@ bool EditorPluginList::forward_spatial_gui_input(Camera3D *p_camera, const Ref<I
bool discard = false;

for (int i = 0; i < plugins_list.size(); i++) {
if ((!serve_when_force_input_enabled) && plugins_list[i]->is_input_event_forwarding_always_enabled()) {
if ((!serve_when_force_input_enabled) && plugins_list[i].plugin->is_input_event_forwarding_always_enabled()) {
continue;
}

if (plugins_list[i]->forward_spatial_gui_input(p_camera, p_event)) {
if (plugins_list[i].plugin->forward_spatial_gui_input(p_camera, p_event)) {
discard = true;
}
}
Expand All @@ -7043,34 +7094,46 @@ bool EditorPluginList::forward_spatial_gui_input(Camera3D *p_camera, const Ref<I

void EditorPluginList::forward_canvas_draw_over_viewport(Control *p_overlay) {
for (int i = 0; i < plugins_list.size(); i++) {
plugins_list[i]->forward_canvas_draw_over_viewport(p_overlay);
plugins_list[i].plugin->forward_canvas_draw_over_viewport(p_overlay);
}
}

void EditorPluginList::forward_canvas_force_draw_over_viewport(Control *p_overlay) {
for (int i = 0; i < plugins_list.size(); i++) {
plugins_list[i]->forward_canvas_force_draw_over_viewport(p_overlay);
plugins_list[i].plugin->forward_canvas_force_draw_over_viewport(p_overlay);
}
}

void EditorPluginList::forward_spatial_draw_over_viewport(Control *p_overlay) {
for (int i = 0; i < plugins_list.size(); i++) {
plugins_list[i]->forward_spatial_draw_over_viewport(p_overlay);
plugins_list[i].plugin->forward_spatial_draw_over_viewport(p_overlay);
}
}

void EditorPluginList::forward_spatial_force_draw_over_viewport(Control *p_overlay) {
for (int i = 0; i < plugins_list.size(); i++) {
plugins_list[i]->forward_spatial_force_draw_over_viewport(p_overlay);
plugins_list[i].plugin->forward_spatial_force_draw_over_viewport(p_overlay);
}
}

void EditorPluginList::add_plugin(EditorPlugin *p_plugin) {
plugins_list.push_back(p_plugin);
void EditorPluginList::add_plugin(EditorPlugin *p_plugin, Object *p_owner) {
ActiveEditor entry;
entry.plugin = p_plugin;
if (p_owner) {
entry.owner = p_owner->get_instance_id();
}
plugins_list.push_back(entry);
}

void EditorPluginList::remove_plugin(EditorPlugin *p_plugin) {
plugins_list.erase(p_plugin);
void EditorPluginList::remove_plugin(EditorPlugin *p_plugin, Object *p_owner) {
int i = 0;
while (i < plugins_list.size()) {
if (plugins_list[i].plugin == p_plugin && (!p_owner || plugins_list[i].owner == p_owner->get_instance_id())) {
plugins_list.remove(i);
} else {
i++;
}
}
}

bool EditorPluginList::is_empty() {
Expand Down
28 changes: 17 additions & 11 deletions editor/editor_node.h
Original file line number Diff line number Diff line change
Expand Up @@ -488,7 +488,6 @@ class EditorNode : public Node {
void _instance_request(const Vector<String> &p_files);

void _display_top_editors(bool p_display);
void _set_top_editors(Vector<EditorPlugin *> p_editor_plugins_over);
void _set_editing_top_editors(Object *p_current_object);

void _quick_opened();
Expand Down Expand Up @@ -726,10 +725,10 @@ class EditorNode : public Node {
static HBoxContainer *get_menu_hb() { return singleton->menu_hb; }

void push_item(Object *p_object, const String &p_property = "", bool p_inspector_only = false);
void edit_item(Object *p_object);
void edit_item_resource(RES p_resource);
void edit_item(Object *p_object, Object *p_owner = nullptr);
void edit_item_resource(RES p_resource, Object *p_owner);
bool item_has_editor(Object *p_object);
void hide_top_editors();
void hide_unused_editors();

void select_editor_by_name(const String &p_name);

Expand Down Expand Up @@ -892,15 +891,19 @@ struct EditorProgress {
};

class EditorPluginList : public Object {
private:
Vector<EditorPlugin *> plugins_list;

public:
void set_plugins_list(Vector<EditorPlugin *> p_plugins_list) {
struct ActiveEditor {
EditorPlugin *plugin;
ObjectID owner;
bool operator==(const ActiveEditor ae) const { return plugin == ae.plugin && owner == ae.owner; }
};
void verify_top_editors(Vector<ActiveEditor> &p_editors);

void set_plugins_list(Vector<ActiveEditor> p_plugins_list) {
plugins_list = p_plugins_list;
}

Vector<EditorPlugin *> &get_plugins_list() {
Vector<ActiveEditor> &get_plugins_list() {
return plugins_list;
}

Expand All @@ -912,13 +915,16 @@ class EditorPluginList : public Object {
bool forward_spatial_gui_input(Camera3D *p_camera, const Ref<InputEvent> &p_event, bool serve_when_force_input_enabled);
void forward_spatial_draw_over_viewport(Control *p_overlay);
void forward_spatial_force_draw_over_viewport(Control *p_overlay);
void add_plugin(EditorPlugin *p_plugin);
void remove_plugin(EditorPlugin *p_plugin);
void add_plugin(EditorPlugin *p_plugin, Object *p_owner);
void remove_plugin(EditorPlugin *p_plugin, Object *p_owner);
void clear();
bool is_empty();

EditorPluginList();
~EditorPluginList();

private:
Vector<ActiveEditor> plugins_list;
};

struct EditorProgressBG {
Expand Down
4 changes: 2 additions & 2 deletions editor/editor_plugin.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -507,13 +507,13 @@ void EditorPlugin::remove_tool_menu_item(const String &p_name) {
void EditorPlugin::set_input_event_forwarding_always_enabled() {
input_event_forwarding_always_enabled = true;
EditorPluginList *always_input_forwarding_list = EditorNode::get_singleton()->get_editor_plugins_force_input_forwarding();
always_input_forwarding_list->add_plugin(this);
always_input_forwarding_list->add_plugin(this, nullptr);
}

void EditorPlugin::set_force_draw_over_forwarding_enabled() {
force_draw_over_forwarding_enabled = true;
EditorPluginList *always_draw_over_forwarding_list = EditorNode::get_singleton()->get_editor_plugins_force_over();
always_draw_over_forwarding_list->add_plugin(this);
always_draw_over_forwarding_list->add_plugin(this, nullptr);
}

void EditorPlugin::notify_scene_changed(const Node *scn_root) {
Expand Down
16 changes: 10 additions & 6 deletions editor/editor_properties.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2828,24 +2828,30 @@ void EditorPropertyResource::_button_input(const Ref<InputEvent> &p_event) {
void EditorPropertyResource::_open_editor_pressed() {
RES res = get_edited_object()->get(get_edited_property());
if (res.is_valid()) {
EditorNode::get_singleton()->call_deferred("edit_item_resource", res); //may clear the editor so do it deferred
EditorNode::get_singleton()->call_deferred("edit_item_resource", res, this); //may clear the editor so do it deferred
}
}

void EditorPropertyResource::_fold_other_editors(Object *p_self) {
if (this == p_self) {
return;
}
EditorPropertyResource *self_prop = Object::cast_to<EditorPropertyResource>(p_self);
if (!self_prop) {
return;
}

RES self_res = self_prop->get_edited_object()->get(self_prop->get_edited_property());
RES res = get_edited_object()->get(get_edited_property());

if (!res.is_valid()) {
return;
}

bool use_editor = false;
for (int i = 0; i < EditorNode::get_editor_data().get_editor_plugin_count(); i++) {
EditorPlugin *ep = EditorNode::get_editor_data().get_editor_plugin(i);
if (ep->handles(res.ptr())) {
if (ep->handles(res.ptr()) && ep->handles(self_res.ptr())) {
use_editor = true;
}
}
Expand Down Expand Up @@ -2962,10 +2968,8 @@ void EditorPropertyResource::update_property() {
memdelete(sub_inspector_vbox);
sub_inspector = nullptr;
sub_inspector_vbox = nullptr;
if (opened_editor) {
EditorNode::get_singleton()->hide_top_editors();
opened_editor = false;
}
opened_editor = false;
EditorNode::get_singleton()->hide_unused_editors();
_update_property_bg();
}
}
Expand Down
Loading

0 comments on commit d627bd7

Please sign in to comment.