QoL: remember each printer's filament/bed/process settings (#1592)

* init work
TODO:
1. support multi filament
2. support project

* Properly handle filament number change when switching printers
This commit is contained in:
SoftFever 2023-07-25 21:54:34 +08:00 committed by GitHub
parent 6aa3e400d1
commit 7f6f01c4c9
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 159 additions and 27 deletions

View file

@ -505,7 +505,11 @@ std::string AppConfig::load()
m_storage[it.key()][iter.key()] = iter.value().get<std::string>(); m_storage[it.key()][iter.key()] = iter.value().get<std::string>();
} }
} }
} else { } else if (it.key() == "orca_presets") {
for (auto& j_model : it.value()) {
m_printer_settings[j_model["machine"].get<std::string>()] = j_model;
}
}else {
if (it.value().is_object()) { if (it.value().is_object()) {
for (auto iter = it.value().begin(); iter != it.value().end(); iter++) { for (auto iter = it.value().begin(); iter != it.value().end(); iter++) {
if (iter.value().is_boolean()) { if (iter.value().is_boolean()) {
@ -630,7 +634,8 @@ void AppConfig::save()
j[category.first][kvp.first] = kvp.second; j[category.first][kvp.first] = kvp.second;
} }
} }
j["presets"]["filaments"] = j_filament_array; if(j_filament_array.size() > 0)
j["presets"]["filaments"] = j_filament_array;
continue; continue;
} }
for (const auto& kvp : category.second) { for (const auto& kvp : category.second) {
@ -665,6 +670,10 @@ void AppConfig::save()
} }
} }
// write machine settings
for (const auto& preset : m_printer_settings) {
j["orca_presets"].push_back(preset.second);
}
boost::nowide::ofstream c; boost::nowide::ofstream c;
c.open(path_pid, std::ios::out | std::ios::trunc); c.open(path_pid, std::ios::out | std::ios::trunc);
c << std::setw(4) << j << std::endl; c << std::setw(4) << j << std::endl;

View file

@ -167,7 +167,33 @@ public:
void set_vendors(VendorMap &&vendors) { m_vendors = std::move(vendors); m_dirty = true; } void set_vendors(VendorMap &&vendors) { m_vendors = std::move(vendors); m_dirty = true; }
const VendorMap& vendors() const { return m_vendors; } const VendorMap& vendors() const { return m_vendors; }
const std::vector<std::string> &get_filament_presets() const { return m_filament_presets; } // Orca printer settings
typedef std::map<std::string, nlohmann::json> MachineSettingMap;
bool has_printer_settings(std::string printer) const {
return m_printer_settings.find(printer) != m_printer_settings.end();
}
void clear_printer_settings(std::string printer) {
m_printer_settings.erase(printer);
m_dirty = true;
}
bool has_printer_setting(std::string printer, std::string name) {
if (!has_printer_settings(printer))
return false;
if (!m_printer_settings[printer].contains(name))
return false;
return true;
}
std::string get_printer_setting(std::string printer, std::string name) {
if (!has_printer_setting(printer, name))
return "";
return m_printer_settings[printer][name];
}
std::string set_printer_setting(std::string printer, std::string name, std::string value) {
return m_printer_settings[printer][name] = value;
m_dirty = true;
}
const std::vector<std::string> &get_filament_presets() const { return m_filament_presets; }
void set_filament_presets(const std::vector<std::string> &filament_presets){ void set_filament_presets(const std::vector<std::string> &filament_presets){
m_filament_presets = filament_presets; m_filament_presets = filament_presets;
m_dirty = true; m_dirty = true;
@ -265,6 +291,9 @@ private:
// Map of enabled vendors / models / variants // Map of enabled vendors / models / variants
VendorMap m_vendors; VendorMap m_vendors;
// Preset for each machine
MachineSettingMap m_printer_settings;
// Has any value been modified since the config.ini has been last saved or loaded? // Has any value been modified since the config.ini has been last saved or loaded?
bool m_dirty; bool m_dirty;
// Original version found in the ini file before it was overwritten // Original version found in the ini file before it was overwritten

View file

@ -1248,6 +1248,72 @@ void PresetBundle::load_installed_sla_materials(AppConfig &config)
preset.set_visible_from_appconfig(config); preset.set_visible_from_appconfig(config);
} }
void PresetBundle::update_selections(AppConfig &config)
{
std::string initial_printer_profile_name = printers.get_selected_preset_name();
// Orca: load from orca_presets
std::string initial_print_profile_name = config.get_printer_setting(initial_printer_profile_name, PRESET_PRINT_NAME);
std::string initial_filament_profile_name = config.get_printer_setting(initial_printer_profile_name, PRESET_FILAMENT_NAME);
// Selects the profiles, which were selected at the last application close.
prints.select_preset_by_name_strict(initial_print_profile_name);
filaments.select_preset_by_name_strict(initial_filament_profile_name);
// Load the names of the other filament profiles selected for a multi-material printer.
// Load it even if the current printer technology is SLA.
// The possibly excessive filament names will be later removed with this->update_multi_material_filament_presets()
// once the FFF technology gets selected.
this->filament_presets = { filaments.get_selected_preset_name() };
for (unsigned int i = 1; i < 1000; ++ i) {
char name[64];
sprintf(name, "filament_%02u", i);
auto f_name = config.get_printer_setting(initial_printer_profile_name, name);
if (f_name.empty())
break;
this->filament_presets.emplace_back(remove_ini_suffix(f_name));
}
std::vector<std::string> filament_colors;
auto f_colors = config.get_printer_setting(initial_printer_profile_name, "filament_colors");
if (!f_colors.empty()) {
boost::algorithm::split(filament_colors, f_colors, boost::algorithm::is_any_of(","));
}
filament_colors.resize(filament_presets.size(), "#00AE42");
project_config.option<ConfigOptionStrings>("filament_colour")->values = filament_colors;
std::vector<std::string> matrix;
if (config.has_printer_setting(initial_printer_profile_name, "flush_volumes_matrix")) {
boost::algorithm::split(matrix, config.get_printer_setting(initial_printer_profile_name, "flush_volumes_matrix"), boost::algorithm::is_any_of("|"));
auto flush_volumes_matrix = matrix | boost::adaptors::transformed(boost::lexical_cast<double, std::string>);
project_config.option<ConfigOptionFloats>("flush_volumes_matrix")->values = std::vector<double>(flush_volumes_matrix.begin(), flush_volumes_matrix.end());
}
if (config.has_printer_setting(initial_printer_profile_name, "flush_volumes_vector")) {
boost::algorithm::split(matrix, config.get_printer_setting(initial_printer_profile_name, "flush_volumes_vector"), boost::algorithm::is_any_of("|"));
auto flush_volumes_vector = matrix | boost::adaptors::transformed(boost::lexical_cast<double, std::string>);
project_config.option<ConfigOptionFloats>("flush_volumes_vector")->values = std::vector<double>(flush_volumes_vector.begin(), flush_volumes_vector.end());
}
if (config.has("app", "flush_multiplier")) {
std::string str_flush_multiplier = config.get("app", "flush_multiplier");
if (!str_flush_multiplier.empty())
project_config.option<ConfigOptionFloat>("flush_multiplier")->set(new ConfigOptionFloat(std::stof(str_flush_multiplier)));
}
// Update visibility of presets based on their compatibility with the active printer.
// Always try to select a compatible print and filament preset to the current printer preset,
// as the application may have been closed with an active "external" preset, which does not
// exist.
this->update_compatible(PresetSelectCompatibleType::Always);
this->update_multi_material_filament_presets();
std::string first_visible_filament_name;
for (auto & fp : filament_presets) {
if (auto it = filaments.find_preset_internal(fp); it == filaments.end() || !it->is_visible || !it->is_compatible) {
if (first_visible_filament_name.empty())
first_visible_filament_name = filaments.first_compatible().name;
fp = first_visible_filament_name;
}
}
}
// Load selections (current print, current filaments, current printer) from config.ini // Load selections (current print, current filaments, current printer) from config.ini
// This is done on application start up or after updates are applied. // This is done on application start up or after updates are applied.
void PresetBundle::load_selections(AppConfig &config, const PresetPreferences& preferred_selection/* = PresetPreferences()*/) void PresetBundle::load_selections(AppConfig &config, const PresetPreferences& preferred_selection/* = PresetPreferences()*/)
@ -1261,10 +1327,8 @@ void PresetBundle::load_selections(AppConfig &config, const PresetPreferences& p
this->load_installed_sla_materials(config); this->load_installed_sla_materials(config);
// Parse the initial print / filament / printer profile names. // Parse the initial print / filament / printer profile names.
std::string initial_print_profile_name = remove_ini_suffix(config.get("presets", PRESET_PRINT_NAME)); // std::string initial_sla_print_profile_name = remove_ini_suffix(config.get("presets", PRESET_SLA_PRINT_NAME));
std::string initial_sla_print_profile_name = remove_ini_suffix(config.get("presets", PRESET_SLA_PRINT_NAME)); // std::string initial_sla_material_profile_name = remove_ini_suffix(config.get("presets", PRESET_SLA_MATERIALS_NAME));
std::string initial_filament_profile_name = remove_ini_suffix(config.get("presets", PRESET_FILAMENT_NAME));
std::string initial_sla_material_profile_name = remove_ini_suffix(config.get("presets", PRESET_SLA_MATERIALS_NAME));
std::string initial_printer_profile_name = remove_ini_suffix(config.get("presets", PRESET_PRINTER_NAME)); std::string initial_printer_profile_name = remove_ini_suffix(config.get("presets", PRESET_PRINTER_NAME));
// Activate print / filament / printer profiles from either the config, // Activate print / filament / printer profiles from either the config,
@ -1278,6 +1342,11 @@ void PresetBundle::load_selections(AppConfig &config, const PresetPreferences& p
const Preset *preferred_printer = printers.find_system_preset_by_model_and_variant(preferred_selection.printer_model_id, preferred_selection.printer_variant); const Preset *preferred_printer = printers.find_system_preset_by_model_and_variant(preferred_selection.printer_model_id, preferred_selection.printer_variant);
printers.select_preset_by_name(preferred_printer ? preferred_printer->name : initial_printer_profile_name, true); printers.select_preset_by_name(preferred_printer ? preferred_printer->name : initial_printer_profile_name, true);
// Orca: load from orca_presets
// const auto os_presets = config.get_machine_settings(initial_printer_profile_name);
std::string initial_print_profile_name = config.get_printer_setting(initial_printer_profile_name, PRESET_PRINT_NAME);
std::string initial_filament_profile_name = config.get_printer_setting(initial_printer_profile_name, PRESET_FILAMENT_NAME);
//BBS: set default print/filament profiles to BBL's default setting //BBS: set default print/filament profiles to BBL's default setting
if (preferred_printer) if (preferred_printer)
{ {
@ -1293,8 +1362,8 @@ void PresetBundle::load_selections(AppConfig &config, const PresetPreferences& p
// Selects the profile, leaves it to -1 if the initial profile name is empty or if it was not found. // Selects the profile, leaves it to -1 if the initial profile name is empty or if it was not found.
prints.select_preset_by_name_strict(initial_print_profile_name); prints.select_preset_by_name_strict(initial_print_profile_name);
filaments.select_preset_by_name_strict(initial_filament_profile_name); filaments.select_preset_by_name_strict(initial_filament_profile_name);
sla_prints.select_preset_by_name_strict(initial_sla_print_profile_name); // sla_prints.select_preset_by_name_strict(initial_sla_print_profile_name);
sla_materials.select_preset_by_name_strict(initial_sla_material_profile_name); // sla_materials.select_preset_by_name_strict(initial_sla_material_profile_name);
// Load the names of the other filament profiles selected for a multi-material printer. // Load the names of the other filament profiles selected for a multi-material printer.
// Load it even if the current printer technology is SLA. // Load it even if the current printer technology is SLA.
@ -1304,24 +1373,26 @@ void PresetBundle::load_selections(AppConfig &config, const PresetPreferences& p
for (unsigned int i = 1; i < 1000; ++ i) { for (unsigned int i = 1; i < 1000; ++ i) {
char name[64]; char name[64];
sprintf(name, "filament_%02u", i); sprintf(name, "filament_%02u", i);
if (! config.has("presets", name)) auto f_name = config.get_printer_setting(initial_printer_profile_name, name);
if (f_name.empty())
break; break;
this->filament_presets.emplace_back(remove_ini_suffix(config.get("presets", name))); this->filament_presets.emplace_back(remove_ini_suffix(f_name));
} }
std::vector<std::string> filament_colors; std::vector<std::string> filament_colors;
if (config.has("presets", "filament_colors")) { auto f_colors = config.get_printer_setting(initial_printer_profile_name, "filament_colors");
boost::algorithm::split(filament_colors, config.get("presets", "filament_colors"), boost::algorithm::is_any_of(",")); if (!f_colors.empty()) {
boost::algorithm::split(filament_colors, f_colors, boost::algorithm::is_any_of(","));
} }
filament_colors.resize(filament_presets.size(), "#00AE42"); filament_colors.resize(filament_presets.size(), "#00AE42");
project_config.option<ConfigOptionStrings>("filament_colour")->values = filament_colors; project_config.option<ConfigOptionStrings>("filament_colour")->values = filament_colors;
std::vector<std::string> matrix; std::vector<std::string> matrix;
if (config.has("presets", "flush_volumes_matrix")) { if (config.has_printer_setting(initial_printer_profile_name, "flush_volumes_matrix")) {
boost::algorithm::split(matrix, config.get("presets", "flush_volumes_matrix"), boost::algorithm::is_any_of("|")); boost::algorithm::split(matrix, config.get_printer_setting(initial_printer_profile_name, "flush_volumes_matrix"), boost::algorithm::is_any_of("|"));
auto flush_volumes_matrix = matrix | boost::adaptors::transformed(boost::lexical_cast<double, std::string>); auto flush_volumes_matrix = matrix | boost::adaptors::transformed(boost::lexical_cast<double, std::string>);
project_config.option<ConfigOptionFloats>("flush_volumes_matrix")->values = std::vector<double>(flush_volumes_matrix.begin(), flush_volumes_matrix.end()); project_config.option<ConfigOptionFloats>("flush_volumes_matrix")->values = std::vector<double>(flush_volumes_matrix.begin(), flush_volumes_matrix.end());
} }
if (config.has("presets", "flush_volumes_vector")) { if (config.has_printer_setting(initial_printer_profile_name, "flush_volumes_vector")) {
boost::algorithm::split(matrix, config.get("presets", "flush_volumes_vector"), boost::algorithm::is_any_of("|")); boost::algorithm::split(matrix, config.get_printer_setting(initial_printer_profile_name, "flush_volumes_vector"), boost::algorithm::is_any_of("|"));
auto flush_volumes_vector = matrix | boost::adaptors::transformed(boost::lexical_cast<double, std::string>); auto flush_volumes_vector = matrix | boost::adaptors::transformed(boost::lexical_cast<double, std::string>);
project_config.option<ConfigOptionFloats>("flush_volumes_vector")->values = std::vector<double>(flush_volumes_vector.begin(), flush_volumes_vector.end()); project_config.option<ConfigOptionFloats>("flush_volumes_vector")->values = std::vector<double>(flush_volumes_vector.begin(), flush_volumes_vector.end());
} }
@ -1383,27 +1454,32 @@ void PresetBundle::export_selections(AppConfig &config)
assert(this->printers.get_edited_preset().printer_technology() != ptFFF || filament_presets.size() >= 1); assert(this->printers.get_edited_preset().printer_technology() != ptFFF || filament_presets.size() >= 1);
//assert(this->printers.get_edited_preset().printer_technology() != ptFFF || filament_presets.size() > 1 || filaments.get_selected_preset_name() == filament_presets.front()); //assert(this->printers.get_edited_preset().printer_technology() != ptFFF || filament_presets.size() > 1 || filaments.get_selected_preset_name() == filament_presets.front());
config.clear_section("presets"); config.clear_section("presets");
config.set("presets", PRESET_PRINT_NAME, prints.get_selected_preset_name()); auto printer_name = printers.get_selected_preset_name();
config.set("presets", PRESET_FILAMENT_NAME, filament_presets.front()); config.set("presets", PRESET_PRINTER_NAME, printer_name);
config.clear_printer_settings(printer_name);
config.set_printer_setting(printer_name, PRESET_PRINTER_NAME, printer_name);
config.set_printer_setting(printer_name, PRESET_PRINT_NAME, prints.get_selected_preset_name());
config.set_printer_setting(printer_name, PRESET_FILAMENT_NAME, filament_presets.front());
config.set_printer_setting(printer_name, "curr_bed_type", config.get("curr_bed_type"));
for (unsigned i = 1; i < filament_presets.size(); ++i) { for (unsigned i = 1; i < filament_presets.size(); ++i) {
char name[64]; char name[64];
assert(!filament_presets[i].empty()); assert(!filament_presets[i].empty());
sprintf(name, "filament_%02u", i); sprintf(name, "filament_%02u", i);
config.set("presets", name, filament_presets[i]); config.set_printer_setting(printer_name, name, filament_presets[i]);
} }
CNumericLocalesSetter locales_setter; CNumericLocalesSetter locales_setter;
std::string filament_colors = boost::algorithm::join(project_config.option<ConfigOptionStrings>("filament_colour")->values, ","); std::string filament_colors = boost::algorithm::join(project_config.option<ConfigOptionStrings>("filament_colour")->values, ",");
config.set("presets", "filament_colors", filament_colors); config.set_printer_setting(printer_name, "filament_colors", filament_colors);
std::string flush_volumes_matrix = boost::algorithm::join(project_config.option<ConfigOptionFloats>("flush_volumes_matrix")->values | std::string flush_volumes_matrix = boost::algorithm::join(project_config.option<ConfigOptionFloats>("flush_volumes_matrix")->values |
boost::adaptors::transformed(static_cast<std::string (*)(double)>(std::to_string)), boost::adaptors::transformed(static_cast<std::string (*)(double)>(std::to_string)),
"|"); "|");
config.set("presets", "flush_volumes_matrix", flush_volumes_matrix); config.set_printer_setting(printer_name, "flush_volumes_matrix", flush_volumes_matrix);
std::string flush_volumes_vector = boost::algorithm::join(project_config.option<ConfigOptionFloats>("flush_volumes_vector")->values | std::string flush_volumes_vector = boost::algorithm::join(project_config.option<ConfigOptionFloats>("flush_volumes_vector")->values |
boost::adaptors::transformed(static_cast<std::string (*)(double)>(std::to_string)), boost::adaptors::transformed(static_cast<std::string (*)(double)>(std::to_string)),
"|"); "|");
config.set("presets", "flush_volumes_vector", flush_volumes_vector); config.set_printer_setting(printer_name, "flush_volumes_vector", flush_volumes_vector);
config.set("presets", PRESET_PRINTER_NAME, printers.get_selected_preset_name());
auto flush_multi_opt = project_config.option<ConfigOptionFloat>("flush_multiplier"); auto flush_multi_opt = project_config.option<ConfigOptionFloat>("flush_multiplier");
config.set("flush_multiplier", std::to_string(flush_multi_opt ? flush_multi_opt->getFloat() : 1.0f)); config.set("flush_multiplier", std::to_string(flush_multi_opt ? flush_multi_opt->getFloat() : 1.0f));

View file

@ -86,6 +86,9 @@ public:
//BBS: check whether this is the only edited filament //BBS: check whether this is the only edited filament
bool is_the_only_edited_filament(unsigned int filament_index); bool is_the_only_edited_filament(unsigned int filament_index);
// Orca: update selected filament and print
void update_selections(AppConfig &config);
PresetCollection prints; PresetCollection prints;
PresetCollection sla_prints; PresetCollection sla_prints;
PresetCollection filaments; PresetCollection filaments;

View file

@ -773,8 +773,8 @@ Sidebar::Sidebar(Plater *parent)
ScalableButton* add_btn = new ScalableButton(p->m_panel_filament_title, wxID_ANY, "add_filament"); ScalableButton* add_btn = new ScalableButton(p->m_panel_filament_title, wxID_ANY, "add_filament");
add_btn->SetToolTip(_L("Add one filament")); add_btn->SetToolTip(_L("Add one filament"));
add_btn->Bind(wxEVT_BUTTON, [this, scrolled_sizer](wxCommandEvent& e){ add_btn->Bind(wxEVT_BUTTON, [this, scrolled_sizer](wxCommandEvent& e){
// BBS: limit filament choices to 16 // Orca: limit filament choices to 64
if (p->combos_filament.size() >= 16) if (p->combos_filament.size() >= 64)
return; return;
int filament_count = p->combos_filament.size() + 1; int filament_count = p->combos_filament.size() + 1;
@ -1035,7 +1035,13 @@ void Sidebar::update_all_preset_comboboxes()
//update print button default value for bbl or third-party printer //update print button default value for bbl or third-party printer
p_mainframe->set_print_button_to_default(MainFrame::PrintSelectType::ePrintPlate); p_mainframe->set_print_button_to_default(MainFrame::PrintSelectType::ePrintPlate);
m_bed_type_list->Enable(); m_bed_type_list->Enable();
auto str_bed_type = wxGetApp().app_config->get_printer_setting(wxGetApp().preset_bundle->printers.get_selected_preset_name(), "curr_bed_type");
if(!str_bed_type.empty()){
int bed_type_value = atoi(str_bed_type.c_str());
if(bed_type_value == 0)
bed_type_value = 1;
m_bed_type_list->SelectAndNotify(bed_type_value - 1);
}
} else { } else {
connection_btn->Show(); connection_btn->Show();
@ -5591,6 +5597,8 @@ void Plater::priv::on_select_bed_type(wxCommandEvent &evt)
// update app_config // update app_config
AppConfig* app_config = wxGetApp().app_config; AppConfig* app_config = wxGetApp().app_config;
app_config->set("curr_bed_type", std::to_string(int(new_bed_type))); app_config->set("curr_bed_type", std::to_string(int(new_bed_type)));
app_config->set_printer_setting(wxGetApp().preset_bundle->printers.get_selected_preset_name(),
"curr_bed_type", std::to_string(int(new_bed_type)));
//update slice status //update slice status
auto plate_list = partplate_list.get_plate_list(); auto plate_list = partplate_list.get_plate_list();

View file

@ -1641,6 +1641,12 @@ void Tab::on_presets_changed()
if (wxGetApp().plater() == nullptr) if (wxGetApp().plater() == nullptr)
return; return;
// Orca: update presets for the selected printer
if(m_type == Preset::TYPE_PRINTER) {
m_preset_bundle->update_selections(*wxGetApp().app_config);
wxGetApp().plater()->sidebar().on_filaments_change(m_preset_bundle->filament_presets.size());
}
// Instead of PostEvent (EVT_TAB_PRESETS_CHANGED) just call update_presets // Instead of PostEvent (EVT_TAB_PRESETS_CHANGED) just call update_presets
wxGetApp().plater()->sidebar().update_presets(m_type); wxGetApp().plater()->sidebar().update_presets(m_type);
@ -1652,6 +1658,7 @@ void Tab::on_presets_changed()
else else
wxGetApp().plater()->get_partplate_list().set_render_option(false, true); wxGetApp().plater()->get_partplate_list().set_render_option(false, true);
// Printer selected at the Printer tab, update "compatible" marks at the print and filament selectors. // Printer selected at the Printer tab, update "compatible" marks at the print and filament selectors.
for (auto t: m_dependent_tabs) for (auto t: m_dependent_tabs)
{ {