From 425ef3a6ddac5054e8f38b19e4a57b96748c8430 Mon Sep 17 00:00:00 2001 From: Noisyfox Date: Thu, 23 Nov 2023 21:42:11 +0800 Subject: [PATCH] Fix "from surface" --- src/slic3r/GUI/GLCanvas3D.cpp | 8 ++- src/slic3r/GUI/Gizmos/GLGizmoMove.cpp | 10 ++- src/slic3r/GUI/Gizmos/GLGizmoScale.cpp | 2 +- .../GUI/Gizmos/GizmoObjectManipulation.cpp | 32 ++++++--- src/slic3r/GUI/Selection.cpp | 71 +++++++------------ src/slic3r/GUI/Selection.hpp | 2 +- 6 files changed, 67 insertions(+), 58 deletions(-) diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index 83bc967d588..3807fa140bb 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -3366,7 +3366,9 @@ void GLCanvas3D::on_key(wxKeyEvent& evt) else displacement = multiplier * direction; - m_selection.translate(displacement); + TransformationType trafo_type; + trafo_type.set_relative(); + m_selection.translate(displacement, trafo_type); m_dirty = true; } );} @@ -4141,7 +4143,9 @@ void GLCanvas3D::on_mouse(wxMouseEvent& evt) } } - m_selection.translate(cur_pos - m_mouse.drag.start_position_3D); + TransformationType trafo_type; + trafo_type.set_relative(); + m_selection.translate(cur_pos - m_mouse.drag.start_position_3D, trafo_type); if (current_printer_technology() == ptFFF && (fff_print()->config().print_sequence == PrintSequence::ByObject)) update_sequential_clearance(); // BBS diff --git a/src/slic3r/GUI/Gizmos/GLGizmoMove.cpp b/src/slic3r/GUI/Gizmos/GLGizmoMove.cpp index 91913914a86..1049e61f5ed 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoMove.cpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoMove.cpp @@ -107,7 +107,15 @@ void GLGizmoMove3D::on_dragging(const UpdateData& data) m_displacement.z() = calc_projection(data); Selection &selection = m_parent.get_selection(); - selection.translate(m_displacement); + TransformationType trafo_type; + trafo_type.set_relative(); + switch (wxGetApp().obj_manipul()->get_coordinates_type()) + { + case ECoordinatesType::Instance: { trafo_type.set_instance(); break; } + case ECoordinatesType::Local: { trafo_type.set_local(); break; } + default: { break; } + } + selection.translate(m_displacement, trafo_type); } void GLGizmoMove3D::on_render() diff --git a/src/slic3r/GUI/Gizmos/GLGizmoScale.cpp b/src/slic3r/GUI/Gizmos/GLGizmoScale.cpp index 93fbf7d9b33..f2dc6ea328c 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoScale.cpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoScale.cpp @@ -91,7 +91,7 @@ bool GLGizmoScale3D::on_mouse(const wxMouseEvent &mouse_event) Selection& selection = m_parent.get_selection(); selection.scale(m_scale, transformation_type); - if (mouse_event.CmdDown()) selection.translate(m_offset, true); + if (mouse_event.CmdDown()) selection.translate(m_offset, transformation_type); } } return use_grabbers(mouse_event); diff --git a/src/slic3r/GUI/Gizmos/GizmoObjectManipulation.cpp b/src/slic3r/GUI/Gizmos/GizmoObjectManipulation.cpp index 8f5b22a2825..387a6bb5c07 100644 --- a/src/slic3r/GUI/Gizmos/GizmoObjectManipulation.cpp +++ b/src/slic3r/GUI/Gizmos/GizmoObjectManipulation.cpp @@ -1,3 +1,7 @@ +///|/ Copyright (c) Prusa Research 2018 - 2023 Enrico Turri @enricoturri1966, Oleksandra Iushchenko @YuSanka, Lukáš Matěna @lukasmatena, Pavel Mikuš @Godrak, Filip Sykala @Jony01, Vojtěch Bubník @bubnikv, Vojtěch Král @vojtechkral +///|/ +///|/ PrusaSlicer is released under the terms of the AGPLv3 or higher +///|/ #include "slic3r/GUI/ImGuiWrapper.hpp" #include @@ -260,7 +264,15 @@ void GizmoObjectManipulation::change_position_value(int axis, double value) Selection& selection = m_glcanvas.get_selection(); selection.setup_cache(); - selection.translate(position - m_cache.position, selection.requires_local_axes()); + TransformationType trafo_type; + trafo_type.set_relative(); + switch (m_coordinates_type) + { + case ECoordinatesType::Instance: { trafo_type.set_instance(); break; } + case ECoordinatesType::Local: { trafo_type.set_local(); break; } + default: { break; } + } + selection.translate(position - m_cache.position, trafo_type); m_glcanvas.do_move(L("Set Position")); m_cache.position = position; @@ -278,14 +290,16 @@ void GizmoObjectManipulation::change_rotation_value(int axis, double value) Selection& selection = m_glcanvas.get_selection(); - TransformationType transformation_type(TransformationType::World_Relative_Joint); - if (selection.is_single_full_instance() || selection.requires_local_axes()) - transformation_type.set_independent(); - if (selection.is_single_full_instance() && !is_world_coordinates()) { - //FIXME Selection::rotate() does not process absoulte rotations correctly: It does not recognize the axis index, which was changed. - // transformation_type.set_absolute(); - transformation_type.set_local(); - } + TransformationType transformation_type; + transformation_type.set_relative(); + if (selection.is_single_full_instance()) + transformation_type.set_independent(); + + if (is_local_coordinates()) + transformation_type.set_local(); + + if (is_instance_coordinates()) + transformation_type.set_instance(); selection.setup_cache(); selection.rotate( diff --git a/src/slic3r/GUI/Selection.cpp b/src/slic3r/GUI/Selection.cpp index 0eaa48bf9d3..c82daeb30a9 100644 --- a/src/slic3r/GUI/Selection.cpp +++ b/src/slic3r/GUI/Selection.cpp @@ -1101,66 +1101,47 @@ void Selection::move_to_center(const Vec3d& displacement, bool local) this->set_bounding_boxes_dirty(); } -void Selection::translate(const Vec3d& displacement, bool local) +void Selection::translate(const Vec3d& displacement, TransformationType transformation_type) { if (!m_valid) return; - EMode translation_type = m_mode; - //BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(": %1%, displacement {%2%, %3%, %4%}") % __LINE__ % displacement(X) % displacement(Y) % displacement(Z); + // Emboss use translate in local coordinate + assert(transformation_type.relative() || + transformation_type.local()); for (unsigned int i : m_list) { GLVolume& v = *(*m_volumes)[i]; - if (v.is_wipe_tower) { - int plate_idx = v.object_idx() - 1000; - BoundingBoxf3 plate_bbox = wxGetApp().plater()->get_partplate_list().get_plate(plate_idx)->get_bounding_box(); - Vec3d tower_size = v.bounding_box().size(); - Vec3d tower_origin = m_cache.volumes_data[i].get_volume_position(); - Vec3d actual_displacement = displacement; - const double margin = 15.f; - - if (!local) - actual_displacement = (m_cache.volumes_data[i].get_instance_rotation_matrix() * m_cache.volumes_data[i].get_instance_scale_matrix() * m_cache.volumes_data[i].get_instance_mirror_matrix()).inverse() * displacement; - - if (tower_origin(0) + actual_displacement(0) - margin < plate_bbox.min(0)) { - actual_displacement(0) = plate_bbox.min(0) - tower_origin(0) + margin; - } - else if (tower_origin(0) + actual_displacement(0) + tower_size(0) + margin > plate_bbox.max(0)) { - actual_displacement(0) = plate_bbox.max(0) - tower_origin(0) - tower_size(0) - margin; - } - - if (tower_origin(1) + actual_displacement(1) - margin < plate_bbox.min(1)) { - actual_displacement(1) = plate_bbox.min(1) - tower_origin(1) + margin; - } - else if (tower_origin(1) + actual_displacement(1) + tower_size(1) + margin > plate_bbox.max(1)) { - actual_displacement(1) = plate_bbox.max(1) - tower_origin(1) - tower_size(1) - margin; + const VolumeCache& volume_data = m_cache.volumes_data[i]; + if (m_mode == Instance && !is_wipe_tower()) { + assert(is_from_fully_selected_instance(i)); + if (transformation_type.instance()) { + const Geometry::Transformation& inst_trafo = volume_data.get_instance_transform(); + v.set_instance_offset(inst_trafo.get_offset() + inst_trafo.get_rotation_matrix() * displacement); } - - v.set_volume_offset(m_cache.volumes_data[i].get_volume_position() + actual_displacement); + else + transform_instance_relative(v, volume_data, transformation_type, Geometry::translation_transform(displacement), m_cache.dragging_center); } - else if (m_mode == Volume || v.is_wipe_tower) { - if (local) - v.set_volume_offset(m_cache.volumes_data[i].get_volume_position() + displacement); - else { - const Vec3d local_displacement = (m_cache.volumes_data[i].get_instance_rotation_matrix() * m_cache.volumes_data[i].get_instance_scale_matrix() * m_cache.volumes_data[i].get_instance_mirror_matrix()).inverse() * displacement; - v.set_volume_offset(m_cache.volumes_data[i].get_volume_position() + local_displacement); + else { + if (transformation_type.local() && transformation_type.absolute()) { + const Geometry::Transformation& vol_trafo = volume_data.get_volume_transform(); + const Geometry::Transformation& inst_trafo = volume_data.get_instance_transform(); + v.set_volume_offset(vol_trafo.get_offset() + inst_trafo.get_scaling_factor_matrix().inverse() * vol_trafo.get_rotation_matrix() * displacement); } - } - else if (m_mode == Instance) { - if (is_from_fully_selected_instance(i)) - v.set_instance_offset(m_cache.volumes_data[i].get_instance_position() + displacement); else { - const Vec3d local_displacement = (m_cache.volumes_data[i].get_instance_rotation_matrix() * m_cache.volumes_data[i].get_instance_scale_matrix() * m_cache.volumes_data[i].get_instance_mirror_matrix()).inverse() * displacement; - v.set_volume_offset(m_cache.volumes_data[i].get_volume_position() + local_displacement); - translation_type = Volume; + Vec3d relative_disp = displacement; + if (transformation_type.world() && transformation_type.instance()) + relative_disp = volume_data.get_instance_transform().get_scaling_factor_matrix().inverse() * relative_disp; + + transform_volume_relative(v, volume_data, transformation_type, Geometry::translation_transform(relative_disp), m_cache.dragging_center); } } } #if !DISABLE_INSTANCES_SYNCH - if (translation_type == Instance) + if (m_mode == Instance) synchronize_unselected_instances(SyncRotationType::NONE); - else if (translation_type == Volume) + else if (m_mode == Volume) synchronize_unselected_volumes(); #endif // !DISABLE_INSTANCES_SYNCH @@ -1409,7 +1390,9 @@ void Selection::scale_to_fit_print_volume(const BuildVolume& volume) // center selection on print bed setup_cache(); offset.z() = -get_bounding_box().min.z(); - translate(offset); + TransformationType trafo_type; + trafo_type.set_relative(); + translate(offset, trafo_type); wxGetApp().plater()->canvas3D()->do_move(""); // avoid storing another snapshot // BBS diff --git a/src/slic3r/GUI/Selection.hpp b/src/slic3r/GUI/Selection.hpp index a5e635235ba..005c5cfdc72 100644 --- a/src/slic3r/GUI/Selection.hpp +++ b/src/slic3r/GUI/Selection.hpp @@ -341,7 +341,7 @@ class Selection void setup_cache(); - void translate(const Vec3d& displacement, bool local = false); + void translate(const Vec3d& displacement, TransformationType transformation_type); void move_to_center(const Vec3d& displacement, bool local = false); void rotate(const Vec3d& rotation, TransformationType transformation_type); void flattening_rotate(const Vec3d& normal);