From ee8ea0df044789a810b5e58d05a5200032348b35 Mon Sep 17 00:00:00 2001 From: Noisyfox Date: Fri, 10 Nov 2023 23:02:11 +0800 Subject: [PATCH] Rewrite bed raycaster registering that fixes crash when creating new project --- src/slic3r/GUI/GLCanvas3D.cpp | 6 ++++++ src/slic3r/GUI/PartPlate.cpp | 39 ++++++++++------------------------- src/slic3r/GUI/PartPlate.hpp | 10 +++++---- 3 files changed, 23 insertions(+), 32 deletions(-) diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index 9d3ffa027..a6e981513 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -2672,6 +2672,7 @@ void GLCanvas3D::reload_scene(bool refresh_immediately, bool force_full_scene_re m_selection.volumes_changed(map_glvolume_old_to_new); // @Enrico suggest this solution to preven accessing pointer on caster without data + m_scene_raycaster.remove_raycasters(SceneRaycaster::EType::Bed); m_scene_raycaster.remove_raycasters(SceneRaycaster::EType::Volume); m_gizmos.update_data(); m_gizmos.update_assemble_view_data(); @@ -2725,6 +2726,11 @@ void GLCanvas3D::reload_scene(bool refresh_immediately, bool force_full_scene_re #endif } + // refresh bed raycasters for picking + if (m_canvas_type == ECanvasType::CanvasView3D) { + wxGetApp().plater()->get_partplate_list().register_raycasters_for_picking(*this); + } + // refresh volume raycasters for picking for (size_t i = 0; i < m_volumes.volumes.size(); ++i) { const GLVolume* v = m_volumes.volumes[i]; diff --git a/src/slic3r/GUI/PartPlate.cpp b/src/slic3r/GUI/PartPlate.cpp index 5d8ba2e08..edbb541a7 100644 --- a/src/slic3r/GUI/PartPlate.cpp +++ b/src/slic3r/GUI/PartPlate.cpp @@ -148,7 +148,6 @@ PartPlate::PartPlate(PartPlateList *partplate_list, Vec3d origin, int width, int PartPlate::~PartPlate() { - unregister_raycasters_for_picking(); clear(); //if (m_quadric != nullptr) // ::gluDeleteQuadric(m_quadric); @@ -996,13 +995,6 @@ void PartPlate::render_only_numbers(bool bottom) } } -void PartPlate::register_rectangle_for_picking(PickingModel &model, int id) -{ - wxGetApp().plater()->canvas3D()->add_raycaster_for_picking(SceneRaycaster::EType::Bed, id, *model.mesh_raycaster, Transform3d::Identity()); - - picking_ids.emplace_back(id); -} - /* void PartPlate::render_label(GLCanvas3D& canvas) const { std::string label = (boost::format("Plate %1%") % (m_plate_index + 1)).str(); @@ -1221,25 +1213,20 @@ void PartPlate::render_right_arrow(const ColorRGBA render_color, bool use_lighti } */ -void PartPlate::register_raycasters_for_picking() +static void register_model_for_picking(GLCanvas3D &canvas, PickingModel &model, int id) { - unregister_raycasters_for_picking(); - - picking_ids.reserve(6); - register_rectangle_for_picking(m_triangles, picking_id_component(0)); - register_rectangle_for_picking(m_del_icon, picking_id_component(1)); - register_rectangle_for_picking(m_orient_icon, picking_id_component(2)); - register_rectangle_for_picking(m_arrange_icon, picking_id_component(3)); - register_rectangle_for_picking(m_lock_icon, picking_id_component(4)); - if (m_partplate_list->render_plate_settings) - register_rectangle_for_picking(m_plate_settings_icon, picking_id_component(5)); + canvas.add_raycaster_for_picking(SceneRaycaster::EType::Bed, id, *model.mesh_raycaster, Transform3d::Identity()); } -void PartPlate::unregister_raycasters_for_picking() { - for (int picking_id : picking_ids) { - wxGetApp().plater()->canvas3D()->remove_raycasters_for_picking(SceneRaycaster::EType::Bed, picking_id); - } - picking_ids.clear(); +void PartPlate::register_raycasters_for_picking(GLCanvas3D &canvas) +{ + register_model_for_picking(canvas, m_triangles, picking_id_component(0)); + register_model_for_picking(canvas, m_del_icon, picking_id_component(1)); + register_model_for_picking(canvas, m_orient_icon, picking_id_component(2)); + register_model_for_picking(canvas, m_arrange_icon, picking_id_component(3)); + register_model_for_picking(canvas, m_lock_icon, picking_id_component(4)); + if (m_partplate_list->render_plate_settings) + register_model_for_picking(canvas, m_plate_settings_icon, picking_id_component(5)); } int PartPlate::picking_id_component(int idx) const @@ -2448,8 +2435,6 @@ bool PartPlate::set_shape(const Pointfs& shape, const Pointfs& exclude_areas, Ve calc_vertex_for_number(0, false, m_plate_idx_icon); // calc vertex for plate name generate_plate_name_texture(); - - register_raycasters_for_picking(); } calc_height_limit(); @@ -3361,8 +3346,6 @@ int PartPlateList::delete_plate(int index) return -1; } - plate->unregister_raycasters_for_picking(); - if (m_plater) { // In GUI mode // BBS: add wipe tower logic diff --git a/src/slic3r/GUI/PartPlate.hpp b/src/slic3r/GUI/PartPlate.hpp index 7b5eee70e..ced713a1f 100644 --- a/src/slic3r/GUI/PartPlate.hpp +++ b/src/slic3r/GUI/PartPlate.hpp @@ -131,7 +131,6 @@ private: PickingModel m_plate_settings_icon; GLModel m_plate_idx_icon; GLTexture m_texture; - std::vector picking_ids; float m_scale_factor{ 1.0f }; GLUquadricObject* m_quadric; @@ -181,9 +180,7 @@ private: void render_icons(bool bottom, bool only_name = false, int hover_id = -1); void render_only_numbers(bool bottom); void render_plate_name_texture(); - void register_rectangle_for_picking(PickingModel &model, int id); - void register_raycasters_for_picking(); - void unregister_raycasters_for_picking(); + void register_raycasters_for_picking(GLCanvas3D& canvas); int picking_id_component(int idx) const; public: @@ -744,6 +741,11 @@ public: void render(const Transform3d& view_matrix, const Transform3d& projection_matrix, bool bottom, bool only_current = false, bool only_body = false, int hover_id = -1, bool render_cali = false); void set_render_option(bool bedtype_texture, bool plate_settings); void set_render_cali(bool value = true) { render_cali_logo = value; } + void register_raycasters_for_picking(GLCanvas3D& canvas) + { + for (auto plate : m_plate_list) + plate->register_raycasters_for_picking(canvas); + } BoundingBoxf3& get_bounding_box() { return m_bounding_box; } //int select_plate_by_hover_id(int hover_id); int select_plate_by_obj(int obj_index, int instance_index);