diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index 2f7d1a5c57..0e5ee1991f 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -805,6 +805,7 @@ GLCanvas3D::Selection::VolumeCache::TransformCache::TransformCache() , rotation_matrix(Transform3d::Identity()) , scale_matrix(Transform3d::Identity()) , mirror_matrix(Transform3d::Identity()) + , full_matrix(Transform3d::Identity()) { } @@ -813,6 +814,7 @@ GLCanvas3D::Selection::VolumeCache::TransformCache::TransformCache(const Geometr , rotation(transform.get_rotation()) , scaling_factor(transform.get_scaling_factor()) , mirror(transform.get_mirror()) + , full_matrix(transform.get_matrix()) { rotation_matrix = Geometry::assemble_transform(Vec3d::Zero(), rotation); scale_matrix = Geometry::assemble_transform(Vec3d::Zero(), Vec3d::Zero(), scaling_factor); @@ -1331,8 +1333,9 @@ void GLCanvas3D::Selection::rotate(const Vec3d& rotation, GLCanvas3D::Transforma Vec3d new_rotation = Geometry::extract_euler_angles(m * m_cache.volumes_data[i].get_volume_rotation_matrix()); if (transformation_type.joint()) { - Vec3d offset = m * (m_cache.volumes_data[i].get_volume_position() + m_cache.volumes_data[i].get_instance_position() - m_cache.dragging_center); - volume.set_volume_offset(m_cache.dragging_center - m_cache.volumes_data[i].get_instance_position() + offset); + Vec3d local_pivot = m_cache.volumes_data[i].get_instance_full_matrix().inverse() * m_cache.dragging_center; + Vec3d offset = m * (m_cache.volumes_data[i].get_volume_position() - local_pivot); + volume.set_volume_offset(local_pivot + offset); } volume.set_volume_rotation(new_rotation); } diff --git a/src/slic3r/GUI/GLCanvas3D.hpp b/src/slic3r/GUI/GLCanvas3D.hpp index 51a1e9213e..ae61558766 100644 --- a/src/slic3r/GUI/GLCanvas3D.hpp +++ b/src/slic3r/GUI/GLCanvas3D.hpp @@ -468,6 +468,7 @@ public: Transform3d rotation_matrix; Transform3d scale_matrix; Transform3d mirror_matrix; + Transform3d full_matrix; TransformCache(); explicit TransformCache(const Geometry::Transformation& transform); @@ -487,6 +488,7 @@ public: const Transform3d& get_volume_rotation_matrix() const { return m_volume.rotation_matrix; } const Transform3d& get_volume_scale_matrix() const { return m_volume.scale_matrix; } const Transform3d& get_volume_mirror_matrix() const { return m_volume.mirror_matrix; } + const Transform3d& get_volume_full_matrix() const { return m_volume.full_matrix; } const Vec3d& get_instance_position() const { return m_instance.position; } const Vec3d& get_instance_rotation() const { return m_instance.rotation; } @@ -495,6 +497,7 @@ public: const Transform3d& get_instance_rotation_matrix() const { return m_instance.rotation_matrix; } const Transform3d& get_instance_scale_matrix() const { return m_instance.scale_matrix; } const Transform3d& get_instance_mirror_matrix() const { return m_instance.mirror_matrix; } + const Transform3d& get_instance_full_matrix() const { return m_instance.full_matrix; } }; typedef std::map VolumesCache; diff --git a/src/slic3r/GUI/GLGizmo.cpp b/src/slic3r/GUI/GLGizmo.cpp index 720da1c0f2..22023825f3 100644 --- a/src/slic3r/GUI/GLGizmo.cpp +++ b/src/slic3r/GUI/GLGizmo.cpp @@ -646,7 +646,7 @@ void GLGizmoRotate::transform_to_local(const GLCanvas3D::Selection& selection) c { ::glTranslated(m_center(0), m_center(1), m_center(2)); - if (selection.is_single_volume() || selection.is_single_modifier()) + if (selection.is_single_volume() || selection.is_single_modifier() || selection.requires_local_axes()) { Transform3d orient_matrix = selection.get_volume(*selection.get_volume_idxs().begin())->get_instance_transformation().get_matrix(true, false, true, true); ::glMultMatrixd(orient_matrix.data()); @@ -703,7 +703,7 @@ Vec3d GLGizmoRotate::mouse_position_in_local_plane(const Linef3& mouse_ray, cons } } - if (selection.is_single_volume() || selection.is_single_modifier()) + if (selection.is_single_volume() || selection.is_single_modifier() || selection.requires_local_axes()) m = m * selection.get_volume(*selection.get_volume_idxs().begin())->get_instance_transformation().get_matrix(true, false, true, true).inverse(); m.translate(-m_center);