mirror of https://github.com/godotengine/godot
Double click on scene tree element to focus currently selected node
In 3D it will focus in the first viewport Enable double click for trees
This commit is contained in:
parent
3cc08ab1f1
commit
70c9979cce
|
|
@ -2328,9 +2328,22 @@ void Tree::_input_event(InputEvent p_event) {
|
|||
range_drag_enabled=false;
|
||||
Input::get_singleton()->set_mouse_mode(Input::MOUSE_MODE_VISIBLE);
|
||||
warp_mouse(range_drag_capture_pos);
|
||||
} else
|
||||
edit_selected();
|
||||
} else {
|
||||
|
||||
if (delayed_text_editor) {
|
||||
uint64_t diff = OS::get_singleton()->get_ticks_msec() - first_selection_time;
|
||||
if (diff >= 400 && diff <= 800)
|
||||
edit_selected();
|
||||
// fast double click
|
||||
else if (diff < 400) {
|
||||
emit_signal("item_double_clicked");
|
||||
}
|
||||
|
||||
first_selection_time = OS::get_singleton()->get_ticks_msec();
|
||||
} else {
|
||||
edit_selected();
|
||||
}
|
||||
}
|
||||
pressing_for_editor=false;
|
||||
|
||||
}
|
||||
|
|
@ -2848,7 +2861,6 @@ void Tree::item_changed(int p_column,TreeItem *p_item) {
|
|||
|
||||
void Tree::item_selected(int p_column,TreeItem *p_item) {
|
||||
|
||||
|
||||
if (select_mode==SELECT_MULTI) {
|
||||
|
||||
if (!p_item->cells[p_column].selectable)
|
||||
|
|
@ -2856,8 +2868,11 @@ void Tree::item_selected(int p_column,TreeItem *p_item) {
|
|||
|
||||
p_item->cells[p_column].selected=true;
|
||||
//emit_signal("multi_selected",p_item,p_column,true); - NO this is for TreeItem::select
|
||||
if (delayed_text_editor)
|
||||
first_selection_time = OS::get_singleton()->get_ticks_msec();
|
||||
|
||||
} else {
|
||||
|
||||
select_single_item(p_item,root,p_column);
|
||||
}
|
||||
update();
|
||||
|
|
@ -3503,6 +3518,16 @@ bool Tree::get_allow_rmb_select() const{
|
|||
return allow_rmb_select;
|
||||
}
|
||||
|
||||
|
||||
void Tree::set_delayed_text_editor(bool enabled) {
|
||||
delayed_text_editor = enabled;
|
||||
}
|
||||
|
||||
bool Tree::is_delayed_text_editor_enabled() const {
|
||||
return delayed_text_editor;
|
||||
}
|
||||
|
||||
|
||||
void Tree::_bind_methods() {
|
||||
|
||||
ObjectTypeDB::bind_method(_MD("_range_click_timeout"),&Tree::_range_click_timeout);
|
||||
|
|
@ -3556,6 +3581,9 @@ void Tree::_bind_methods() {
|
|||
ObjectTypeDB::bind_method(_MD("set_allow_rmb_select","allow"),&Tree::set_allow_rmb_select);
|
||||
ObjectTypeDB::bind_method(_MD("get_allow_rmb_select"),&Tree::get_allow_rmb_select);
|
||||
|
||||
ObjectTypeDB::bind_method(_MD("set_delayed_text_editor","enable"),&Tree::set_delayed_text_editor);
|
||||
ObjectTypeDB::bind_method(_MD("is_delayed_text_editor_enabled"),&Tree::is_delayed_text_editor_enabled);
|
||||
|
||||
|
||||
ObjectTypeDB::bind_method(_MD("set_single_select_cell_editing_only_when_already_selected","enable"),&Tree::set_single_select_cell_editing_only_when_already_selected);
|
||||
ObjectTypeDB::bind_method(_MD("get_single_select_cell_editing_only_when_already_selected"),&Tree::get_single_select_cell_editing_only_when_already_selected);
|
||||
|
|
@ -3566,6 +3594,7 @@ void Tree::_bind_methods() {
|
|||
ADD_SIGNAL( MethodInfo("item_rmb_selected",PropertyInfo(Variant::VECTOR2,"pos")));
|
||||
ADD_SIGNAL( MethodInfo("empty_tree_rmb_selected",PropertyInfo(Variant::VECTOR2,"pos")));
|
||||
ADD_SIGNAL( MethodInfo("item_edited"));
|
||||
ADD_SIGNAL( MethodInfo("item_double_clicked"));
|
||||
ADD_SIGNAL( MethodInfo("item_collapsed",PropertyInfo(Variant::OBJECT,"item")));
|
||||
//ADD_SIGNAL( MethodInfo("item_doubleclicked" ) );
|
||||
ADD_SIGNAL( MethodInfo("button_pressed",PropertyInfo(Variant::OBJECT,"item"),PropertyInfo(Variant::INT,"column"),PropertyInfo(Variant::INT,"id")));
|
||||
|
|
@ -3669,6 +3698,9 @@ Tree::Tree() {
|
|||
force_select_on_already_selected=false;
|
||||
|
||||
allow_rmb_select=false;
|
||||
|
||||
first_selection_time = 0;
|
||||
delayed_text_editor = false;
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -433,6 +433,9 @@ friend class TreeItem;
|
|||
float last_drag_time;
|
||||
float time_since_motion;*/
|
||||
|
||||
bool delayed_text_editor;
|
||||
uint64_t first_selection_time;
|
||||
|
||||
float drag_speed;
|
||||
float drag_from;
|
||||
float drag_accum;
|
||||
|
|
@ -527,6 +530,9 @@ public:
|
|||
|
||||
void set_value_evaluator(ValueEvaluator *p_evaluator);
|
||||
|
||||
void set_delayed_text_editor(bool enabled);
|
||||
bool is_delayed_text_editor_enabled() const;
|
||||
|
||||
Tree();
|
||||
~Tree();
|
||||
|
||||
|
|
|
|||
|
|
@ -2979,57 +2979,7 @@ void CanvasItemEditor::_popup_callback(int p_op) {
|
|||
case VIEW_CENTER_TO_SELECTION:
|
||||
case VIEW_FRAME_TO_SELECTION: {
|
||||
|
||||
Vector2 center(0.f, 0.f);
|
||||
Rect2 rect;
|
||||
int count = 0;
|
||||
|
||||
Map<Node*,Object*> &selection = editor_selection->get_selection();
|
||||
for(Map<Node*,Object*>::Element *E=selection.front();E;E=E->next()) {
|
||||
CanvasItem *canvas_item = E->key()->cast_to<CanvasItem>();
|
||||
if (!canvas_item) continue;
|
||||
if (canvas_item->get_viewport()!=EditorNode::get_singleton()->get_scene_root())
|
||||
continue;
|
||||
|
||||
|
||||
// counting invisible items, for now
|
||||
//if (!canvas_item->is_visible()) continue;
|
||||
++count;
|
||||
|
||||
Rect2 item_rect = canvas_item->get_item_rect();
|
||||
|
||||
Vector2 pos = canvas_item->get_global_transform().get_origin();
|
||||
Vector2 scale = canvas_item->get_global_transform().get_scale();
|
||||
real_t angle = canvas_item->get_global_transform().get_rotation();
|
||||
|
||||
Matrix32 t(angle, Vector2(0.f,0.f));
|
||||
item_rect = t.xform(item_rect);
|
||||
Rect2 canvas_item_rect(pos + scale*item_rect.pos, scale*item_rect.size);
|
||||
if (count == 1) {
|
||||
rect = canvas_item_rect;
|
||||
} else {
|
||||
rect = rect.merge(canvas_item_rect);
|
||||
}
|
||||
};
|
||||
if (count==0) break;
|
||||
|
||||
if (p_op == VIEW_CENTER_TO_SELECTION) {
|
||||
|
||||
center = rect.pos + rect.size/2;
|
||||
Vector2 offset = viewport->get_size()/2 - editor->get_scene_root()->get_global_canvas_transform().xform(center);
|
||||
h_scroll->set_val(h_scroll->get_val() - offset.x/zoom);
|
||||
v_scroll->set_val(v_scroll->get_val() - offset.y/zoom);
|
||||
|
||||
} else { // VIEW_FRAME_TO_SELECTION
|
||||
|
||||
if (rect.size.x > CMP_EPSILON && rect.size.y > CMP_EPSILON) {
|
||||
float scale_x = viewport->get_size().x/rect.size.x;
|
||||
float scale_y = viewport->get_size().y/rect.size.y;
|
||||
zoom = scale_x < scale_y? scale_x:scale_y;
|
||||
zoom *= 0.90;
|
||||
_update_scroll(0);
|
||||
call_deferred("_popup_callback", VIEW_CENTER_TO_SELECTION);
|
||||
}
|
||||
}
|
||||
_focus_selection(p_op);
|
||||
|
||||
} break;
|
||||
case SKELETON_MAKE_BONES: {
|
||||
|
|
@ -3142,6 +3092,62 @@ template< class P, class C > void CanvasItemEditor::space_selected_items() {
|
|||
}
|
||||
#endif
|
||||
|
||||
|
||||
void CanvasItemEditor::_focus_selection(int p_op) {
|
||||
Vector2 center(0.f, 0.f);
|
||||
Rect2 rect;
|
||||
int count = 0;
|
||||
|
||||
Map<Node*,Object*> &selection = editor_selection->get_selection();
|
||||
for(Map<Node*,Object*>::Element *E=selection.front();E;E=E->next()) {
|
||||
CanvasItem *canvas_item = E->key()->cast_to<CanvasItem>();
|
||||
if (!canvas_item) continue;
|
||||
if (canvas_item->get_viewport()!=EditorNode::get_singleton()->get_scene_root())
|
||||
continue;
|
||||
|
||||
|
||||
// counting invisible items, for now
|
||||
//if (!canvas_item->is_visible()) continue;
|
||||
++count;
|
||||
|
||||
Rect2 item_rect = canvas_item->get_item_rect();
|
||||
|
||||
Vector2 pos = canvas_item->get_global_transform().get_origin();
|
||||
Vector2 scale = canvas_item->get_global_transform().get_scale();
|
||||
real_t angle = canvas_item->get_global_transform().get_rotation();
|
||||
|
||||
Matrix32 t(angle, Vector2(0.f,0.f));
|
||||
item_rect = t.xform(item_rect);
|
||||
Rect2 canvas_item_rect(pos + scale*item_rect.pos, scale*item_rect.size);
|
||||
if (count == 1) {
|
||||
rect = canvas_item_rect;
|
||||
} else {
|
||||
rect = rect.merge(canvas_item_rect);
|
||||
}
|
||||
};
|
||||
if (count==0) return;
|
||||
|
||||
if (p_op == VIEW_CENTER_TO_SELECTION) {
|
||||
|
||||
center = rect.pos + rect.size/2;
|
||||
Vector2 offset = viewport->get_size()/2 - editor->get_scene_root()->get_global_canvas_transform().xform(center);
|
||||
h_scroll->set_val(h_scroll->get_val() - offset.x/zoom);
|
||||
v_scroll->set_val(v_scroll->get_val() - offset.y/zoom);
|
||||
|
||||
} else { // VIEW_FRAME_TO_SELECTION
|
||||
|
||||
if (rect.size.x > CMP_EPSILON && rect.size.y > CMP_EPSILON) {
|
||||
float scale_x = viewport->get_size().x/rect.size.x;
|
||||
float scale_y = viewport->get_size().y/rect.size.y;
|
||||
zoom = scale_x < scale_y? scale_x:scale_y;
|
||||
zoom *= 0.90;
|
||||
_update_scroll(0);
|
||||
call_deferred("_popup_callback", VIEW_CENTER_TO_SELECTION);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void CanvasItemEditor::_bind_methods() {
|
||||
|
||||
ObjectTypeDB::bind_method("_node_removed",&CanvasItemEditor::_node_removed);
|
||||
|
|
@ -3247,6 +3253,12 @@ VSplitContainer *CanvasItemEditor::get_bottom_split() {
|
|||
return bottom_split;
|
||||
}
|
||||
|
||||
|
||||
void CanvasItemEditor::focus_selection() {
|
||||
_focus_selection(VIEW_CENTER_TO_SELECTION);
|
||||
}
|
||||
|
||||
|
||||
CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) {
|
||||
|
||||
tool = TOOL_SELECT;
|
||||
|
|
|
|||
|
|
@ -352,6 +352,8 @@ class CanvasItemEditor : public VBoxContainer {
|
|||
void _viewport_input_event(const InputEvent& p_event);
|
||||
void _viewport_draw();
|
||||
|
||||
void _focus_selection(int p_op);
|
||||
|
||||
void _set_anchor(Control::AnchorType p_left,Control::AnchorType p_top,Control::AnchorType p_right,Control::AnchorType p_bottom);
|
||||
|
||||
HSplitContainer *palette_split;
|
||||
|
|
@ -414,10 +416,12 @@ public:
|
|||
|
||||
Control *get_viewport_control() { return viewport; }
|
||||
|
||||
|
||||
bool get_remove_list(List<Node*> *p_list);
|
||||
void set_undo_redo(UndoRedo *p_undo_redo) {undo_redo=p_undo_redo; }
|
||||
void edit(CanvasItem *p_canvas_item);
|
||||
|
||||
void focus_selection();
|
||||
|
||||
CanvasItemEditor(EditorNode *p_editor);
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -1980,33 +1980,8 @@ void SpatialEditorViewport::_menu_option(int p_option) {
|
|||
} break;
|
||||
case VIEW_CENTER_TO_SELECTION: {
|
||||
|
||||
if (!get_selected_count())
|
||||
break;
|
||||
focus_selection();
|
||||
|
||||
Vector3 center;
|
||||
int count=0;
|
||||
|
||||
List<Node*> &selection = editor_selection->get_selected_node_list();
|
||||
|
||||
for(List<Node*>::Element *E=selection.front();E;E=E->next()) {
|
||||
|
||||
Spatial *sp = E->get()->cast_to<Spatial>();
|
||||
if (!sp)
|
||||
continue;
|
||||
|
||||
SpatialEditorSelectedItem *se=editor_selection->get_node_editor_data<SpatialEditorSelectedItem>(sp);
|
||||
if (!se)
|
||||
continue;
|
||||
|
||||
center+=sp->get_global_transform().origin;
|
||||
count++;
|
||||
}
|
||||
|
||||
if( count != 0 ) {
|
||||
center/=float(count);
|
||||
}
|
||||
|
||||
cursor.pos=center;
|
||||
} break;
|
||||
case VIEW_ALIGN_SELECTION_WITH_VIEW: {
|
||||
|
||||
|
|
@ -2323,6 +2298,38 @@ void SpatialEditorViewport::reset() {
|
|||
_update_name();
|
||||
}
|
||||
|
||||
|
||||
void SpatialEditorViewport::focus_selection() {
|
||||
if (!get_selected_count())
|
||||
return;
|
||||
|
||||
Vector3 center;
|
||||
int count=0;
|
||||
|
||||
List<Node*> &selection = editor_selection->get_selected_node_list();
|
||||
|
||||
for(List<Node*>::Element *E=selection.front();E;E=E->next()) {
|
||||
|
||||
Spatial *sp = E->get()->cast_to<Spatial>();
|
||||
if (!sp)
|
||||
continue;
|
||||
|
||||
SpatialEditorSelectedItem *se=editor_selection->get_node_editor_data<SpatialEditorSelectedItem>(sp);
|
||||
if (!se)
|
||||
continue;
|
||||
|
||||
center+=sp->get_global_transform().origin;
|
||||
count++;
|
||||
}
|
||||
|
||||
if( count != 0 ) {
|
||||
center/=float(count);
|
||||
}
|
||||
|
||||
cursor.pos=center;
|
||||
}
|
||||
|
||||
|
||||
SpatialEditorViewport::SpatialEditorViewport(SpatialEditor *p_spatial_editor, EditorNode *p_editor, int p_index) {
|
||||
|
||||
_edit.mode=TRANSFORM_NONE;
|
||||
|
|
|
|||
|
|
@ -253,6 +253,9 @@ public:
|
|||
void set_state(const Dictionary& p_state);
|
||||
Dictionary get_state() const;
|
||||
void reset();
|
||||
|
||||
void focus_selection();
|
||||
|
||||
Viewport *get_viewport_node() { return viewport; }
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -33,6 +33,7 @@
|
|||
#include "scene/resources/packed_scene.h"
|
||||
#include "editor_settings.h"
|
||||
#include "tools/editor/plugins/canvas_item_editor_plugin.h"
|
||||
#include "tools/editor/plugins/spatial_editor_plugin.h"
|
||||
#include "script_editor_debugger.h"
|
||||
#include "tools/editor/plugins/script_editor_plugin.h"
|
||||
#include "core/io/resource_saver.h"
|
||||
|
|
@ -1825,6 +1826,21 @@ void SceneTreeDock::set_filter(const String& p_filter){
|
|||
scene_tree->set_filter(p_filter);
|
||||
}
|
||||
|
||||
|
||||
void SceneTreeDock::_focus_node() {
|
||||
|
||||
Node *node = scene_tree->get_selected();
|
||||
ERR_FAIL_COND(!node);
|
||||
|
||||
if (node->is_type("CanvasItem")) {
|
||||
CanvasItemEditorPlugin *editor = editor_data->get_editor("2D")->cast_to<CanvasItemEditorPlugin>();
|
||||
editor->get_canvas_item_editor()->focus_selection();
|
||||
} else {
|
||||
SpatialEditorPlugin *editor = editor_data->get_editor("3D")->cast_to<SpatialEditorPlugin>();
|
||||
editor->get_spatial_editor()->get_editor_viewport(0)->focus_selection();
|
||||
}
|
||||
}
|
||||
|
||||
void SceneTreeDock::_bind_methods() {
|
||||
|
||||
ObjectTypeDB::bind_method(_MD("_tool_selected"),&SceneTreeDock::_tool_selected,DEFVAL(false));
|
||||
|
|
@ -1849,6 +1865,7 @@ void SceneTreeDock::_bind_methods() {
|
|||
ObjectTypeDB::bind_method(_MD("_files_dropped"),&SceneTreeDock::_files_dropped);
|
||||
ObjectTypeDB::bind_method(_MD("_tree_rmb"),&SceneTreeDock::_tree_rmb);
|
||||
ObjectTypeDB::bind_method(_MD("_filter_changed"),&SceneTreeDock::_filter_changed);
|
||||
ObjectTypeDB::bind_method(_MD("_focus_node"),&SceneTreeDock::_focus_node);
|
||||
|
||||
|
||||
ObjectTypeDB::bind_method(_MD("instance"),&SceneTreeDock::instance);
|
||||
|
|
@ -1930,6 +1947,9 @@ SceneTreeDock::SceneTreeDock(EditorNode *p_editor,Node *p_scene_root,EditorSelec
|
|||
scene_tree->connect("files_dropped",this,"_files_dropped");
|
||||
scene_tree->connect("nodes_dragged",this,"_nodes_drag_begin");
|
||||
|
||||
scene_tree->get_scene_tree()->connect("item_double_clicked", this, "_focus_node");
|
||||
scene_tree->get_scene_tree()->set_delayed_text_editor(true);
|
||||
|
||||
scene_tree->set_undo_redo(&editor_data->get_undo_redo());
|
||||
scene_tree->set_editor_selection(editor_selection);
|
||||
|
||||
|
|
|
|||
|
|
@ -163,6 +163,8 @@ public:
|
|||
String get_filter();
|
||||
void set_filter(const String& p_filter);
|
||||
|
||||
void _focus_node();
|
||||
|
||||
void import_subscene();
|
||||
void set_edited_scene(Node* p_scene);
|
||||
void instance(const String& p_path);
|
||||
|
|
|
|||
Loading…
Reference in New Issue