diff --git a/src/libslic3r/Format/bbs_3mf.cpp b/src/libslic3r/Format/bbs_3mf.cpp index 3a7d35b72d..1a6ecb81dd 100644 --- a/src/libslic3r/Format/bbs_3mf.cpp +++ b/src/libslic3r/Format/bbs_3mf.cpp @@ -235,6 +235,7 @@ static constexpr const char* FIRST_TRIANGLE_ID_ATTR = "firstid"; static constexpr const char* LAST_TRIANGLE_ID_ATTR = "lastid"; static constexpr const char* SUBTYPE_ATTR = "subtype"; static constexpr const char* LOCK_ATTR = "locked"; +static constexpr const char* BED_TYPE_ATTR = "bed_type"; static constexpr const char* GCODE_FILE_ATTR = "gcode_file"; static constexpr const char* THUMBNAIL_FILE_ATTR = "thumbnail_file"; static constexpr const char* PATTERN_FILE_ATTR = "pattern_file"; @@ -3131,6 +3132,12 @@ void PlateData::parse_filament_info(GCodeProcessorResult *result) { std::istringstream(value) >> std::boolalpha >> m_curr_plater->locked; } + else if (key == BED_TYPE_ATTR) + { + BedType bed_type = BedType::btPC; + ConfigOptionEnum::from_string(value, bed_type); + m_curr_plater->config.set_key_value("curr_bed_type", new ConfigOptionEnum(bed_type)); + } else if (key == GCODE_FILE_ATTR) { m_curr_plater->gcode_file = value; @@ -5563,6 +5570,11 @@ void PlateData::parse_filament_info(GCodeProcessorResult *result) //plate index stream << " <" << METADATA_TAG << " " << KEY_ATTR << "=\"" << PLATERID_ATTR << "\" " << VALUE_ATTR << "=\"" << plate_data->plate_index + 1 << "\"/>\n"; stream << " <" << METADATA_TAG << " " << KEY_ATTR << "=\"" << LOCK_ATTR << "\" " << VALUE_ATTR << "=\"" << std::boolalpha<< plate_data->locked<< "\"/>\n"; + ConfigOption* bed_type_opt = plate_data->config.option("curr_bed_type"); + t_config_enum_names bed_type_names = ConfigOptionEnum::get_enum_names(); + if (bed_type_opt != nullptr && bed_type_names.size() > bed_type_opt->getInt()) + stream << " <" << METADATA_TAG << " " << KEY_ATTR << "=\"" << BED_TYPE_ATTR << "\" " << VALUE_ATTR << "=\"" << bed_type_names[bed_type_opt->getInt()] << "\"/>\n"; + if (save_gcode) stream << " <" << METADATA_TAG << " " << KEY_ATTR << "=\"" << GCODE_FILE_ATTR << "\" " << VALUE_ATTR << "=\"" << std::boolalpha << xml_escape(plate_data->gcode_file) << "\"/>\n"; if (!plate_data->gcode_file.empty()) { diff --git a/src/libslic3r/Format/bbs_3mf.hpp b/src/libslic3r/Format/bbs_3mf.hpp index 07d55f8976..43734bd391 100644 --- a/src/libslic3r/Format/bbs_3mf.hpp +++ b/src/libslic3r/Format/bbs_3mf.hpp @@ -67,6 +67,7 @@ struct PlateData std::string gcode_prediction; std::string gcode_weight; std::vector slice_filaments_info; + DynamicPrintConfig config; bool is_sliced_valid = false; bool toolpath_outside {false}; diff --git a/src/libslic3r/PrintConfig.cpp b/src/libslic3r/PrintConfig.cpp index 9b902f24b9..eabc89fc9e 100644 --- a/src/libslic3r/PrintConfig.cpp +++ b/src/libslic3r/PrintConfig.cpp @@ -564,7 +564,7 @@ void PrintConfigDef::init_fff_params() def->max = 120; def->set_default_value(new ConfigOptionInts{45}); - def = this->add("curr_bed_type", coEnums); + def = this->add("curr_bed_type", coEnum); def->label = L("Bed type"); def->tooltip = L("Bed types supported by the printer"); def->mode = comSimple; diff --git a/src/slic3r/GUI/BackgroundSlicingProcess.cpp b/src/slic3r/GUI/BackgroundSlicingProcess.cpp index 6da922ce48..4f62c33e63 100644 --- a/src/slic3r/GUI/BackgroundSlicingProcess.cpp +++ b/src/slic3r/GUI/BackgroundSlicingProcess.cpp @@ -654,7 +654,10 @@ Print::ApplyStatus BackgroundSlicingProcess::apply(const Model &model, const Dyn { assert(m_print != nullptr); assert(config.opt_enum("printer_technology") == m_print->technology()); - Print::ApplyStatus invalidated = m_print->apply(model, config); + // TODO: add partplate config + DynamicPrintConfig new_config = config; + new_config.apply(*m_current_plate->config()); + Print::ApplyStatus invalidated = m_print->apply(model, new_config); if ((invalidated & PrintBase::APPLY_STATUS_INVALIDATED) != 0 && m_print->technology() == ptFFF && !m_fff_print->is_step_done(psGCodeExport)) { // Some FFF status was invalidated, and the G-code was not exported yet. diff --git a/src/slic3r/GUI/GUI_ObjectList.cpp b/src/slic3r/GUI/GUI_ObjectList.cpp index e14d69b37e..78e152d031 100644 --- a/src/slic3r/GUI/GUI_ObjectList.cpp +++ b/src/slic3r/GUI/GUI_ObjectList.cpp @@ -4036,11 +4036,18 @@ void ObjectList::select_items(const std::vector& ov_ids) void ObjectList::select_items(const wxDataViewItemArray& sels) { m_prevent_list_events = true; - m_last_selected_item = sels.empty() ? wxDataViewItem(nullptr) : sels.back(); UnselectAll(); - SetSelections(sels); + + if (!sels.empty()) { + SetSelections(sels); + } + else { + int curr_plate_idx = wxGetApp().plater()->get_partplate_list().get_curr_plate_index(); + on_plate_selected(curr_plate_idx); + } + part_selection_changed(); m_prevent_list_events = false; diff --git a/src/slic3r/GUI/PartPlate.cpp b/src/slic3r/GUI/PartPlate.cpp index 1c41948423..9f77f83e9a 100644 --- a/src/slic3r/GUI/PartPlate.cpp +++ b/src/slic3r/GUI/PartPlate.cpp @@ -130,6 +130,33 @@ void PartPlate::init() m_print = nullptr; } +BedType PartPlate::get_bed_type() +{ + std::string bed_type_key = "curr_bed_type"; + + if (m_config.has(bed_type_key)) + return m_config.opt_enum(bed_type_key); + + if (m_plater) { + // In GUI mode + DynamicConfig& proj_cfg = wxGetApp().preset_bundle->project_config; + if (proj_cfg.has(bed_type_key)) + return proj_cfg.opt_enum(bed_type_key); + } + + return BedType::btPC; +} + +void PartPlate::set_bed_type(BedType bed_type) +{ + m_config.set_key_value("curr_bed_type", new ConfigOptionEnum(bed_type)); +} + +void PartPlate::reset_bed_type() +{ + m_config.erase("curr_bed_type"); +} + bool PartPlate::valid_instance(int obj_id, int instance_id) { if ((obj_id >= 0) && (obj_id < m_model->objects.size())) @@ -4015,6 +4042,7 @@ int PartPlateList::store_to_3mf_structure(PlateDataPtrs& plate_data_list, bool w plate_data_item->locked = m_plate_list[i]->m_locked; plate_data_item->plate_index = m_plate_list[i]->m_plate_index; plate_data_item->plate_thumbnail.load_from(m_plate_list[i]->thumbnail_data); + plate_data_item->config.apply(*m_plate_list[i]->config()); if (m_plate_list[i]->obj_to_instance_set.size() > 0) { @@ -4080,6 +4108,7 @@ int PartPlateList::load_from_3mf_structure(PlateDataPtrs& plate_data_list) { int index = create_plate(false); m_plate_list[index]->m_locked = plate_data_list[i]->locked; + m_plate_list[index]->config()->apply(plate_data_list[i]->config); if (plate_data_list[i]->plate_index != index) { BOOST_LOG_TRIVIAL(warning) << __FUNCTION__ << boost::format(":plate index %1% seems invalid, skip it")% plate_data_list[i]->plate_index; diff --git a/src/slic3r/GUI/PartPlate.hpp b/src/slic3r/GUI/PartPlate.hpp index b194a96efa..e2606e6db1 100644 --- a/src/slic3r/GUI/PartPlate.hpp +++ b/src/slic3r/GUI/PartPlate.hpp @@ -142,6 +142,9 @@ private: int m_hover_id; bool m_selected; + // BBS + DynamicPrintConfig m_config; + void init(); bool valid_instance(int obj_id, int instance_id); void generate_print_polygon(ExPolygon &print_polygon); @@ -200,6 +203,11 @@ public: //clear alll the instances in plate void clear(bool clear_sliced_result = true); + BedType get_bed_type(); + void set_bed_type(BedType); + void reset_bed_type(); + DynamicPrintConfig* config() { return &m_config; } + //static const int plate_x_offset = 20; //mm //static const double plate_x_gap = 0.2; ThumbnailData thumbnail_data; @@ -373,7 +381,7 @@ public: std::vector> objects_and_instances; std::vector> instances_outside; - ar(m_plate_index, m_print_index, m_origin, m_width, m_depth, m_height, m_locked, m_selected, m_ready_for_slice, m_slice_result_valid, m_printable, m_tmp_gcode_path, objects_and_instances, instances_outside); + ar(m_plate_index, m_print_index, m_origin, m_width, m_depth, m_height, m_locked, m_selected, m_ready_for_slice, m_slice_result_valid, m_printable, m_tmp_gcode_path, objects_and_instances, instances_outside, m_config); for (std::vector>::iterator it = objects_and_instances.begin(); it != objects_and_instances.end(); ++it) obj_to_instance_set.insert(std::pair(it->first, it->second)); @@ -391,7 +399,7 @@ public: for (std::set>::iterator it = obj_to_instance_set.begin(); it != obj_to_instance_set.end(); ++it) objects_and_instances.emplace_back(it->first, it->second); - ar(m_plate_index, m_print_index, m_origin, m_width, m_depth, m_height, m_locked, m_selected, m_ready_for_slice, m_slice_result_valid, m_printable, m_tmp_gcode_path, objects_and_instances, instances_outside); + ar(m_plate_index, m_print_index, m_origin, m_width, m_depth, m_height, m_locked, m_selected, m_ready_for_slice, m_slice_result_valid, m_printable, m_tmp_gcode_path, objects_and_instances, instances_outside, m_config); } /*template void serialize(Archive& ar) { diff --git a/src/slic3r/GUI/Plater.cpp b/src/slic3r/GUI/Plater.cpp index 2add56986d..da76505612 100644 --- a/src/slic3r/GUI/Plater.cpp +++ b/src/slic3r/GUI/Plater.cpp @@ -2527,7 +2527,7 @@ void Plater::setExtruderParams(std::map& extPara for (unsigned int i = 0; i != numExtruders; ++i) { std::string matName = ""; // BBS - int bedTemp = 0; + int bedTemp = 35; double endTemp = 0.f; if (config.has("filament_type")) { matName = config.opt_string("filament_type", i); @@ -2536,10 +2536,14 @@ void Plater::setExtruderParams(std::map& extPara endTemp = config.opt_int("nozzle_temperature", i); } + // FIXME: curr_bed_type is now a plate config rather than a global config. + // Currently bed temp is not used for brim generation, so just comment it for now. +#if 0 if (config.has("curr_bed_type")) { BedType curr_bed_type = config.opt_enum("curr_bed_type"); bedTemp = config.opt_int(get_bed_temp_key(curr_bed_type), i); } +#endif if (i == 0) extParas.insert({ i,{matName, bedTemp, endTemp} }); extParas.insert({ i + 1,{matName, bedTemp, endTemp} }); } @@ -5146,6 +5150,7 @@ void Plater::priv::on_select_bed_type(wxCommandEvent &evt) DynamicPrintConfig& config = wxGetApp().preset_bundle->project_config; const t_config_enum_values* keys_map = print_config_def.get("curr_bed_type")->enum_keys_map; + if (keys_map) { BedType bed_type = btCount; for (auto item : *keys_map) { @@ -5155,6 +5160,11 @@ void Plater::priv::on_select_bed_type(wxCommandEvent &evt) if (bed_type != btCount) { config.set_key_value("curr_bed_type", new ConfigOptionEnum(bed_type)); + + // clear all plates' bed type config + for (int i = 0; i < partplate_list.get_plate_count(); i++) + partplate_list.get_plate(i)->reset_bed_type(); + // update plater with new config q->on_config_change(wxGetApp().preset_bundle->full_config()); @@ -5781,7 +5791,7 @@ void Plater::priv::on_action_export_to_sdcard(SimpleEvent&) void Plater::priv::on_plate_selected(SimpleEvent&) { BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << ":received plate selected event\n" ; - //sidebar->obj_list()->on_plate_selected(partplate_list.get_curr_plate_index()); + sidebar->obj_list()->on_plate_selected(partplate_list.get_curr_plate_index()); } void Plater::priv::on_action_request_model_id(wxCommandEvent& evt) @@ -10084,6 +10094,9 @@ int Plater::select_plate(int plate_index, bool need_slice) } } } + + p->on_plate_selected(SimpleEvent(EVT_GLCANVAS_PLATE_SELECT)); + BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << boost::format(" %1%: plate %2%, return %3%")%__LINE__ %plate_index %ret; return ret; }