Merge some BS1.7 changes:
bring back fill_bed feature, original implemention from PrusaSlicer. BS added exclusion logic.
This commit is contained in:
parent
b8db25ac0e
commit
3acd89e877
20 changed files with 242 additions and 180 deletions
|
@ -86,18 +86,21 @@ template<class PConf>
|
|||
void fill_config(PConf& pcfg, const ArrangeParams ¶ms) {
|
||||
|
||||
if (params.is_seq_print) {
|
||||
// Align the arranged pile into the center of the bin
|
||||
pcfg.alignment = PConf::Alignment::CENTER;
|
||||
// Start placing the items from the center of the print bed
|
||||
pcfg.starting_point = PConf::Alignment::BOTTOM_LEFT;
|
||||
}
|
||||
else {
|
||||
// Align the arranged pile into the center of the bin
|
||||
pcfg.alignment = PConf::Alignment::CENTER;
|
||||
// Start placing the items from the center of the print bed
|
||||
pcfg.starting_point = PConf::Alignment::TOP_RIGHT;
|
||||
}
|
||||
|
||||
if (params.do_final_align) {
|
||||
// Align the arranged pile into the center of the bin
|
||||
pcfg.alignment = PConf::Alignment::CENTER;
|
||||
}else
|
||||
pcfg.alignment = PConf::Alignment::DONT_ALIGN;
|
||||
|
||||
|
||||
// Try 4 angles (45 degree step) and find the one with min cost
|
||||
if (params.allow_rotations)
|
||||
pcfg.rotations = {0., PI / 4., PI/2, 3. * PI / 4. };
|
||||
|
@ -452,27 +455,25 @@ protected:
|
|||
}
|
||||
|
||||
std::set<int> extruder_ids;
|
||||
int non_virt_cnt = 0;
|
||||
std::set<int> first_object_extruder_ids;
|
||||
for (int i = 0; i < m_items.size(); i++) {
|
||||
Item& p = m_items[i];
|
||||
if (p.is_virt_object) continue;
|
||||
extruder_ids.insert(p.extrude_ids.begin(),p.extrude_ids.end());
|
||||
non_virt_cnt++;
|
||||
if (non_virt_cnt == 1) { first_object_extruder_ids.insert(p.extrude_ids.begin(), p.extrude_ids.end()); }
|
||||
}
|
||||
extruder_ids.insert(item.extrude_ids.begin(),item.extrude_ids.end());
|
||||
|
||||
// add a large cost if not multi materials on same plate is not allowed
|
||||
if (!params.allow_multi_materials_on_same_plate) {
|
||||
bool first_object = non_virt_cnt == 0;
|
||||
bool same_color_with_first_object = std::all_of(item.extrude_ids.begin(), item.extrude_ids.end(),
|
||||
[&](int color) { return first_object_extruder_ids.find(color) != first_object_extruder_ids.end(); });
|
||||
// non_virt_cnt==0 means it's the first object, which can be multi-color
|
||||
if (!(first_object || same_color_with_first_object)) score += LARGE_COST_TO_REJECT * 1.3;
|
||||
// it's the first object, which can be multi-color
|
||||
bool first_object = extruder_ids.empty();
|
||||
// the two objects (previously packed items and the current item) are considered having same color if either one's colors are a subset of the other
|
||||
std::set<int> item_extruder_ids(item.extrude_ids.begin(), item.extrude_ids.end());
|
||||
bool same_color_with_previous_items = std::includes(item_extruder_ids.begin(), item_extruder_ids.end(), extruder_ids.begin(), extruder_ids.end())
|
||||
|| std::includes(extruder_ids.begin(), extruder_ids.end(), item_extruder_ids.begin(), item_extruder_ids.end());
|
||||
if (!(first_object || same_color_with_previous_items)) score += LARGE_COST_TO_REJECT * 1.3;
|
||||
}
|
||||
// for layered printing, we want extruder change as few as possible
|
||||
// this has very weak effect, CAN NOT use a large weight
|
||||
extruder_ids.insert(item.extrude_ids.begin(), item.extrude_ids.end());
|
||||
if (!params.is_seq_print) {
|
||||
score += 1 * std::max(0, ((int) extruder_ids.size() - 1));
|
||||
}
|
||||
|
@ -544,12 +545,6 @@ public:
|
|||
if (items.empty()) return;
|
||||
|
||||
auto binbb = sl::boundingBox(m_bin);
|
||||
// BBS: excluded region (virtual object but not wipe tower) should not affect final alignment
|
||||
//bool all_is_excluded_region = std::all_of(items.begin(), items.end(), [](Item &itm) { return itm.is_virt_object && !itm.is_wipe_tower; });
|
||||
//if (!all_is_excluded_region)
|
||||
// cfg.alignment = PConfig::Alignment::DONT_ALIGN;
|
||||
//else
|
||||
// cfg.alignment = PConfig::Alignment::CENTER;
|
||||
|
||||
auto starting_point = cfg.starting_point == PConfig::Alignment::BOTTOM_LEFT ? binbb.minCorner() : binbb.center();
|
||||
// if we have wipe tower, items should be arranged around wipe tower
|
||||
|
@ -561,15 +556,7 @@ public:
|
|||
}
|
||||
|
||||
cfg.object_function = [this, binbb, starting_point](const Item &item, const ItemGroup &packed_items) {
|
||||
// 在我们的摆盘中,没有天然的固定对象。固定对象只有:屏蔽区域、挤出补偿区域、料塔。
|
||||
// 对于屏蔽区域,摆入的对象仍然是可以向右上滑动的;
|
||||
// 对挤出料塔,摆入的对象不能滑动(必须围绕料塔)
|
||||
bool pack_around_wipe_tower = std::any_of(packed_items.begin(), packed_items.end(), [](Item& itm) { return itm.is_wipe_tower; });
|
||||
//if(pack_around_wipe_tower)
|
||||
return fixed_overfit(objfunc(item, starting_point), binbb);
|
||||
//else {
|
||||
// return fixed_overfit_topright_sliding(objfunc(item, starting_point), binbb, m_excluded_and_extruCali_regions);
|
||||
//}
|
||||
return fixed_overfit(objfunc(item, starting_point), binbb);
|
||||
};
|
||||
};
|
||||
|
||||
|
|
|
@ -57,7 +57,7 @@ struct ArrangePolygon {
|
|||
//BBS: add row/col for sudoku-style layout
|
||||
int row{0};
|
||||
int col{0};
|
||||
std::vector<int> extrude_ids{1}; ///extruder_id for least extruder switch
|
||||
std::vector<int> extrude_ids{}; /// extruder_id for least extruder switch
|
||||
int bed_temp{0}; ///bed temperature for different material judge
|
||||
int print_temp{0}; ///print temperature for different material judge
|
||||
int first_bed_temp{ 0 }; ///first layer bed temperature for different material judge
|
||||
|
@ -114,6 +114,8 @@ struct ArrangeParams {
|
|||
|
||||
bool allow_rotations = false;
|
||||
|
||||
bool do_final_align = true;
|
||||
|
||||
//BBS: add specific arrange params
|
||||
bool allow_multi_materials_on_same_plate = true;
|
||||
bool avoid_extrusion_cali_region = true;
|
||||
|
|
|
@ -807,7 +807,7 @@ void PerimeterGenerator::split_top_surfaces(const ExPolygons &orig_polygons, ExP
|
|||
offset_top_surface = 0;
|
||||
// don't takes into account too thin areas
|
||||
// skip if the exposed area is smaller than 2x perimeter width
|
||||
double min_width_top_surface = std::max(double(ext_perimeter_spacing / 2 + 10), 2.0 * (double(perimeter_width)));
|
||||
double min_width_top_surface = std::max(double(ext_perimeter_spacing / 2 + 10), 2.5 * (double(perimeter_width)));
|
||||
|
||||
Polygons grown_upper_slices = offset(*this->upper_slices, min_width_top_surface);
|
||||
|
||||
|
|
|
@ -685,9 +685,9 @@ bool Preset::is_custom_defined()
|
|||
return false;
|
||||
}
|
||||
|
||||
bool Preset::is_bbl_vendor_preset(PresetBundle *preset_bundle)
|
||||
bool Preset::has_lidar(PresetBundle *preset_bundle)
|
||||
{
|
||||
bool is_bbl_vendor_preset = false;
|
||||
bool has_lidar = false;
|
||||
if (preset_bundle) {
|
||||
auto config = &preset_bundle->printers.get_edited_preset().config;
|
||||
std::string vendor_name;
|
||||
|
@ -700,9 +700,9 @@ bool Preset::is_bbl_vendor_preset(PresetBundle *preset_bundle)
|
|||
}
|
||||
}
|
||||
if (!vendor_name.empty())
|
||||
is_bbl_vendor_preset = vendor_name.compare("BBL") == 0 ? true : false;
|
||||
has_lidar = vendor_name.compare("BBL") == 0 ? true : false;
|
||||
}
|
||||
return is_bbl_vendor_preset;
|
||||
return has_lidar;
|
||||
}
|
||||
|
||||
static std::vector<std::string> s_Preset_print_options {
|
||||
|
|
|
@ -302,7 +302,7 @@ public:
|
|||
std::string get_current_printer_type(PresetBundle *preset_bundle); // get current preset type
|
||||
bool is_custom_defined();
|
||||
|
||||
bool is_bbl_vendor_preset(PresetBundle *preset_bundle);
|
||||
bool has_lidar(PresetBundle *preset_bundle);
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -187,7 +187,7 @@ void BackgroundSlicingProcess::process_fff()
|
|||
{
|
||||
assert(m_print == m_fff_print);
|
||||
PresetBundle &preset_bundle = *wxGetApp().preset_bundle;
|
||||
m_fff_print->is_BBL_printer() = preset_bundle.printers.get_edited_preset().is_bbl_vendor_preset(&preset_bundle);
|
||||
m_fff_print->is_BBL_printer() = preset_bundle.printers.get_edited_preset().has_lidar(&preset_bundle);
|
||||
//BBS: add the logic to process from an existed gcode file
|
||||
if (m_print->finished()) {
|
||||
BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << boost::format(" %1%: skip slicing, to process previous gcode file")%__LINE__;
|
||||
|
|
|
@ -5399,11 +5399,13 @@ bool GLCanvas3D::_render_arrange_menu(float left, float right, float bottom, flo
|
|||
|
||||
// only show this option if the printer has micro Lidar and can do first layer scan
|
||||
DynamicPrintConfig ¤t_config = wxGetApp().preset_bundle->printers.get_edited_preset().config;
|
||||
PresetBundle* preset_bundle = wxGetApp().preset_bundle;
|
||||
const bool has_lidar = preset_bundle->printers.get_edited_preset().has_lidar(preset_bundle);
|
||||
auto op = current_config.option("scan_first_layer");
|
||||
if (op && op->getBool()) {
|
||||
if (has_lidar && op && op->getBool()) {
|
||||
if (imgui->bbl_checkbox(_L("Avoid extrusion calibration region"), settings.avoid_extrusion_cali_region)) {
|
||||
settings_out.avoid_extrusion_cali_region = settings.avoid_extrusion_cali_region;
|
||||
appcfg->set("arrange", avoid_extrusion_key.c_str(), settings_out.avoid_extrusion_cali_region);
|
||||
appcfg->set("arrange", avoid_extrusion_key.c_str(), settings_out.avoid_extrusion_cali_region ? "1" : "0");
|
||||
settings_changed = true;
|
||||
}
|
||||
} else {
|
||||
|
|
|
@ -656,6 +656,13 @@ wxMenuItem* MenuFactory::append_menu_item_instance_to_object(wxMenu* menu)
|
|||
return menu_item;
|
||||
}
|
||||
|
||||
void MenuFactory::append_menu_item_fill_bed(wxMenu *menu)
|
||||
{
|
||||
append_menu_item(
|
||||
menu, wxID_ANY, _L("Fill bed with copies"), _L("Fill the remaining area of bed with copies of the selected object"),
|
||||
[](wxCommandEvent &) { plater()->fill_bed_with_instances(); }, "", nullptr, []() { return plater()->can_increase_instances(); }, m_parent);
|
||||
}
|
||||
|
||||
wxMenuItem* MenuFactory::append_menu_item_printable(wxMenu* menu)
|
||||
{
|
||||
// BBS: to be checked
|
||||
|
@ -1040,8 +1047,9 @@ void MenuFactory::create_object_menu()
|
|||
// "Add (volumes)" popupmenu will be added later in append_menu_items_add_volume()
|
||||
}
|
||||
|
||||
void MenuFactory::create_bbl_object_menu()
|
||||
void MenuFactory::create_extra_object_menu()
|
||||
{
|
||||
append_menu_item_fill_bed(&m_object_menu);
|
||||
// Object Clone
|
||||
append_menu_item_clone(&m_object_menu);
|
||||
// Object Repair
|
||||
|
@ -1262,7 +1270,7 @@ void MenuFactory::init(wxWindow* parent)
|
|||
create_sla_object_menu();
|
||||
//create_part_menu();
|
||||
|
||||
create_bbl_object_menu();
|
||||
create_extra_object_menu();
|
||||
create_bbl_part_menu();
|
||||
create_bbl_assemble_object_menu();
|
||||
create_bbl_assemble_part_menu();
|
||||
|
|
|
@ -108,7 +108,7 @@ private:
|
|||
//BBS: add part plate related logic
|
||||
void create_plate_menu();
|
||||
//BBS: add bbl object menu
|
||||
void create_bbl_object_menu();
|
||||
void create_extra_object_menu();
|
||||
void create_bbl_part_menu();
|
||||
void create_bbl_assemble_object_menu();
|
||||
void create_bbl_assemble_part_menu();
|
||||
|
@ -150,6 +150,7 @@ private:
|
|||
void append_menu_item_change_filament(wxMenu* menu);
|
||||
void append_menu_item_set_printable(wxMenu* menu);
|
||||
void append_menu_item_locked(wxMenu* menu);
|
||||
void append_menu_item_fill_bed(wxMenu *menu);
|
||||
|
||||
};
|
||||
|
||||
|
|
|
@ -3547,7 +3547,7 @@ void ObjectList::update_info_items(size_t obj_idx, wxDataViewItemArray* selectio
|
|||
|
||||
|
||||
|
||||
void ObjectList::add_object_to_list(size_t obj_idx, bool call_selection_changed, bool notify_partplate)
|
||||
void ObjectList::add_object_to_list(size_t obj_idx, bool call_selection_changed, bool notify_partplate, bool do_info_update)
|
||||
{
|
||||
auto model_object = (*m_objects)[obj_idx];
|
||||
//BBS start add obj_idx for debug
|
||||
|
@ -3564,6 +3564,9 @@ void ObjectList::add_object_to_list(size_t obj_idx, bool call_selection_changed,
|
|||
const auto item = m_objects_model->AddObject(model_object, warning_bitmap, model_object->is_cut());
|
||||
Expand(m_objects_model->GetParent(item));
|
||||
|
||||
if (!do_info_update)
|
||||
return;
|
||||
|
||||
update_info_items(obj_idx, nullptr, call_selection_changed);
|
||||
|
||||
add_volumes_to_object_in_list(obj_idx);
|
||||
|
|
|
@ -325,7 +325,7 @@ public:
|
|||
void part_selection_changed();
|
||||
|
||||
// Add object to the list
|
||||
void add_object_to_list(size_t obj_idx, bool call_selection_changed = true, bool notify_partplate = true);
|
||||
void add_object_to_list(size_t obj_idx, bool call_selection_changed = true, bool notify_partplate = true, bool do_info_update = true);
|
||||
// Add object's volumes to the list
|
||||
// Return selected items, if add_to_selection is defined
|
||||
wxDataViewItemArray add_volumes_to_object_in_list(size_t obj_idx, std::function<bool(const ModelVolume *)> add_to_selection = nullptr);
|
||||
|
|
|
@ -353,7 +353,7 @@ void ArrangeJob::prepare_partplate() {
|
|||
ModelObject* mo = model.objects[oidx];
|
||||
for (size_t inst_idx = 0; inst_idx < mo->instances.size(); ++inst_idx)
|
||||
{
|
||||
bool in_plate = plate->contain_instance(oidx, inst_idx);
|
||||
bool in_plate = plate->contain_instance(oidx, inst_idx) || plate->intersect_instance(oidx, inst_idx);
|
||||
ArrangePolygon&& ap = prepare_arrange_polygon(mo->instances[inst_idx]);
|
||||
|
||||
ArrangePolygons& cont = mo->instances[inst_idx]->printable ?
|
||||
|
@ -392,20 +392,7 @@ void ArrangeJob::prepare()
|
|||
NotificationManager::NotificationLevel::RegularNotificationLevel, _u8L("Arranging..."));
|
||||
m_plater->get_notification_manager()->bbl_close_plateinfo_notification();
|
||||
|
||||
{
|
||||
const GLCanvas3D::ArrangeSettings &settings = static_cast<const GLCanvas3D *>(m_plater->canvas3D())->get_arrange_settings();
|
||||
auto & print = wxGetApp().plater()->get_partplate_list().get_current_fff_print();
|
||||
|
||||
params.clearance_height_to_rod = print.config().extruder_clearance_height_to_rod.value;
|
||||
params.clearance_height_to_lid = print.config().extruder_clearance_height_to_lid.value;
|
||||
params.cleareance_radius = print.config().extruder_clearance_radius.value;
|
||||
params.printable_height = print.config().printable_height.value;
|
||||
params.allow_rotations = settings.enable_rotation;
|
||||
params.allow_multi_materials_on_same_plate = settings.allow_multi_materials_on_same_plate;
|
||||
params.avoid_extrusion_cali_region = settings.avoid_extrusion_cali_region;
|
||||
params.is_seq_print = settings.is_seq_print;
|
||||
params.min_obj_distance = scaled(settings.distance);
|
||||
}
|
||||
params = init_arrange_params(m_plater);
|
||||
|
||||
//BBS update extruder params and speed table before arranging
|
||||
Plater::setExtruderParams(Model::extruderParamsMap);
|
||||
|
@ -510,85 +497,27 @@ void ArrangeJob::process()
|
|||
auto & partplate_list = m_plater->get_partplate_list();
|
||||
auto& print = wxGetApp().plater()->get_partplate_list().get_current_fff_print();
|
||||
|
||||
if (params.is_seq_print)
|
||||
params.min_obj_distance = std::max(params.min_obj_distance, scaled(params.cleareance_radius + 0.001)); // +0.001mm to avoid clearance check fail due to rounding error
|
||||
|
||||
if (params.avoid_extrusion_cali_region && print.full_print_config().opt_bool("scan_first_layer"))
|
||||
const Slic3r::DynamicPrintConfig& global_config = wxGetApp().preset_bundle->full_config();
|
||||
PresetBundle* preset_bundle = wxGetApp().preset_bundle;
|
||||
const bool has_lidar = preset_bundle->printers.get_edited_preset().has_lidar(preset_bundle);
|
||||
if (has_lidar && params.avoid_extrusion_cali_region && global_config.opt_bool("scan_first_layer"))
|
||||
partplate_list.preprocess_nonprefered_areas(m_unselected, MAX_NUM_PLATES);
|
||||
|
||||
double skirt_distance = print.has_skirt() ? print.config().skirt_distance.value : 0;
|
||||
double brim_max = 0;
|
||||
std::for_each(m_selected.begin(), m_selected.end(), [&](ArrangePolygon ap) { brim_max = std::max(brim_max, ap.brim_width); });
|
||||
update_arrange_params(params, *m_plater, m_selected);
|
||||
update_selected_items_inflation(m_selected, *m_plater, params);
|
||||
update_unselected_items_inflation(m_unselected, *m_plater, params);
|
||||
|
||||
// Note: skirt_distance is now defined between outermost brim and skirt, not the object and skirt.
|
||||
// So we can't do max but do adding instead.
|
||||
params.brim_skirt_distance = skirt_distance + brim_max;
|
||||
params.bed_shrink_x = settings.bed_shrink_x + params.brim_skirt_distance;
|
||||
params.bed_shrink_y = settings.bed_shrink_y + params.brim_skirt_distance;
|
||||
// for sequential print, we need to inflate the bed because cleareance_radius is so large
|
||||
if (params.is_seq_print) {
|
||||
float shift_dist = params.cleareance_radius / 2 - 5;
|
||||
params.bed_shrink_x -= shift_dist;
|
||||
params.bed_shrink_y -= shift_dist;
|
||||
// dont forget to move the excluded region
|
||||
for (auto& region : m_unselected) {
|
||||
if (region.is_virt_object)
|
||||
region.poly.translate(-scaled(shift_dist), -scaled(shift_dist));
|
||||
}
|
||||
}
|
||||
|
||||
if (print.full_print_config().opt_bool("enable_support")) {
|
||||
params.bed_shrink_x = std::max(5.f, params.bed_shrink_x);
|
||||
params.bed_shrink_y = std::max(5.f, params.bed_shrink_y);
|
||||
params.min_obj_distance = std::max(scaled(10.0), params.min_obj_distance);
|
||||
}
|
||||
|
||||
// do not inflate brim_width. Objects are allowed to have overlapped brim.
|
||||
Points bedpts = get_bed_shape(*m_plater->config());
|
||||
BoundingBox bedbb = Polygon(bedpts).bounding_box();
|
||||
std::for_each(m_selected.begin(), m_selected.end(), [&](ArrangePolygon &ap) {
|
||||
ap.inflation = params.min_obj_distance / 2;
|
||||
BoundingBox apbb = ap.poly.contour.bounding_box();
|
||||
auto diffx = bedbb.size().x() - apbb.size().x() - 5;
|
||||
auto diffy = bedbb.size().y() - apbb.size().y() - 5;
|
||||
if (diffx > 0 && diffy > 0) {
|
||||
auto min_diff = std::min(diffx, diffy);
|
||||
ap.inflation = std::min(min_diff / 2, ap.inflation);
|
||||
}
|
||||
});
|
||||
// For occulusion regions, inflation should be larger to prevent genrating brim on them.
|
||||
// However, extrusion cali regions are exceptional, since we can allow brim overlaps them.
|
||||
// 屏蔽区域只需要膨胀brim宽度,防止brim长过去;挤出标定区域不需要膨胀,brim可以长过去。
|
||||
// 以前我们认为还需要膨胀clearance_radius/2,这其实是不需要的,因为这些区域并不会真的摆放物体,
|
||||
// 其他物体的膨胀轮廓是可以跟它们重叠的。
|
||||
Points bedpts = get_shrink_bedpts(*m_plater,params);
|
||||
double scaled_exclusion_gap = scale_(1);
|
||||
std::for_each(m_unselected.begin(), m_unselected.end(), [&](auto &ap) {
|
||||
ap.inflation = !ap.is_virt_object ?
|
||||
params.min_obj_distance / 2 :
|
||||
(ap.is_extrusion_cali_object ? 0 : scaled_exclusion_gap);
|
||||
});
|
||||
|
||||
|
||||
partplate_list.preprocess_exclude_areas(params.excluded_regions, 1, scaled_exclusion_gap);
|
||||
|
||||
// shrink bed by moving to center by dist
|
||||
auto shrinkFun = [](Points& bedpts, double dist, int direction) {
|
||||
#define SGN(x) ((x)>=0?1:-1)
|
||||
Point center = Polygon(bedpts).bounding_box().center();
|
||||
for (auto& pt : bedpts)
|
||||
pt[direction] += dist * SGN(center[direction] - pt[direction]);
|
||||
};
|
||||
shrinkFun(bedpts, scaled(params.bed_shrink_x), 0);
|
||||
shrinkFun(bedpts, scaled(params.bed_shrink_y), 1);
|
||||
|
||||
BOOST_LOG_TRIVIAL(debug) << "arrange bed_shrink_x=" << params.bed_shrink_x
|
||||
<< ", brim_max= "<<brim_max<<", "
|
||||
<< "; bedpts:" << bedpts[0].transpose() << ", " << bedpts[1].transpose() << ", " << bedpts[2].transpose() << ", " << bedpts[3].transpose();
|
||||
|
||||
params.stopcondition = [this]() { return was_canceled(); };
|
||||
|
||||
params.progressind = [this](unsigned num_finished, std::string str="") {
|
||||
update_status(num_finished, _L("Arranging") + " " + str);
|
||||
params.progressind = [this](unsigned num_finished, std::string str = "") {
|
||||
update_status(num_finished, _L("Arranging") + " "+ wxString::FromUTF8(str));
|
||||
};
|
||||
|
||||
{
|
||||
|
@ -765,8 +694,8 @@ void ArrangeJob::finalize() {
|
|||
std::optional<arrangement::ArrangePolygon>
|
||||
get_wipe_tower_arrangepoly(const Plater &plater)
|
||||
{
|
||||
// BBS FIXME: use actual plate_idx
|
||||
if (auto wti = get_wipe_tower(plater, 0))
|
||||
int id = plater.canvas3D()->fff_print()->get_plate_index();
|
||||
if (auto wti = get_wipe_tower(plater, id))
|
||||
return get_wipetower_arrange_poly(&wti);
|
||||
|
||||
return {};
|
||||
|
@ -775,12 +704,12 @@ get_wipe_tower_arrangepoly(const Plater &plater)
|
|||
//BBS: add sudoku-style stride
|
||||
double bed_stride_x(const Plater* plater) {
|
||||
double bedwidth = plater->build_volume().bounding_box().size().x();
|
||||
return scaled<double>((1. + LOGICAL_BED_GAP) * bedwidth);
|
||||
return (1. + LOGICAL_BED_GAP) * bedwidth;
|
||||
}
|
||||
|
||||
double bed_stride_y(const Plater* plater) {
|
||||
double beddepth = plater->build_volume().bounding_box().size().y();
|
||||
return scaled<double>((1. + LOGICAL_BED_GAP) * beddepth);
|
||||
return (1. + LOGICAL_BED_GAP) * beddepth;
|
||||
}
|
||||
|
||||
|
||||
|
@ -800,4 +729,107 @@ arrangement::ArrangeParams get_arrange_params(Plater *p)
|
|||
return params;
|
||||
}
|
||||
|
||||
// call before get selected and unselected
|
||||
arrangement::ArrangeParams init_arrange_params(Plater *p)
|
||||
{
|
||||
arrangement::ArrangeParams params;
|
||||
const GLCanvas3D::ArrangeSettings &settings = static_cast<const GLCanvas3D *>(p->canvas3D())->get_arrange_settings();
|
||||
auto & print = wxGetApp().plater()->get_partplate_list().get_current_fff_print();
|
||||
|
||||
params.clearance_height_to_rod = print.config().extruder_clearance_height_to_rod.value;
|
||||
params.clearance_height_to_lid = print.config().extruder_clearance_height_to_lid.value;
|
||||
params.cleareance_radius = print.config().extruder_clearance_radius.value;
|
||||
params.printable_height = print.config().printable_height.value;
|
||||
params.allow_rotations = settings.enable_rotation;
|
||||
params.allow_multi_materials_on_same_plate = settings.allow_multi_materials_on_same_plate;
|
||||
params.avoid_extrusion_cali_region = settings.avoid_extrusion_cali_region;
|
||||
params.is_seq_print = settings.is_seq_print;
|
||||
params.min_obj_distance = scaled(settings.distance);
|
||||
params.bed_shrink_x = settings.bed_shrink_x;
|
||||
params.bed_shrink_y = settings.bed_shrink_y;
|
||||
|
||||
int state = p->get_prepare_state();
|
||||
if (state == Job::JobPrepareState::PREPARE_STATE_MENU) {
|
||||
PartPlateList &plate_list = p->get_partplate_list();
|
||||
PartPlate * plate = plate_list.get_curr_plate();
|
||||
params.is_seq_print = plate->get_real_print_seq() == PrintSequence::ByObject;
|
||||
}
|
||||
|
||||
if (params.is_seq_print)
|
||||
params.min_obj_distance = std::max(params.min_obj_distance, scaled(params.cleareance_radius + 0.001)); // +0.001mm to avoid clearance check fail due to rounding error
|
||||
return params;
|
||||
}
|
||||
|
||||
//after get selected.call this to update bed_shrink
|
||||
void update_arrange_params(arrangement::ArrangeParams ¶ms, const Plater &p, const arrangement::ArrangePolygons &selected)
|
||||
{
|
||||
const GLCanvas3D::ArrangeSettings &settings = static_cast<const GLCanvas3D *>(p.canvas3D())->get_arrange_settings();
|
||||
auto & print = wxGetApp().plater()->get_partplate_list().get_current_fff_print();
|
||||
double skirt_distance = print.has_skirt() ? print.config().skirt_distance.value : 0;
|
||||
double brim_max = 0;
|
||||
std::for_each(selected.begin(), selected.end(), [&](const ArrangePolygon &ap) { brim_max = std::max(brim_max, ap.brim_width); });
|
||||
// Note: skirt_distance is now defined between outermost brim and skirt, not the object and skirt.
|
||||
// So we can't do max but do adding instead.
|
||||
params.brim_skirt_distance = skirt_distance + brim_max;
|
||||
params.bed_shrink_x = settings.bed_shrink_x + params.brim_skirt_distance;
|
||||
params.bed_shrink_y = settings.bed_shrink_y + params.brim_skirt_distance;
|
||||
// for sequential print, we need to inflate the bed because cleareance_radius is so large
|
||||
if (params.is_seq_print) {
|
||||
float shift_dist = params.cleareance_radius / 2 - 5;
|
||||
params.bed_shrink_x -= shift_dist;
|
||||
params.bed_shrink_y -= shift_dist;
|
||||
}
|
||||
}
|
||||
|
||||
//it will bed accurate after call update_params
|
||||
Points get_shrink_bedpts(const Plater &plater, const arrangement::ArrangeParams ¶ms)
|
||||
{
|
||||
Points bedpts = get_bed_shape(*plater.config());
|
||||
// shrink bed by moving to center by dist
|
||||
auto shrinkFun = [](Points &bedpts, double dist, int direction) {
|
||||
#define SGN(x) ((x) >= 0 ? 1 : -1)
|
||||
Point center = Polygon(bedpts).bounding_box().center();
|
||||
for (auto &pt : bedpts) pt[direction] += dist * SGN(center[direction] - pt[direction]);
|
||||
};
|
||||
shrinkFun(bedpts, scaled(params.bed_shrink_x), 0);
|
||||
shrinkFun(bedpts, scaled(params.bed_shrink_y), 1);
|
||||
return bedpts;
|
||||
}
|
||||
|
||||
void update_selected_items_inflation(arrangement::ArrangePolygons &selected, const Plater &p, const arrangement::ArrangeParams ¶ms) {
|
||||
// do not inflate brim_width. Objects are allowed to have overlapped brim.
|
||||
Points bedpts = get_shrink_bedpts(p, params);
|
||||
BoundingBox bedbb = Polygon(bedpts).bounding_box();
|
||||
std::for_each(selected.begin(), selected.end(), [&](ArrangePolygon &ap) {
|
||||
ap.inflation = std::max(scaled(ap.brim_width), params.min_obj_distance / 2);
|
||||
BoundingBox apbb = ap.poly.contour.bounding_box();
|
||||
auto diffx = bedbb.size().x() - apbb.size().x() - 5;
|
||||
auto diffy = bedbb.size().y() - apbb.size().y() - 5;
|
||||
if (diffx > 0 && diffy > 0) {
|
||||
auto min_diff = std::min(diffx, diffy);
|
||||
ap.inflation = std::min(min_diff / 2, ap.inflation);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
void update_unselected_items_inflation(arrangement::ArrangePolygons &unselected, const Plater &p, const arrangement::ArrangeParams ¶ms)
|
||||
{
|
||||
if (params.is_seq_print) {
|
||||
float shift_dist = params.cleareance_radius / 2 - 5;
|
||||
// dont forget to move the excluded region
|
||||
for (auto ®ion : unselected) {
|
||||
if (region.is_virt_object) region.poly.translate(-scaled(shift_dist), -scaled(shift_dist));
|
||||
}
|
||||
}
|
||||
// For occulusion regions, inflation should be larger to prevent genrating brim on them.
|
||||
// However, extrusion cali regions are exceptional, since we can allow brim overlaps them.
|
||||
// 屏蔽区域只需要膨胀brim宽度,防止brim长过去;挤出标定区域不需要膨胀,brim可以长过去。
|
||||
// 以前我们认为还需要膨胀clearance_radius/2,这其实是不需要的,因为这些区域并不会真的摆放物体,
|
||||
// 其他物体的膨胀轮廓是可以跟它们重叠的。
|
||||
double scaled_exclusion_gap = scale_(1);
|
||||
std::for_each(unselected.begin(), unselected.end(),
|
||||
[&](auto &ap) { ap.inflation = !ap.is_virt_object ? std::max(scaled(ap.brim_width), params.min_obj_distance / 2)
|
||||
: (ap.is_extrusion_cali_object ? 0 : scaled_exclusion_gap); });
|
||||
}
|
||||
|
||||
}} // namespace Slic3r::GUI
|
||||
|
|
|
@ -78,6 +78,16 @@ double bed_stride_y(const Plater* plater);
|
|||
|
||||
arrangement::ArrangeParams get_arrange_params(Plater *p);
|
||||
|
||||
arrangement::ArrangeParams init_arrange_params(Plater *p);
|
||||
|
||||
Points get_shrink_bedpts(const Plater& plater,const arrangement::ArrangeParams& params);
|
||||
|
||||
void update_arrange_params(arrangement::ArrangeParams ¶ms, const Plater &p, const arrangement::ArrangePolygons &selected);
|
||||
|
||||
void update_selected_items_inflation(arrangement::ArrangePolygons &selected, const Plater &p, const arrangement::ArrangeParams ¶ms);
|
||||
|
||||
void update_unselected_items_inflation(arrangement::ArrangePolygons &unselected, const Plater &p, const arrangement::ArrangeParams ¶ms);
|
||||
|
||||
}} // namespace Slic3r::GUI
|
||||
|
||||
#endif // ARRANGEJOB_HPP
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
#include "slic3r/GUI/Plater.hpp"
|
||||
#include "slic3r/GUI/GLCanvas3D.hpp"
|
||||
#include "slic3r/GUI/GUI_ObjectList.hpp"
|
||||
#include "libnest2d/common.hpp"
|
||||
|
||||
#include <numeric>
|
||||
|
||||
|
@ -22,6 +23,8 @@ void FillBedJob::prepare()
|
|||
m_unselected.clear();
|
||||
m_bedpts.clear();
|
||||
|
||||
params = init_arrange_params(m_plater);
|
||||
|
||||
m_object_idx = m_plater->get_selected_object_idx();
|
||||
if (m_object_idx == -1)
|
||||
return;
|
||||
|
@ -42,6 +45,7 @@ void FillBedJob::prepare()
|
|||
ModelObject *model_object = m_plater->model().objects[m_object_idx];
|
||||
if (model_object->instances.empty()) return;
|
||||
|
||||
const Slic3r::DynamicPrintConfig& global_config = wxGetApp().preset_bundle->full_config();
|
||||
m_selected.reserve(model_object->instances.size());
|
||||
for (size_t oidx = 0; oidx < model.objects.size(); ++oidx)
|
||||
{
|
||||
|
@ -50,7 +54,7 @@ void FillBedJob::prepare()
|
|||
{
|
||||
bool selected = (oidx == m_object_idx);
|
||||
|
||||
ArrangePolygon ap = get_arrange_poly(mo->instances[inst_idx]);
|
||||
ArrangePolygon ap = get_instance_arrange_poly(mo->instances[inst_idx], global_config);
|
||||
BoundingBox ap_bb = ap.transformed_poly().contour.bounding_box();
|
||||
ap.height = 1;
|
||||
ap.name = mo->name;
|
||||
|
@ -117,6 +121,8 @@ void FillBedJob::prepare()
|
|||
if (m_selected.empty()) return;
|
||||
|
||||
//add the virtual object into unselect list if has
|
||||
double scaled_exclusion_gap = scale_(1);
|
||||
plate_list.preprocess_exclude_areas(params.excluded_regions, 1, scaled_exclusion_gap);
|
||||
plate_list.preprocess_exclude_areas(m_unselected);
|
||||
|
||||
m_bedpts = get_bed_shape(*m_plater->config());
|
||||
|
@ -134,14 +140,15 @@ void FillBedJob::prepare()
|
|||
ap.bed_idx = arrangement::UNARRANGED;
|
||||
|
||||
m_unselected.emplace_back(ap);
|
||||
}
|
||||
|
||||
}*/
|
||||
if (auto wt = get_wipe_tower_arrangepoly(*m_plater))
|
||||
m_unselected.emplace_back(std::move(*wt));*/
|
||||
m_unselected.emplace_back(std::move(*wt));
|
||||
|
||||
double sc = scaled<double>(1.) * scaled(1.);
|
||||
|
||||
ExPolygon poly = m_selected.front().poly;
|
||||
const GLCanvas3D::ArrangeSettings& settings = static_cast<const GLCanvas3D*>(m_plater->canvas3D())->get_arrange_settings();
|
||||
auto polys = offset_ex(m_selected.front().poly, scaled(settings.distance) / 2);
|
||||
ExPolygon poly = polys.empty() ? m_selected.front().poly : polys.front();
|
||||
double poly_area = poly.area() / sc;
|
||||
double unsel_area = std::accumulate(m_unselected.begin(),
|
||||
m_unselected.end(), 0.,
|
||||
|
@ -161,7 +168,7 @@ void FillBedJob::prepare()
|
|||
// if the selection is not a single instance, choose the first as template
|
||||
//sel_id = std::max(sel_id, 0);
|
||||
ModelInstance *mi = model_object->instances[sel_id];
|
||||
ArrangePolygon template_ap = get_arrange_poly(mi);
|
||||
ArrangePolygon template_ap = get_instance_arrange_poly(mi, global_config);
|
||||
|
||||
for (int i = 0; i < needed_items; ++i) {
|
||||
ArrangePolygon ap = template_ap;
|
||||
|
@ -171,8 +178,10 @@ void FillBedJob::prepare()
|
|||
ap.itemid = -1;
|
||||
ap.setter = [this, mi](const ArrangePolygon &p) {
|
||||
ModelObject *mo = m_plater->model().objects[m_object_idx];
|
||||
ModelInstance *inst = mo->add_instance(*mi);
|
||||
inst->apply_arrange_result(p.translation.cast<double>(), p.rotation);
|
||||
ModelObject* newObj = m_plater->model().add_object(*mo);
|
||||
newObj->name = mo->name +" "+ std::to_string(p.itemid);
|
||||
for (ModelInstance *newInst : newObj->instances) { newInst->apply_arrange_result(p.translation.cast<double>(), p.rotation); }
|
||||
//m_plater->sidebar().obj_list()->paste_objects_into_list({m_plater->model().objects.size()-1});
|
||||
};
|
||||
m_selected.emplace_back(ap);
|
||||
}
|
||||
|
@ -196,9 +205,19 @@ void FillBedJob::process()
|
|||
const GLCanvas3D::ArrangeSettings &settings =
|
||||
static_cast<const GLCanvas3D*>(m_plater->canvas3D())->get_arrange_settings();
|
||||
|
||||
arrangement::ArrangeParams params;
|
||||
params.allow_rotations = settings.enable_rotation;
|
||||
params.min_obj_distance = scaled(settings.distance);
|
||||
update_arrange_params(params, *m_plater, m_selected);
|
||||
m_bedpts = get_shrink_bedpts(*m_plater, params);
|
||||
|
||||
auto &partplate_list = m_plater->get_partplate_list();
|
||||
auto &print = wxGetApp().plater()->get_partplate_list().get_current_fff_print();
|
||||
const Slic3r::DynamicPrintConfig& global_config = wxGetApp().preset_bundle->full_config();
|
||||
PresetBundle* preset_bundle = wxGetApp().preset_bundle;
|
||||
const bool has_lidar = preset_bundle->printers.get_edited_preset().has_lidar(preset_bundle);
|
||||
if (has_lidar && params.avoid_extrusion_cali_region && global_config.opt_bool("scan_first_layer"))
|
||||
partplate_list.preprocess_nonprefered_areas(m_unselected, MAX_NUM_PLATES);
|
||||
|
||||
update_selected_items_inflation(m_selected, *m_plater, params);
|
||||
update_unselected_items_inflation(m_unselected, *m_plater, params);
|
||||
|
||||
bool do_stop = false;
|
||||
params.stopcondition = [this, &do_stop]() {
|
||||
|
@ -206,20 +225,22 @@ void FillBedJob::process()
|
|||
};
|
||||
|
||||
params.progressind = [this](unsigned st,std::string str="") {
|
||||
// if (st > 0)
|
||||
// update_status(int(m_status_range - st), _L("Filling bed " + str));
|
||||
if (st > 0)
|
||||
update_status(st, _L("Filling bed " + str));
|
||||
};
|
||||
|
||||
params.on_packed = [&do_stop] (const ArrangePolygon &ap) {
|
||||
do_stop = ap.bed_idx > 0 && ap.priority == 0;
|
||||
};
|
||||
// final align用的是凸包,在有fixed item的情况下可能找到的参考点位置是错的,这里就不做了。见STUDIO-3265
|
||||
params.do_final_align = !has_lidar;
|
||||
|
||||
arrangement::arrange(m_selected, m_unselected, m_bedpts, params);
|
||||
|
||||
// finalize just here.
|
||||
// update_status(m_status_range, was_canceled() ?
|
||||
// _(L("Bed filling canceled.")) :
|
||||
// _(L("Bed filling done.")));
|
||||
update_status(m_status_range, was_canceled() ?
|
||||
_(L("Bed filling canceled.")) :
|
||||
_(L("Bed filling done.")));
|
||||
}
|
||||
|
||||
void FillBedJob::finalize()
|
||||
|
@ -243,11 +264,14 @@ void FillBedJob::finalize()
|
|||
return s + int(ap.priority == 0 && ap.bed_idx == 0);
|
||||
});
|
||||
|
||||
int oldSize = m_plater->model().objects.size();
|
||||
|
||||
if (added_cnt > 0) {
|
||||
//BBS: adjust the selected instances
|
||||
for (ArrangePolygon& ap : m_selected) {
|
||||
if (ap.bed_idx != 0) {
|
||||
if (ap.itemid == -1)
|
||||
BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(":skipped: bed_id %1%, trans {%2%,%3%}") % ap.bed_idx % unscale<double>(ap.translation(X)) % unscale<double>(ap.translation(Y));
|
||||
/*if (ap.itemid == -1)*/
|
||||
continue;
|
||||
ap.bed_idx = plate_list.get_plate_count();
|
||||
}
|
||||
|
@ -263,33 +287,24 @@ void FillBedJob::finalize()
|
|||
|
||||
BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(":selected: bed_id %1%, trans {%2%,%3%}") % ap.bed_idx % unscale<double>(ap.translation(X)) % unscale<double>(ap.translation(Y));
|
||||
}
|
||||
for (size_t inst_idx = 0; inst_idx < model_object->instances.size(); ++inst_idx)
|
||||
{
|
||||
plate_list.notify_instance_update(m_object_idx, inst_idx);
|
||||
|
||||
int newSize = m_plater->model().objects.size();
|
||||
auto obj_list = m_plater->sidebar().obj_list();
|
||||
for (size_t i = oldSize; i < newSize; i++) {
|
||||
obj_list->add_object_to_list(i, true, true, false);
|
||||
}
|
||||
|
||||
BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << ": paste_objects_into_list";
|
||||
|
||||
/*for (ArrangePolygon& ap : m_selected) {
|
||||
if (ap.bed_idx != arrangement::UNARRANGED && (ap.priority != 0 || ap.bed_idx == 0))
|
||||
ap.apply();
|
||||
}*/
|
||||
|
||||
model_object->ensure_on_bed();
|
||||
//model_object->ensure_on_bed();
|
||||
//BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << ": model_object->ensure_on_bed()";
|
||||
|
||||
m_plater->update();
|
||||
|
||||
//BBS: add partplate related logic
|
||||
int added_cnt = std::accumulate(m_selected.begin(), m_selected.end(), 0,
|
||||
[cur_plate](int s, auto& ap) {
|
||||
return s + int(ap.priority == 0 && ap.bed_idx == cur_plate);
|
||||
//return s + int(ap.priority == 0 && ap.bed_idx == 0);
|
||||
});
|
||||
|
||||
// FIXME: somebody explain why this is needed for increase_object_instances
|
||||
if (inst_cnt == 1) added_cnt++;
|
||||
|
||||
if (added_cnt > 0)
|
||||
m_plater->sidebar()
|
||||
.obj_list()->increase_object_instances(m_object_idx, size_t(added_cnt));
|
||||
}
|
||||
|
||||
Job::finalize();
|
||||
|
|
|
@ -21,6 +21,8 @@ class FillBedJob : public PlaterJob
|
|||
|
||||
Points m_bedpts;
|
||||
|
||||
arrangement::ArrangeParams params;
|
||||
|
||||
int m_status_range = 0;
|
||||
|
||||
protected:
|
||||
|
|
|
@ -549,7 +549,7 @@ DPIFrame(NULL, wxID_ANY, "", wxDefaultPosition, wxDefaultSize, BORDERLESS_FRAME_
|
|||
m_print_btn->Enable(m_print_enable);
|
||||
if (m_print_enable) {
|
||||
PresetBundle &preset_bundle = *wxGetApp().preset_bundle;
|
||||
if (preset_bundle.printers.get_edited_preset().is_bbl_vendor_preset(&preset_bundle))
|
||||
if (preset_bundle.printers.get_edited_preset().has_lidar(&preset_bundle))
|
||||
wxPostEvent(m_plater, SimpleEvent(EVT_GLTOOLBAR_PRINT_PLATE));
|
||||
else
|
||||
wxPostEvent(m_plater, SimpleEvent(EVT_GLTOOLBAR_SEND_GCODE));
|
||||
|
@ -907,7 +907,7 @@ void MainFrame::init_tabpanel() {
|
|||
int old_sel = e.GetOldSelection();
|
||||
int new_sel = e.GetSelection();
|
||||
if (wxGetApp().preset_bundle &&
|
||||
wxGetApp().preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(wxGetApp().preset_bundle) &&
|
||||
wxGetApp().preset_bundle->printers.get_edited_preset().has_lidar(wxGetApp().preset_bundle) &&
|
||||
new_sel == tpMonitor) {
|
||||
if (!wxGetApp().getAgent()) {
|
||||
e.Veto();
|
||||
|
@ -1505,7 +1505,7 @@ wxBoxSizer* MainFrame::create_side_tools()
|
|||
SidePopup* p = new SidePopup(this);
|
||||
|
||||
if (wxGetApp().preset_bundle
|
||||
&& !wxGetApp().preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(wxGetApp().preset_bundle)) {
|
||||
&& !wxGetApp().preset_bundle->printers.get_edited_preset().has_lidar(wxGetApp().preset_bundle)) {
|
||||
// ThirdParty Buttons
|
||||
SideButton* export_gcode_btn = new SideButton(p, _L("Export G-code file"), "");
|
||||
export_gcode_btn->SetCornerRadius(0);
|
||||
|
@ -3410,7 +3410,7 @@ void MainFrame::load_printer_url(wxString url)
|
|||
void MainFrame::load_printer_url()
|
||||
{
|
||||
PresetBundle &preset_bundle = *wxGetApp().preset_bundle;
|
||||
if (preset_bundle.printers.get_edited_preset().is_bbl_vendor_preset(&preset_bundle))
|
||||
if (preset_bundle.printers.get_edited_preset().has_lidar(&preset_bundle))
|
||||
return;
|
||||
|
||||
auto cfg = preset_bundle.printers.get_edited_preset().config;
|
||||
|
|
|
@ -23,7 +23,7 @@ PlateSettingsDialog::PlateSettingsDialog(wxWindow* parent, wxWindowID id, const
|
|||
top_sizer->SetFlexibleDirection(wxBOTH);
|
||||
top_sizer->SetNonFlexibleGrowMode(wxFLEX_GROWMODE_SPECIFIED);
|
||||
|
||||
bool is_bbl = wxGetApp().preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(wxGetApp().preset_bundle);
|
||||
bool is_bbl = wxGetApp().preset_bundle->printers.get_edited_preset().has_lidar(wxGetApp().preset_bundle);
|
||||
if (is_bbl) {
|
||||
m_bed_type_choice = new ComboBox(this, wxID_ANY, wxEmptyString, wxDefaultPosition, wxSize(FromDIP(240), -1), 0,
|
||||
NULL, wxCB_READONLY);
|
||||
|
|
|
@ -1024,7 +1024,7 @@ void Sidebar::update_all_preset_comboboxes()
|
|||
PresetBundle &preset_bundle = *wxGetApp().preset_bundle;
|
||||
const auto print_tech = preset_bundle.printers.get_edited_preset().printer_technology();
|
||||
|
||||
bool is_bbl_preset = preset_bundle.printers.get_edited_preset().is_bbl_vendor_preset(&preset_bundle);
|
||||
bool is_bbl_preset = preset_bundle.printers.get_edited_preset().has_lidar(&preset_bundle);
|
||||
|
||||
auto p_mainframe = wxGetApp().mainframe;
|
||||
|
||||
|
@ -8183,7 +8183,7 @@ void Plater::_calib_pa_pattern(const Calib_Params& params)
|
|||
|
||||
const DynamicPrintConfig full_config = wxGetApp().preset_bundle->full_config();
|
||||
PresetBundle* preset_bundle = wxGetApp().preset_bundle;
|
||||
const bool is_bbl_machine = preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(preset_bundle);
|
||||
const bool is_bbl_machine = preset_bundle->printers.get_edited_preset().has_lidar(preset_bundle);
|
||||
const Vec3d plate_origin = get_partplate_list().get_current_plate_origin();
|
||||
CalibPressureAdvancePattern pa_pattern(
|
||||
params,
|
||||
|
@ -10403,7 +10403,7 @@ void Plater::reslice()
|
|||
|
||||
model().calib_pa_pattern->generate_custom_gcodes(
|
||||
wxGetApp().preset_bundle->full_config(),
|
||||
preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(preset_bundle),
|
||||
preset_bundle->printers.get_edited_preset().has_lidar(preset_bundle),
|
||||
model(),
|
||||
get_partplate_list().get_current_plate_origin()
|
||||
);
|
||||
|
|
|
@ -1039,7 +1039,7 @@ void PlaterPresetComboBox::update()
|
|||
//if (i + 1 == m_collection->num_default_presets())
|
||||
// set_label_marker(Append(separator(L("System presets")), wxNullBitmap));
|
||||
}
|
||||
if (m_type == Preset::TYPE_FILAMENT && m_preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(m_preset_bundle))
|
||||
if (m_type == Preset::TYPE_FILAMENT && m_preset_bundle->printers.get_edited_preset().has_lidar(m_preset_bundle))
|
||||
add_ams_filaments(into_u8(selected_user_preset), true);
|
||||
|
||||
//BBS: add project embedded preset logic
|
||||
|
@ -1267,7 +1267,7 @@ void TabPresetComboBox::update()
|
|||
// set_label_marker(Append(separator(L("System presets")), wxNullBitmap));
|
||||
}
|
||||
|
||||
if (m_type == Preset::TYPE_FILAMENT && m_preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(m_preset_bundle))
|
||||
if (m_type == Preset::TYPE_FILAMENT && m_preset_bundle->printers.get_edited_preset().has_lidar(m_preset_bundle))
|
||||
add_ams_filaments(into_u8(selected));
|
||||
|
||||
//BBS: add project embedded preset logic
|
||||
|
|
|
@ -1644,9 +1644,9 @@ void Tab::on_presets_changed()
|
|||
// Instead of PostEvent (EVT_TAB_PRESETS_CHANGED) just call update_presets
|
||||
wxGetApp().plater()->sidebar().update_presets(m_type);
|
||||
|
||||
bool is_bbl_vendor_preset = wxGetApp().preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(wxGetApp().preset_bundle);
|
||||
bool has_lidar = wxGetApp().preset_bundle->printers.get_edited_preset().has_lidar(wxGetApp().preset_bundle);
|
||||
auto& printer_cfg = wxGetApp().preset_bundle->printers.get_edited_preset().config;
|
||||
if (is_bbl_vendor_preset)
|
||||
if (has_lidar)
|
||||
wxGetApp().plater()->get_partplate_list().set_render_option(
|
||||
!printer_cfg.option<ConfigOptionBool>("bbl_calib_mark_logo")->value, true);
|
||||
else
|
||||
|
@ -2873,7 +2873,7 @@ void TabFilament::toggle_options()
|
|||
bool is_BBL_printer = false;
|
||||
if (m_preset_bundle) {
|
||||
is_BBL_printer =
|
||||
m_preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(
|
||||
m_preset_bundle->printers.get_edited_preset().has_lidar(
|
||||
m_preset_bundle);
|
||||
}
|
||||
|
||||
|
@ -3669,7 +3669,7 @@ void TabPrinter::toggle_options()
|
|||
//BBS: whether the preset is Bambu Lab printer
|
||||
bool is_BBL_printer = false;
|
||||
if (m_preset_bundle) {
|
||||
is_BBL_printer = m_preset_bundle->printers.get_edited_preset().is_bbl_vendor_preset(m_preset_bundle);
|
||||
is_BBL_printer = m_preset_bundle->printers.get_edited_preset().has_lidar(m_preset_bundle);
|
||||
}
|
||||
|
||||
bool have_multiple_extruders = true;
|
||||
|
|
Loading…
Reference in a new issue