Tech ENABLE_ALLOW_NEGATIVE_Z->Fixed object popping up after editing layer range fields

This commit is contained in:
enricoturri1966 2021-04-28 11:07:15 +02:00
parent a83cd647da
commit c58572deaa
6 changed files with 59 additions and 68 deletions

View file

@ -954,30 +954,39 @@ void ModelObject::center_around_origin(bool include_modifiers)
{ {
// calculate the displacements needed to // calculate the displacements needed to
// center this object around the origin // center this object around the origin
BoundingBoxf3 bb = include_modifiers ? full_raw_mesh_bounding_box() : raw_mesh_bounding_box(); const BoundingBoxf3 bb = include_modifiers ? full_raw_mesh_bounding_box() : raw_mesh_bounding_box();
// Shift is the vector from the center of the bounding box to the origin // Shift is the vector from the center of the bounding box to the origin
Vec3d shift = -bb.center(); const Vec3d shift = -bb.center();
this->translate(shift); this->translate(shift);
this->origin_translation += shift; this->origin_translation += shift;
} }
#if ENABLE_ALLOW_NEGATIVE_Z
void ModelObject::ensure_on_bed(bool allow_negative_z)
{
const double min_z = get_min_z();
if (!allow_negative_z || min_z > 0.0)
translate_instances({ 0.0, 0.0, -min_z });
}
#else
void ModelObject::ensure_on_bed() void ModelObject::ensure_on_bed()
{ {
translate_instances(Vec3d(0.0, 0.0, -get_min_z())); translate_instances({ 0.0, 0.0, -get_min_z() });
} }
#endif // ENABLE_ALLOW_NEGATIVE_Z
void ModelObject::translate_instances(const Vec3d& vector) void ModelObject::translate_instances(const Vec3d& vector)
{ {
for (size_t i = 0; i < instances.size(); ++i) for (size_t i = 0; i < instances.size(); ++i) {
{
translate_instance(i, vector); translate_instance(i, vector);
} }
} }
void ModelObject::translate_instance(size_t instance_idx, const Vec3d& vector) void ModelObject::translate_instance(size_t instance_idx, const Vec3d& vector)
{ {
assert(instance_idx < instances.size());
ModelInstance* i = instances[instance_idx]; ModelInstance* i = instances[instance_idx];
i->set_offset(i->get_offset() + vector); i->set_offset(i->get_offset() + vector);
invalidate_bounding_box(); invalidate_bounding_box();
@ -985,8 +994,7 @@ void ModelObject::translate_instance(size_t instance_idx, const Vec3d& vector)
void ModelObject::translate(double x, double y, double z) void ModelObject::translate(double x, double y, double z)
{ {
for (ModelVolume *v : this->volumes) for (ModelVolume *v : this->volumes) {
{
v->translate(x, y, z); v->translate(x, y, z);
} }
@ -996,8 +1004,7 @@ void ModelObject::translate(double x, double y, double z)
void ModelObject::scale(const Vec3d &versor) void ModelObject::scale(const Vec3d &versor)
{ {
for (ModelVolume *v : this->volumes) for (ModelVolume *v : this->volumes) {
{
v->scale(versor); v->scale(versor);
} }
this->invalidate_bounding_box(); this->invalidate_bounding_box();
@ -1005,41 +1012,34 @@ void ModelObject::scale(const Vec3d &versor)
void ModelObject::rotate(double angle, Axis axis) void ModelObject::rotate(double angle, Axis axis)
{ {
for (ModelVolume *v : this->volumes) for (ModelVolume *v : this->volumes) {
{
v->rotate(angle, axis); v->rotate(angle, axis);
} }
center_around_origin(); center_around_origin();
this->invalidate_bounding_box(); this->invalidate_bounding_box();
} }
void ModelObject::rotate(double angle, const Vec3d& axis) void ModelObject::rotate(double angle, const Vec3d& axis)
{ {
for (ModelVolume *v : this->volumes) for (ModelVolume *v : this->volumes) {
{
v->rotate(angle, axis); v->rotate(angle, axis);
} }
center_around_origin(); center_around_origin();
this->invalidate_bounding_box(); this->invalidate_bounding_box();
} }
void ModelObject::mirror(Axis axis) void ModelObject::mirror(Axis axis)
{ {
for (ModelVolume *v : this->volumes) for (ModelVolume *v : this->volumes) {
{
v->mirror(axis); v->mirror(axis);
} }
this->invalidate_bounding_box(); this->invalidate_bounding_box();
} }
// This method could only be called before the meshes of this ModelVolumes are not shared! // This method could only be called before the meshes of this ModelVolumes are not shared!
void ModelObject::scale_mesh_after_creation(const Vec3d &versor) void ModelObject::scale_mesh_after_creation(const Vec3d &versor)
{ {
for (ModelVolume *v : this->volumes) for (ModelVolume *v : this->volumes) {
{
v->scale_geometry_after_creation(versor); v->scale_geometry_after_creation(versor);
v->set_offset(versor.cwiseProduct(v->get_offset())); v->set_offset(versor.cwiseProduct(v->get_offset()));
} }

View file

@ -308,7 +308,11 @@ public:
void center_around_origin(bool include_modifiers = true); void center_around_origin(bool include_modifiers = true);
#if ENABLE_ALLOW_NEGATIVE_Z
void ensure_on_bed(bool allow_negative_z = false);
#else
void ensure_on_bed(); void ensure_on_bed();
#endif // ENABLE_ALLOW_NEGATIVE_Z
void translate_instances(const Vec3d& vector); void translate_instances(const Vec3d& vector);
void translate_instance(size_t instance_idx, const Vec3d& vector); void translate_instance(size_t instance_idx, const Vec3d& vector);
void translate(const Vec3d &vector) { this->translate(vector(0), vector(1), vector(2)); } void translate(const Vec3d &vector) { this->translate(vector(0), vector(1), vector(2)); }

View file

@ -142,7 +142,7 @@ wxSizer* ObjectLayers::create_layer(const t_layer_height_range& range, PlusMinus
auto sizer = new wxBoxSizer(wxHORIZONTAL); auto sizer = new wxBoxSizer(wxHORIZONTAL);
sizer->Add(editor); sizer->Add(editor);
auto temp = new wxStaticText(m_parent, wxID_ANY, _(L("mm"))); auto temp = new wxStaticText(m_parent, wxID_ANY, _L("mm"));
temp->SetBackgroundStyle(wxBG_STYLE_PAINT); temp->SetBackgroundStyle(wxBG_STYLE_PAINT);
temp->SetFont(wxGetApp().normal_font()); temp->SetFont(wxGetApp().normal_font());
sizer->Add(temp, 0, wxLEFT, wxGetApp().em_unit()); sizer->Add(temp, 0, wxLEFT, wxGetApp().em_unit());
@ -154,15 +154,14 @@ wxSizer* ObjectLayers::create_layer(const t_layer_height_range& range, PlusMinus
void ObjectLayers::create_layers_list() void ObjectLayers::create_layers_list()
{ {
for (const auto &layer : m_object->layer_config_ranges) for (const auto &layer : m_object->layer_config_ranges) {
{
const t_layer_height_range& range = layer.first; const t_layer_height_range& range = layer.first;
auto del_btn = new PlusMinusButton(m_parent, m_bmp_delete, range); auto del_btn = new PlusMinusButton(m_parent, m_bmp_delete, range);
del_btn->SetToolTip(_(L("Remove layer range"))); del_btn->SetToolTip(_L("Remove layer range"));
auto add_btn = new PlusMinusButton(m_parent, m_bmp_add, range); auto add_btn = new PlusMinusButton(m_parent, m_bmp_add, range);
wxString tooltip = wxGetApp().obj_list()->can_add_new_range_after_current(range); wxString tooltip = wxGetApp().obj_list()->can_add_new_range_after_current(range);
add_btn->SetToolTip(tooltip.IsEmpty() ? _(L("Add layer range")) : tooltip); add_btn->SetToolTip(tooltip.IsEmpty() ? _L("Add layer range") : tooltip);
add_btn->Enable(tooltip.IsEmpty()); add_btn->Enable(tooltip.IsEmpty());
auto sizer = create_layer(range, del_btn, add_btn); auto sizer = create_layer(range, del_btn, add_btn);
@ -242,11 +241,9 @@ void ObjectLayers::msw_rescale()
// rescale edit-boxes // rescale edit-boxes
const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount(); const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount();
for (int i = 0; i < cells_cnt; i++) for (int i = 0; i < cells_cnt; ++i) {
{
const wxSizerItem* item = m_grid_sizer->GetItem(i); const wxSizerItem* item = m_grid_sizer->GetItem(i);
if (item->IsWindow()) if (item->IsWindow()) {
{
LayerRangeEditor* editor = dynamic_cast<LayerRangeEditor*>(item->GetWindow()); LayerRangeEditor* editor = dynamic_cast<LayerRangeEditor*>(item->GetWindow());
if (editor != nullptr) if (editor != nullptr)
editor->msw_rescale(); editor->msw_rescale();
@ -283,8 +280,7 @@ void ObjectLayers::sys_color_changed()
// rescale edit-boxes // rescale edit-boxes
const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount(); const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount();
for (int i = 0; i < cells_cnt; i++) for (int i = 0; i < cells_cnt; ++i) {
{
const wxSizerItem* item = m_grid_sizer->GetItem(i); const wxSizerItem* item = m_grid_sizer->GetItem(i);
if (item->IsSizer()) {// case when we have editor with buttons if (item->IsSizer()) {// case when we have editor with buttons
const std::vector<size_t> btns = {2, 3}; // del_btn, add_btn const std::vector<size_t> btns = {2, 3}; // del_btn, add_btn
@ -405,11 +401,9 @@ coordf_t LayerRangeEditor::get_value()
str.Replace(",", ".", false); str.Replace(",", ".", false);
if (str == ".") if (str == ".")
layer_height = 0.0; layer_height = 0.0;
else else {
{ if (!str.ToCDouble(&layer_height) || layer_height < 0.0f) {
if (!str.ToCDouble(&layer_height) || layer_height < 0.0f) show_error(m_parent, _L("Invalid numeric input."));
{
show_error(m_parent, _(L("Invalid numeric input.")));
SetValue(double_to_string(layer_height)); SetValue(double_to_string(layer_height));
} }
} }

View file

@ -2113,18 +2113,15 @@ void ObjectList::part_selection_changed()
const auto item = GetSelection(); const auto item = GetSelection();
if ( multiple_selection() || (item && m_objects_model->GetItemType(item) == itInstanceRoot )) if ( multiple_selection() || (item && m_objects_model->GetItemType(item) == itInstanceRoot )) {
{ og_name = _L("Group manipulation");
og_name = _(L("Group manipulation"));
const Selection& selection = scene_selection(); const Selection& selection = scene_selection();
// don't show manipulation panel for case of all Object's parts selection // don't show manipulation panel for case of all Object's parts selection
update_and_show_manipulations = !selection.is_single_full_instance(); update_and_show_manipulations = !selection.is_single_full_instance();
} }
else else {
{ if (item) {
if (item)
{
const ItemType type = m_objects_model->GetItemType(item); const ItemType type = m_objects_model->GetItemType(item);
const wxDataViewItem parent = m_objects_model->GetParent(item); const wxDataViewItem parent = m_objects_model->GetParent(item);
const ItemType parent_type = m_objects_model->GetItemType(parent); const ItemType parent_type = m_objects_model->GetItemType(parent);
@ -2132,7 +2129,7 @@ void ObjectList::part_selection_changed()
if (parent == wxDataViewItem(nullptr) if (parent == wxDataViewItem(nullptr)
|| type == itInfo) { || type == itInfo) {
og_name = _(L("Object manipulation")); og_name = _L("Object manipulation");
m_config = &(*m_objects)[obj_idx]->config; m_config = &(*m_objects)[obj_idx]->config;
update_and_show_manipulations = true; update_and_show_manipulations = true;
@ -2152,35 +2149,35 @@ void ObjectList::part_selection_changed()
else { else {
if (type & itSettings) { if (type & itSettings) {
if (parent_type & itObject) { if (parent_type & itObject) {
og_name = _(L("Object Settings to modify")); og_name = _L("Object Settings to modify");
m_config = &(*m_objects)[obj_idx]->config; m_config = &(*m_objects)[obj_idx]->config;
} }
else if (parent_type & itVolume) { else if (parent_type & itVolume) {
og_name = _(L("Part Settings to modify")); og_name = _L("Part Settings to modify");
volume_id = m_objects_model->GetVolumeIdByItem(parent); volume_id = m_objects_model->GetVolumeIdByItem(parent);
m_config = &(*m_objects)[obj_idx]->volumes[volume_id]->config; m_config = &(*m_objects)[obj_idx]->volumes[volume_id]->config;
} }
else if (parent_type & itLayer) { else if (parent_type & itLayer) {
og_name = _(L("Layer range Settings to modify")); og_name = _L("Layer range Settings to modify");
m_config = &get_item_config(parent); m_config = &get_item_config(parent);
} }
update_and_show_settings = true; update_and_show_settings = true;
} }
else if (type & itVolume) { else if (type & itVolume) {
og_name = _(L("Part manipulation")); og_name = _L("Part manipulation");
volume_id = m_objects_model->GetVolumeIdByItem(item); volume_id = m_objects_model->GetVolumeIdByItem(item);
m_config = &(*m_objects)[obj_idx]->volumes[volume_id]->config; m_config = &(*m_objects)[obj_idx]->volumes[volume_id]->config;
update_and_show_manipulations = true; update_and_show_manipulations = true;
} }
else if (type & itInstance) { else if (type & itInstance) {
og_name = _(L("Instance manipulation")); og_name = _L("Instance manipulation");
update_and_show_manipulations = true; update_and_show_manipulations = true;
// fill m_config by object's values // fill m_config by object's values
m_config = &(*m_objects)[obj_idx]->config; m_config = &(*m_objects)[obj_idx]->config;
} }
else if (type & (itLayerRoot|itLayer)) { else if (type & (itLayerRoot|itLayer)) {
og_name = type & itLayerRoot ? _(L("Height ranges")) : _(L("Settings for height range")); og_name = type & itLayerRoot ? _L("Height ranges") : _L("Settings for height range");
update_and_show_layers = true; update_and_show_layers = true;
if (type & itLayer) if (type & itLayer)
@ -2815,7 +2812,7 @@ bool ObjectList::edit_layer_range(const t_layer_height_range& range, const t_lay
const int obj_idx = m_selected_object_id; const int obj_idx = m_selected_object_id;
if (obj_idx < 0) return false; if (obj_idx < 0) return false;
take_snapshot(_(L("Edit Height Range"))); take_snapshot(_L("Edit Height Range"));
const ItemType sel_type = m_objects_model->GetItemType(GetSelection()); const ItemType sel_type = m_objects_model->GetItemType(GetSelection());

View file

@ -5805,7 +5805,11 @@ void Plater::changed_object(int obj_idx)
return; return;
// recenter and re - align to Z = 0 // recenter and re - align to Z = 0
auto model_object = p->model.objects[obj_idx]; auto model_object = p->model.objects[obj_idx];
#if ENABLE_ALLOW_NEGATIVE_Z
model_object->ensure_on_bed(true);
#else
model_object->ensure_on_bed(); model_object->ensure_on_bed();
#endif // ENABLE_ALLOW_NEGATIVE_Z
if (this->p->printer_technology == ptSLA) { if (this->p->printer_technology == ptSLA) {
// Update the SLAPrint from the current Model, so that the reload_scene() // Update the SLAPrint from the current Model, so that the reload_scene()
// pulls the correct data, update the 3D scene. // pulls the correct data, update the 3D scene.
@ -5823,8 +5827,7 @@ void Plater::changed_objects(const std::vector<size_t>& object_idxs)
if (object_idxs.empty()) if (object_idxs.empty())
return; return;
for (size_t obj_idx : object_idxs) for (size_t obj_idx : object_idxs) {
{
if (obj_idx < p->model.objects.size()) if (obj_idx < p->model.objects.size())
// recenter and re - align to Z = 0 // recenter and re - align to Z = 0
p->model.objects[obj_idx]->ensure_on_bed(); p->model.objects[obj_idx]->ensure_on_bed();

View file

@ -672,24 +672,20 @@ void Selection::translate(const Vec3d& displacement, bool local)
EMode translation_type = m_mode; EMode translation_type = m_mode;
for (unsigned int i : m_list) for (unsigned int i : m_list) {
{ if (m_mode == Volume || (*m_volumes)[i]->is_wipe_tower)
if ((m_mode == Volume) || (*m_volumes)[i]->is_wipe_tower)
{ {
if (local) if (local)
(*m_volumes)[i]->set_volume_offset(m_cache.volumes_data[i].get_volume_position() + displacement); (*m_volumes)[i]->set_volume_offset(m_cache.volumes_data[i].get_volume_position() + displacement);
else else {
{
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; 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;
(*m_volumes)[i]->set_volume_offset(m_cache.volumes_data[i].get_volume_position() + local_displacement); (*m_volumes)[i]->set_volume_offset(m_cache.volumes_data[i].get_volume_position() + local_displacement);
} }
} }
else if (m_mode == Instance) else if (m_mode == Instance) {
{
if (is_from_fully_selected_instance(i)) if (is_from_fully_selected_instance(i))
(*m_volumes)[i]->set_instance_offset(m_cache.volumes_data[i].get_instance_position() + displacement); (*m_volumes)[i]->set_instance_offset(m_cache.volumes_data[i].get_instance_position() + displacement);
else else {
{
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; 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;
(*m_volumes)[i]->set_volume_offset(m_cache.volumes_data[i].get_volume_position() + local_displacement); (*m_volumes)[i]->set_volume_offset(m_cache.volumes_data[i].get_volume_position() + local_displacement);
translation_type = Volume; translation_type = Volume;
@ -2153,10 +2149,8 @@ void Selection::ensure_on_bed()
typedef std::map<std::pair<int, int>, double> InstancesToZMap; typedef std::map<std::pair<int, int>, double> InstancesToZMap;
InstancesToZMap instances_min_z; InstancesToZMap instances_min_z;
for (GLVolume* volume : *m_volumes) for (GLVolume* volume : *m_volumes) {
{ if (!volume->is_wipe_tower && !volume->is_modifier) {
if (!volume->is_wipe_tower && !volume->is_modifier)
{
double min_z = volume->transformed_convex_hull_bounding_box().min(2); double min_z = volume->transformed_convex_hull_bounding_box().min(2);
std::pair<int, int> instance = std::make_pair(volume->object_idx(), volume->instance_idx()); std::pair<int, int> instance = std::make_pair(volume->object_idx(), volume->instance_idx());
InstancesToZMap::iterator it = instances_min_z.find(instance); InstancesToZMap::iterator it = instances_min_z.find(instance);
@ -2167,8 +2161,7 @@ void Selection::ensure_on_bed()
} }
} }
for (GLVolume* volume : *m_volumes) for (GLVolume* volume : *m_volumes) {
{
std::pair<int, int> instance = std::make_pair(volume->object_idx(), volume->instance_idx()); std::pair<int, int> instance = std::make_pair(volume->object_idx(), volume->instance_idx());
InstancesToZMap::iterator it = instances_min_z.find(instance); InstancesToZMap::iterator it = instances_min_z.find(instance);
if (it != instances_min_z.end()) if (it != instances_min_z.end())