From ae5fe9ce8cfd57f53362bd133a77629249faa87d Mon Sep 17 00:00:00 2001 From: Lukas Matena Date: Tue, 28 Mar 2023 13:06:11 +0200 Subject: [PATCH] Cut: separate Model for the pre-cut object --- src/slic3r/GUI/Gizmos/GLGizmoCut.cpp | 35 +++++++++++++++------------- src/slic3r/GUI/Gizmos/GLGizmoCut.hpp | 6 +++-- 2 files changed, 23 insertions(+), 18 deletions(-) diff --git a/src/slic3r/GUI/Gizmos/GLGizmoCut.cpp b/src/slic3r/GUI/Gizmos/GLGizmoCut.cpp index 4aaa7ea8b0..38bccfb4a7 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoCut.cpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoCut.cpp @@ -1406,7 +1406,7 @@ void GLGizmoCut3D::PartSelection::render(const Vec3d* normal) // FIXME: Cache the transforms. - const Vec3d inst_offset = model_object->instances[instance_idx]->get_offset(); + const Vec3d inst_offset = model_object()->instances[instance_idx]->get_offset(); const Transform3d view_inst_matrix= camera.get_view_matrix() * translation_transform(inst_offset); const bool is_looking_forward = normal && camera.get_dir_forward().dot(*normal) < 0.05; @@ -1415,7 +1415,7 @@ void GLGizmoCut3D::PartSelection::render(const Vec3d* normal) if (normal && (( is_looking_forward && parts[id].selected) || (!is_looking_forward && !parts[id].selected) ) ) continue; - const Vec3d volume_offset = model_object->volumes[id]->get_offset(); + const Vec3d volume_offset = model_object()->volumes[id]->get_offset(); shader->set_uniform("view_model_matrix", view_inst_matrix * translation_transform(volume_offset)); parts[id].glmodel.set_color(parts[id].selected ? UPPER_PART_COLOR : LOWER_PART_COLOR); parts[id].glmodel.render(); @@ -1437,8 +1437,8 @@ void GLGizmoCut3D::PartSelection::toggle_selection(const Vec2d& mouse_pos) std::vector> hits_id_and_sqdist; for (size_t id=0; idvolumes[id]->get_offset(); - Transform3d tr = model_object->instances[instance_idx]->get_matrix() * model_object->volumes[id]->get_matrix(); + const Vec3d volume_offset = model_object()->volumes[id]->get_offset(); + Transform3d tr = model_object()->instances[instance_idx]->get_matrix() * model_object()->volumes[id]->get_matrix(); if (parts[id].raycaster.unproject_on_mesh(mouse_pos, tr, camera, pos, normal)) { hits_id_and_sqdist.emplace_back(id, (camera_pos - tr*(pos.cast())).squaredNorm()); } @@ -1730,12 +1730,21 @@ void GLGizmoCut3D::flip_cut_plane() } -GLGizmoCut3D::PartSelection::PartSelection(ModelObject* mo, int instance_idx_in, const Vec3d& center, const Vec3d& normal) +GLGizmoCut3D::PartSelection::PartSelection(const ModelObject* mo, const Transform3d& cut_matrix, int instance_idx_in, const Vec3d& center, const Vec3d& normal) { - model_object = mo; // FIXME: Ownership. + model = Model(); + model.add_object(*mo); + ModelObjectPtrs cut_part_ptrs = model.objects.front()->cut(instance_idx_in, cut_matrix, + ModelObjectCutAttribute::KeepUpper | + ModelObjectCutAttribute::KeepLower | + ModelObjectCutAttribute::KeepAsParts); + assert(cut_part_ptrs.size() == 1); + model = Model(); + model.add_object(*cut_part_ptrs.front()); + instance_idx = instance_idx_in; - const ModelVolumePtrs& volumes = mo->volumes; + const ModelVolumePtrs& volumes = model_object()->volumes; // split to parts for (int id = int(volumes.size())-1; id >= 0; id--) @@ -1750,7 +1759,7 @@ GLGizmoCut3D::PartSelection::PartSelection(ModelObject* mo, int instance_idx_in, parts.back().glmodel.init_from(volume->mesh()); // Now check whether this part is below or above the plane. - Transform3d tr = (model_object->instances[instance_idx]->get_matrix() * volume->get_matrix()).inverse(); + Transform3d tr = (model_object()->instances[instance_idx]->get_matrix() * volume->get_matrix()).inverse(); Vec3f pos = (tr * center).cast(); Vec3f norm = (tr.linear().inverse().transpose() * normal).cast(); for (const Vec3f& v : volume->mesh().its.vertices) { @@ -1786,13 +1795,7 @@ void GLGizmoCut3D::process_contours() const int instance_idx = selection.get_instance_idx(); const int object_idx = selection.get_object_idx(); - ModelObjectPtrs cut_part_ptrs = model_objects[object_idx]->cut(instance_idx, get_cut_matrix(selection), - ModelObjectCutAttribute::KeepUpper | - ModelObjectCutAttribute::KeepLower | - ModelObjectCutAttribute::KeepAsParts); - assert(cut_part_ptrs.size() == 1); - - m_part_selection = PartSelection(cut_part_ptrs.front(), instance_idx, m_plane_center, m_cut_normal); + m_part_selection = PartSelection(model_objects[object_idx], get_cut_matrix(selection), instance_idx, m_plane_center, m_cut_normal); m_parent.toggle_model_objects_visibility(false); } @@ -2348,7 +2351,7 @@ void GLGizmoCut3D::perform_cut(const Selection& selection) Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Cut by Plane")); const bool cut_by_contour = m_part_selection.valid; - ModelObject* cut_mo = cut_by_contour ? m_part_selection.model_object : nullptr; + ModelObject* cut_mo = cut_by_contour ? m_part_selection.model_object() : nullptr; if (cut_mo) cut_mo->cut_connectors = mo->cut_connectors; diff --git a/src/slic3r/GUI/Gizmos/GLGizmoCut.hpp b/src/slic3r/GUI/Gizmos/GLGizmoCut.hpp index 793d363582..37f4610380 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoCut.hpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoCut.hpp @@ -139,18 +139,20 @@ class GLGizmoCut3D : public GLGizmoBase struct PartSelection { PartSelection() = default; - PartSelection(ModelObject* mo, int instance_idx, const Vec3d& center, const Vec3d& normal); + PartSelection(const ModelObject* mo, const Transform3d& cut_matrix, int instance_idx, const Vec3d& center, const Vec3d& normal); void render(const Vec3d* normal = nullptr); void toggle_selection(const Vec2d& mouse_pos); void turn_over_selection(); + ModelObject* model_object() { return model.objects.front(); } struct Part { GLModel glmodel; MeshRaycaster raycaster; bool selected; }; - ModelObject* model_object; // FIXME: Ownership ! + + Model model; int instance_idx; std::vector parts; bool valid = false;