diff options
Diffstat (limited to 'scene')
-rw-r--r-- | scene/main/canvas_item.cpp | 11 | ||||
-rw-r--r-- | scene/main/canvas_item.h | 1 | ||||
-rw-r--r-- | scene/main/viewport.cpp | 31 | ||||
-rw-r--r-- | scene/main/viewport.h | 3 |
4 files changed, 46 insertions, 0 deletions
diff --git a/scene/main/canvas_item.cpp b/scene/main/canvas_item.cpp index cde3503bdf..0d9a02968e 100644 --- a/scene/main/canvas_item.cpp +++ b/scene/main/canvas_item.cpp @@ -491,6 +491,17 @@ int CanvasItem::get_z_index() const { return z_index; } +int CanvasItem::get_effective_z_index() const { + int effective_z_index = z_index; + if (is_z_relative()) { + CanvasItem *p = get_parent_item(); + if (p) { + effective_z_index += p->get_effective_z_index(); + } + } + return effective_z_index; +} + void CanvasItem::set_y_sort_enabled(bool p_enabled) { y_sort_enabled = p_enabled; RS::get_singleton()->canvas_item_set_sort_children_by_y(canvas_item, y_sort_enabled); diff --git a/scene/main/canvas_item.h b/scene/main/canvas_item.h index 1ddfaa288c..4e2c78af61 100644 --- a/scene/main/canvas_item.h +++ b/scene/main/canvas_item.h @@ -246,6 +246,7 @@ public: void set_z_index(int p_z); int get_z_index() const; + int get_effective_z_index() const; void set_z_as_relative(bool p_enabled); bool is_z_relative() const; diff --git a/scene/main/viewport.cpp b/scene/main/viewport.cpp index b6bcbe04a3..5a231e8278 100644 --- a/scene/main/viewport.cpp +++ b/scene/main/viewport.cpp @@ -36,6 +36,7 @@ #include "core/object/message_queue.h" #include "core/string/translation.h" #include "core/templates/pair.h" +#include "core/templates/sort_array.h" #include "scene/2d/audio_listener_2d.h" #include "scene/2d/camera_2d.h" #include "scene/2d/collision_object_2d.h" @@ -664,6 +665,25 @@ void Viewport::_process_picking() { point_params.pick_point = true; int rc = ss2d->intersect_point(point_params, res, 64); + if (physics_object_picking_sort) { + struct ComparatorCollisionObjects { + bool operator()(const PhysicsDirectSpaceState2D::ShapeResult &p_a, const PhysicsDirectSpaceState2D::ShapeResult &p_b) const { + CollisionObject2D *a = Object::cast_to<CollisionObject2D>(p_a.collider); + CollisionObject2D *b = Object::cast_to<CollisionObject2D>(p_b.collider); + if (!a || !b) { + return false; + } + int za = a->get_effective_z_index(); + int zb = b->get_effective_z_index(); + if (za != zb) { + return zb < za; + } + return a->is_greater_than(b); + } + }; + SortArray<PhysicsDirectSpaceState2D::ShapeResult, ComparatorCollisionObjects> sorter; + sorter.sort(res, rc); + } for (int i = 0; i < rc; i++) { if (res[i].collider_id.is_valid() && res[i].collider) { CollisionObject2D *co = Object::cast_to<CollisionObject2D>(res[i].collider); @@ -2858,6 +2878,14 @@ bool Viewport::get_physics_object_picking() { return physics_object_picking; } +void Viewport::set_physics_object_picking_sort(bool p_enable) { + physics_object_picking_sort = p_enable; +} + +bool Viewport::get_physics_object_picking_sort() { + return physics_object_picking_sort; +} + Vector2 Viewport::get_camera_coords(const Vector2 &p_viewport_coords) const { Transform2D xf = stretch_transform * global_canvas_transform; return xf.xform(p_viewport_coords); @@ -3792,6 +3820,8 @@ void Viewport::_bind_methods() { ClassDB::bind_method(D_METHOD("set_physics_object_picking", "enable"), &Viewport::set_physics_object_picking); ClassDB::bind_method(D_METHOD("get_physics_object_picking"), &Viewport::get_physics_object_picking); + ClassDB::bind_method(D_METHOD("set_physics_object_picking_sort", "enable"), &Viewport::set_physics_object_picking_sort); + ClassDB::bind_method(D_METHOD("get_physics_object_picking_sort"), &Viewport::get_physics_object_picking_sort); ClassDB::bind_method(D_METHOD("get_viewport_rid"), &Viewport::get_viewport_rid); ClassDB::bind_method(D_METHOD("push_text_input", "text"), &Viewport::push_text_input); @@ -3943,6 +3973,7 @@ void Viewport::_bind_methods() { #endif ADD_GROUP("Physics", "physics_"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "physics_object_picking"), "set_physics_object_picking", "get_physics_object_picking"); + ADD_PROPERTY(PropertyInfo(Variant::BOOL, "physics_object_picking_sort"), "set_physics_object_picking_sort", "get_physics_object_picking_sort"); ADD_GROUP("GUI", "gui_"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "gui_disable_input"), "set_disable_input", "is_input_disabled"); ADD_PROPERTY(PropertyInfo(Variant::BOOL, "gui_snap_controls_to_pixels"), "set_snap_controls_to_pixels", "is_snap_controls_to_pixels_enabled"); diff --git a/scene/main/viewport.h b/scene/main/viewport.h index e081013fde..dc8d95b713 100644 --- a/scene/main/viewport.h +++ b/scene/main/viewport.h @@ -246,6 +246,7 @@ private: bool snap_2d_vertices_to_pixel = false; bool physics_object_picking = false; + bool physics_object_picking_sort = false; List<Ref<InputEvent>> physics_picking_events; ObjectID physics_object_capture; ObjectID physics_object_over; @@ -577,6 +578,8 @@ public: void set_physics_object_picking(bool p_enable); bool get_physics_object_picking(); + void set_physics_object_picking_sort(bool p_enable); + bool get_physics_object_picking_sort(); Variant gui_get_drag_data() const; |