Ported Config::_handle_legacy() to XS

This commit is contained in:
Alessandro Ranellucci 2017-03-18 11:29:48 +01:00
parent 90395f9394
commit e7c854c919
5 changed files with 110 additions and 72 deletions

View File

@ -8,12 +8,6 @@ use utf8;
use List::Util qw(first max); use List::Util qw(first max);
# cemetery of old config settings
our @Ignore = qw(duplicate_x duplicate_y multiply_x multiply_y support_material_tool acceleration
adjust_overhang_flow standby_temperature scale rotate duplicate duplicate_grid
rotate scale duplicate_grid start_perimeters_at_concave_points start_perimeters_at_non_overhang
randomize_start seal_position bed_size print_center g0);
# C++ Slic3r::PrintConfigDef exported as a Perl hash of hashes. # C++ Slic3r::PrintConfigDef exported as a Perl hash of hashes.
# The C++ counterpart is a constant singleton. # The C++ counterpart is a constant singleton.
our $Options = print_config_def(); our $Options = print_config_def();
@ -120,11 +114,7 @@ sub load_ini_hash {
my ($ini_hash) = @_; my ($ini_hash) = @_;
my $config = $class->new; my $config = $class->new;
foreach my $opt_key (keys %$ini_hash) { $config->set_deserialize($_, $ini_hash->{$_}) for keys %$ini_hash;
($opt_key, my $value) = _handle_legacy($opt_key, $ini_hash->{$opt_key});
next if !defined $opt_key;
$config->set_deserialize($opt_key, $value);
}
return $config; return $config;
} }
@ -145,60 +135,6 @@ sub get_value {
: $self->get($opt_key); : $self->get($opt_key);
} }
sub _handle_legacy {
my ($opt_key, $value) = @_;
# handle legacy options
if ($opt_key =~ /^(extrusion_width|bottom_layer_speed|first_layer_height)_ratio$/) {
$opt_key = $1;
$opt_key =~ s/^bottom_layer_speed$/first_layer_speed/;
$value = $value =~ /^\d+(?:\.\d+)?$/ && $value != 0 ? ($value*100) . "%" : 0;
}
if ($opt_key eq 'threads' && !$Slic3r::have_threads) {
$value = 1;
}
if ($opt_key eq 'gcode_flavor' && $value eq 'makerbot') {
$value = 'makerware';
}
if ($opt_key eq 'fill_density' && defined($value) && $value !~ /%/ && $value <= 1) {
# fill_density was turned into a percent value
$value *= 100;
$value = "$value"; # force update of the PV value, workaround for bug https://rt.cpan.org/Ticket/Display.html?id=94110
}
if ($opt_key eq 'randomize_start' && $value) {
$opt_key = 'seam_position';
$value = 'random';
}
if ($opt_key eq 'bed_size' && $value) {
$opt_key = 'bed_shape';
my ($x, $y) = split /,/, $value;
$value = "0x0,${x}x0,${x}x${y},0x${y}";
}
return () if first { $_ eq $opt_key } @Ignore;
# For historical reasons, the world's full of configs having these very low values;
# to avoid unexpected behavior we need to ignore them. Banning these two hard-coded
# values is a dirty hack and will need to be removed sometime in the future, but it
# will avoid lots of complaints for now.
if ($opt_key eq 'perimeter_acceleration' && $value == '25') {
$value = 0;
}
if ($opt_key eq 'infill_acceleration' && $value == '50') {
$value = 0;
}
if (!exists $Options->{$opt_key}) {
my @keys = grep { $Options->{$_}{aliases} && grep $_ eq $opt_key, @{$Options->{$_}{aliases}} } keys %$Options;
if (!@keys) {
warn "Unknown option $opt_key\n";
return ();
}
$opt_key = $keys[0];
}
return ($opt_key, $value);
}
# Create a hash of hashes from the underlying C++ Slic3r::DynamicPrintConfig. # Create a hash of hashes from the underlying C++ Slic3r::DynamicPrintConfig.
# The first hash key is '_' meaning no category. # The first hash key is '_' meaning no category.
sub as_ini { sub as_ini {

View File

@ -9,6 +9,7 @@
#include <boost/algorithm/string/classification.hpp> #include <boost/algorithm/string/classification.hpp>
#include <boost/algorithm/string/erase.hpp> #include <boost/algorithm/string/erase.hpp>
#include <boost/algorithm/string/predicate.hpp> #include <boost/algorithm/string/predicate.hpp>
#include <boost/algorithm/string/replace.hpp>
#include <boost/foreach.hpp> #include <boost/foreach.hpp>
#include <boost/lexical_cast.hpp> #include <boost/lexical_cast.hpp>
#include <boost/property_tree/ini_parser.hpp> #include <boost/property_tree/ini_parser.hpp>
@ -220,6 +221,12 @@ ConfigDef::add(const t_config_option_key &opt_key, const ConfigOptionDef &def)
return &this->options[opt_key]; return &this->options[opt_key];
} }
bool
ConfigDef::has(const t_config_option_key &opt_key) const
{
return this->options.count(opt_key) > 0;
}
const ConfigOptionDef* const ConfigOptionDef*
ConfigDef::get(const t_config_option_key &opt_key) const ConfigDef::get(const t_config_option_key &opt_key) const
{ {
@ -288,12 +295,27 @@ ConfigBase::serialize(const t_config_option_key &opt_key) const {
} }
bool bool
ConfigBase::set_deserialize(const t_config_option_key &opt_key, std::string str, bool append) { ConfigBase::set_deserialize(t_config_option_key opt_key, std::string str, bool append) {
const ConfigOptionDef* optdef = this->def->get(opt_key); const ConfigOptionDef* optdef = this->def->get(opt_key);
if (optdef == NULL) throw UnknownOptionException(); if (optdef == NULL) {
// If we didn't find an option, look for any other option having this as an alias.
for (const auto &opt : this->def->options) {
for (const t_config_option_key &opt_key2 : opt.second.aliases) {
if (opt_key2 == opt_key) {
opt_key = opt_key2;
optdef = &opt.second;
break;
}
}
if (optdef != NULL) break;
}
if (optdef == NULL)
throw UnknownOptionException();
}
if (!optdef->shortcut.empty()) { if (!optdef->shortcut.empty()) {
for (std::vector<t_config_option_key>::const_iterator it = optdef->shortcut.begin(); it != optdef->shortcut.end(); ++it) { for (const t_config_option_key &shortcut : optdef->shortcut) {
if (!this->set_deserialize(*it, str)) return false; if (!this->set_deserialize(shortcut, str)) return false;
} }
return true; return true;
} }
@ -373,7 +395,9 @@ ConfigBase::load(const std::string &file)
pt::read_ini(file, tree); pt::read_ini(file, tree);
BOOST_FOREACH(const pt::ptree::value_type &v, tree) { BOOST_FOREACH(const pt::ptree::value_type &v, tree) {
try { try {
this->set_deserialize(v.first.c_str(), v.second.get_value<std::string>().c_str()); t_config_option_key opt_key = v.first;
std::string value = v.second.get_value<std::string>();
this->set_deserialize(opt_key, value);
} catch (UnknownOptionException &e) { } catch (UnknownOptionException &e) {
// ignore // ignore
} }

View File

@ -649,6 +649,7 @@ class ConfigDef
t_optiondef_map options; t_optiondef_map options;
ConfigOptionDef* add(const t_config_option_key &opt_key, ConfigOptionType type); ConfigOptionDef* add(const t_config_option_key &opt_key, ConfigOptionType type);
ConfigOptionDef* add(const t_config_option_key &opt_key, const ConfigOptionDef &def); ConfigOptionDef* add(const t_config_option_key &opt_key, const ConfigOptionDef &def);
bool has(const t_config_option_key &opt_key) const;
const ConfigOptionDef* get(const t_config_option_key &opt_key) const; const ConfigOptionDef* get(const t_config_option_key &opt_key) const;
void merge(const ConfigDef &other); void merge(const ConfigDef &other);
}; };
@ -675,7 +676,7 @@ class ConfigBase
bool equals(ConfigBase &other); bool equals(ConfigBase &other);
t_config_option_keys diff(ConfigBase &other); t_config_option_keys diff(ConfigBase &other);
std::string serialize(const t_config_option_key &opt_key) const; std::string serialize(const t_config_option_key &opt_key) const;
bool set_deserialize(const t_config_option_key &opt_key, std::string str, bool append = false); virtual bool set_deserialize(t_config_option_key opt_key, std::string str, bool append = false);
double get_abs_value(const t_config_option_key &opt_key) const; double get_abs_value(const t_config_option_key &opt_key) const;
double get_abs_value(const t_config_option_key &opt_key, double ratio_over) const; double get_abs_value(const t_config_option_key &opt_key, double ratio_over) const;
void setenv_(); void setenv_();

View File

@ -1,4 +1,5 @@
#include "PrintConfig.hpp" #include "PrintConfig.hpp"
#include <boost/algorithm/string/replace.hpp>
#include <boost/thread.hpp> #include <boost/thread.hpp>
namespace Slic3r { namespace Slic3r {
@ -1577,6 +1578,79 @@ PrintConfigBase::min_object_distance() const
: duplicate_distance; : duplicate_distance;
} }
bool
PrintConfigBase::set_deserialize(t_config_option_key opt_key, std::string str, bool append)
{
this->_handle_legacy(opt_key, str);
if (opt_key.empty()) return true; // ignore option
return ConfigBase::set_deserialize(opt_key, str, append);
}
void
PrintConfigBase::_handle_legacy(t_config_option_key &opt_key, std::string &value) const
{
// handle legacy options
if (opt_key == "extrusion_width_ratio" || opt_key == "bottom_layer_speed_ratio"
|| opt_key == "first_layer_height_ratio") {
boost::replace_first(opt_key, "_ratio", "");
if (opt_key == "bottom_layer_speed") opt_key = "first_layer_speed";
try {
float v = boost::lexical_cast<float>(value);
if (v != 0)
value = boost::lexical_cast<std::string>(v*100) + "%";
} catch (boost::bad_lexical_cast &) {
value = "0";
}
} else if (opt_key == "gcode_flavor" && value == "makerbot") {
value = "makerware";
} else if (opt_key == "fill_density" && value.find("%") == std::string::npos) {
try {
// fill_density was turned into a percent value
float v = boost::lexical_cast<float>(value);
value = boost::lexical_cast<std::string>(v*100) + "%";
} catch (boost::bad_lexical_cast &) {}
} else if (opt_key == "randomize_start" && value == "1") {
opt_key = "seam_position";
value = "random";
} else if (opt_key == "bed_size" && !value.empty()) {
opt_key = "bed_shape";
ConfigOptionPoint p;
p.deserialize(value);
std::ostringstream oss;
oss << "0x0," << p.value.x << "x0," << p.value.x << "x" << p.value.y << ",0x" << p.value.y;
value = oss.str();
} else if ((opt_key == "perimeter_acceleration" && value == "25")
|| (opt_key == "infill_acceleration" && value == "50")) {
/* For historical reasons, the world's full of configs having these very low values;
to avoid unexpected behavior we need to ignore them. Banning these two hard-coded
values is a dirty hack and will need to be removed sometime in the future, but it
will avoid lots of complaints for now. */
value = "0";
}
// cemetery of old config settings
if (opt_key == "duplicate_x" || opt_key == "duplicate_y" || opt_key == "multiply_x"
|| opt_key == "multiply_y" || opt_key == "support_material_tool"
|| opt_key == "acceleration" || opt_key == "adjust_overhang_flow"
|| opt_key == "standby_temperature" || opt_key == "scale" || opt_key == "rotate"
|| opt_key == "duplicate" || opt_key == "duplicate_grid" || opt_key == "rotate"
|| opt_key == "scale" || opt_key == "duplicate_grid"
|| opt_key == "start_perimeters_at_concave_points"
|| opt_key == "start_perimeters_at_non_overhang" || opt_key == "randomize_start"
|| opt_key == "seal_position" || opt_key == "bed_size"
|| opt_key == "print_center" || opt_key == "g0" || opt_key == "threads")
{
opt_key = "";
return;
}
if (!this->def->has(opt_key)) {
printf("Unknown option %s\n", opt_key.c_str());
opt_key = "";
return;
}
}
CLIConfigDef::CLIConfigDef() CLIConfigDef::CLIConfigDef()
{ {
ConfigOptionDef* def; ConfigOptionDef* def;

View File

@ -112,8 +112,11 @@ class PrintConfigBase : public virtual ConfigBase
PrintConfigBase() { PrintConfigBase() {
this->def = &print_config_def; this->def = &print_config_def;
}; };
bool set_deserialize(t_config_option_key opt_key, std::string str, bool append = false);
double min_object_distance() const; double min_object_distance() const;
protected:
void _handle_legacy(t_config_option_key &opt_key, std::string &value) const;
}; };
// Slic3r dynamic configuration, used to override the configuration // Slic3r dynamic configuration, used to override the configuration