Add ViewPanner to 2D editor

This commit is contained in:
kobewi 2022-01-19 19:59:12 +01:00
parent 249c60e9d1
commit 74bfe88267
21 changed files with 263 additions and 244 deletions

View file

@ -40,6 +40,7 @@
#include "scene/gui/menu_button.h"
#include "scene/gui/panel.h"
#include "scene/gui/progress_bar.h"
#include "scene/gui/view_panner.h"
#include "scene/main/window.h"
void AnimationNodeBlendTreeEditor::add_custom_type(const String &p_name, const Ref<Script> &p_script) {
@ -733,7 +734,8 @@ void AnimationNodeBlendTreeEditor::_removed_from_graph() {
void AnimationNodeBlendTreeEditor::_notification(int p_what) {
if (p_what == NOTIFICATION_ENTER_TREE || p_what == EditorSettings::NOTIFICATION_EDITOR_SETTINGS_CHANGED) {
graph->set_panning_scheme((GraphEdit::PanningScheme)EDITOR_GET("interface/editors/sub_editor_panning_scheme").operator int());
graph->get_panner()->setup((ViewPanner::ControlScheme)EDITOR_GET("editors/panning/sub_editor_panning_scheme").operator int(), ED_GET_SHORTCUT("canvas_item_editor/pan_view"), bool(EditorSettings::get_singleton()->get("editors/panning/simple_panning")));
graph->set_warped_panning(bool(EditorSettings::get_singleton()->get("editors/panning/warped_mouse_panning")));
}
if (p_what == NOTIFICATION_ENTER_TREE || p_what == NOTIFICATION_THEME_CHANGED) {

View file

@ -51,6 +51,7 @@
#include "scene/gui/grid_container.h"
#include "scene/gui/nine_patch_rect.h"
#include "scene/gui/subviewport_container.h"
#include "scene/gui/view_panner.h"
#include "scene/main/canvas_layer.h"
#include "scene/main/window.h"
#include "scene/resources/packed_scene.h"
@ -1116,77 +1117,14 @@ bool CanvasItemEditor::_gui_input_rulers_and_guides(const Ref<InputEvent> &p_eve
}
bool CanvasItemEditor::_gui_input_zoom_or_pan(const Ref<InputEvent> &p_event, bool p_already_accepted) {
Ref<InputEventMouseButton> b = p_event;
if (b.is_valid() && !p_already_accepted) {
const bool pan_on_scroll = bool(EditorSettings::get_singleton()->get("editors/2d/scroll_to_pan")) && !b->is_ctrl_pressed();
bool panner_active = panner->gui_input(p_event, warped_panning ? viewport->get_global_rect() : Rect2());
if (panner->is_panning() != pan_pressed) {
pan_pressed = panner->is_panning();
_update_cursor();
}
if (pan_on_scroll) {
// Perform horizontal scrolling first so we can check for Shift being held.
if (b->is_pressed() &&
(b->get_button_index() == MouseButton::WHEEL_LEFT || (b->is_shift_pressed() && b->get_button_index() == MouseButton::WHEEL_UP))) {
// Pan left
view_offset.x -= int(EditorSettings::get_singleton()->get("editors/2d/pan_speed")) / zoom * b->get_factor();
update_viewport();
return true;
}
if (b->is_pressed() &&
(b->get_button_index() == MouseButton::WHEEL_RIGHT || (b->is_shift_pressed() && b->get_button_index() == MouseButton::WHEEL_DOWN))) {
// Pan right
view_offset.x += int(EditorSettings::get_singleton()->get("editors/2d/pan_speed")) / zoom * b->get_factor();
update_viewport();
return true;
}
}
if (b->is_pressed() && b->get_button_index() == MouseButton::WHEEL_DOWN) {
// Scroll or pan down
if (pan_on_scroll) {
view_offset.y += int(EditorSettings::get_singleton()->get("editors/2d/pan_speed")) / zoom * b->get_factor();
update_viewport();
} else {
zoom_widget->set_zoom_by_increments(-1, Input::get_singleton()->is_key_pressed(Key::ALT));
if (!Math::is_equal_approx(b->get_factor(), 1.0f)) {
// Handle high-precision (analog) scrolling.
zoom_widget->set_zoom(zoom * ((zoom_widget->get_zoom() / zoom - 1.f) * b->get_factor() + 1.f));
}
_zoom_on_position(zoom_widget->get_zoom(), b->get_position());
}
return true;
}
if (b->is_pressed() && b->get_button_index() == MouseButton::WHEEL_UP) {
// Scroll or pan up
if (pan_on_scroll) {
view_offset.y -= int(EditorSettings::get_singleton()->get("editors/2d/pan_speed")) / zoom * b->get_factor();
update_viewport();
} else {
zoom_widget->set_zoom_by_increments(1, Input::get_singleton()->is_key_pressed(Key::ALT));
if (!Math::is_equal_approx(b->get_factor(), 1.0f)) {
// Handle high-precision (analog) scrolling.
zoom_widget->set_zoom(zoom * ((zoom_widget->get_zoom() / zoom - 1.f) * b->get_factor() + 1.f));
}
_zoom_on_position(zoom_widget->get_zoom(), b->get_position());
}
return true;
}
if (!panning) {
if (b->is_pressed() &&
(b->get_button_index() == MouseButton::MIDDLE ||
(b->get_button_index() == MouseButton::LEFT && tool == TOOL_PAN) ||
(b->get_button_index() == MouseButton::LEFT && !EditorSettings::get_singleton()->get("editors/2d/simple_panning") && pan_pressed))) {
// Pan the viewport
panning = true;
}
}
if (panning) {
if (!b->is_pressed() && (pan_on_scroll || (b->get_button_index() != MouseButton::WHEEL_DOWN && b->get_button_index() != MouseButton::WHEEL_UP))) {
// Stop panning the viewport (for any mouse button press except zooming)
panning = false;
}
}
if (panner_active) {
return true;
}
Ref<InputEventKey> k = p_event;
@ -1214,44 +1152,6 @@ bool CanvasItemEditor::_gui_input_zoom_or_pan(const Ref<InputEvent> &p_event, bo
_update_zoom(16.0 * MAX(1, EDSCALE));
}
}
bool is_pan_key = pan_view_shortcut.is_valid() && pan_view_shortcut->matches_event(p_event);
if (is_pan_key && (EditorSettings::get_singleton()->get("editors/2d/simple_panning") || drag_type != DRAG_NONE)) {
if (!panning) {
if (k->is_pressed() && !k->is_echo()) {
//Pan the viewport
panning = true;
}
} else {
if (!k->is_pressed()) {
// Stop panning the viewport (for any mouse button press)
panning = false;
}
}
}
if (is_pan_key && pan_pressed != k->is_pressed()) {
pan_pressed = k->is_pressed();
_update_cursor();
}
}
Ref<InputEventMouseMotion> m = p_event;
if (m.is_valid()) {
if (panning) {
// Pan the viewport
Point2i relative;
if (bool(EditorSettings::get_singleton()->get("editors/2d/warped_mouse_panning"))) {
relative = Input::get_singleton()->warp_mouse_motion(m, viewport->get_global_rect());
} else {
relative = m->get_relative();
}
view_offset.x -= relative.x / zoom;
view_offset.y -= relative.y / zoom;
update_viewport();
return true;
}
}
Ref<InputEventMagnifyGesture> magnify_gesture = p_event;
@ -1277,7 +1177,7 @@ bool CanvasItemEditor::_gui_input_zoom_or_pan(const Ref<InputEvent> &p_event, bo
}
// Pan gesture
const Vector2 delta = (int(EditorSettings::get_singleton()->get("editors/2d/pan_speed")) / zoom) * pan_gesture->get_delta();
const Vector2 delta = (pan_speed / zoom) * pan_gesture->get_delta();
view_offset.x += delta.x;
view_offset.y += delta.y;
update_viewport();
@ -1287,6 +1187,25 @@ bool CanvasItemEditor::_gui_input_zoom_or_pan(const Ref<InputEvent> &p_event, bo
return false;
}
void CanvasItemEditor::_scroll_callback(Vector2 p_scroll_vec) {
_pan_callback(-p_scroll_vec * pan_speed);
}
void CanvasItemEditor::_pan_callback(Vector2 p_scroll_vec) {
view_offset.x -= p_scroll_vec.x / zoom;
view_offset.y -= p_scroll_vec.y / zoom;
update_viewport();
}
void CanvasItemEditor::_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt) {
zoom_widget->set_zoom_by_increments(-1, p_alt);
if (!Math::is_equal_approx(p_scroll_vec.y, (real_t)1.0)) {
// Handle high-precision (analog) scrolling.
zoom_widget->set_zoom(zoom * ((zoom_widget->get_zoom() / zoom - 1.f) * p_scroll_vec.y + 1.f));
}
_zoom_on_position(zoom_widget->get_zoom(), p_origin);
}
bool CanvasItemEditor::_gui_input_pivot(const Ref<InputEvent> &p_event) {
Ref<InputEventMouseMotion> m = p_event;
Ref<InputEventMouseButton> b = p_event;
@ -2281,7 +2200,7 @@ bool CanvasItemEditor::_gui_input_select(const Ref<InputEvent> &p_event) {
return true;
}
if (b.is_valid() && b->get_button_index() == MouseButton::LEFT && b->is_pressed() && tool == TOOL_SELECT) {
if (b.is_valid() && b->get_button_index() == MouseButton::LEFT && b->is_pressed() && tool == TOOL_SELECT && !panner->is_panning()) {
// Single item selection
Point2 click = transform.affine_inverse().xform(b->get_position());
@ -2498,31 +2417,34 @@ bool CanvasItemEditor::_gui_input_hover(const Ref<InputEvent> &p_event) {
void CanvasItemEditor::_gui_input_viewport(const Ref<InputEvent> &p_event) {
bool accepted = false;
if (EditorSettings::get_singleton()->get("editors/2d/simple_panning") || !pan_pressed) {
Ref<InputEventMouseButton> mb = p_event;
bool release_lmb = (mb.is_valid() && !mb->is_pressed() && mb->get_button_index() == MouseButton::LEFT); // Required to properly release some stuff (e.g. selection box) while panning.
if (EditorSettings::get_singleton()->get("editors/panning/simple_panning") || !pan_pressed || release_lmb) {
if ((accepted = _gui_input_rulers_and_guides(p_event))) {
//printf("Rulers and guides\n");
// print_line("Rulers and guides");
} else if ((accepted = editor->get_editor_plugins_over()->forward_gui_input(p_event))) {
//printf("Plugin\n");
// print_line("Plugin");
} else if ((accepted = _gui_input_open_scene_on_double_click(p_event))) {
//printf("Open scene on double click\n");
// print_line("Open scene on double click");
} else if ((accepted = _gui_input_scale(p_event))) {
//printf("Set scale\n");
// print_line("Set scale");
} else if ((accepted = _gui_input_pivot(p_event))) {
//printf("Set pivot\n");
// print_line("Set pivot");
} else if ((accepted = _gui_input_resize(p_event))) {
//printf("Resize\n");
// print_line("Resize");
} else if ((accepted = _gui_input_rotate(p_event))) {
//printf("Rotate\n");
// print_line("Rotate");
} else if ((accepted = _gui_input_move(p_event))) {
//printf("Move\n");
// print_line("Move");
} else if ((accepted = _gui_input_anchors(p_event))) {
//printf("Anchors\n");
// print_line("Anchors");
} else if ((accepted = _gui_input_select(p_event))) {
//printf("Selection\n");
// print_line("Selection");
} else if ((accepted = _gui_input_ruler_tool(p_event))) {
//printf("Measure\n");
// print_line("Measure");
} else {
//printf("Not accepted\n");
// print_line("Not accepted");
}
}
@ -3935,6 +3857,10 @@ void CanvasItemEditor::_notification(int p_what) {
anchors_popup->add_icon_item(get_theme_icon(SNAME("ControlAlignWide"), SNAME("EditorIcons")), TTR("Full Rect"), ANCHORS_PRESET_WIDE);
anchor_mode_button->set_icon(get_theme_icon(SNAME("Anchor"), SNAME("EditorIcons")));
panner->setup((ViewPanner::ControlScheme)EDITOR_GET("interface/editors/2d_editor_panning_scheme").operator int(), ED_GET_SHORTCUT("canvas_item_editor/pan_view"), bool(EditorSettings::get_singleton()->get("editors/panning/simple_panning")));
pan_speed = int(EditorSettings::get_singleton()->get("editors/panning/2d_editor_pan_speed"));
warped_panning = bool(EditorSettings::get_singleton()->get("editors/panning/warped_mouse_panning"));
}
if (p_what == NOTIFICATION_VISIBILITY_CHANGED) {
@ -5205,7 +5131,6 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) {
dragged_guide_index = -1;
is_hovering_h_guide = false;
is_hovering_v_guide = false;
panning = false;
pan_pressed = false;
ruler_tool_active = false;
@ -5260,6 +5185,9 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) {
controls_vb = memnew(VBoxContainer);
controls_vb->set_begin(Point2(5, 5));
panner.instantiate();
panner->set_callbacks(callable_mp(this, &CanvasItemEditor::_scroll_callback), callable_mp(this, &CanvasItemEditor::_pan_callback), callable_mp(this, &CanvasItemEditor::_zoom_callback));
viewport = memnew(CanvasItemEditorViewport(p_editor, this));
viewport_scrollable->add_child(viewport);
viewport->set_mouse_filter(MOUSE_FILTER_PASS);
@ -5268,6 +5196,7 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) {
viewport->set_focus_mode(FOCUS_ALL);
viewport->connect("draw", callable_mp(this, &CanvasItemEditor::_draw_viewport));
viewport->connect("gui_input", callable_mp(this, &CanvasItemEditor::_gui_input_viewport));
viewport->connect("focus_exited", callable_mp(panner.ptr(), &ViewPanner::release_pan_key));
h_scroll = memnew(HScrollBar);
viewport->add_child(h_scroll);
@ -5624,7 +5553,6 @@ CanvasItemEditor::CanvasItemEditor(EditorNode *p_editor) {
multiply_grid_step_shortcut = ED_SHORTCUT("canvas_item_editor/multiply_grid_step", TTR("Multiply grid step by 2"), Key::KP_MULTIPLY);
divide_grid_step_shortcut = ED_SHORTCUT("canvas_item_editor/divide_grid_step", TTR("Divide grid step by 2"), Key::KP_DIVIDE);
pan_view_shortcut = ED_SHORTCUT("canvas_item_editor/pan_view", TTR("Pan View"), Key::SPACE);
skeleton_menu->get_popup()->set_item_checked(skeleton_menu->get_popup()->get_item_index(SKELETON_SHOW_BONES), true);
singleton = this;

View file

@ -42,6 +42,7 @@
#include "scene/main/canvas_item.h"
class CanvasItemEditorViewport;
class ViewPanner;
class CanvasItemEditorSelectedItem : public Object {
GDCLASS(CanvasItemEditorSelectedItem, Object);
@ -276,7 +277,6 @@ private:
bool key_pos;
bool key_rot;
bool key_scale;
bool panning;
bool pan_pressed;
bool ruler_tool_active;
@ -402,7 +402,13 @@ private:
Ref<Shortcut> set_pivot_shortcut;
Ref<Shortcut> multiply_grid_step_shortcut;
Ref<Shortcut> divide_grid_step_shortcut;
Ref<Shortcut> pan_view_shortcut;
Ref<ViewPanner> panner;
bool warped_panning = true;
int pan_speed = 20;
void _scroll_callback(Vector2 p_scroll_vec);
void _pan_callback(Vector2 p_scroll_vec);
void _zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt);
bool _is_node_locked(const Node *p_node);
bool _is_node_movable(const Node *p_node, bool p_popup_warning = false);

View file

@ -66,7 +66,7 @@ void Polygon2DEditor::_notification(int p_what) {
switch (p_what) {
case NOTIFICATION_ENTER_TREE:
case EditorSettings::NOTIFICATION_EDITOR_SETTINGS_CHANGED: {
uv_panner->set_control_scheme((ViewPanner::ControlScheme)EDITOR_GET("interface/editors/sub_editor_panning_scheme").operator int());
uv_panner->setup((ViewPanner::ControlScheme)EDITOR_GET("editors/panning/sub_editor_panning_scheme").operator int(), ED_GET_SHORTCUT("canvas_item_editor/pan_view"), bool(EditorSettings::get_singleton()->get("editors/panning/simple_panning")));
} break;
case NOTIFICATION_READY: {
button_uv->set_icon(get_theme_icon(SNAME("Uv"), SNAME("EditorIcons")));
@ -935,7 +935,7 @@ void Polygon2DEditor::_uv_pan_callback(Vector2 p_scroll_vec) {
uv_vscroll->set_value(uv_vscroll->get_value() - p_scroll_vec.y);
}
void Polygon2DEditor::_uv_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin) {
void Polygon2DEditor::_uv_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt) {
if (p_scroll_vec.y < 0) {
uv_zoom->set_value(uv_zoom->get_value() / (1 - (0.1 * Math::abs(p_scroll_vec.y))));
} else {
@ -1280,10 +1280,6 @@ Polygon2DEditor::Polygon2DEditor(EditorNode *p_editor) :
uv_edit_mode[2]->connect("pressed", callable_mp(this, &Polygon2DEditor::_uv_edit_mode_select), varray(2));
uv_edit_mode[3]->connect("pressed", callable_mp(this, &Polygon2DEditor::_uv_edit_mode_select), varray(3));
uv_panner.instantiate();
uv_panner->set_callbacks(callable_mp(this, &Polygon2DEditor::_uv_scroll_callback), callable_mp(this, &Polygon2DEditor::_uv_pan_callback), callable_mp(this, &Polygon2DEditor::_uv_zoom_callback));
uv_panner->set_disable_rmb(true);
uv_mode_hb->add_child(memnew(VSeparator));
uv_main_vb->add_child(uv_mode_hb);
@ -1470,8 +1466,13 @@ Polygon2DEditor::Polygon2DEditor(EditorNode *p_editor) :
bone_scroll_vb = memnew(VBoxContainer);
bone_scroll->add_child(bone_scroll_vb);
uv_panner.instantiate();
uv_panner->set_callbacks(callable_mp(this, &Polygon2DEditor::_uv_scroll_callback), callable_mp(this, &Polygon2DEditor::_uv_pan_callback), callable_mp(this, &Polygon2DEditor::_uv_zoom_callback));
uv_edit_draw->connect("draw", callable_mp(this, &Polygon2DEditor::_uv_draw));
uv_edit_draw->connect("gui_input", callable_mp(this, &Polygon2DEditor::_uv_input));
uv_edit_draw->connect("focus_exited", callable_mp(uv_panner.ptr(), &ViewPanner::release_pan_key));
uv_edit_draw->set_focus_mode(FOCUS_CLICK);
uv_draw_zoom = 1.0;
point_drag_index = -1;
uv_drag = false;

View file

@ -83,7 +83,7 @@ class Polygon2DEditor : public AbstractPolygon2DEditor {
Ref<ViewPanner> uv_panner;
void _uv_scroll_callback(Vector2 p_scroll_vec);
void _uv_pan_callback(Vector2 p_scroll_vec);
void _uv_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin);
void _uv_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt);
VBoxContainer *bone_scroll_main_vb;
ScrollContainer *bone_scroll;

View file

@ -35,6 +35,7 @@
#include "core/os/keyboard.h"
#include "editor/editor_scale.h"
#include "scene/gui/check_box.h"
#include "scene/gui/view_panner.h"
void draw_margin_line(Control *edit_draw, Vector2 from, Vector2 to) {
Vector2 line = (to - from).normalized() * 10;
@ -259,6 +260,10 @@ void TextureRegionEditor::_region_draw() {
}
void TextureRegionEditor::_region_input(const Ref<InputEvent> &p_input) {
if (panner->gui_input(p_input)) {
return;
}
Transform2D mtx;
mtx.elements[2] = -draw_ofs * draw_zoom;
mtx.scale_basis(Vector2(draw_zoom, draw_zoom));
@ -281,7 +286,7 @@ void TextureRegionEditor::_region_input(const Ref<InputEvent> &p_input) {
Ref<InputEventMouseButton> mb = p_input;
if (mb.is_valid()) {
if (mb->get_button_index() == MouseButton::LEFT) {
if (mb->is_pressed()) {
if (mb->is_pressed() && !panner->is_panning()) {
if (node_ninepatch || obj_styleBox.is_valid()) {
edited_margin = -1;
float margins[4] = { 0 };
@ -400,7 +405,7 @@ void TextureRegionEditor::_region_input(const Ref<InputEvent> &p_input) {
}
}
} else if (drag) {
} else if (!mb->is_pressed() && drag) {
if (edited_margin >= 0) {
undo_redo->create_action(TTR("Set Margin"));
static Side side[4] = { SIDE_TOP, SIDE_BOTTOM, SIDE_LEFT, SIDE_RIGHT };
@ -461,21 +466,13 @@ void TextureRegionEditor::_region_input(const Ref<InputEvent> &p_input) {
drag_index = -1;
}
}
} else if (mb->get_button_index() == MouseButton::WHEEL_UP && mb->is_pressed()) {
_zoom_on_position(draw_zoom * ((0.95 + (0.05 * mb->get_factor())) / 0.95), mb->get_position());
} else if (mb->get_button_index() == MouseButton::WHEEL_DOWN && mb->is_pressed()) {
_zoom_on_position(draw_zoom * (1 - (0.05 * mb->get_factor())), mb->get_position());
}
}
Ref<InputEventMouseMotion> mm = p_input;
if (mm.is_valid()) {
if ((mm->get_button_mask() & MouseButton::MASK_MIDDLE) != MouseButton::NONE || Input::get_singleton()->is_key_pressed(Key::SPACE)) {
Vector2 dragged(mm->get_relative().x / draw_zoom, mm->get_relative().y / draw_zoom);
hscroll->set_value(hscroll->get_value() - dragged.x);
vscroll->set_value(vscroll->get_value() - dragged.y);
} else if (drag) {
if (drag) {
if (edited_margin >= 0) {
float new_margin = 0;
@ -605,6 +602,24 @@ void TextureRegionEditor::_region_input(const Ref<InputEvent> &p_input) {
}
}
void TextureRegionEditor::_scroll_callback(Vector2 p_scroll_vec) {
_pan_callback(-p_scroll_vec * 32);
}
void TextureRegionEditor::_pan_callback(Vector2 p_scroll_vec) {
p_scroll_vec /= draw_zoom;
hscroll->set_value(hscroll->get_value() - p_scroll_vec.x);
vscroll->set_value(vscroll->get_value() - p_scroll_vec.y);
}
void TextureRegionEditor::_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt) {
if (p_scroll_vec.y < 0) {
_zoom_on_position(draw_zoom * ((0.95 + (0.05 * Math::abs(p_scroll_vec.y))) / 0.95), p_origin);
} else {
_zoom_on_position(draw_zoom * (1 - (0.05 * Math::abs(p_scroll_vec.y))), p_origin);
}
}
void TextureRegionEditor::_scroll_changed(float) {
if (updating_scroll) {
return;
@ -802,6 +817,10 @@ void TextureRegionEditor::_notification(int p_what) {
vscroll->set_anchors_and_offsets_preset(PRESET_RIGHT_WIDE);
hscroll->set_anchors_and_offsets_preset(PRESET_BOTTOM_WIDE);
[[fallthrough]];
}
case EditorSettings::NOTIFICATION_EDITOR_SETTINGS_CHANGED: {
panner->setup((ViewPanner::ControlScheme)EDITOR_GET("editors/panning/sub_editor_panning_scheme").operator int(), ED_GET_SHORTCUT("canvas_item_editor/pan_view"), bool(EditorSettings::get_singleton()->get("editors/panning/simple_panning")));
} break;
case NOTIFICATION_VISIBILITY_CHANGED: {
if (snap_mode == SNAP_AUTOSLICE && is_visible() && autoslice_is_dirty) {
@ -1058,11 +1077,16 @@ TextureRegionEditor::TextureRegionEditor(EditorNode *p_editor) {
hb_grid->hide();
panner.instantiate();
panner->set_callbacks(callable_mp(this, &TextureRegionEditor::_scroll_callback), callable_mp(this, &TextureRegionEditor::_pan_callback), callable_mp(this, &TextureRegionEditor::_zoom_callback));
edit_draw = memnew(Panel);
add_child(edit_draw);
edit_draw->set_v_size_flags(SIZE_EXPAND_FILL);
edit_draw->connect("draw", callable_mp(this, &TextureRegionEditor::_region_draw));
edit_draw->connect("gui_input", callable_mp(this, &TextureRegionEditor::_region_input));
edit_draw->connect("focus_exited", callable_mp(panner.ptr(), &ViewPanner::release_pan_key));
edit_draw->set_focus_mode(FOCUS_CLICK);
draw_zoom = 1.0;
edit_draw->set_clip_contents(true);

View file

@ -40,6 +40,8 @@
#include "scene/resources/style_box.h"
#include "scene/resources/texture.h"
class ViewPanner;
class TextureRegionEditor : public VBoxContainer {
GDCLASS(TextureRegionEditor, VBoxContainer);
@ -98,6 +100,11 @@ class TextureRegionEditor : public VBoxContainer {
Vector2 drag_from;
int drag_index;
Ref<ViewPanner> panner;
void _scroll_callback(Vector2 p_scroll_vec);
void _pan_callback(Vector2 p_scroll_vec);
void _zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt);
void _set_snap_mode(int p_mode);
void _set_snap_off_x(float p_val);
void _set_snap_off_y(float p_val);

View file

@ -58,7 +58,7 @@ void TileAtlasView::_pan_callback(Vector2 p_scroll_vec) {
_update_zoom_and_panning(true);
}
void TileAtlasView::_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin) {
void TileAtlasView::_zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt) {
zoom_widget->set_zoom_by_increments(-p_scroll_vec.y * 2);
emit_signal(SNAME("transform_changed"), zoom_widget->get_zoom(), panning);
_update_zoom_and_panning(true);
@ -524,7 +524,7 @@ void TileAtlasView::_notification(int p_what) {
switch (p_what) {
case NOTIFICATION_ENTER_TREE:
case EditorSettings::NOTIFICATION_EDITOR_SETTINGS_CHANGED:
panner->set_control_scheme((ViewPanner::ControlScheme)EDITOR_GET("interface/editors/sub_editor_panning_scheme").operator int());
panner->setup((ViewPanner::ControlScheme)EDITOR_GET("editors/panning/sub_editor_panning_scheme").operator int(), ED_GET_SHORTCUT("canvas_item_editor/pan_view"), bool(EditorSettings::get_singleton()->get("editors/panning/simple_panning")));
break;
case NOTIFICATION_READY:
@ -540,9 +540,6 @@ void TileAtlasView::_bind_methods() {
TileAtlasView::TileAtlasView() {
set_texture_filter(CanvasItem::TEXTURE_FILTER_NEAREST);
panner.instantiate();
panner->set_callbacks(callable_mp(this, &TileAtlasView::_scroll_callback), callable_mp(this, &TileAtlasView::_pan_callback), callable_mp(this, &TileAtlasView::_zoom_callback));
Panel *panel = memnew(Panel);
panel->set_clip_contents(true);
panel->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
@ -566,10 +563,16 @@ TileAtlasView::TileAtlasView() {
button_center_view->set_tooltip(TTR("Center View"));
add_child(button_center_view);
panner.instantiate();
panner->set_callbacks(callable_mp(this, &TileAtlasView::_scroll_callback), callable_mp(this, &TileAtlasView::_pan_callback), callable_mp(this, &TileAtlasView::_zoom_callback));
panner->set_enable_rmb(true);
center_container = memnew(CenterContainer);
center_container->set_mouse_filter(Control::MOUSE_FILTER_IGNORE);
center_container->set_anchors_preset(Control::PRESET_CENTER);
center_container->connect("gui_input", callable_mp(this, &TileAtlasView::gui_input));
center_container->connect("focus_exited", callable_mp(panner.ptr(), &ViewPanner::release_pan_key));
center_container->set_focus_mode(FOCUS_CLICK);
panel->add_child(center_container);
missing_source_label = memnew(Label);

View file

@ -69,7 +69,7 @@ private:
Ref<ViewPanner> panner;
void _scroll_callback(Vector2 p_scroll_vec);
void _pan_callback(Vector2 p_scroll_vec);
void _zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin);
void _zoom_callback(Vector2 p_scroll_vec, Vector2 p_origin, bool p_alt);
Map<Vector2, Map<int, Rect2i>> alternative_tiles_rect_cache;
void _update_alternative_tiles_rect_cache();

View file

@ -42,6 +42,7 @@
#include "scene/animation/animation_player.h"
#include "scene/gui/menu_button.h"
#include "scene/gui/panel.h"
#include "scene/gui/view_panner.h"
#include "scene/main/window.h"
#include "scene/resources/visual_shader_nodes.h"
#include "scene/resources/visual_shader_particle_nodes.h"
@ -3222,7 +3223,8 @@ void VisualShaderEditor::_notification(int p_what) {
}
if (p_what == NOTIFICATION_ENTER_TREE || p_what == EditorSettings::NOTIFICATION_EDITOR_SETTINGS_CHANGED) {
graph->set_panning_scheme((GraphEdit::PanningScheme)EDITOR_GET("interface/editors/sub_editor_panning_scheme").operator int());
graph->get_panner()->setup((ViewPanner::ControlScheme)EDITOR_GET("editors/panning/sub_editor_panning_scheme").operator int(), ED_GET_SHORTCUT("canvas_item_editor/pan_view"), bool(EditorSettings::get_singleton()->get("editors/panning/simple_panning")));
graph->set_warped_panning(bool(EditorSettings::get_singleton()->get("editors/panning/warped_mouse_panning")));
}
if (p_what == NOTIFICATION_DRAG_BEGIN) {