Cleaned up the abstract polygon2d editor class

This commit is contained in:
Mireille Arseneault 2024-10-02 15:56:57 -03:00
parent f4af8201ba
commit 08e18c1eb1
14 changed files with 339 additions and 324 deletions

View file

@ -42,20 +42,20 @@
#include "scene/gui/dialogs.h"
#include "scene/gui/separator.h"
bool AbstractPolygon2DEditor::Vertex::operator==(const AbstractPolygon2DEditor::Vertex &p_vertex) const {
bool Polygon2DEditorVertex::operator==(const Polygon2DEditorVertex &p_vertex) const {
return polygon == p_vertex.polygon && vertex == p_vertex.vertex;
}
bool AbstractPolygon2DEditor::Vertex::operator!=(const AbstractPolygon2DEditor::Vertex &p_vertex) const {
bool Polygon2DEditorVertex::operator!=(const Polygon2DEditorVertex &p_vertex) const {
return !(*this == p_vertex);
}
bool AbstractPolygon2DEditor::Vertex::valid() const {
bool Polygon2DEditorVertex::valid() const {
return vertex >= 0;
}
bool AbstractPolygon2DEditor::_is_empty() const {
if (!_get_node()) {
if (!_get_target_node()) {
return true;
}
@ -72,6 +72,14 @@ bool AbstractPolygon2DEditor::_is_empty() const {
return true;
}
Variant AbstractPolygon2DEditor::_get_polygon(int p_idx) const {
return _get_target_node()->get("polygon");
}
void AbstractPolygon2DEditor::_set_polygon(int p_idx, const Variant &p_polygon) const {
_get_target_node()->set("polygon", p_polygon);
}
bool AbstractPolygon2DEditor::_is_line() const {
return false;
}
@ -84,16 +92,8 @@ int AbstractPolygon2DEditor::_get_polygon_count() const {
return 1;
}
Variant AbstractPolygon2DEditor::_get_polygon(int p_idx) const {
return _get_node()->get("polygon");
}
void AbstractPolygon2DEditor::_set_polygon(int p_idx, const Variant &p_polygon) const {
_get_node()->set("polygon", p_polygon);
}
void AbstractPolygon2DEditor::_action_set_polygon(int p_idx, const Variant &p_previous, const Variant &p_polygon) {
Node2D *node = _get_node();
Node2D *node = _get_target_node();
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->add_do_method(node, "set_polygon", p_polygon);
undo_redo->add_undo_method(node, "set_polygon", p_previous);
@ -175,7 +175,7 @@ void AbstractPolygon2DEditor::_notification(int p_what) {
}
void AbstractPolygon2DEditor::_node_removed(Node *p_node) {
if (p_node == _get_node()) {
if (p_node == _get_target_node()) {
edit(nullptr);
hide();
@ -212,8 +212,8 @@ void AbstractPolygon2DEditor::_wip_close() {
undo_redo->create_action(TTR("Create Polygon"));
_action_add_polygon(wip);
if (_has_uv()) {
undo_redo->add_do_method(_get_node(), "set_uv", Vector<Vector2>());
undo_redo->add_undo_method(_get_node(), "set_uv", _get_node()->get("uv"));
undo_redo->add_do_method(_get_target_node(), "set_uv", Vector<Vector2>());
undo_redo->add_undo_method(_get_target_node(), "set_uv", _get_target_node()->get("uv"));
}
_commit_action();
} else {
@ -252,11 +252,11 @@ void AbstractPolygon2DEditor::disable_polygon_editing(bool p_disable, const Stri
}
bool AbstractPolygon2DEditor::forward_gui_input(const Ref<InputEvent> &p_event) {
if (!_get_node() || !_polygon_editing_enabled) {
if (!_get_target_node() || !_polygon_editing_enabled) {
return false;
}
if (!_get_node()->is_visible_in_tree()) {
if (!_get_target_node()->is_visible_in_tree()) {
return false;
}
@ -277,10 +277,10 @@ bool AbstractPolygon2DEditor::forward_gui_input(const Ref<InputEvent> &p_event)
}
if (mb.is_valid()) {
Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_node()->get_global_transform();
Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_target_node()->get_global_transform();
Vector2 gpoint = mb->get_position();
Vector2 cpoint = _get_node()->to_local(canvas_item_editor->snap_point(canvas_item_editor->get_canvas_transform().affine_inverse().xform(mb->get_position())));
Vector2 cpoint = _get_target_node()->to_local(canvas_item_editor->snap_point(canvas_item_editor->get_canvas_transform().affine_inverse().xform(mb->get_position())));
if (mode == MODE_EDIT || (_is_line() && mode == MODE_CREATE)) {
if (mb->get_button_index() == MouseButton::LEFT) {
@ -412,7 +412,7 @@ bool AbstractPolygon2DEditor::forward_gui_input(const Ref<InputEvent> &p_event)
Vector2 gpoint = mm->get_position();
if (edited_point.valid() && (wip_active || mm->get_button_mask().has_flag(MouseButtonMask::LEFT))) {
Vector2 cpoint = _get_node()->to_local(canvas_item_editor->snap_point(canvas_item_editor->get_canvas_transform().affine_inverse().xform(gpoint)));
Vector2 cpoint = _get_target_node()->to_local(canvas_item_editor->snap_point(canvas_item_editor->get_canvas_transform().affine_inverse().xform(gpoint)));
//Move the point in a single axis. Should only work when editing a polygon and while holding shift.
if (mode == MODE_EDIT && mm->is_shift_pressed()) {
@ -491,15 +491,15 @@ bool AbstractPolygon2DEditor::forward_gui_input(const Ref<InputEvent> &p_event)
}
void AbstractPolygon2DEditor::forward_canvas_draw_over_viewport(Control *p_overlay) {
if (!_get_node()) {
if (!_get_target_node()) {
return;
}
if (!_get_node()->is_visible_in_tree()) {
if (!_get_target_node()->is_visible_in_tree()) {
return;
}
Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_node()->get_global_transform();
Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_target_node()->get_global_transform();
// All polygon points are sharp, so use the sharp handle icon
const Ref<Texture2D> handle = get_editor_theme_icon(SNAME("EditorPathSharpHandle"));
@ -593,13 +593,13 @@ void AbstractPolygon2DEditor::forward_canvas_draw_over_viewport(Control *p_overl
}
}
void AbstractPolygon2DEditor::edit(Node *p_polygon) {
void AbstractPolygon2DEditor::edit(Node2D *p_polygon) {
if (!canvas_item_editor) {
canvas_item_editor = CanvasItemEditor::get_singleton();
}
if (p_polygon) {
_set_node(p_polygon);
_set_target_node(p_polygon);
// Enable the pencil tool if the polygon is empty.
if (_is_empty()) {
@ -614,7 +614,7 @@ void AbstractPolygon2DEditor::edit(Node *p_polygon) {
hover_point = Vertex();
selected_point = Vertex();
} else {
_set_node(nullptr);
_set_target_node(nullptr);
}
canvas_item_editor->update_viewport();
@ -654,7 +654,7 @@ AbstractPolygon2DEditor::PosVertex AbstractPolygon2DEditor::closest_point(const
const real_t grab_threshold = EDITOR_GET("editors/polygon_editor/point_grab_radius");
const int n_polygons = _get_polygon_count();
const Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_node()->get_global_transform();
const Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_target_node()->get_global_transform();
PosVertex closest;
real_t closest_dist = 1e10;
@ -684,7 +684,7 @@ AbstractPolygon2DEditor::PosVertex AbstractPolygon2DEditor::closest_edge_point(c
const real_t eps2 = eps * eps;
const int n_polygons = _get_polygon_count();
const Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_node()->get_global_transform();
const Transform2D xform = canvas_item_editor->get_canvas_transform() * _get_target_node()->get_global_transform();
PosVertex closest;
real_t closest_dist = 1e10;
@ -747,30 +747,38 @@ AbstractPolygon2DEditor::AbstractPolygon2DEditor(bool p_wip_destructive) {
create_resource->set_ok_button_text(TTR("Create"));
}
bool AbstractPolygon2DEditorPlugin::forward_canvas_gui_input(const Ref<InputEvent> &p_event) {
return editor->forward_gui_input(p_event);
}
void AbstractPolygon2DEditorPlugin::forward_canvas_draw_over_viewport(Control *p_overlay) {
editor->forward_canvas_draw_over_viewport(p_overlay);
}
void AbstractPolygon2DEditorPlugin::edit(Object *p_object) {
Node *polygon_node = Object::cast_to<Node>(p_object);
polygon_editor->edit(polygon_node);
Node2D *polygon_node = Object::cast_to<Node2D>(p_object);
editor->edit(polygon_node);
make_visible(polygon_node != nullptr);
}
bool AbstractPolygon2DEditorPlugin::handles(Object *p_object) const {
return p_object->is_class(klass);
return p_object->is_class(target_class);
}
void AbstractPolygon2DEditorPlugin::make_visible(bool p_visible) {
if (p_visible) {
polygon_editor->show();
editor->show();
} else {
polygon_editor->hide();
polygon_editor->edit(nullptr);
editor->hide();
editor->edit(nullptr);
}
}
AbstractPolygon2DEditorPlugin::AbstractPolygon2DEditorPlugin(AbstractPolygon2DEditor *p_polygon_editor, const String &p_class) :
polygon_editor(p_polygon_editor),
klass(p_class) {
CanvasItemEditor::get_singleton()->add_control_to_menu_panel(polygon_editor);
polygon_editor->hide();
AbstractPolygon2DEditorPlugin::AbstractPolygon2DEditorPlugin(AbstractPolygon2DEditor *p_editor, const String &p_target_class) :
editor(p_editor),
target_class(p_target_class) {
CanvasItemEditor::get_singleton()->add_control_to_menu_panel(editor);
editor->hide();
}
AbstractPolygon2DEditorPlugin::~AbstractPolygon2DEditorPlugin() {

View file

@ -39,42 +39,47 @@ class Button;
class CanvasItemEditor;
class ConfirmationDialog;
struct Polygon2DEditorVertex {
int polygon = -1;
int vertex = -1;
Polygon2DEditorVertex() {}
Polygon2DEditorVertex(int p_vertex) :
vertex(p_vertex) {}
Polygon2DEditorVertex(int p_polygon, int p_vertex) :
polygon(p_polygon),
vertex(p_vertex) {}
bool operator==(const Polygon2DEditorVertex &p_vertex) const;
bool operator!=(const Polygon2DEditorVertex &p_vertex) const;
bool valid() const;
};
struct Polygon2DEditorPosVertex : public Polygon2DEditorVertex {
Vector2 pos;
Polygon2DEditorPosVertex() {}
Polygon2DEditorPosVertex(const Polygon2DEditorVertex &p_vertex, const Vector2 &p_pos) :
Polygon2DEditorVertex(p_vertex.polygon, p_vertex.vertex),
pos(p_pos) {}
Polygon2DEditorPosVertex(int p_polygon, int p_vertex, const Vector2 &p_pos) :
Polygon2DEditorVertex(p_polygon, p_vertex),
pos(p_pos) {}
};
class AbstractPolygon2DEditor : public HBoxContainer {
GDCLASS(AbstractPolygon2DEditor, HBoxContainer);
protected:
using Vertex = Polygon2DEditorVertex;
using PosVertex = Polygon2DEditorPosVertex;
private:
Button *button_create = nullptr;
Button *button_edit = nullptr;
Button *button_delete = nullptr;
struct Vertex {
Vertex() {}
Vertex(int p_vertex) :
vertex(p_vertex) {}
Vertex(int p_polygon, int p_vertex) :
polygon(p_polygon),
vertex(p_vertex) {}
bool operator==(const Vertex &p_vertex) const;
bool operator!=(const Vertex &p_vertex) const;
bool valid() const;
int polygon = -1;
int vertex = -1;
};
struct PosVertex : public Vertex {
PosVertex() {}
PosVertex(const Vertex &p_vertex, const Vector2 &p_pos) :
Vertex(p_vertex.polygon, p_vertex.vertex),
pos(p_pos) {}
PosVertex(int p_polygon, int p_vertex, const Vector2 &p_pos) :
Vertex(p_polygon, p_vertex),
pos(p_pos) {}
Vector2 pos;
};
PosVertex edited_point;
Vertex hover_point; // point under mouse cursor
Vertex selected_point; // currently selected
@ -103,6 +108,7 @@ protected:
int mode = MODE_EDIT;
virtual void _menu_option(int p_option);
void _wip_changed();
void _wip_close();
void _wip_cancel();
@ -117,13 +123,14 @@ protected:
bool _is_empty() const;
virtual Node2D *_get_node() const = 0;
virtual void _set_node(Node *p_polygon) = 0;
virtual Node2D *_get_target_node() const = 0;
virtual void _set_target_node(Node2D *p_node) = 0;
virtual bool _is_line() const;
virtual bool _has_uv() const;
virtual int _get_polygon_count() const;
virtual Vector2 _get_offset(int p_idx) const;
virtual Variant _get_polygon(int p_idx) const;
virtual void _set_polygon(int p_idx, const Variant &p_polygon) const;
@ -142,27 +149,28 @@ public:
bool forward_gui_input(const Ref<InputEvent> &p_event);
void forward_canvas_draw_over_viewport(Control *p_overlay);
void edit(Node *p_polygon);
void edit(Node2D *p_polygon);
AbstractPolygon2DEditor(bool p_wip_destructive = true);
};
class AbstractPolygon2DEditorPlugin : public EditorPlugin {
GDCLASS(AbstractPolygon2DEditorPlugin, EditorPlugin);
AbstractPolygon2DEditor *polygon_editor = nullptr;
String klass;
protected:
AbstractPolygon2DEditor *editor = nullptr;
String target_class;
public:
virtual bool forward_canvas_gui_input(const Ref<InputEvent> &p_event) override { return polygon_editor->forward_gui_input(p_event); }
virtual void forward_canvas_draw_over_viewport(Control *p_overlay) override { polygon_editor->forward_canvas_draw_over_viewport(p_overlay); }
virtual bool forward_canvas_gui_input(const Ref<InputEvent> &p_event) override;
virtual void forward_canvas_draw_over_viewport(Control *p_overlay) override;
bool has_main_screen() const override { return false; }
virtual String get_name() const override { return klass; }
virtual String get_name() const override { return target_class; }
virtual void edit(Object *p_object) override;
virtual bool handles(Object *p_object) const override;
virtual void make_visible(bool p_visible) override;
AbstractPolygon2DEditorPlugin(AbstractPolygon2DEditor *p_polygon_editor, const String &p_class);
AbstractPolygon2DEditorPlugin(AbstractPolygon2DEditor *p_editor, const String &p_target_class);
~AbstractPolygon2DEditorPlugin();
};

View file

@ -30,12 +30,12 @@
#include "collision_polygon_2d_editor_plugin.h"
Node2D *CollisionPolygon2DEditor::_get_node() const {
return node;
Node2D *CollisionPolygon2DEditor::_get_target_node() const {
return target_polygon;
}
void CollisionPolygon2DEditor::_set_node(Node *p_polygon) {
node = Object::cast_to<CollisionPolygon2D>(p_polygon);
void CollisionPolygon2DEditor::_set_target_node(Node2D *p_node) {
target_polygon = Object::cast_to<CollisionPolygon2D>(p_node);
}
CollisionPolygon2DEditor::CollisionPolygon2DEditor() {}

View file

@ -37,11 +37,11 @@
class CollisionPolygon2DEditor : public AbstractPolygon2DEditor {
GDCLASS(CollisionPolygon2DEditor, AbstractPolygon2DEditor);
CollisionPolygon2D *node = nullptr;
CollisionPolygon2D *target_polygon = nullptr;
protected:
virtual Node2D *_get_node() const override;
virtual void _set_node(Node *p_polygon) override;
virtual Node2D *_get_target_node() const override;
virtual void _set_target_node(Node2D *p_node) override;
public:
CollisionPolygon2DEditor();

View file

@ -34,24 +34,24 @@
#include "editor/editor_undo_redo_manager.h"
Ref<OccluderPolygon2D> LightOccluder2DEditor::_ensure_occluder() const {
Ref<OccluderPolygon2D> occluder = node->get_occluder_polygon();
Ref<OccluderPolygon2D> occluder = target_occluder->get_occluder_polygon();
if (!occluder.is_valid()) {
occluder = Ref<OccluderPolygon2D>(memnew(OccluderPolygon2D));
node->set_occluder_polygon(occluder);
target_occluder->set_occluder_polygon(occluder);
}
return occluder;
}
Node2D *LightOccluder2DEditor::_get_node() const {
return node;
Node2D *LightOccluder2DEditor::_get_target_node() const {
return target_occluder;
}
void LightOccluder2DEditor::_set_node(Node *p_polygon) {
node = Object::cast_to<LightOccluder2D>(p_polygon);
void LightOccluder2DEditor::_set_target_node(Node2D *p_node) {
target_occluder = Object::cast_to<LightOccluder2D>(p_node);
}
bool LightOccluder2DEditor::_is_line() const {
Ref<OccluderPolygon2D> occluder = node->get_occluder_polygon();
Ref<OccluderPolygon2D> occluder = target_occluder->get_occluder_polygon();
if (occluder.is_valid()) {
return !occluder->is_closed();
} else {
@ -60,7 +60,7 @@ bool LightOccluder2DEditor::_is_line() const {
}
int LightOccluder2DEditor::_get_polygon_count() const {
Ref<OccluderPolygon2D> occluder = node->get_occluder_polygon();
Ref<OccluderPolygon2D> occluder = target_occluder->get_occluder_polygon();
if (occluder.is_valid()) {
return occluder->get_polygon().size();
} else {
@ -69,7 +69,7 @@ int LightOccluder2DEditor::_get_polygon_count() const {
}
Variant LightOccluder2DEditor::_get_polygon(int p_idx) const {
Ref<OccluderPolygon2D> occluder = node->get_occluder_polygon();
Ref<OccluderPolygon2D> occluder = target_occluder->get_occluder_polygon();
if (occluder.is_valid()) {
return occluder->get_polygon();
} else {
@ -90,18 +90,18 @@ void LightOccluder2DEditor::_action_set_polygon(int p_idx, const Variant &p_prev
}
bool LightOccluder2DEditor::_has_resource() const {
return node && node->get_occluder_polygon().is_valid();
return target_occluder && target_occluder->get_occluder_polygon().is_valid();
}
void LightOccluder2DEditor::_create_resource() {
if (!node) {
if (!target_occluder) {
return;
}
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->create_action(TTR("Create Occluder Polygon"));
undo_redo->add_do_method(node, "set_occluder_polygon", Ref<OccluderPolygon2D>(memnew(OccluderPolygon2D)));
undo_redo->add_undo_method(node, "set_occluder_polygon", Variant(Ref<RefCounted>()));
undo_redo->add_do_method(target_occluder, "set_occluder_polygon", Ref<OccluderPolygon2D>(memnew(OccluderPolygon2D)));
undo_redo->add_undo_method(target_occluder, "set_occluder_polygon", Variant(Ref<RefCounted>()));
undo_redo->commit_action();
_menu_option(MODE_CREATE);

View file

@ -37,13 +37,13 @@
class LightOccluder2DEditor : public AbstractPolygon2DEditor {
GDCLASS(LightOccluder2DEditor, AbstractPolygon2DEditor);
LightOccluder2D *node = nullptr;
LightOccluder2D *target_occluder = nullptr;
Ref<OccluderPolygon2D> _ensure_occluder() const;
protected:
virtual Node2D *_get_node() const override;
virtual void _set_node(Node *p_polygon) override;
virtual Node2D *_get_target_node() const override;
virtual void _set_target_node(Node2D *p_node) override;
virtual bool _is_line() const override;
virtual int _get_polygon_count() const override;

View file

@ -33,12 +33,12 @@
#include "editor/editor_node.h"
#include "editor/editor_undo_redo_manager.h"
Node2D *Line2DEditor::_get_node() const {
return node;
Node2D *Line2DEditor::_get_target_node() const {
return target_line;
}
void Line2DEditor::_set_node(Node *p_line) {
node = Object::cast_to<Line2D>(p_line);
void Line2DEditor::_set_target_node(Node2D *p_node) {
target_line = Object::cast_to<Line2D>(p_node);
}
bool Line2DEditor::_is_line() const {
@ -46,18 +46,17 @@ bool Line2DEditor::_is_line() const {
}
Variant Line2DEditor::_get_polygon(int p_idx) const {
return _get_node()->get("points");
return target_line->get("points");
}
void Line2DEditor::_set_polygon(int p_idx, const Variant &p_polygon) const {
_get_node()->set("points", p_polygon);
target_line->set("points", p_polygon);
}
void Line2DEditor::_action_set_polygon(int p_idx, const Variant &p_previous, const Variant &p_polygon) {
Node2D *_node = _get_node();
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->add_do_method(_node, "set_points", p_polygon);
undo_redo->add_undo_method(_node, "set_points", p_previous);
undo_redo->add_do_method(target_line, "set_points", p_polygon);
undo_redo->add_undo_method(target_line, "set_points", p_previous);
}
Line2DEditor::Line2DEditor() {}

View file

@ -37,11 +37,11 @@
class Line2DEditor : public AbstractPolygon2DEditor {
GDCLASS(Line2DEditor, AbstractPolygon2DEditor);
Line2D *node = nullptr;
Line2D *target_line = nullptr;
protected:
virtual Node2D *_get_node() const override;
virtual void _set_node(Node *p_line) override;
virtual Node2D *_get_target_node() const override;
virtual void _set_target_node(Node2D *p_node) override;
virtual bool _is_line() const override;
virtual Variant _get_polygon(int p_idx) const override;

View file

@ -33,38 +33,38 @@
#include "editor/editor_node.h"
#include "editor/editor_undo_redo_manager.h"
Node2D *NavigationObstacle2DEditor::_get_node() const {
return node;
Node2D *NavigationObstacle2DEditor::_get_target_node() const {
return target_obstacle;
}
void NavigationObstacle2DEditor::_set_node(Node *p_polygon) {
node = Object::cast_to<NavigationObstacle2D>(p_polygon);
void NavigationObstacle2DEditor::_set_target_node(Node2D *p_node) {
target_obstacle = Object::cast_to<NavigationObstacle2D>(p_node);
}
Variant NavigationObstacle2DEditor::_get_polygon(int p_idx) const {
return node->get_vertices();
return target_obstacle->get_vertices();
}
void NavigationObstacle2DEditor::_set_polygon(int p_idx, const Variant &p_polygon) const {
node->set_vertices(p_polygon);
target_obstacle->set_vertices(p_polygon);
}
void NavigationObstacle2DEditor::_action_add_polygon(const Variant &p_polygon) {
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->add_do_method(node, "set_vertices", p_polygon);
undo_redo->add_undo_method(node, "set_vertices", node->get_vertices());
undo_redo->add_do_method(target_obstacle, "set_vertices", p_polygon);
undo_redo->add_undo_method(target_obstacle, "set_vertices", target_obstacle->get_vertices());
}
void NavigationObstacle2DEditor::_action_remove_polygon(int p_idx) {
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->add_do_method(node, "set_vertices", Variant(Vector<Vector2>()));
undo_redo->add_undo_method(node, "set_vertices", node->get_vertices());
undo_redo->add_do_method(target_obstacle, "set_vertices", Variant(Vector<Vector2>()));
undo_redo->add_undo_method(target_obstacle, "set_vertices", target_obstacle->get_vertices());
}
void NavigationObstacle2DEditor::_action_set_polygon(int p_idx, const Variant &p_previous, const Variant &p_polygon) {
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->add_do_method(node, "set_vertices", p_polygon);
undo_redo->add_undo_method(node, "set_vertices", node->get_vertices());
undo_redo->add_do_method(target_obstacle, "set_vertices", p_polygon);
undo_redo->add_undo_method(target_obstacle, "set_vertices", target_obstacle->get_vertices());
}
NavigationObstacle2DEditor::NavigationObstacle2DEditor() {}

View file

@ -37,11 +37,11 @@
class NavigationObstacle2DEditor : public AbstractPolygon2DEditor {
GDCLASS(NavigationObstacle2DEditor, AbstractPolygon2DEditor);
NavigationObstacle2D *node = nullptr;
NavigationObstacle2D *target_obstacle = nullptr;
protected:
virtual Node2D *_get_node() const override;
virtual void _set_node(Node *p_polygon) override;
virtual Node2D *_get_target_node() const override;
virtual void _set_target_node(Node2D *p_node) override;
virtual Variant _get_polygon(int p_idx) const override;
virtual void _set_polygon(int p_idx, const Variant &p_polygon) const override;

View file

@ -37,22 +37,22 @@
#include "scene/gui/dialogs.h"
Ref<NavigationPolygon> NavigationPolygonEditor::_ensure_navpoly() const {
Ref<NavigationPolygon> navpoly = node->get_navigation_polygon();
Ref<NavigationPolygon> navpoly = target_region->get_navigation_polygon();
if (!navpoly.is_valid()) {
navpoly = Ref<NavigationPolygon>(memnew(NavigationPolygon));
node->set_navigation_polygon(navpoly);
target_region->set_navigation_polygon(navpoly);
}
return navpoly;
}
Node2D *NavigationPolygonEditor::_get_node() const {
return node;
Node2D *NavigationPolygonEditor::_get_target_node() const {
return target_region;
}
void NavigationPolygonEditor::_set_node(Node *p_polygon) {
node = Object::cast_to<NavigationRegion2D>(p_polygon);
if (node) {
Ref<NavigationPolygon> navpoly = node->get_navigation_polygon();
void NavigationPolygonEditor::_set_target_node(Node2D *p_node) {
target_region = Object::cast_to<NavigationRegion2D>(p_node);
if (target_region) {
Ref<NavigationPolygon> navpoly = target_region->get_navigation_polygon();
if (navpoly.is_valid() && navpoly->get_outline_count() > 0 && navpoly->get_polygon_count() == 0) {
// We have outlines drawn / added by the user but no polygons were created for this navmesh yet so let's bake once immediately.
_rebake_timer_timeout();
@ -61,7 +61,7 @@ void NavigationPolygonEditor::_set_node(Node *p_polygon) {
}
int NavigationPolygonEditor::_get_polygon_count() const {
Ref<NavigationPolygon> navpoly = node->get_navigation_polygon();
Ref<NavigationPolygon> navpoly = target_region->get_navigation_polygon();
if (navpoly.is_valid()) {
return navpoly->get_outline_count();
} else {
@ -70,7 +70,7 @@ int NavigationPolygonEditor::_get_polygon_count() const {
}
Variant NavigationPolygonEditor::_get_polygon(int p_idx) const {
Ref<NavigationPolygon> navpoly = node->get_navigation_polygon();
Ref<NavigationPolygon> navpoly = target_region->get_navigation_polygon();
if (navpoly.is_valid()) {
return navpoly->get_outline(p_idx);
} else {
@ -121,18 +121,18 @@ void NavigationPolygonEditor::_action_set_polygon(int p_idx, const Variant &p_pr
}
bool NavigationPolygonEditor::_has_resource() const {
return node && node->get_navigation_polygon().is_valid();
return target_region && target_region->get_navigation_polygon().is_valid();
}
void NavigationPolygonEditor::_create_resource() {
if (!node) {
if (!target_region) {
return;
}
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->create_action(TTR("Create Navigation Polygon"));
undo_redo->add_do_method(node, "set_navigation_polygon", Ref<NavigationPolygon>(memnew(NavigationPolygon)));
undo_redo->add_undo_method(node, "set_navigation_polygon", Variant(Ref<RefCounted>()));
undo_redo->add_do_method(target_region, "set_navigation_polygon", Ref<NavigationPolygon>(memnew(NavigationPolygon)));
undo_redo->add_undo_method(target_region, "set_navigation_polygon", Variant(Ref<RefCounted>()));
undo_redo->commit_action();
_menu_option(MODE_CREATE);
@ -171,7 +171,7 @@ NavigationPolygonEditor::NavigationPolygonEditor() {
err_dialog = memnew(AcceptDialog);
add_child(err_dialog);
node = nullptr;
target_region = nullptr;
}
void NavigationPolygonEditor::_notification(int p_what) {
@ -197,45 +197,45 @@ void NavigationPolygonEditor::_bake_pressed() {
}
button_bake->set_pressed(false);
ERR_FAIL_NULL(node);
Ref<NavigationPolygon> navigation_polygon = node->get_navigation_polygon();
ERR_FAIL_NULL(target_region);
Ref<NavigationPolygon> navigation_polygon = target_region->get_navigation_polygon();
if (navigation_polygon.is_null()) {
err_dialog->set_text(TTR("A NavigationPolygon resource must be set or created for this node to work."));
err_dialog->popup_centered();
return;
}
node->bake_navigation_polygon(true);
target_region->bake_navigation_polygon(true);
node->queue_redraw();
target_region->queue_redraw();
}
void NavigationPolygonEditor::_clear_pressed() {
if (rebake_timer) {
rebake_timer->stop();
}
if (node) {
if (node->get_navigation_polygon().is_valid()) {
node->get_navigation_polygon()->clear();
if (target_region) {
if (target_region->get_navigation_polygon().is_valid()) {
target_region->get_navigation_polygon()->clear();
// Needed to update all the region internals.
node->set_navigation_polygon(node->get_navigation_polygon());
target_region->set_navigation_polygon(target_region->get_navigation_polygon());
}
}
button_bake->set_pressed(false);
bake_info->set_text("");
if (node) {
node->queue_redraw();
if (target_region) {
target_region->queue_redraw();
}
}
void NavigationPolygonEditor::_update_polygon_editing_state() {
if (!_get_node()) {
if (!target_region) {
return;
}
if (node != nullptr && node->get_navigation_polygon().is_valid()) {
if (target_region != nullptr && target_region->get_navigation_polygon().is_valid()) {
bake_hbox->show();
} else {
bake_hbox->hide();
@ -243,16 +243,16 @@ void NavigationPolygonEditor::_update_polygon_editing_state() {
}
void NavigationPolygonEditor::_rebake_timer_timeout() {
if (!node) {
if (!target_region) {
return;
}
Ref<NavigationPolygon> navigation_polygon = node->get_navigation_polygon();
Ref<NavigationPolygon> navigation_polygon = target_region->get_navigation_polygon();
if (!navigation_polygon.is_valid()) {
return;
}
node->bake_navigation_polygon(true);
node->queue_redraw();
target_region->bake_navigation_polygon(true);
target_region->queue_redraw();
}
NavigationPolygonEditorPlugin::NavigationPolygonEditorPlugin() :

View file

@ -45,7 +45,7 @@ class NavigationPolygonEditor : public AbstractPolygon2DEditor {
GDCLASS(NavigationPolygonEditor, AbstractPolygon2DEditor);
NavigationRegion2D *node = nullptr;
NavigationRegion2D *target_region = nullptr;
Ref<NavigationPolygon> _ensure_navpoly() const;
@ -68,8 +68,8 @@ class NavigationPolygonEditor : public AbstractPolygon2DEditor {
protected:
void _notification(int p_what);
virtual Node2D *_get_node() const override;
virtual void _set_node(Node *p_polygon) override;
virtual Node2D *_get_target_node() const override;
virtual void _set_target_node(Node2D *p_node) override;
virtual int _get_polygon_count() const override;
virtual Variant _get_polygon(int p_idx) const override;

View file

@ -77,21 +77,21 @@ class UVEditDialog : public AcceptDialog {
}
};
Node2D *Polygon2DEditor::_get_node() const {
return node;
Node2D *Polygon2DEditor::_get_target_node() const {
return target_polygon;
}
void Polygon2DEditor::_set_node(Node *p_polygon) {
node = Object::cast_to<Polygon2D>(p_polygon);
void Polygon2DEditor::_set_target_node(Node2D *p_node) {
target_polygon = Object::cast_to<Polygon2D>(p_node);
_update_polygon_editing_state();
}
Vector2 Polygon2DEditor::_get_offset(int p_idx) const {
return node->get_offset();
return target_polygon->get_offset();
}
int Polygon2DEditor::_get_polygon_count() const {
if (node->get_internal_vertex_count() > 0) {
if (target_polygon->get_internal_vertex_count() > 0) {
return 0; //do not edit if internal vertices exist
} else {
return 1;
@ -152,16 +152,16 @@ void Polygon2DEditor::_notification(int p_what) {
void Polygon2DEditor::_sync_bones() {
Skeleton2D *skeleton = nullptr;
if (!node->has_node(node->get_skeleton())) {
if (!target_polygon->has_node(target_polygon->get_skeleton())) {
error->set_text(TTR("The skeleton property of the Polygon2D does not point to a Skeleton2D node"));
error->popup_centered();
} else {
Node *sn = node->get_node(node->get_skeleton());
Node *sn = target_polygon->get_node(target_polygon->get_skeleton());
skeleton = Object::cast_to<Skeleton2D>(sn);
}
Array prev_bones = node->call("_get_bones");
node->clear_bones();
Array prev_bones = target_polygon->call("_get_bones");
target_polygon->clear_bones();
if (!skeleton) {
error->set_text(TTR("The skeleton property of the Polygon2D does not point to a Skeleton2D node"));
@ -170,7 +170,7 @@ void Polygon2DEditor::_sync_bones() {
for (int i = 0; i < skeleton->get_bone_count(); i++) {
NodePath path = skeleton->get_path_to(skeleton->get_bone(i));
Vector<float> weights;
int wc = node->get_polygon().size();
int wc = target_polygon->get_polygon().size();
for (int j = 0; j < prev_bones.size(); j += 2) {
NodePath pvp = prev_bones[j];
@ -188,16 +188,16 @@ void Polygon2DEditor::_sync_bones() {
}
}
node->add_bone(path, weights);
target_polygon->add_bone(path, weights);
}
}
Array new_bones = node->call("_get_bones");
Array new_bones = target_polygon->call("_get_bones");
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
undo_redo->create_action(TTR("Sync Bones"));
undo_redo->add_do_method(node, "_set_bones", new_bones);
undo_redo->add_undo_method(node, "_set_bones", prev_bones);
undo_redo->add_do_method(target_polygon, "_set_bones", new_bones);
undo_redo->add_undo_method(target_polygon, "_set_bones", prev_bones);
undo_redo->add_do_method(this, "_update_bone_list");
undo_redo->add_undo_method(this, "_update_bone_list");
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
@ -217,9 +217,9 @@ void Polygon2DEditor::_update_bone_list() {
Ref<ButtonGroup> bg;
bg.instantiate();
for (int i = 0; i < node->get_bone_count(); i++) {
for (int i = 0; i < target_polygon->get_bone_count(); i++) {
CheckBox *cb = memnew(CheckBox);
NodePath np = node->get_bone_path(i);
NodePath np = target_polygon->get_bone_path(i);
String name;
if (np.get_name_count()) {
name = np.get_name(np.get_name_count() - 1);
@ -326,14 +326,14 @@ void Polygon2DEditor::_menu_option(int p_option) {
EditorUndoRedoManager *undo_redo = EditorUndoRedoManager::get_singleton();
switch (p_option) {
case MODE_EDIT_UV: {
uv_edit_draw->set_texture_filter(node->get_texture_filter_in_tree());
uv_edit_draw->set_texture_filter(target_polygon->get_texture_filter_in_tree());
Vector<Vector2> points = node->get_polygon();
Vector<Vector2> uvs = node->get_uv();
Vector<Vector2> points = target_polygon->get_polygon();
Vector<Vector2> uvs = target_polygon->get_uv();
if (uvs.size() != points.size()) {
undo_redo->create_action(TTR("Create UV Map"));
undo_redo->add_do_method(node, "set_uv", points);
undo_redo->add_undo_method(node, "set_uv", uvs);
undo_redo->add_do_method(target_polygon, "set_uv", points);
undo_redo->add_undo_method(target_polygon, "set_uv", uvs);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -349,40 +349,40 @@ void Polygon2DEditor::_menu_option(int p_option) {
get_tree()->connect("process_frame", callable_mp(this, &Polygon2DEditor::_center_view), CONNECT_ONE_SHOT);
} break;
case UVEDIT_POLYGON_TO_UV: {
Vector<Vector2> points = node->get_polygon();
Vector<Vector2> points = target_polygon->get_polygon();
if (points.size() == 0) {
break;
}
Vector<Vector2> uvs = node->get_uv();
Vector<Vector2> uvs = target_polygon->get_uv();
undo_redo->create_action(TTR("Create UV Map"));
undo_redo->add_do_method(node, "set_uv", points);
undo_redo->add_undo_method(node, "set_uv", uvs);
undo_redo->add_do_method(target_polygon, "set_uv", points);
undo_redo->add_undo_method(target_polygon, "set_uv", uvs);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
} break;
case UVEDIT_UV_TO_POLYGON: {
Vector<Vector2> points = node->get_polygon();
Vector<Vector2> uvs = node->get_uv();
Vector<Vector2> points = target_polygon->get_polygon();
Vector<Vector2> uvs = target_polygon->get_uv();
if (uvs.size() == 0) {
break;
}
undo_redo->create_action(TTR("Create Polygon"));
undo_redo->add_do_method(node, "set_polygon", uvs);
undo_redo->add_undo_method(node, "set_polygon", points);
undo_redo->add_do_method(target_polygon, "set_polygon", uvs);
undo_redo->add_undo_method(target_polygon, "set_polygon", points);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
} break;
case UVEDIT_UV_CLEAR: {
Vector<Vector2> uvs = node->get_uv();
Vector<Vector2> uvs = target_polygon->get_uv();
if (uvs.size() == 0) {
break;
}
undo_redo->create_action(TTR("Create UV Map"));
undo_redo->add_do_method(node, "set_uv", Vector<Vector2>());
undo_redo->add_undo_method(node, "set_uv", uvs);
undo_redo->add_do_method(target_polygon, "set_uv", Vector<Vector2>());
undo_redo->add_undo_method(target_polygon, "set_uv", uvs);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -400,20 +400,20 @@ void Polygon2DEditor::_cancel_editing() {
if (uv_create) {
uv_drag = false;
uv_create = false;
node->set_uv(uv_create_uv_prev);
node->set_polygon(uv_create_poly_prev);
node->set_internal_vertex_count(uv_create_prev_internal_vertices);
node->set_vertex_colors(uv_create_colors_prev);
node->call("_set_bones", uv_create_bones_prev);
node->set_polygons(polygons_prev);
target_polygon->set_uv(uv_create_uv_prev);
target_polygon->set_polygon(uv_create_poly_prev);
target_polygon->set_internal_vertex_count(uv_create_prev_internal_vertices);
target_polygon->set_vertex_colors(uv_create_colors_prev);
target_polygon->call("_set_bones", uv_create_bones_prev);
target_polygon->set_polygons(polygons_prev);
_update_polygon_editing_state();
} else if (uv_drag) {
uv_drag = false;
if (uv_edit_mode[0]->is_pressed()) { // Edit UV.
node->set_uv(points_prev);
target_polygon->set_uv(points_prev);
} else if (uv_edit_mode[1]->is_pressed()) { // Edit polygon.
node->set_polygon(points_prev);
target_polygon->set_polygon(points_prev);
}
}
@ -421,11 +421,11 @@ void Polygon2DEditor::_cancel_editing() {
}
void Polygon2DEditor::_update_polygon_editing_state() {
if (!_get_node()) {
if (!target_polygon) {
return;
}
if (node->get_internal_vertex_count() > 0) {
if (target_polygon->get_internal_vertex_count() > 0) {
disable_polygon_editing(true, TTR("Polygon 2D has internal vertices, so it can no longer be edited in the viewport."));
} else {
disable_polygon_editing(false, String());
@ -490,7 +490,7 @@ void Polygon2DEditor::_uv_mode(int p_mode) {
}
void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
if (!_get_node()) {
if (!target_polygon) {
return;
}
@ -511,12 +511,12 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
if (mb->is_pressed()) {
uv_drag_from = snap_point(mb->get_position());
uv_drag = true;
points_prev = node->get_uv();
points_prev = target_polygon->get_uv();
if (uv_edit_mode[0]->is_pressed()) { //edit uv
points_prev = node->get_uv();
points_prev = target_polygon->get_uv();
} else { //edit polygon
points_prev = node->get_polygon();
points_prev = target_polygon->get_polygon();
}
uv_move_current = uv_mode;
@ -530,16 +530,16 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
uv_drag_from = tuv;
uv_drag = true;
uv_create = true;
uv_create_uv_prev = node->get_uv();
uv_create_poly_prev = node->get_polygon();
uv_create_prev_internal_vertices = node->get_internal_vertex_count();
uv_create_colors_prev = node->get_vertex_colors();
uv_create_bones_prev = node->call("_get_bones");
polygons_prev = node->get_polygons();
uv_create_uv_prev = target_polygon->get_uv();
uv_create_poly_prev = target_polygon->get_polygon();
uv_create_prev_internal_vertices = target_polygon->get_internal_vertex_count();
uv_create_colors_prev = target_polygon->get_vertex_colors();
uv_create_bones_prev = target_polygon->call("_get_bones");
polygons_prev = target_polygon->get_polygons();
disable_polygon_editing(false, String());
node->set_polygon(points_prev);
node->set_uv(points_prev);
node->set_internal_vertex_count(0);
target_polygon->set_polygon(points_prev);
target_polygon->set_uv(points_prev);
target_polygon->set_internal_vertex_count(0);
uv_edit_draw->queue_redraw();
} else {
@ -548,16 +548,16 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
// Close the polygon if selected point is near start. Threshold for closing scaled by zoom level
if (points_prev.size() > 2 && tuv.distance_to(points_prev[0]) < (8 / uv_draw_zoom)) {
undo_redo->create_action(TTR("Create Polygon & UV"));
undo_redo->add_do_method(node, "set_uv", node->get_uv());
undo_redo->add_undo_method(node, "set_uv", uv_create_uv_prev);
undo_redo->add_do_method(node, "set_polygon", node->get_polygon());
undo_redo->add_undo_method(node, "set_polygon", uv_create_poly_prev);
undo_redo->add_do_method(node, "set_internal_vertex_count", 0);
undo_redo->add_undo_method(node, "set_internal_vertex_count", uv_create_prev_internal_vertices);
undo_redo->add_do_method(node, "set_vertex_colors", Vector<Color>());
undo_redo->add_undo_method(node, "set_vertex_colors", uv_create_colors_prev);
undo_redo->add_do_method(node, "clear_bones");
undo_redo->add_undo_method(node, "_set_bones", uv_create_bones_prev);
undo_redo->add_do_method(target_polygon, "set_uv", target_polygon->get_uv());
undo_redo->add_undo_method(target_polygon, "set_uv", uv_create_uv_prev);
undo_redo->add_do_method(target_polygon, "set_polygon", target_polygon->get_polygon());
undo_redo->add_undo_method(target_polygon, "set_polygon", uv_create_poly_prev);
undo_redo->add_do_method(target_polygon, "set_internal_vertex_count", 0);
undo_redo->add_undo_method(target_polygon, "set_internal_vertex_count", uv_create_prev_internal_vertices);
undo_redo->add_do_method(target_polygon, "set_vertex_colors", Vector<Color>());
undo_redo->add_undo_method(target_polygon, "set_vertex_colors", uv_create_colors_prev);
undo_redo->add_do_method(target_polygon, "clear_bones");
undo_redo->add_undo_method(target_polygon, "_set_bones", uv_create_bones_prev);
undo_redo->add_do_method(this, "_update_polygon_editing_state");
undo_redo->add_undo_method(this, "_update_polygon_editing_state");
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
@ -573,19 +573,19 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
point_drag_index = points_prev.size() - 1;
uv_drag_from = tuv;
}
node->set_polygon(points_prev);
node->set_uv(points_prev);
target_polygon->set_polygon(points_prev);
target_polygon->set_uv(points_prev);
}
CanvasItemEditor::get_singleton()->update_viewport();
}
if (uv_move_current == UV_MODE_CREATE_INTERNAL) {
uv_create_uv_prev = node->get_uv();
uv_create_poly_prev = node->get_polygon();
uv_create_colors_prev = node->get_vertex_colors();
uv_create_bones_prev = node->call("_get_bones");
int internal_vertices = node->get_internal_vertex_count();
uv_create_uv_prev = target_polygon->get_uv();
uv_create_poly_prev = target_polygon->get_polygon();
uv_create_colors_prev = target_polygon->get_vertex_colors();
uv_create_bones_prev = target_polygon->call("_get_bones");
int internal_vertices = target_polygon->get_internal_vertex_count();
Vector2 pos = mtx.affine_inverse().xform(snap_point(mb->get_position()));
@ -596,20 +596,20 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
undo_redo->create_action(TTR("Create Internal Vertex"));
undo_redo->add_do_method(node, "set_uv", uv_create_uv_prev);
undo_redo->add_undo_method(node, "set_uv", node->get_uv());
undo_redo->add_do_method(node, "set_polygon", uv_create_poly_prev);
undo_redo->add_undo_method(node, "set_polygon", node->get_polygon());
undo_redo->add_do_method(node, "set_vertex_colors", uv_create_colors_prev);
undo_redo->add_undo_method(node, "set_vertex_colors", node->get_vertex_colors());
for (int i = 0; i < node->get_bone_count(); i++) {
Vector<float> bonew = node->get_bone_weights(i);
undo_redo->add_do_method(target_polygon, "set_uv", uv_create_uv_prev);
undo_redo->add_undo_method(target_polygon, "set_uv", target_polygon->get_uv());
undo_redo->add_do_method(target_polygon, "set_polygon", uv_create_poly_prev);
undo_redo->add_undo_method(target_polygon, "set_polygon", target_polygon->get_polygon());
undo_redo->add_do_method(target_polygon, "set_vertex_colors", uv_create_colors_prev);
undo_redo->add_undo_method(target_polygon, "set_vertex_colors", target_polygon->get_vertex_colors());
for (int i = 0; i < target_polygon->get_bone_count(); i++) {
Vector<float> bonew = target_polygon->get_bone_weights(i);
bonew.push_back(0);
undo_redo->add_do_method(node, "set_bone_weights", i, bonew);
undo_redo->add_undo_method(node, "set_bone_weights", i, node->get_bone_weights(i));
undo_redo->add_do_method(target_polygon, "set_bone_weights", i, bonew);
undo_redo->add_undo_method(target_polygon, "set_bone_weights", i, target_polygon->get_bone_weights(i));
}
undo_redo->add_do_method(node, "set_internal_vertex_count", internal_vertices + 1);
undo_redo->add_undo_method(node, "set_internal_vertex_count", internal_vertices);
undo_redo->add_do_method(target_polygon, "set_internal_vertex_count", internal_vertices + 1);
undo_redo->add_undo_method(target_polygon, "set_internal_vertex_count", internal_vertices);
undo_redo->add_do_method(this, "_update_polygon_editing_state");
undo_redo->add_undo_method(this, "_update_polygon_editing_state");
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
@ -618,11 +618,11 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
if (uv_move_current == UV_MODE_REMOVE_INTERNAL) {
uv_create_uv_prev = node->get_uv();
uv_create_poly_prev = node->get_polygon();
uv_create_colors_prev = node->get_vertex_colors();
uv_create_bones_prev = node->call("_get_bones");
int internal_vertices = node->get_internal_vertex_count();
uv_create_uv_prev = target_polygon->get_uv();
uv_create_poly_prev = target_polygon->get_polygon();
uv_create_colors_prev = target_polygon->get_vertex_colors();
uv_create_bones_prev = target_polygon->call("_get_bones");
int internal_vertices = target_polygon->get_internal_vertex_count();
if (internal_vertices <= 0) {
return;
@ -651,20 +651,20 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
undo_redo->create_action(TTR("Remove Internal Vertex"));
undo_redo->add_do_method(node, "set_uv", uv_create_uv_prev);
undo_redo->add_undo_method(node, "set_uv", node->get_uv());
undo_redo->add_do_method(node, "set_polygon", uv_create_poly_prev);
undo_redo->add_undo_method(node, "set_polygon", node->get_polygon());
undo_redo->add_do_method(node, "set_vertex_colors", uv_create_colors_prev);
undo_redo->add_undo_method(node, "set_vertex_colors", node->get_vertex_colors());
for (int i = 0; i < node->get_bone_count(); i++) {
Vector<float> bonew = node->get_bone_weights(i);
undo_redo->add_do_method(target_polygon, "set_uv", uv_create_uv_prev);
undo_redo->add_undo_method(target_polygon, "set_uv", target_polygon->get_uv());
undo_redo->add_do_method(target_polygon, "set_polygon", uv_create_poly_prev);
undo_redo->add_undo_method(target_polygon, "set_polygon", target_polygon->get_polygon());
undo_redo->add_do_method(target_polygon, "set_vertex_colors", uv_create_colors_prev);
undo_redo->add_undo_method(target_polygon, "set_vertex_colors", target_polygon->get_vertex_colors());
for (int i = 0; i < target_polygon->get_bone_count(); i++) {
Vector<float> bonew = target_polygon->get_bone_weights(i);
bonew.remove_at(closest);
undo_redo->add_do_method(node, "set_bone_weights", i, bonew);
undo_redo->add_undo_method(node, "set_bone_weights", i, node->get_bone_weights(i));
undo_redo->add_do_method(target_polygon, "set_bone_weights", i, bonew);
undo_redo->add_undo_method(target_polygon, "set_bone_weights", i, target_polygon->get_bone_weights(i));
}
undo_redo->add_do_method(node, "set_internal_vertex_count", internal_vertices - 1);
undo_redo->add_undo_method(node, "set_internal_vertex_count", internal_vertices);
undo_redo->add_do_method(target_polygon, "set_internal_vertex_count", internal_vertices - 1);
undo_redo->add_undo_method(target_polygon, "set_internal_vertex_count", internal_vertices);
undo_redo->add_do_method(this, "_update_polygon_editing_state");
undo_redo->add_undo_method(this, "_update_polygon_editing_state");
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
@ -717,14 +717,14 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
error->set_text(TTR("Invalid Polygon (need 3 different vertices)"));
error->popup_centered();
} else {
Array polygons = node->get_polygons();
Array polygons = target_polygon->get_polygons();
polygons = polygons.duplicate(); //copy because its a reference
//todo, could check whether it already exists?
polygons.push_back(polygon_create);
undo_redo->create_action(TTR("Add Custom Polygon"));
undo_redo->add_do_method(node, "set_polygons", polygons);
undo_redo->add_undo_method(node, "set_polygons", node->get_polygons());
undo_redo->add_do_method(target_polygon, "set_polygons", polygons);
undo_redo->add_undo_method(target_polygon, "set_polygons", target_polygon->get_polygons());
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -739,7 +739,7 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
if (uv_move_current == UV_MODE_REMOVE_POLYGON) {
Array polygons = node->get_polygons();
Array polygons = target_polygon->get_polygons();
polygons = polygons.duplicate(); //copy because its a reference
int erase_index = -1;
@ -764,8 +764,8 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
if (erase_index != -1) {
polygons.remove_at(erase_index);
undo_redo->create_action(TTR("Remove Custom Polygon"));
undo_redo->add_do_method(node, "set_polygons", polygons);
undo_redo->add_undo_method(node, "set_polygons", node->get_polygons());
undo_redo->add_do_method(target_polygon, "set_polygons", polygons);
undo_redo->add_undo_method(target_polygon, "set_polygons", target_polygon->get_polygons());
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -782,8 +782,8 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
}
if (bone_selected != -1 && node->get_bone_weights(bone_selected).size() == points_prev.size()) {
prev_weights = node->get_bone_weights(bone_selected);
if (bone_selected != -1 && target_polygon->get_bone_weights(bone_selected).size() == points_prev.size()) {
prev_weights = target_polygon->get_bone_weights(bone_selected);
bone_painting = true;
bone_painting_bone = bone_selected;
}
@ -792,8 +792,8 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
if (uv_drag && !uv_create) {
if (uv_edit_mode[0]->is_pressed()) {
undo_redo->create_action(TTR("Transform UV Map"));
undo_redo->add_do_method(node, "set_uv", node->get_uv());
undo_redo->add_undo_method(node, "set_uv", points_prev);
undo_redo->add_do_method(target_polygon, "set_uv", target_polygon->get_uv());
undo_redo->add_undo_method(target_polygon, "set_uv", points_prev);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -804,8 +804,8 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
case UV_MODE_ROTATE:
case UV_MODE_SCALE: {
undo_redo->create_action(TTR("Transform Polygon"));
undo_redo->add_do_method(node, "set_polygon", node->get_polygon());
undo_redo->add_undo_method(node, "set_polygon", points_prev);
undo_redo->add_do_method(target_polygon, "set_polygon", target_polygon->get_polygon());
undo_redo->add_undo_method(target_polygon, "set_polygon", points_prev);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -820,8 +820,8 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
if (bone_painting) {
undo_redo->create_action(TTR("Paint Bone Weights"));
undo_redo->add_do_method(node, "set_bone_weights", bone_painting_bone, node->get_bone_weights(bone_painting_bone));
undo_redo->add_undo_method(node, "set_bone_weights", bone_painting_bone, prev_weights);
undo_redo->add_do_method(target_polygon, "set_bone_weights", bone_painting_bone, target_polygon->get_bone_weights(bone_painting_bone));
undo_redo->add_undo_method(target_polygon, "set_bone_weights", bone_painting_bone, prev_weights);
undo_redo->add_do_method(uv_edit_draw, "queue_redraw");
undo_redo->add_undo_method(uv_edit_draw, "queue_redraw");
undo_redo->commit_action();
@ -832,7 +832,7 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
_cancel_editing();
if (bone_painting) {
node->set_bone_weights(bone_painting_bone, prev_weights);
target_polygon->set_bone_weights(bone_painting_bone, prev_weights);
}
uv_edit_draw->queue_redraw();
@ -858,9 +858,9 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
uv_new.set(point_drag_index, uv_new[point_drag_index] + drag);
if (uv_edit_mode[0]->is_pressed()) { //edit uv
node->set_uv(uv_new);
target_polygon->set_uv(uv_new);
} else if (uv_edit_mode[1]->is_pressed()) { //edit polygon
node->set_polygon(uv_new);
target_polygon->set_polygon(uv_new);
}
} break;
case UV_MODE_MOVE: {
@ -870,9 +870,9 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
if (uv_edit_mode[0]->is_pressed()) { //edit uv
node->set_uv(uv_new);
target_polygon->set_uv(uv_new);
} else if (uv_edit_mode[1]->is_pressed()) { //edit polygon
node->set_polygon(uv_new);
target_polygon->set_polygon(uv_new);
}
} break;
case UV_MODE_ROTATE: {
@ -893,9 +893,9 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
if (uv_edit_mode[0]->is_pressed()) { //edit uv
node->set_uv(uv_new);
target_polygon->set_uv(uv_new);
} else if (uv_edit_mode[1]->is_pressed()) { //edit polygon
node->set_polygon(uv_new);
target_polygon->set_polygon(uv_new);
}
} break;
case UV_MODE_SCALE: {
@ -922,9 +922,9 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
if (uv_edit_mode[0]->is_pressed()) { //edit uv
node->set_uv(uv_new);
target_polygon->set_uv(uv_new);
} else if (uv_edit_mode[1]->is_pressed()) { //edit polygon
node->set_polygon(uv_new);
target_polygon->set_polygon(uv_new);
}
} break;
case UV_MODE_PAINT_WEIGHT:
@ -936,7 +936,7 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
if (bone_painting) {
Vector<float> painted_weights = node->get_bone_weights(bone_painting_bone);
Vector<float> painted_weights = target_polygon->get_bone_weights(bone_painting_bone);
{
int pc = painted_weights.size();
@ -958,7 +958,7 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
}
}
node->set_bone_weights(bone_painting_bone, painted_weights);
target_polygon->set_bone_weights(bone_painting_bone, painted_weights);
}
uv_edit_draw->queue_redraw();
@ -975,8 +975,8 @@ void Polygon2DEditor::_uv_input(const Ref<InputEvent> &p_input) {
void Polygon2DEditor::_center_view() {
Size2 texture_size;
if (node->get_texture().is_valid()) {
texture_size = node->get_texture()->get_size();
if (target_polygon->get_texture().is_valid()) {
texture_size = target_polygon->get_texture()->get_size();
Vector2 zoom_factor = (uv_edit_draw->get_size() - Vector2(1, 1) * 50 * EDSCALE) / texture_size;
zoom_widget->set_zoom(MIN(zoom_factor.x, zoom_factor.y));
} else {
@ -1016,11 +1016,11 @@ void Polygon2DEditor::_update_zoom_and_pan(bool p_zoom_at_center) {
Point2 min_corner;
Point2 max_corner;
if (node->get_texture().is_valid()) {
max_corner += node->get_texture()->get_size();
if (target_polygon->get_texture().is_valid()) {
max_corner += target_polygon->get_texture()->get_size();
}
Vector<Vector2> points = uv_edit_mode[0]->is_pressed() ? node->get_uv() : node->get_polygon();
Vector<Vector2> points = uv_edit_mode[0]->is_pressed() ? target_polygon->get_uv() : target_polygon->get_polygon();
for (int i = 0; i < points.size(); i++) {
min_corner = min_corner.min(points[i]);
max_corner = max_corner.max(points[i]);
@ -1048,11 +1048,11 @@ void Polygon2DEditor::_update_zoom_and_pan(bool p_zoom_at_center) {
}
void Polygon2DEditor::_uv_draw() {
if (!uv_edit->is_visible() || !_get_node()) {
if (!uv_edit->is_visible() || !target_polygon) {
return;
}
Ref<Texture2D> base_tex = node->get_texture();
Ref<Texture2D> base_tex = target_polygon->get_texture();
String warning;
@ -1061,10 +1061,10 @@ void Polygon2DEditor::_uv_draw() {
mtx.scale_basis(Vector2(uv_draw_zoom, uv_draw_zoom));
// Draw texture as a background if editing uvs or no uv mapping exist.
if (uv_edit_mode[0]->is_pressed() || uv_mode == UV_MODE_CREATE || node->get_polygon().is_empty() || node->get_uv().size() != node->get_polygon().size()) {
if (uv_edit_mode[0]->is_pressed() || uv_mode == UV_MODE_CREATE || target_polygon->get_polygon().is_empty() || target_polygon->get_uv().size() != target_polygon->get_polygon().size()) {
if (base_tex.is_valid()) {
Transform2D texture_transform = Transform2D(node->get_texture_rotation(), node->get_texture_offset());
texture_transform.scale(node->get_texture_scale());
Transform2D texture_transform = Transform2D(target_polygon->get_texture_rotation(), target_polygon->get_texture_offset());
texture_transform.scale(target_polygon->get_texture_scale());
texture_transform.affine_invert();
RS::get_singleton()->canvas_item_add_set_transform(uv_edit_draw->get_canvas_item(), mtx * texture_transform);
uv_edit_draw->draw_texture(base_tex, Point2());
@ -1074,21 +1074,21 @@ void Polygon2DEditor::_uv_draw() {
} else {
preview_polygon->set_transform(mtx);
// Keep in sync with newly added Polygon2D properties (when relevant).
preview_polygon->set_texture(node->get_texture());
preview_polygon->set_texture_offset(node->get_texture_offset());
preview_polygon->set_texture_rotation(node->get_texture_rotation());
preview_polygon->set_texture_scale(node->get_texture_scale());
preview_polygon->set_texture_filter(node->get_texture_filter_in_tree());
preview_polygon->set_texture_repeat(node->get_texture_repeat_in_tree());
preview_polygon->set_polygon(node->get_polygon());
preview_polygon->set_uv(node->get_uv());
preview_polygon->set_invert(node->get_invert());
preview_polygon->set_invert_border(node->get_invert_border());
preview_polygon->set_internal_vertex_count(node->get_internal_vertex_count());
preview_polygon->set_texture(target_polygon->get_texture());
preview_polygon->set_texture_offset(target_polygon->get_texture_offset());
preview_polygon->set_texture_rotation(target_polygon->get_texture_rotation());
preview_polygon->set_texture_scale(target_polygon->get_texture_scale());
preview_polygon->set_texture_filter(target_polygon->get_texture_filter_in_tree());
preview_polygon->set_texture_repeat(target_polygon->get_texture_repeat_in_tree());
preview_polygon->set_polygon(target_polygon->get_polygon());
preview_polygon->set_uv(target_polygon->get_uv());
preview_polygon->set_invert(target_polygon->get_invert());
preview_polygon->set_invert_border(target_polygon->get_invert_border());
preview_polygon->set_internal_vertex_count(target_polygon->get_internal_vertex_count());
if (uv_mode == UV_MODE_ADD_POLYGON) {
preview_polygon->set_polygons(Array());
} else {
preview_polygon->set_polygons(node->get_polygons());
preview_polygon->set_polygons(target_polygon->get_polygons());
}
preview_polygon->show();
}
@ -1125,13 +1125,13 @@ void Polygon2DEditor::_uv_draw() {
}
}
Array polygons = node->get_polygons();
Array polygons = target_polygon->get_polygons();
Vector<Vector2> uvs;
if (uv_edit_mode[0]->is_pressed()) { //edit uv
uvs = node->get_uv();
uvs = target_polygon->get_uv();
} else { //edit polygon
uvs = node->get_polygon();
uvs = target_polygon->get_polygon();
}
const float *weight_r = nullptr;
@ -1146,8 +1146,8 @@ void Polygon2DEditor::_uv_draw() {
}
}
if (bone_selected != -1 && node->get_bone_weights(bone_selected).size() == uvs.size()) {
weight_r = node->get_bone_weights(bone_selected).ptr();
if (bone_selected != -1 && target_polygon->get_bone_weights(bone_selected).size() == uvs.size()) {
weight_r = target_polygon->get_bone_weights(bone_selected).ptr();
}
}
@ -1165,7 +1165,7 @@ void Polygon2DEditor::_uv_draw() {
int uv_draw_max = uvs.size();
uv_draw_max -= node->get_internal_vertex_count();
uv_draw_max -= target_polygon->get_internal_vertex_count();
if (uv_draw_max < 0) {
uv_draw_max = 0;
}
@ -1237,16 +1237,16 @@ void Polygon2DEditor::_uv_draw() {
for (int i = 0; i < bone_scroll_vb->get_child_count(); i++) {
CheckBox *c = Object::cast_to<CheckBox>(bone_scroll_vb->get_child(i));
if (c && c->is_pressed()) {
bone_path = node->get_bone_path(i);
bone_path = target_polygon->get_bone_path(i);
break;
}
}
//draw skeleton
NodePath skeleton_path = node->get_skeleton();
Skeleton2D *skeleton = Object::cast_to<Skeleton2D>(node->get_node_or_null(skeleton_path));
NodePath skeleton_path = target_polygon->get_skeleton();
Skeleton2D *skeleton = Object::cast_to<Skeleton2D>(target_polygon->get_node_or_null(skeleton_path));
if (skeleton) {
Transform2D skeleton_xform = node->get_global_transform().affine_inverse().translated(-node->get_offset()) * skeleton->get_global_transform();
Transform2D skeleton_xform = target_polygon->get_global_transform().affine_inverse().translated(-target_polygon->get_offset()) * skeleton->get_global_transform();
for (int i = 0; i < skeleton->get_bone_count(); i++) {
Bone2D *bone = skeleton->get_bone(i);
if (bone->get_rest() == Transform2D(0, 0, 0, 0, 0, 0)) {

View file

@ -76,7 +76,7 @@ class Polygon2DEditor : public AbstractPolygon2DEditor {
Button *uv_edit_mode[4];
Ref<ButtonGroup> uv_edit_group;
Polygon2D *node = nullptr;
Polygon2D *target_polygon = nullptr;
UVMode uv_mode;
AcceptDialog *uv_edit = nullptr;
@ -163,8 +163,8 @@ class Polygon2DEditor : public AbstractPolygon2DEditor {
int _get_polygon_count() const override;
protected:
virtual Node2D *_get_node() const override;
virtual void _set_node(Node *p_polygon) override;
virtual Node2D *_get_target_node() const override;
virtual void _set_target_node(Node2D *p_node) override;
virtual Vector2 _get_offset(int p_idx) const override;