Tech ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES - Volumes rotation in all reference systems using Rotate gizmo and part manipulator fields

Fixed conflicts during rebase with master
This commit is contained in:
enricoturri1966 2021-11-04 12:46:22 +01:00
parent 5767feecab
commit 65adbd5b0d
4 changed files with 54 additions and 15 deletions

View File

@ -18,19 +18,25 @@ public:
enum Enum { enum Enum {
// Transforming in a world coordinate system // Transforming in a world coordinate system
World = 0, World = 0,
// Transforming in a instance coordinate system
Instance = 1,
// Transforming in a local coordinate system // Transforming in a local coordinate system
Local = 1, Local = 2,
// Absolute transformations, allowed in local coordinate system only. // Absolute transformations, allowed in local coordinate system only.
Absolute = 0, Absolute = 0,
// Relative transformations, allowed in both local and world coordinate system. // Relative transformations, allowed in both local and world coordinate system.
Relative = 2, Relative = 4,
// For group selection, the transformation is performed as if the group made a single solid body. // For group selection, the transformation is performed as if the group made a single solid body.
Joint = 0, Joint = 0,
// For group selection, the transformation is performed on each object independently. // For group selection, the transformation is performed on each object independently.
Independent = 4, Independent = 8,
World_Relative_Joint = World | Relative | Joint, World_Relative_Joint = World | Relative | Joint,
World_Relative_Independent = World | Relative | Independent, World_Relative_Independent = World | Relative | Independent,
Instance_Absolute_Joint = Instance | Absolute | Joint,
Instance_Absolute_Independent = Instance | Absolute | Independent,
Instance_Relative_Joint = Instance | Relative | Joint,
Instance_Relative_Independent = Instance | Relative | Independent,
Local_Absolute_Joint = Local | Absolute | Joint, Local_Absolute_Joint = Local | Absolute | Joint,
Local_Absolute_Independent = Local | Absolute | Independent, Local_Absolute_Independent = Local | Absolute | Independent,
Local_Relative_Joint = Local | Relative | Joint, Local_Relative_Joint = Local | Relative | Joint,
@ -44,14 +50,16 @@ public:
Enum operator()() const { return m_value; } Enum operator()() const { return m_value; }
bool has(Enum v) const { return ((unsigned int)m_value & (unsigned int)v) != 0; } bool has(Enum v) const { return ((unsigned int)m_value & (unsigned int)v) != 0; }
void set_world() { this->remove(Local); } void set_world() { this->remove(Instance); this->remove(Local); }
void set_local() { this->add(Local); } void set_instance() { this->remove(Local); this->add(Instance); }
void set_local() { this->remove(Instance); this->add(Local); }
void set_absolute() { this->remove(Relative); } void set_absolute() { this->remove(Relative); }
void set_relative() { this->add(Relative); } void set_relative() { this->add(Relative); }
void set_joint() { this->remove(Independent); } void set_joint() { this->remove(Independent); }
void set_independent() { this->add(Independent); } void set_independent() { this->add(Independent); }
bool world() const { return !this->has(Local); } bool world() const { return !this->has(Instance) && !this->has(Local); }
bool instance() const { return this->has(Instance); }
bool local() const { return this->has(Local); } bool local() const { return this->has(Local); }
bool absolute() const { return !this->has(Relative); } bool absolute() const { return !this->has(Relative); }
bool relative() const { return this->has(Relative); } bool relative() const { return this->has(Relative); }

View File

@ -838,7 +838,11 @@ void ObjectManipulation::update_reset_buttons_visibility()
bool show_drop_to_bed = false; bool show_drop_to_bed = false;
#if ENABLE_WORLD_COORDINATE #if ENABLE_WORLD_COORDINATE
#if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
if (m_coordinates_type != ECoordinatesType::Local && (selection.is_single_full_instance() || selection.is_single_volume_or_modifier())) {
#else
if (selection.is_single_full_instance() || selection.is_single_volume_or_modifier()) { if (selection.is_single_full_instance() || selection.is_single_volume_or_modifier()) {
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin()); const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
Vec3d rotation = Vec3d::Zero(); Vec3d rotation = Vec3d::Zero();
Vec3d scale = Vec3d::Ones(); Vec3d scale = Vec3d::Ones();

View File

@ -288,23 +288,32 @@ void GLGizmoRotate::on_render_for_picking()
void GLGizmoRotate::init_data_from_selection(const Selection& selection) void GLGizmoRotate::init_data_from_selection(const Selection& selection)
{ {
#if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES #if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
if (wxGetApp().obj_manipul()->is_world_coordinates()) { const ECoordinatesType coordinates_type = wxGetApp().obj_manipul()->get_coordinates_type();
if (coordinates_type == ECoordinatesType::World) {
#else #else
if (wxGetApp().obj_manipul()->get_world_coordinates()) { if (wxGetApp().obj_manipul()->get_world_coordinates()) {
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES #endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
m_bounding_box = selection.get_bounding_box(); m_bounding_box = selection.get_bounding_box();
m_center = m_bounding_box.center(); m_center = m_bounding_box.center();
} }
#if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
else if (coordinates_type == ECoordinatesType::Local && selection.is_single_volume_or_modifier()) {
const GLVolume& v = *selection.get_volume(*selection.get_volume_idxs().begin());
m_bounding_box = v.transformed_convex_hull_bounding_box(v.get_instance_transformation().get_matrix(true, true, false, true) * v.get_volume_transformation().get_matrix(true, true, false, true));
m_center = v.world_matrix() * m_bounding_box.center();
}
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
else { else {
m_bounding_box.reset(); m_bounding_box.reset();
const Selection::IndicesList& ids = selection.get_volume_idxs(); const Selection::IndicesList& ids = selection.get_volume_idxs();
for (unsigned int id : ids) { for (unsigned int id : ids) {
const GLVolume* v = selection.get_volume(id); const GLVolume& v = *selection.get_volume(id);
m_bounding_box.merge(v->transformed_convex_hull_bounding_box(v->get_volume_transformation().get_matrix())); m_bounding_box.merge(v.transformed_convex_hull_bounding_box(v.get_volume_transformation().get_matrix()));
} }
m_bounding_box = m_bounding_box.transformed(selection.get_volume(*ids.begin())->get_instance_transformation().get_matrix(true, true, false, true)); m_bounding_box = m_bounding_box.transformed(selection.get_volume(*ids.begin())->get_instance_transformation().get_matrix(true, true, false, true));
m_center = selection.get_volume(*ids.begin())->get_instance_transformation().get_matrix(false, false, true, false) * m_bounding_box.center(); m_center = selection.get_volume(*ids.begin())->get_instance_transformation().get_matrix(false, false, true, false) * m_bounding_box.center();
} }
m_radius = Offset + m_bounding_box.radius(); m_radius = Offset + m_bounding_box.radius();
m_snap_coarse_in_radius = m_radius / 3.0f; m_snap_coarse_in_radius = m_radius / 3.0f;
m_snap_coarse_out_radius = 2.0f * m_snap_coarse_in_radius; m_snap_coarse_out_radius = 2.0f * m_snap_coarse_in_radius;
@ -312,13 +321,18 @@ void GLGizmoRotate::init_data_from_selection(const Selection& selection)
m_snap_fine_out_radius = m_snap_fine_in_radius + m_radius * ScaleLongTooth; m_snap_fine_out_radius = m_snap_fine_in_radius + m_radius * ScaleLongTooth;
#if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES #if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
if (wxGetApp().obj_manipul()->is_world_coordinates()) if (coordinates_type == ECoordinatesType::World)
m_orient_matrix = Transform3d::Identity();
else if (coordinates_type == ECoordinatesType::Local && selection.is_single_volume_or_modifier()) {
const GLVolume& v = *selection.get_volume(*selection.get_volume_idxs().begin());
m_orient_matrix = v.get_instance_transformation().get_matrix(true, false, true, true) * v.get_volume_transformation().get_matrix(true, false, true, true);
}
#else #else
if (wxGetApp().obj_manipul()->get_world_coordinates()) if (wxGetApp().obj_manipul()->get_world_coordinates())
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
m_orient_matrix = Transform3d::Identity(); m_orient_matrix = Transform3d::Identity();
else else
m_orient_matrix = selection.get_volume(*selection.get_volume_idxs().begin())->get_instance_transformation().get_matrix(true, false, true, true); m_orient_matrix = selection.get_volume(*selection.get_volume_idxs().begin())->get_instance_transformation().get_matrix(true, false, true, true);
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
} }
#endif // ENABLE_WORLD_COORDINATE #endif // ENABLE_WORLD_COORDINATE

View File

@ -602,7 +602,7 @@ bool Selection::requires_uniform_scale() const
#else #else
return wxGetApp().obj_manipul()->get_world_coordinates() ? return wxGetApp().obj_manipul()->get_world_coordinates() ?
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES #endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
!Geometry::is_rotation_ninety_degrees(get_volume(*m_list.begin())->get_instance_rotation()) : false; !Geometry::is_rotation_ninety_degrees(get_volume(*m_list.begin())->get_instance_rotation()) : false;
return true; return true;
#else #else
@ -829,10 +829,11 @@ void Selection::rotate(const Vec3d& rotation, TransformationType transformation_
const Vec3d new_rotation = transformation_type.world() ? const Vec3d new_rotation = transformation_type.world() ?
Geometry::extract_euler_angles(m * m_cache.volumes_data[i].get_instance_rotation_matrix()) : Geometry::extract_euler_angles(m * m_cache.volumes_data[i].get_instance_rotation_matrix()) :
transformation_type.absolute() ? rotation : Geometry::extract_euler_angles(m_cache.volumes_data[i].get_instance_rotation_matrix() * m); transformation_type.absolute() ? rotation : Geometry::extract_euler_angles(m_cache.volumes_data[i].get_instance_rotation_matrix() * m);
if (rot_axis_max == 2 && transformation_type.joint()) { const Vec3d relative_instance_offset = m_cache.volumes_data[i].get_instance_position() - m_cache.dragging_center;
if (rot_axis_max == 2 && transformation_type.joint() && !relative_instance_offset.isApprox(Vec3d::Zero())) {
// Only allow rotation of multiple instances as a single rigid body when rotating around the Z axis. // Only allow rotation of multiple instances as a single rigid body when rotating around the Z axis.
const double z_diff = Geometry::rotation_diff_z(m_cache.volumes_data[i].get_instance_rotation(), new_rotation); const double z_diff = Geometry::rotation_diff_z(m_cache.volumes_data[i].get_instance_rotation(), new_rotation);
volume.set_instance_offset(m_cache.dragging_center + Eigen::AngleAxisd(z_diff, Vec3d::UnitZ()) * (m_cache.volumes_data[i].get_instance_position() - m_cache.dragging_center)); volume.set_instance_offset(m_cache.dragging_center + Eigen::AngleAxisd(z_diff, Vec3d::UnitZ()) * relative_instance_offset);
} }
#else #else
const Vec3d new_rotation = transformation_type.world() ? const Vec3d new_rotation = transformation_type.world() ?
@ -856,10 +857,21 @@ void Selection::rotate(const Vec3d& rotation, TransformationType transformation_
GLVolume &v = *(*m_volumes)[i]; GLVolume &v = *(*m_volumes)[i];
if (is_single_full_instance()) if (is_single_full_instance())
rotate_instance(v, i); rotate_instance(v, i);
else if (is_single_volume() || is_single_modifier()) {
#if ENABLE_WORLD_COORDINATE #if ENABLE_WORLD_COORDINATE
else if (is_single_volume_or_modifier()) {
#if ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
if (transformation_type.local()) {
const Transform3d m = Geometry::assemble_transform(Vec3d::Zero(), rotation);
v.set_volume_rotation(Geometry::extract_euler_angles(m_cache.volumes_data[i].get_volume_rotation_matrix() * m));
}
else if (transformation_type.instance()) {
const Transform3d m = Geometry::assemble_transform(Vec3d::Zero(), rotation);
v.set_volume_rotation(Geometry::extract_euler_angles(m * m_cache.volumes_data[i].get_volume_rotation_matrix()));
}
#else
if (transformation_type.local()) if (transformation_type.local())
v.set_volume_rotation(m_cache.volumes_data[i].get_volume_rotation() + rotation); v.set_volume_rotation(m_cache.volumes_data[i].get_volume_rotation() + rotation);
#endif // ENABLE_INSTANCE_COORDINATES_FOR_VOLUMES
else { else {
Transform3d m = Geometry::assemble_transform(Vec3d::Zero(), rotation); Transform3d m = Geometry::assemble_transform(Vec3d::Zero(), rotation);
m = m * m_cache.volumes_data[i].get_instance_rotation_matrix(); m = m * m_cache.volumes_data[i].get_instance_rotation_matrix();
@ -868,6 +880,7 @@ void Selection::rotate(const Vec3d& rotation, TransformationType transformation_
v.set_volume_rotation(Geometry::extract_euler_angles(m)); v.set_volume_rotation(Geometry::extract_euler_angles(m));
} }
#else #else
else if (is_single_volume() || is_single_modifier()) {
if (transformation_type.independent()) if (transformation_type.independent())
v.set_volume_rotation(v.get_volume_rotation() + rotation); v.set_volume_rotation(v.get_volume_rotation() + rotation);
else { else {