43
43
#include " editor/gui/editor_bottom_panel.h"
44
44
#include " editor/themes/editor_scale.h"
45
45
#include " editor/window_wrapper.h"
46
+ #include " scene/resources/style_box_flat.h"
46
47
47
48
enum class TabStyle {
48
49
TEXT_ONLY,
@@ -52,6 +53,120 @@ enum class TabStyle {
52
53
53
54
EditorDockManager *EditorDockManager::singleton = nullptr ;
54
55
56
+ // Implemented in input(..) as nearly every single child consumes the mouse input.
57
+ void EditorDockTabContainer::input (const Ref<InputEvent> &p_event) {
58
+ // Only run if we are dragging a dock.
59
+ Ref<InputEventMouseMotion> me = p_event;
60
+ if (me.is_valid ()) {
61
+ if (mouse_inside != get_global_rect ().has_point (me->get_position ())) {
62
+ mouse_inside = !mouse_inside;
63
+ queue_redraw ();
64
+ }
65
+
66
+ if (mouse_inside) {
67
+ callable_mp (DisplayServer::get_singleton (), &DisplayServer::cursor_set_shape).call_deferred (can_drop_dock ? DisplayServer::CURSOR_CAN_DROP : DisplayServer::CURSOR_FORBIDDEN);
68
+ }
69
+ }
70
+ }
71
+
72
+ void EditorDockTabContainer::_notification (int p_what) {
73
+ switch (p_what) {
74
+ case EditorSettings::NOTIFICATION_EDITOR_SETTINGS_CHANGED: {
75
+ if (EditorSettings::get_singleton ()->check_changed_settings_in_group (" interface/theme" )) {
76
+ dock_drop_highlight->set_corner_radius_all (EDSCALE * EDITOR_GET (" interface/theme/corner_radius" ).operator int ());
77
+ if (mouse_inside) {
78
+ queue_redraw ();
79
+ }
80
+ }
81
+ } break ;
82
+
83
+ case NOTIFICATION_THEME_CHANGED: {
84
+ valid_drop_color = get_theme_color (SNAME (" accent_color" ), EditorStringName (Editor));
85
+ invalid_drop_color = get_theme_color (SNAME (" error_color" ), EditorStringName (Editor));
86
+ } break ;
87
+
88
+ case NOTIFICATION_DRAG_BEGIN: {
89
+ if (!is_visible_in_tree ()) {
90
+ return ;
91
+ }
92
+
93
+ dock_drop_data = get_viewport ()->gui_get_drag_data ();
94
+
95
+ // Check if we are dragging a dock.
96
+ const String type = dock_drop_data.get (" type" , " " );
97
+ if (type == " tab_container_tab" ) {
98
+ Node *from_node = get_node (dock_drop_data[" from_path" ]);
99
+ if (!from_node) {
100
+ return ;
101
+ }
102
+
103
+ EditorDockTabContainer *parent = Object::cast_to<EditorDockTabContainer>(from_node->get_parent ());
104
+ if (!parent) {
105
+ return ;
106
+ }
107
+
108
+ Control *dock = parent->get_tab_control (dock_drop_data[" tab_index" ]);
109
+ if (!dock) {
110
+ return ;
111
+ }
112
+
113
+ is_dragging_dock = true ;
114
+ mouse_inside = get_global_rect ().has_point (get_global_mouse_position ());
115
+
116
+ // TODO: Update logic when GH-106503 is merged to use flags.
117
+ can_drop_dock = is_layout_horizontal ? bool (dock->call (" _can_dock_horizontal" )) : true ;
118
+ dock_drop_highlight->set_border_color (can_drop_dock ? valid_drop_color : invalid_drop_color);
119
+
120
+ set_process_input (true );
121
+ queue_redraw ();
122
+ }
123
+ } break ;
124
+ case NOTIFICATION_DRAG_END: {
125
+ if (!is_dragging_dock) {
126
+ return ;
127
+ }
128
+
129
+ is_dragging_dock = false ;
130
+ set_process_input (false );
131
+
132
+ if (mouse_inside && can_drop_dock) {
133
+ // Only perform a manual drop if an automatic drop was not performed.
134
+ if (!get_tab_bar ()->get_global_rect ().has_point (get_global_mouse_position ())) {
135
+ get_tab_bar ()->drop_data (get_local_mouse_position (), dock_drop_data);
136
+ }
137
+
138
+ queue_redraw ();
139
+ } else if (mouse_inside) {
140
+ queue_redraw ();
141
+ }
142
+
143
+ mouse_inside = false ;
144
+ } break ;
145
+
146
+ case NOTIFICATION_DRAW: {
147
+ // Draw highlights around docks that can be dropped.
148
+ if (is_dragging_dock && mouse_inside) {
149
+ Rect2 dock_rect = Rect2 (Vector2 (), get_size ()).grow (Math::round (2 * EDSCALE));
150
+ draw_style_box (dock_drop_highlight, dock_rect);
151
+ }
152
+ } break ;
153
+
154
+ case NOTIFICATION_VISIBILITY_CHANGED: {
155
+ set_process_input (is_dragging_dock && is_visible_in_tree ());
156
+ } break ;
157
+ }
158
+ }
159
+
160
+ EditorDockTabContainer::EditorDockTabContainer () {
161
+ dock_drop_highlight.instantiate ();
162
+ dock_drop_highlight->set_draw_center (false );
163
+ dock_drop_highlight->set_corner_radius_all (EDSCALE * EDITOR_GET (" interface/theme/corner_radius" ).operator int ());
164
+ dock_drop_highlight->set_border_width_all (Math::round (2 * EDSCALE));
165
+ }
166
+
167
+ // //////////////////////////////////////////////
168
+ // //////////////////////////////////////////////
169
+
55
170
void DockSplitContainer::_update_visibility () {
56
171
if (is_updating) {
57
172
return ;
@@ -114,6 +229,9 @@ void DockSplitContainer::remove_child_notify(Node *p_child) {
114
229
_update_visibility ();
115
230
}
116
231
232
+ // //////////////////////////////////////////////
233
+ // //////////////////////////////////////////////
234
+
117
235
void EditorDockManager::_dock_split_dragged (int p_offset) {
118
236
EditorNode::get_singleton ()->save_editor_layout_delayed ();
119
237
}
@@ -854,6 +972,9 @@ EditorDockManager::EditorDockManager() {
854
972
EditorNode::get_singleton ()->get_gui_base ()->connect (SceneStringName (theme_changed), callable_mp (this , &EditorDockManager::update_docks_menu));
855
973
}
856
974
975
+ // //////////////////////////////////////////////
976
+ // //////////////////////////////////////////////
977
+
857
978
void DockContextPopup::_notification (int p_what) {
858
979
switch (p_what) {
859
980
case Control::NOTIFICATION_LAYOUT_DIRECTION_CHANGED:
0 commit comments