From 6a84d0abbfd7d72d1038be2a36667a7fa564319c Mon Sep 17 00:00:00 2001 From: Arthur Date: Mon, 31 Mar 2025 11:57:54 +0800 Subject: [PATCH] FIX: auto arranging of bed switching was wrong due to locked plates jira: STUDIO-11140, STUDIO-10891, STUDIO-11002, STUDIO-11221 Change-Id: Iaead21849aa45a5ebdb9b2a5ff8189d17a1a7a67 --- src/slic3r/GUI/Jobs/ArrangeJob.cpp | 37 +++++++++++++++++++----------- src/slic3r/GUI/Jobs/ArrangeJob.hpp | 1 - src/slic3r/GUI/PartPlate.cpp | 2 +- 3 files changed, 24 insertions(+), 16 deletions(-) diff --git a/src/slic3r/GUI/Jobs/ArrangeJob.cpp b/src/slic3r/GUI/Jobs/ArrangeJob.cpp index eca703bd3..570574258 100644 --- a/src/slic3r/GUI/Jobs/ArrangeJob.cpp +++ b/src/slic3r/GUI/Jobs/ArrangeJob.cpp @@ -96,7 +96,6 @@ void ArrangeJob::clear_input() m_unselected.clear(); m_unprintable.clear(); m_locked.clear(); - m_unarranged.clear(); m_uncompatible_plates.clear(); m_selected.reserve(count + 1 /* for optional wti */); m_unselected.reserve(count + 1 /* for optional wti */); @@ -473,6 +472,7 @@ void ArrangeJob::prepare_outside_plate() { //} } + std::set locked_plates; for (int obj_idx = 0; obj_idx < model.objects.size(); obj_idx++) { ModelObject *object = model.objects[obj_idx]; for (size_t inst_idx = 0; inst_idx < object->instances.size(); ++inst_idx) { @@ -486,7 +486,10 @@ void ArrangeJob::prepare_outside_plate() { continue; } else { int plate_idx = iter1->second; - if (plate_list.get_plate(plate_idx)->is_locked()) { plate_locked = plate_list.get_plate(plate_idx); } + if (plate_list.get_plate(plate_idx)->is_locked()) { + plate_locked = plate_list.get_plate(plate_idx); + locked_plates.insert(plate_idx); + } } if (iter2 != all_outside_objects.end()) { outside_plate = true; @@ -504,6 +507,20 @@ void ArrangeJob::prepare_outside_plate() { } } + if (!locked_plates.empty()) { + std::sort(m_unselected.begin(), m_unselected.end(), [](auto &ap1, auto &ap2) { return ap1.bed_idx < ap2.bed_idx; }); + for (auto &ap : m_unselected) { + int locked_plate_count = 0; + for (auto &plate_idx : locked_plates) { + if (plate_idx < ap.bed_idx) + locked_plate_count++; + else + break; + } + ap.bed_idx -= locked_plate_count; + } + } + prepare_wipe_tower(true); // add the virtual object into unselect list if has @@ -753,6 +770,8 @@ void ArrangeJob::finalize() plate_list.postprocess_arrange_polygon(ap, false); ap.apply(); + ARRANGE_LOG(debug) << boost::format(": locked %4%: bed_id %1%, trans {%2%, %3%}") % ap.bed_idx % unscale(ap.translation(X)) % + unscale(ap.translation(Y)) % ap.name; } // Apply the arrange result to all selected objects @@ -772,6 +791,8 @@ void ArrangeJob::finalize() plate_list.postprocess_arrange_polygon(ap, false); ap.apply(); + ARRANGE_LOG(debug) << boost::format(": unselected %4%: bed_id %1%, trans {%2%, %3%}") % ap.bed_idx % unscale(ap.translation(X)) % + unscale(ap.translation(Y)) % ap.name; } // Move the unprintable items to the last virtual bed. @@ -785,18 +806,6 @@ void ArrangeJob::finalize() } m_plater->update(); - // BBS - //wxGetApp().obj_manipul()->set_dirty(); - - if (!m_unarranged.empty()) { - std::set names; - for (ModelInstance* mi : m_unarranged) - names.insert(mi->get_object()->name); - - m_plater->get_notification_manager()->push_notification(GUI::format( - _L("Arrangement ignored the following objects which can't fit into a single bed:\n%s"), - concat_strings(names, "\n"))); - } // unlock the plates we just locked for (int i : m_uncompatible_plates) { diff --git a/src/slic3r/GUI/Jobs/ArrangeJob.hpp b/src/slic3r/GUI/Jobs/ArrangeJob.hpp index 49fa0cef7..87cf73dde 100644 --- a/src/slic3r/GUI/Jobs/ArrangeJob.hpp +++ b/src/slic3r/GUI/Jobs/ArrangeJob.hpp @@ -19,7 +19,6 @@ class ArrangeJob : public PlaterJob //BBS: add locked logic ArrangePolygons m_selected, m_unselected, m_unprintable, m_locked; - std::vector m_unarranged; std::map m_selected_groups; // groups of selected items for sequential printing std::vector m_uncompatible_plates; // plate indices with different printing sequence than global diff --git a/src/slic3r/GUI/PartPlate.cpp b/src/slic3r/GUI/PartPlate.cpp index a96db02fa..2c9beea49 100644 --- a/src/slic3r/GUI/PartPlate.cpp +++ b/src/slic3r/GUI/PartPlate.cpp @@ -4848,7 +4848,7 @@ bool PartPlateList::preprocess_arrange_polygon(int obj_index, int instance_index arrange_polygon.translation(Y) += scaled(plate_stride_y() * arrange_polygon.row); } } - BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(": obj_id %1% instance_id %2% already in plate %3%, locked %4%, row %5%, col %6%\n") % obj_index % instance_index % i % locked % arrange_polygon.row % arrange_polygon.col; + BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(": obj_id %1% name %7% instance_id %2% already in plate %3%, locked %4%, row %5%, col %6%\n") % obj_index % instance_index % i % locked % arrange_polygon.row % arrange_polygon.col % arrange_polygon.name; return locked; } if (m_plate_list[i]->is_locked())