Fix face the camera

This commit is contained in:
Filip Sykala - NTB T15p 2023-10-25 16:16:33 +02:00
parent 2b83ff1e7a
commit fe47296945
4 changed files with 112 additions and 57 deletions

View File

@ -692,10 +692,20 @@ void GLGizmoEmboss::volume_transformation_changed()
{
if (m_volume == nullptr ||
!m_volume->text_configuration.has_value() ||
!m_volume->emboss_shape.has_value()) {
!m_volume->emboss_shape.has_value() ||
!m_style_manager.is_active_font()) {
assert(false);
return;
}
if (!m_keep_up) {
// Re-Calculate current angle of up vector
m_style_manager.get_style().angle = calc_angle(m_parent.get_selection());
} else {
// angle should be the same
assert(is_approx(m_style_manager.get_style().angle, calc_angle(m_parent.get_selection())));
}
const TextConfiguration &tc = *m_volume->text_configuration;
const EmbossShape &es = *m_volume->emboss_shape;
@ -708,6 +718,26 @@ void GLGizmoEmboss::volume_transformation_changed()
// Update surface by new position
if (use_surface || per_glyph)
process();
else {
// inform slicing process that model changed
// SLA supports, processing
// ensure on bed
const ModelObjectPtrs objects = m_parent.get_model()->objects;
ModelObject *object = m_volume->get_object();
object->invalidate_bounding_box();
object->ensure_on_bed();
int obj_idx = -1;
for (int i = 0; i < objects.size(); i++)
if (objects[i]->id() == object->id()) {
obj_idx = i;
break;
}
wxGetApp().plater()->changed_object(obj_idx);
// Check outside bed
m_parent.requires_check_outside_state();
}
// Show correct value of height & depth inside of inputs
calculate_scale();
@ -990,17 +1020,7 @@ void GLGizmoEmboss::on_stop_dragging()
// apply rotation
m_parent.do_rotate(L("Text-Rotate"));
// Re-Calculate current angle of up vector
const Selection &selection = m_parent.get_selection();
const GLVolume *gl_volume = get_selected_gl_volume(selection);
assert(m_style_manager.is_active_font());
assert(gl_volume != nullptr);
if (m_style_manager.is_active_font() && gl_volume != nullptr)
m_style_manager.get_style().angle = calc_angle(selection);
m_rotate_start_angle.reset();
volume_transformation_changed();
}
void GLGizmoEmboss::on_dragging(const UpdateData &data) { m_rotate_gizmo.dragging(data); }
@ -2955,27 +2975,9 @@ void GLGizmoEmboss::draw_advanced()
if (ImGui::Button(_u8L("Set text to face camera").c_str())) {
assert(get_selected_volume(m_parent.get_selection()) == m_volume);
const Camera &cam = wxGetApp().plater()->get_camera();
auto wanted_up_limit = (m_keep_up) ? std::optional<double>(UP_LIMIT) : std::optional<double>{};
if (face_selected_volume_to_camera(cam, m_parent, wanted_up_limit)) {
if (!m_keep_up) {
// update current style
m_style_manager.get_style().angle = calc_angle(m_parent.get_selection());
} else {
// after set face to camera, angle should be the same
assert(is_approx(m_style_manager.get_style().angle, calc_angle(m_parent.get_selection())));
}
FontProp &fp = m_style_manager.get_font_prop();
if (use_surface || fp.per_glyph) {
if (fp.per_glyph)
reinit_text_lines();
process();
} else {
// Check outside bed
m_parent.requires_check_outside_state();
}
}
auto wanted_up_limit = m_keep_up ? std::optional<double>(UP_LIMIT) : std::optional<double>{};
if (face_selected_volume_to_camera(cam, m_parent, wanted_up_limit))
volume_transformation_changed();
} else if (ImGui::IsItemHovered()) {
ImGui::SetTooltip("%s", _u8L("Orient the text towards the camera.").c_str());
}

View File

@ -326,6 +326,50 @@ bool GLGizmoSVG::on_mouse_for_translate(const wxMouseEvent &mouse_event)
return res;
}
void GLGizmoSVG::volume_transformation_changed()
{
if (m_volume == nullptr ||
!m_volume->emboss_shape.has_value()) {
assert(false);
return;
}
if (!m_keep_up) {
// update current style
m_angle = calc_angle(m_parent.get_selection());
} else {
// angle should be the same
assert(is_approx(m_angle, calc_angle(m_parent.get_selection())));
}
// Update surface by new position
if (m_volume->emboss_shape->projection.use_surface) {
process();
} else {
// inform slicing process that model changed
// SLA supports, processing
// ensure on bed
const ModelObjectPtrs objects = m_parent.get_model()->objects;
ModelObject *object = m_volume->get_object();
object->invalidate_bounding_box();
object->ensure_on_bed();
int obj_idx = -1;
for (int i = 0; i < objects.size(); i++)
if (objects[i]->id() == object->id()) {
obj_idx = i;
break;
}
wxGetApp().plater()->changed_object(obj_idx);
// Check outside bed
m_parent.requires_check_outside_state();
}
// Show correct value of height & depth inside of inputs
calculate_scale();
}
bool GLGizmoSVG::on_mouse(const wxMouseEvent &mouse_event)
{
// not selected volume
@ -546,9 +590,9 @@ void GLGizmoSVG::on_stop_dragging()
m_rotate_gizmo.set_angle(PI/2);
// apply rotation
m_parent.do_rotate(L("Text-Rotate"));
m_parent.do_rotate(L("SVG-Rotate"));
m_rotate_start_angle.reset();
volume_transformation_changed();
// recalculate for surface cut
if (m_volume != nullptr &&
@ -1327,21 +1371,8 @@ void GLGizmoSVG::draw_window()
if (ImGui::Button(_u8L("Face the camera").c_str())) {
const Camera &cam = wxGetApp().plater()->get_camera();
auto wanted_up_limit = (m_keep_up) ? std::optional<double>(UP_LIMIT) : std::optional<double>{};
if (face_selected_volume_to_camera(cam, m_parent, wanted_up_limit)) {
if (!m_keep_up) {
m_angle = calc_angle(m_parent.get_selection());
} else {
// after set face to camera, angle should be the same
assert(is_approx(m_angle, calc_angle(m_parent.get_selection())));
}
if (m_volume->emboss_shape->projection.use_surface) {
process();
} else {
// Check outside bed
m_parent.requires_check_outside_state();
}
}
if (face_selected_volume_to_camera(cam, m_parent, wanted_up_limit))
volume_transformation_changed();
}
ImGui::Unindent(m_gui_cfg->icon_width);

View File

@ -128,6 +128,8 @@ private:
// process mouse event
bool on_mouse_for_rotation(const wxMouseEvent &mouse_event);
bool on_mouse_for_translate(const wxMouseEvent &mouse_event);
void volume_transformation_changed();
struct GuiCfg;
std::unique_ptr<const GuiCfg> m_gui_cfg;

View File

@ -298,7 +298,7 @@ void selection_transform(Selection &selection, const std::function<void()> &sele
selection.setup_cache();
}
bool face_selected_volume_to_camera(const Camera &camera, GLCanvas3D &canvas, const std::optional<double>& wanted_up_limit)
bool face_selected_volume_to_camera(const Camera &camera, GLCanvas3D &canvas, const std::optional<double> &wanted_up_limit)
{
GLVolume *gl_volume_ptr = get_selected_gl_volume(canvas);
if (gl_volume_ptr == nullptr)
@ -306,17 +306,17 @@ bool face_selected_volume_to_camera(const Camera &camera, GLCanvas3D &canvas, co
GLVolume &gl_volume = *gl_volume_ptr;
const ModelObjectPtrs &objects = canvas.get_model()->objects;
const ModelObject *object_ptr = get_model_object(gl_volume, objects);
ModelObject *object_ptr = get_model_object(gl_volume, objects);
assert(object_ptr != nullptr);
if (object_ptr == nullptr)
return false;
const ModelObject &object = *object_ptr;
ModelObject &object = *object_ptr;
const ModelInstance *instance_ptr = get_model_instance(gl_volume, object);
ModelInstance *instance_ptr = get_model_instance(gl_volume, object);
assert(instance_ptr != nullptr);
if (instance_ptr == nullptr)
return false;
const ModelInstance &instance = *instance_ptr;
ModelInstance &instance = *instance_ptr;
ModelVolume *volume_ptr = get_model_volume(gl_volume, object);
assert(volume_ptr != nullptr);
@ -346,9 +346,29 @@ bool face_selected_volume_to_camera(const Camera &camera, GLCanvas3D &canvas, co
Transform3d new_volume_tr = get_volume_transformation(world_tr, wanted_direction, world_position,
fix, instance_tr_inv, current_angle, wanted_up_limit);
// write result transformation
gl_volume.set_volume_transformation(Geometry::Transformation(new_volume_tr));
volume.set_transformation(new_volume_tr);
if (canvas.get_selection().is_single_full_object()) {
// transform instance instead of volume
Transform3d new_instance_tr = instance_tr * new_volume_tr * volume.get_matrix().inverse();
instance.set_transformation(Geometry::Transformation(new_instance_tr));
gl_volume.set_instance_transformation(new_instance_tr);
} else {
// write result transformation
gl_volume.set_volume_transformation(Geometry::Transformation(new_volume_tr));
volume.set_transformation(new_volume_tr);
}
if (volume.type() == ModelVolumeType::MODEL_PART)
object.ensure_on_bed();
//int obj_idx = -1;
//for (int i = 0; i < objects.size(); i++)
// if (objects[i]->id() == object.id()) {
// obj_idx = i;
// break;
// }
// object change !!!
// Plater::changed_object(obj_idx);
return true;
}