OrcaSlicer latest
OrcaSlicer
Loading...
Searching...
No Matches
Slic3r::GUI::PluginField Class Reference

#include </home/runner/work/OrcaSlicer/OrcaSlicer/src/slic3r/GUI/Field.hpp>

Inheritance diagram for Slic3r::GUI::PluginField:
Collaboration diagram for Slic3r::GUI::PluginField:

Classes

struct  PluginRow

Public Member Functions

 PluginField (const ConfigOptionDef &opt, const t_config_option_key &id)
 PluginField (wxWindow *parent, const ConfigOptionDef &opt, const t_config_option_key &id)
 ~PluginField ()
void BUILD () override
 Finish constructing the Field's wxWidget-related properties, including setting its own sizer, etc.
void set_selector (std::function< std::string()> selector)
void set_value (const boost::any &value, bool change_event=false) override
 Sets a value for this control. subclasses should overload with a specific version Postcondition: Method does not fire the on_change event.
boost::any & get_value () override
 Gets a boost::any representing this control. subclasses should overload with a specific version.
void enable () override
void disable () override
wxWindow * getWindow () override
void msw_rescale () override
void on_back_to_initial_value ()
 Call the attached m_back_to_initial_value method.
void on_back_to_sys_value ()
 Call the attached m_back_to_sys_value method.
void on_edit_value ()
 Call the attached m_fn_edit_value method.
virtual void propagate_value ()
virtual void set_last_meaningful_value ()
virtual void set_na_value ()
virtual void update_na_value (const boost::any &value)
void toggle (bool en)
 Fires the enable or disable function, based on the input.
virtual wxString get_tooltip_text (const wxString &default_string)
void field_changed ()
virtual wxSizer * getSizer ()
 If you don't know what you are getting back, check both methods for nullptr.
bool is_matched (const std::string &string, const std::string &pattern)
void get_value_by_opt_type (wxString &str, const bool check_value=true)
virtual void sys_color_changed ()
bool get_enter_pressed () const
void set_enter_pressed (bool pressed)
const bool combine_side_text ()
bool set_undo_bitmap (const ScalableBitmap *bmp)
bool set_undo_to_sys_bitmap (const ScalableBitmap *bmp)
bool set_label_colour (const wxColour *clr)
bool set_undo_tooltip (const wxString *tip)
bool set_undo_to_sys_tooltip (const wxString *tip)
bool set_edit_bitmap (const ScalableBitmap *bmp)
bool set_edit_tooltip (const wxString &tip)
bool has_undo_ui () const
const ScalableBitmap * undo_bitmap () const
const wxString * undo_tooltip () const
const ScalableBitmap * undo_to_sys_bitmap () const
const wxString * undo_to_sys_tooltip () const
const wxColour * label_color () const
const bool blink () const
bool * get_blink_ptr ()
bool has_edit_ui () const
const wxBitmap * edit_bitmap () const
const wxString * edit_tooltip () const

Static Public Member Functions

template<class T>
static t_field Create (wxWindow *parent, const ConfigOptionDef &opt, const t_config_option_key &id)
 Factory method for generating new derived classes.
static int def_width ()
static int def_width_wider ()
static int def_width_thinner ()

Public Attributes

wxWindow * m_parent {nullptr}
 parent wx item, opportunity to refactor (probably not necessary - data duplication)
t_kill_focus m_on_kill_focus {nullptr}
 Function object to store callback passed in from owning object.
t_change m_on_change {nullptr}
 Function object to store callback passed in from owning object.
t_back_to_init m_back_to_initial_value { nullptr }
 Function object to store callback passed in from owning object.
t_back_to_init m_back_to_sys_value { nullptr }
t_back_to_init m_fn_edit_value { nullptr }
 Callback function to edit field value.
bool m_disable_change_event {false}
bool m_is_modified_value {false}
bool m_is_nonsys_value {true}
const ConfigOptionDef m_opt {ConfigOptionDef()}
 Copy of ConfigOption for deduction purposes.
const t_config_option_key m_opt_id
int m_opt_idx = 0
 {""};
double opt_height { 0.0 }
bool parent_is_custom_ctrl { false }

Protected Member Functions

virtual void PostInitialize ()
void on_kill_focus ()
 Call the attached on_kill_focus method. It's important to use wxEvent instead of wxFocusEvent, in another case we can't unfocused control at all.
void on_change_field ()
 Call the attached on_change method.

Protected Attributes

boost::any m_value
boost::any m_last_meaningful_value
int m_em_unit
bool m_combine_side_text = false
bool bEnterPressed = false
wxString m_na_value = _(L("N/A"))

Private Member Functions

void rebuild_ui ()
void add_empty_state_row ()
void add_plugin_row (const wxString &value=wxEmptyString, bool is_last=false)
wxString display_name_for_value (const std::string &value) const
void on_select_clicked (size_t index)
void on_add_clicked ()
void on_remove_clicked (size_t index)
wxString get_row_value (size_t index) const
void set_row_value (size_t index, const wxString &value)
 Field (const ConfigOptionDef &opt, const t_config_option_key &id)
 Field (wxWindow *parent, const ConfigOptionDef &opt, const t_config_option_key &id)

Private Attributes

wxWindow * window { nullptr }
wxBoxSizer * m_main_sizer { nullptr }
std::vector< PluginRow > m_rows
std::vector< std::string > m_values
Button * m_standalone_add_btn { nullptr }
std::function< std::string()> m_selector
UndoValueUI m_undo_ui
EditValueUI m_edit_ui

Detailed Description


Class Documentation

◆ Slic3r::GUI::PluginField::PluginRow

struct Slic3r::GUI::PluginField::PluginRow
Collaboration diagram for Slic3r::GUI::PluginField::PluginRow:
Class Members
ComboBox * display { nullptr }
ScalableButton * remove_btn { nullptr }
wxBoxSizer * sizer { nullptr }

Constructor & Destructor Documentation

◆ PluginField() [1/2]

Slic3r::GUI::PluginField::PluginField ( const ConfigOptionDef & opt,
const t_config_option_key & id )
inline
528: Field(opt, id) {}
Field(const ConfigOptionDef &opt, const t_config_option_key &id)
Definition Field.hpp:265

References Field().

Here is the call graph for this function:

◆ PluginField() [2/2]

Slic3r::GUI::PluginField::PluginField ( wxWindow * parent,
const ConfigOptionDef & opt,
const t_config_option_key & id )
inline
529: Field(parent, opt, id) {}

References Field().

Here is the call graph for this function:

◆ ~PluginField()

Slic3r::GUI::PluginField::~PluginField ( )
inline
530{}

Member Function Documentation

◆ add_empty_state_row()

void Slic3r::GUI::PluginField::add_empty_state_row ( )
private
2335{
2336 auto add_btn = new Button(window, _L("Add plugin"), "param_add", 0, 16);
2337 add_btn->SetStyle(ButtonStyle::Regular, ButtonType::Parameter);
2338
2339 add_btn->Bind(wxEVT_BUTTON, [this](wxCommandEvent&) { on_add_clicked(); });
2340
2341 m_main_sizer->Add(add_btn, 0, wxEXPAND | wxBOTTOM, window->FromDIP(SidebarProps::ContentMarginV()));
2342
2343 m_standalone_add_btn = add_btn;
2344}
@ Regular
Definition Button.hpp:24
@ Parameter
Definition Button.hpp:34
#define _L(s)
Definition OBJ.cpp:34
void on_add_clicked()
Definition Field.cpp:2409
Button * m_standalone_add_btn
Definition Field.hpp:569
wxBoxSizer * m_main_sizer
Definition Field.hpp:566
wxWindow * window
Definition Field.hpp:565
static int ContentMarginV()
Definition Plater.hpp:150

References _L, Slic3r::GUI::SidebarProps::ContentMarginV(), m_main_sizer, m_standalone_add_btn, on_add_clicked(), Parameter, Regular, and window.

Referenced by rebuild_ui().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ add_plugin_row()

void Slic3r::GUI::PluginField::add_plugin_row ( const wxString & value = wxEmptyString,
bool is_last = false )
private
2347{
2348 auto row_sizer = new wxBoxSizer(wxHORIZONTAL);
2349
2350 ComboBox* display = new ComboBox(window, wxID_ANY, value, wxDefaultPosition, wxDefaultSize, 0, NULL, wxCB_READONLY | CB_NO_DROP_ICON);
2351 display->SetIcon("edit");
2352 display->SetToolTip(get_tooltip_text(value));
2353
2354 ScalableButton* remove_btn = new ScalableButton(window, wxID_ANY, "cross", wxEmptyString,
2355 wxDefaultSize, wxDefaultPosition, wxBU_EXACTFIT | wxNO_BORDER, true, 16);
2356 remove_btn->SetToolTip(_L("Remove plugin"));
2357
2358 if (m_opt.readonly)
2359 remove_btn->Disable();
2360
2361 const size_t row_index = m_rows.size();
2362 display->Bind(wxEVT_LEFT_DOWN, [this, row_index](wxMouseEvent& ) { on_select_clicked(row_index); });
2363 remove_btn->Bind(wxEVT_BUTTON, [this, row_index](wxCommandEvent&) { on_remove_clicked(row_index); });
2364
2365 row_sizer->Add(display , 1, wxALIGN_CENTER_VERTICAL);
2366 row_sizer->Add(remove_btn, 0, wxALIGN_CENTER_VERTICAL | wxLEFT, window->FromDIP(SidebarProps::ElementSpacing()));
2367
2368 m_main_sizer->Add(row_sizer, 0, wxEXPAND | wxBOTTOM, window->FromDIP(is_last ? SidebarProps::ContentMarginV() : 4));
2369
2370 PluginRow row;
2371 row.display = display;
2372 row.remove_btn = remove_btn;
2373 row.sizer = row_sizer;
2374 m_rows.push_back(row);
2375}
#define CB_NO_DROP_ICON
Definition ComboBox.hpp:17
virtual wxString get_tooltip_text(const wxString &default_string)
Definition Field.cpp:441
const ConfigOptionDef m_opt
Copy of ConfigOption for deduction purposes.
Definition Field.hpp:235
ComboBox * display
Definition Field.hpp:550
void on_select_clicked(size_t index)
Definition Field.cpp:2385
std::vector< PluginRow > m_rows
Definition Field.hpp:567
void on_remove_clicked(size_t index)
Definition Field.cpp:2429
Definition Field.hpp:549
static int ElementSpacing()
Definition Plater.hpp:153
wxMouseEvent
Definition CameraPopup.cpp:47

References _L, CB_NO_DROP_ICON, Slic3r::GUI::SidebarProps::ContentMarginV(), Slic3r::GUI::PluginField::PluginRow::display, Slic3r::GUI::SidebarProps::ElementSpacing(), Slic3r::GUI::Field::get_tooltip_text(), m_main_sizer, Slic3r::GUI::Field::m_opt, m_rows, on_remove_clicked(), on_select_clicked(), Slic3r::GUI::PluginField::PluginRow::remove_btn, Slic3r::GUI::PluginField::PluginRow::sizer, window, and Slic3r::GUI::wxMouseEvent.

Referenced by rebuild_ui().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ blink()

const bool Slic3r::GUI::UndoValueUIManager::blink ( ) const
inlineinherited
170{ return m_undo_ui.blink; }
UndoValueUI m_undo_ui
Definition Field.hpp:120

References m_undo_ui.

Referenced by Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ BUILD()

void Slic3r::GUI::PluginField::BUILD ( )
overridevirtual

Finish constructing the Field's wxWidget-related properties, including setting its own sizer, etc.

Implements Slic3r::GUI::Field.

2273{
2274 auto* panel = new wxPanel(m_parent, wxID_ANY);
2275 panel->SetBackgroundColour(*wxWHITE);
2276 wxGetApp().UpdateDarkUI(panel);
2277 window = panel;
2278
2279 m_main_sizer = new wxBoxSizer(wxVERTICAL);
2280 panel->SetSizer(m_main_sizer);
2281
2282 if (m_opt.type == coStrings) {
2283 const ConfigOptionStrings* vec = m_opt.get_default_value<ConfigOptionStrings>();
2284 if (vec != nullptr && !vec->values.empty()) {
2285 m_values = vec->values;
2286 }
2287 }
2288
2289 rebuild_ui();
2290 m_value = m_values;
2291}
boost::any m_value
Definition Field.hpp:300
wxWindow * m_parent
parent wx item, opportunity to refactor (probably not necessary - data duplication)
Definition Field.hpp:214
void rebuild_ui()
Definition Field.cpp:2308
std::vector< std::string > m_values
Definition Field.hpp:568
@ coStrings
Definition Config.hpp:194

References Slic3r::coStrings, m_main_sizer, Slic3r::GUI::Field::m_opt, Slic3r::GUI::Field::m_parent, Slic3r::GUI::Field::m_value, m_values, rebuild_ui(), Slic3r::ConfigOptionVector< T >::values, and window.

Here is the call graph for this function:

◆ combine_side_text()

const bool Slic3r::GUI::Field::combine_side_text ( )
inlineinherited
296{ return m_combine_side_text; } // BBS: new param style
bool m_combine_side_text
Definition Field.hpp:305

References m_combine_side_text.

Referenced by Slic3r::GUI::OG_CustomCtrl::get_pos(), and Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ Create()

template<class T>
t_field Slic3r::GUI::Field::Create ( wxWindow * parent,
const ConfigOptionDef & opt,
const t_config_option_key & id )
inlinestaticinherited

Factory method for generating new derived classes.

p;

279 {
280 auto p = Slic3r::make_unique<T>(parent, opt, id);
281 p->PostInitialize();
282 return std::move(p);
283 }
std::unique_ptr< T > make_unique(Args &&... args)
Definition libslic3r.h:239

References Slic3r::make_unique().

Referenced by Slic3r::GUI::OptionsGroup::build_field().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ def_width()

int Slic3r::GUI::Field::def_width ( )
staticinherited
401{ return 8; }

Referenced by Slic3r::GUI::OptionsGroup::activate_line().

Here is the caller graph for this function:

◆ def_width_thinner()

int Slic3r::GUI::Field::def_width_thinner ( )
staticinherited
403{ return 4; }

Referenced by Slic3r::GUI::DiamTextCtrl::DiamTextCtrl(), Slic3r::GUI::OptionsGroup::activate_line(), and Slic3r::GUI::ObjectTableSettings::update_settings_list().

Here is the caller graph for this function:

◆ def_width_wider()

◆ disable()

void Slic3r::GUI::PluginField::disable ( )
overridevirtual

Implements Slic3r::GUI::Field.

2506{
2507 for (auto& row : m_rows) {
2508 if (row.display)
2509 row.display->Disable();
2510 if (row.remove_btn)
2511 row.remove_btn->Disable();
2512 }
2514 m_standalone_add_btn->Disable();
2515}

References m_rows, and m_standalone_add_btn.

◆ display_name_for_value()

wxString Slic3r::GUI::PluginField::display_name_for_value ( const std::string & value) const
private
2378{
2379 if (value.empty())
2380 return _L("No plugin selected");
2381
2382 return from_u8(value);
2383}
wxString from_u8(const std::string &str)
Definition GUI.cpp:544

References _L, and Slic3r::GUI::from_u8().

Referenced by on_select_clicked(), and rebuild_ui().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ edit_bitmap()

const wxBitmap * Slic3r::GUI::UndoValueUIManager::edit_bitmap ( ) const
inlineinherited
175{ return &m_edit_ui.bitmap->bmp(); }
EditValueUI m_edit_ui
Definition Field.hpp:144

References m_edit_ui.

Referenced by Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ edit_tooltip()

const wxString * Slic3r::GUI::UndoValueUIManager::edit_tooltip ( ) const
inlineinherited
176{ return &m_edit_ui.tooltip; }

References m_edit_ui.

◆ enable()

void Slic3r::GUI::PluginField::enable ( )
overridevirtual

Implements Slic3r::GUI::Field.

2494{
2495 for (auto& row : m_rows) {
2496 if (row.display)
2497 row.display->Enable();
2498 if (row.remove_btn)
2499 row.remove_btn->Enable();
2500 }
2502 m_standalone_add_btn->Enable();
2503}

References m_rows, and m_standalone_add_btn.

◆ Field() [1/2]

Slic3r::GUI::Field::Field ( const ConfigOptionDef & opt,
const t_config_option_key & id )
inlineprivate
265: m_opt(opt), m_opt_id(id) {}
const t_config_option_key m_opt_id
Definition Field.hpp:236

Referenced by PluginField(), and PluginField().

Here is the caller graph for this function:

◆ Field() [2/2]

Slic3r::GUI::Field::Field ( wxWindow * parent,
const ConfigOptionDef & opt,
const t_config_option_key & id )
inlineprivate
266: m_parent(parent), m_opt(opt), m_opt_id(id) {}

◆ field_changed()

void Slic3r::GUI::Field::field_changed ( )
inlineinherited
263{ on_change_field(); }
void on_change_field()
Call the attached on_change method.
Definition Field.cpp:412

References on_change_field().

Referenced by Slic3r::GUI::Tab::commit_preset_config_value().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ get_blink_ptr()

bool * Slic3r::GUI::UndoValueUIManager::get_blink_ptr ( )
inlineinherited
171{ return &m_undo_ui.blink; }

References m_undo_ui.

Referenced by Slic3r::GUI::ConfigOptionsGroup::get_custom_ctrl_with_blinking_ptr().

Here is the caller graph for this function:

◆ get_enter_pressed()

bool Slic3r::GUI::Field::get_enter_pressed ( ) const
inlineinherited
288{ return bEnterPressed; }
bool bEnterPressed
Definition Field.hpp:307

References bEnterPressed.

◆ get_row_value()

wxString Slic3r::GUI::PluginField::get_row_value ( size_t index) const
private
2443{
2444 if (index >= m_rows.size() || !m_rows[index].display)
2445 return wxEmptyString;
2446 return m_rows[index].display->GetValue();
2447}

References m_rows.

◆ get_tooltip_text()

wxString Slic3r::GUI::Field::get_tooltip_text ( const wxString & default_string)
virtualinherited
442{
443 wxString tooltip_text = get_formatted_tooltip_text(m_opt, m_opt_id);
444
445 return tooltip_text.length() > 0 ? tooltip_text : default_string;
446}
wxString get_formatted_tooltip_text(const ConfigOptionDef &opt, const t_config_option_key &id)
Definition Field.cpp:163

References Slic3r::GUI::get_formatted_tooltip_text(), m_opt, and m_opt_id.

Referenced by Slic3r::GUI::PluginField::add_plugin_row(), Slic3r::GUI::CheckBox::BUILD(), Slic3r::GUI::Choice::BUILD(), Slic3r::GUI::ColourPicker::BUILD(), Slic3r::GUI::PluginConfigField::BUILD(), Slic3r::GUI::PointCtrl::BUILD(), Slic3r::GUI::PrinterAgentChoice::BUILD(), Slic3r::GUI::SpinCtrl::BUILD(), Slic3r::GUI::StaticText::BUILD(), Slic3r::GUI::TextCtrl::BUILD(), and Slic3r::GUI::PluginField::set_row_value().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ get_value()

boost::any & Slic3r::GUI::PluginField::get_value ( )
overridevirtual

Gets a boost::any representing this control. subclasses should overload with a specific version.

Implements Slic3r::GUI::Field.

2488{
2489 m_value = m_values;
2490 return m_value;
2491}

References Slic3r::GUI::Field::m_value, and m_values.

◆ get_value_by_opt_type()

void Slic3r::GUI::Field::get_value_by_opt_type ( wxString & str,
const bool check_value = true )
inherited
455{
456 switch (m_opt.type) {
457 case coInts:
458 case coInt: {
459 long val = 0;
460
461 bool is_na_value = m_opt.nullable && str == m_na_value;
462
463 if (is_na_value)
465 else if (!str.ToLong(&val)) {
466 if (!check_value) {
467 m_value.clear();
468 break;
469 }
470 show_error(m_parent, _(L("Invalid numeric.")));
471 set_value(int(val), true);
472 }
473
474 if (!m_opt.is_value_valid(double(val))) {
475 if (!check_value) {
476 m_value.clear();
477 break;
478 }
479
480 if (!is_na_value) {
481 // Orca: no need to check ranges for the nil value
482 show_error(m_parent, _L("Value is out of range."));
483
484 int min = static_cast<int>(m_opt.min);
485 int max = static_cast<int>(m_opt.max);
486
487 if (min > val) val = min;
488 if (val > max) val = max;
489
490 set_value(int(val), true);
491 }
492 }
493
494 m_value = int(val);
495 break;
496 }
497 case coPercent:
498 case coPercents:
499 case coFloats:
500 case coFloat:{
501 if (m_opt.type == coPercent && !str.IsEmpty() && str.Last() == '%')
502 str.RemoveLast();
503 else if (!str.IsEmpty() && str.Last() == '%')
504 {
505 if (!check_value) {
506 m_value.clear();
507 break;
508 }
509
510 wxString label = m_opt.full_label.empty() ? _(m_opt.label) : _(m_opt.full_label);
511 show_error(m_parent, from_u8((boost::format(_utf8(L("%s can\u2019t be a percentage"))) % into_u8(label)).str()));
512 set_value(double_to_string(m_opt.min), true);
513 m_value = double(m_opt.min);
514 break;
515 }
516 double val;
517
518 bool is_na_value = m_opt.nullable && str == m_na_value;
519
520 const char dec_sep = is_decimal_separator_point() ? '.' : ',';
521 const char dec_sep_alt = dec_sep == '.' ? ',' : '.';
522 // Replace the first incorrect separator in decimal number,
523 // if this value doesn't "N/A" value in some language
524 if (!is_na_value && str.Replace(dec_sep_alt, dec_sep, false) != 0)
525 set_value(str, false);
526
527 if (str == dec_sep)
528 val = 0.0;
529 else
530 {
531 if (is_na_value)
533 else if (!str.ToDouble(&val))
534 {
535 if (!check_value) {
536 m_value.clear();
537 break;
538 }
539 show_error(m_parent, _(L("Invalid numeric.")));
540 set_value(double_to_string(val), true);
541 }
542 if (!m_opt.is_value_valid(val))
543 {
544 if (!check_value) {
545 m_value.clear();
546 break;
547 }
548 std::string opt_key_without_idx = m_opt_id.substr(0, m_opt_id.find('#'));
549 if (m_opt_id == "filament_flow_ratio") {
550 if (m_value.empty() || boost::any_cast<double>(m_value) != val) {
551 wxString msg_text = format_wxstr(_L("Value %s is out of range, continue?"), str);
552// wxMessageDialog dialog(m_parent, msg_text, _L("Parameter validation") + ": " + m_opt_id, wxICON_WARNING | wxYES | wxNO);
553 WarningDialog dialog(m_parent, msg_text, _L("Parameter validation") + ": " + m_opt_id, wxYES | wxNO);
554 if (dialog.ShowModal() == wxID_NO) {
555 if (m_value.empty()) {
556 if (m_opt.min > val) val = m_opt.min;
557 if (val > m_opt.max) val = m_opt.max;
558 }
559 else
560 val = boost::any_cast<double>(m_value);
561 set_value(double_to_string(val), true);
562 }
563 }
564 }
565 else if(m_opt_id == "filament_retraction_distances_when_cut" || opt_key_without_idx == "retraction_distances_when_cut"){
566 if (m_value.empty() || boost::any_cast<double>(m_value) != val) {
567 wxString msg_text = format_wxstr(_L("Value %s is out of range. The valid range is from %d to %d."), str, m_opt.min, m_opt.max);
568 WarningDialog dialog(m_parent, msg_text, _L("Parameter validation") + ": " + m_opt_id, wxOK);
569 if (dialog.ShowModal()) {
570 if (m_value.empty()) {
571 if (m_opt.min > val) val = m_opt.min;
572 if (val > m_opt.max) val = m_opt.max;
573 }
574 else
575 val = boost::any_cast<double>(m_value);
576 set_value(double_to_string(val), true);
577 }
578 }
579 }
580 else if (!is_na_value) {
581 // Orca: no need to check ranges for the nil value
582 show_error(m_parent, _L("Value is out of range."));
583 if (m_opt.min > val) val = m_opt.min;
584 if (val > m_opt.max) val = m_opt.max;
585 set_value(double_to_string(val), true);
586 }
587 }
588 }
589 m_value = val;
590 break; }
591 case coString:
592 case coStrings:
593 case coFloatOrPercent:
594 case coFloatsOrPercents: {
595 if ((m_opt.type == coFloatOrPercent || m_opt.type == coFloatsOrPercents) && !str.IsEmpty() &&
596 !(m_opt.nullable && str == m_na_value)) {
597 bool update_control = false;
598 wxString numeric_str = str;
599 double val = 0.;
600
601 const char dec_sep = is_decimal_separator_point() ? '.' : ',';
602 const char dec_sep_alt = dec_sep == '.' ? ',' : '.';
603 // Orca: normalize the decimal separator and optional unit before
604 // detecting the percentage suffix and parsing the numeric part.
605 update_control |= numeric_str.Replace(dec_sep_alt, dec_sep, false) != 0;
606 update_control |= numeric_str.Replace(" ", "", true) != 0;
607 const bool has_literal_unit = numeric_str.EndsWith("mm");
608 if (has_literal_unit) {
609 numeric_str.RemoveLast(2);
610 update_control = true;
611 }
612 bool is_percent = !numeric_str.IsEmpty() && numeric_str.Last() == '%';
613 if (is_percent)
614 numeric_str.RemoveLast();
615
616 if ((has_literal_unit && is_percent) || !numeric_str.ToDouble(&val) || !std::isfinite(val)) {
617 if (!check_value) {
618 m_value.clear();
619 break;
620 }
621 show_error(m_parent, _L("Invalid numeric."));
622 numeric_str = double_to_string(std::clamp(0., double(m_opt.min), double(m_opt.max)));
623 is_percent = false;
624 update_control = true;
625 } else {
626 const bool looks_like_missing_percent = !is_percent && !has_literal_unit &&
627 ((m_opt.sidetext.rfind("mm/s") != std::string::npos && val > m_opt.max) ||
628 (m_opt.sidetext.rfind("mm ") != std::string::npos && val > m_opt.max_literal));
629 // Orca: validate explicit percentages and literal values before
630 // asking whether an otherwise valid literal was meant as a percentage.
631 const bool out_of_range = !m_opt.is_value_valid(val);
632 if (out_of_range) {
633 if (!check_value) {
634 m_value.clear();
635 break;
636 }
637 show_error(m_parent, _L("Value is out of range."));
638 val = std::clamp(val, double(m_opt.min), double(m_opt.max));
639 // Orca: retain the inferred percent unit when clamping a
640 // suspicious unitless value, so 2000 becomes 100%, not 100 mm.
641 is_percent |= looks_like_missing_percent;
642 numeric_str = double_to_string(val);
643 update_control = true;
644 } else {
645 const bool value_changed = m_value.empty() || into_u8(str) != boost::any_cast<std::string>(m_value);
646 if (looks_like_missing_percent && value_changed) {
647 if (!check_value) {
648 m_value.clear();
649 break;
650 }
651
652 const std::string sidetext = m_opt.sidetext.rfind("mm/s") != std::string::npos ? "mm/s" : "mm";
653 const wxString stVal = numeric_str;
654 const wxString msg_text = from_u8((boost::format(_utf8(L("Is it %s%% or %s %s?"))) %
655 stVal % stVal % sidetext).str());
656 WarningDialog dialog(m_parent, msg_text, _L("Parameter validation") + ": " + m_opt_id, wxYES | wxNO);
657 dialog.SetButtonLabel(wxID_YES, stVal + _L("%"));
658 dialog.SetButtonLabel(wxID_NO, stVal + " " + _L(sidetext));
659 dialog.GetSizer()->SetSizeHints(&dialog);
660 dialog.Fit();
661 dialog.CenterOnParent();
662 is_percent = dialog.ShowModal() == wxID_YES;
663 update_control = true;
664 }
665 }
666
667 // Orca: also enforce the literal limit after clamping an explicit mm input.
668 if (!is_percent && m_opt.sidetext.rfind("mm ") != std::string::npos && val > m_opt.max_literal) {
669 if (!check_value) {
670 m_value.clear();
671 break;
672 }
673 if (!out_of_range)
674 show_error(m_parent, _L("Value is out of range."));
675 val = m_opt.max_literal;
676 numeric_str = double_to_string(val);
677 update_control = true;
678 }
679 }
680
681 if (update_control) {
682 str = numeric_str + (is_percent ? "%" : "");
683 set_value(str, true);
684 }
685 }
686 if (m_opt.opt_key == "thumbnails") {
687 wxString str_out = str;
689 if (errors != enum_bitmask<ThumbnailError>()) {
690 set_value(str_out, true);
691 wxString error_str;
692 if (errors.has(ThumbnailError::InvalidVal))
693 error_str += format_wxstr(_L("Invalid input format. Expected vector of dimensions in the following format: \"%1%\""),
694 "XxY/EXT, XxY/EXT, ...");
695 if (errors.has(ThumbnailError::OutOfRange)) {
696 if (!error_str.empty())
697 error_str += "\n\n";
698 error_str += _L("Input value is out of range");
699 }
700 if (errors.has(ThumbnailError::InvalidExt)) {
701 if (!error_str.empty())
702 error_str += "\n\n";
703 error_str += _L("Some extension in the input is invalid");
704 }
705 show_error(m_parent, error_str);
706 } else if (str_out != str) {
707 str = str_out;
708 set_value(str, true);
709 }
710 } else if (m_opt.opt_key == "sparse_infill_rotate_template" || m_opt.opt_key == "solid_infill_rotate_template") {
711 std::string ustr(str.utf8_string());
713 std::string v;
714 std::smatch match;
715 std::string ps = (m_opt.opt_key == "sparse_infill_rotate_template") ?
716 u8"[BT][!]?|[#][\\d]+[!]?|[+\\-]?[\\d.]+[%]?[*]?[\\d]*[/NnZz$LlUuQq~^|#]?[+\\-]?[\\d.]*[%#\'\"cm]?[m]?[BT]?[!*]?" :
717 u8"[#][\\d]+[!]?|[+\\-]?[\\d.]+[%]?[*]?[\\d]*[/NnZz$LlUuQq~^|#]?[+\\-]?[\\d.]*[%#\'\"cm]?[m]?[!*]?";
718
719 while (std::regex_search(ustr, match, std::regex(ps))) {
720 for (auto x : match) v += x.str() + ", ";
721 ustr = match.suffix().str();
722 }
723 v = v.substr(0, v.length() - 2);
724 try {
725 this->set_value(from_u8(v), true);
726 m_value = into_u8(v);
727 } catch (...) {
728 show_error(m_parent, format_wxstr(_L("This parameter expects a valid template.")));
729 wxString old_value(boost::any_cast<std::string>(m_value));
730 this->set_value(old_value, true); // Revert to previous value
731 }
732 } else {
733 // Valid string, so update m_value with the new string from the control.
734 m_value = into_u8(str);
735 }
736 break;
737 } else if (m_opt.opt_key == "bed_exclude_volumes" || m_opt.opt_key == "extruder_bed_exclude_volumes") {
738 const std::string definition = into_u8(str);
739 if (!is_valid_bed_exclude_volumes_string(definition, std::numeric_limits<double>::max())) {
740 show_error(m_parent, _L("Invalid collision volume format. Use XxY, XxY, ... or ZMIN..ZMAX;XxY, XxY, ... and separate multiple volumes with |."));
741 const std::string old_value = m_value.empty() ? std::string{} : boost::any_cast<std::string>(m_value);
742 set_value(from_u8(old_value), true);
743 break;
744 }
745 } else if (m_opt.opt_key == "extra_solid_infills") {
746 std::string ustr(str.utf8_string());
747 // New rule: accept either interval form (N or N#K) or explicit list (e.g. 1,7,9), with optional quotes.
748 const std::regex rx_interval(u8R"(^\s*['"]?\s*\d+\s*(?:#\s*\d*)?\s*['"]?\s*$)");
749 // List entries may be plain numbers or number with optional #K count, e.g., 5, 9#2, 18
750 const std::regex rx_list(u8R"(^\s*['"]?\s*\d+(?:\s*#\s*\d*)?(?:\s*,\s*\d+(?:\s*#\s*\d*)?)*\s*['"]?\s*$)");
751 bool is_valid = ustr.empty() || std::regex_match(ustr, rx_interval) || std::regex_match(ustr, rx_list);
752 if (!is_valid) {
753 show_error(m_parent, format_wxstr(_L("Invalid pattern. Use N, N#K, or a comma-separated list with optional #K per entry. Examples: 5, 5#2, 1,7,9, 5,9#2,18.")));
754 wxString old_value(boost::any_cast<std::string>(m_value));
755 this->set_value(old_value, true); // Revert to previous value
756 }
757 // Valid string or empty, so update m_value with the new string from the control.
758 m_value = into_u8(str);
759 break;
760 }
761
762 m_value = into_u8(str);
763 break; }
764 case coPoint:{
765 Vec2d out_value;
766 str.Replace(" ", wxEmptyString, true);
767 if (!str.IsEmpty()) {
768 bool invalid_val = true;
769 double x, y;
770 wxStringTokenizer thumbnail(str, "x");
771 if (thumbnail.HasMoreTokens()) {
772 wxString x_str = thumbnail.GetNextToken();
773 if (x_str.ToDouble(&x) && thumbnail.HasMoreTokens()) {
774 wxString y_str = thumbnail.GetNextToken();
775 if (y_str.ToDouble(&y) && !thumbnail.HasMoreTokens()) {
776 out_value = Vec2d(x, y);
777 invalid_val = false;
778 }
779 }
780 }
781
782 if (invalid_val) {
783 wxString text_value;
784 if (!m_value.empty()) text_value = get_thumbnail_string(boost::any_cast<Vec2d>(m_value));
785 set_value(text_value, true);
786 show_error(m_parent, format_wxstr(_L("Invalid format. Expected vector format: \"%1%\""), "XxY, XxY, ..."));
787 }
788 }
789
790 m_value = out_value;
791 break; }
792
793 case coPoints: {
794 std::vector<Vec2d> out_values;
795 str.Replace(" ", wxEmptyString, true);
796 const bool bed_exclusion_volume_syntax = m_opt_id == "bed_exclude_area" &&
797 (str.Find("|") != wxNOT_FOUND || (str.Find("..") != wxNOT_FOUND && str.Find(";") != wxNOT_FOUND));
798 if (bed_exclusion_volume_syntax) {
799 // Leave volume validation and the copy prompt to the printer tab.
800 m_value = into_u8(str);
801 break;
802 }
803 if (!str.IsEmpty()) {
804 bool invalid_val = false;
805 wxStringTokenizer points(str, ",");
806 while (points.HasMoreTokens()) {
807 wxString token = points.GetNextToken();
808 double x, y;
809 wxStringTokenizer thumbnail(token, "x");
810 if (thumbnail.HasMoreTokens()) {
811 wxString x_str = thumbnail.GetNextToken();
812 if (x_str.ToDouble(&x) && thumbnail.HasMoreTokens()) {
813 wxString y_str = thumbnail.GetNextToken();
814 if (y_str.ToDouble(&y) && !thumbnail.HasMoreTokens()) {
815 out_values.push_back(Vec2d(x, y));
816 continue;
817 }
818 }
819 }
820 invalid_val = true;
821 break;
822 }
823
824 if (invalid_val) {
825 wxString text_value;
826 if (!m_value.empty() && boost::any_cast<std::vector<Vec2d>>(&m_value) != nullptr)
827 text_value = get_thumbnails_string(boost::any_cast<std::vector<Vec2d>>(m_value));
828 set_value(text_value, true);
829 show_error(m_parent, format_wxstr(_L("Invalid format. Expected vector format: \"%1%\""), "XxY, XxY, ..."));
830 break;
831 }
832 }
833
834 m_value = out_values;
835 break; }
836
837 default:
838 break;
839 }
840}
#define _(s)
Definition 3mf.cpp:306
#define L(s)
Definition ExtrusionEntity.cpp:25
static double nil_value()
Definition Config.hpp:899
static bool validate_string(const std::string &str)
Definition Config.hpp:959
static int nil_value()
Definition Config.hpp:1083
virtual void set_value(const boost::any &value, bool change_event)=0
Sets a value for this control. subclasses should overload with a specific version Postcondition: Meth...
wxString m_na_value
Definition Field.hpp:309
wxString double_to_string(double const value, const int max_precision)
Definition Field.cpp:99
wxString format_wxstr(const char *fmt, TArgs &&... args)
Definition format.hpp:22
void show_error(wxWindow *parent, const wxString &message, bool has_code_excerpts)
Definition GUI.cpp:296
ThumbnailErrors validate_thumbnails_string(wxString &str, const wxString &def_ext="PNG")
Definition Field.cpp:145
std::string into_u8(const wxString &str)
Definition GUI.cpp:549
wxString get_thumbnail_string(const Vec2d &value)
Definition Field.cpp:129
wxString get_thumbnails_string(const std::vector< Vec2d > &values)
Definition Field.cpp:135
enum_bitmask< ThumbnailError > ThumbnailErrors
Definition Thumbnails.hpp:22
@ OutOfRange
Definition Thumbnails.hpp:21
@ InvalidVal
Definition Thumbnails.hpp:21
@ InvalidExt
Definition Thumbnails.hpp:21
bool is_decimal_separator_point()
Definition LocalesUtils.cpp:78
bool is_valid_bed_exclude_volumes_string(const std::string &value, const double printable_height)
Definition PrintConfig.cpp:14298
@ coFloatsOrPercents
Definition Config.hpp:202
@ coString
Definition Config.hpp:192
@ coPoint
Definition Config.hpp:204
@ coPercents
Definition Config.hpp:198
@ coInts
Definition Config.hpp:190
@ coPoints
Definition Config.hpp:206
@ coInt
Definition Config.hpp:188
@ coFloat
Definition Config.hpp:184
@ coFloatOrPercent
Definition Config.hpp:200
@ coFloats
Definition Config.hpp:186
@ coPercent
Definition Config.hpp:196
Eigen::Matrix< double, 2, 1, Eigen::DontAlign > Vec2d
Definition Point.hpp:67
bool is_valid(const FontFile &font, unsigned int index)
Definition Emboss.cpp:284
#define _utf8(s)
Definition I18N.hpp:10

References _, _L, _utf8, Slic3r::coFloat, Slic3r::coFloatOrPercent, Slic3r::coFloats, Slic3r::coFloatsOrPercents, Slic3r::coInt, Slic3r::coInts, Slic3r::coPercent, Slic3r::coPercents, Slic3r::coPoint, Slic3r::coPoints, Slic3r::coString, Slic3r::coStrings, Slic3r::GUI::double_to_string(), Slic3r::GUI::format_wxstr(), Slic3r::GUI::from_u8(), Slic3r::GUI::get_thumbnail_string(), Slic3r::GUI::get_thumbnails_string(), Slic3r::enum_bitmask< option_type, typename >::has(), Slic3r::GUI::into_u8(), Slic3r::InvalidExt, Slic3r::InvalidVal, Slic3r::is_decimal_separator_point(), Slic3r::is_valid_bed_exclude_volumes_string(), L, m_na_value, m_opt, m_opt_id, m_parent, m_value, Slic3r::ConfigOptionFloatsTempl< true >::nil_value(), Slic3r::ConfigOptionIntsTempl< true >::nil_value(), Slic3r::OutOfRange, set_value(), Slic3r::GUI::MsgDialog::SetButtonLabel(), Slic3r::GUI::show_error(), Slic3r::GUI::DPIAware< P >::ShowModal(), Slic3r::ConfigOptionFloatsTempl< false >::validate_string(), and Slic3r::GUI::validate_thumbnails_string().

Referenced by Slic3r::GUI::Choice::get_value(), Slic3r::GUI::TextCtrl::get_value(), Slic3r::GUI::TextCtrl::set_value(), and Slic3r::GUI::TextCtrl::value_was_changed().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ getSizer()

virtual wxSizer * Slic3r::GUI::Field::getSizer ( )
inlinevirtualinherited

If you don't know what you are getting back, check both methods for nullptr.

Reimplemented in Slic3r::GUI::PointCtrl, and Slic3r::GUI::SliderCtrl.

270{ return nullptr; }

Referenced by Slic3r::GUI::OG_CustomCtrl::CtrlLine::correct_items_positions(), Slic3r::GUI::is_bad_field(), Slic3r::GUI::is_sizer_field(), Slic3r::GUI::is_window_field(), Slic3r::GUI::OG_CustomCtrl::CtrlLine::render(), and Slic3r::GUI::OG_CustomCtrl::CtrlLine::update_visibility().

Here is the caller graph for this function:

◆ getWindow()

wxWindow * Slic3r::GUI::PluginField::getWindow ( )
inlineoverridevirtual

Reimplemented from Slic3r::GUI::Field.

544{ return window; }

References window.

◆ has_edit_ui()

bool Slic3r::GUI::UndoValueUIManager::has_edit_ui ( ) const
inlineinherited
174{ return !m_edit_ui.tooltip.IsEmpty(); }

References m_edit_ui.

Referenced by Slic3r::GUI::Tab::decorate(), and Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ has_undo_ui()

bool Slic3r::GUI::UndoValueUIManager::has_undo_ui ( ) const
inlineinherited
160{ return m_undo_ui.undo_bitmap != nullptr; }

References m_undo_ui.

Referenced by Slic3r::GUI::OG_CustomCtrl::get_pos().

Here is the caller graph for this function:

◆ is_matched()

bool Slic3r::GUI::Field::is_matched ( const std::string & string,
const std::string & pattern )
inherited
449{
450 std::regex regex_pattern(pattern, std::regex_constants::icase); // use ::icase to make the matching case insensitive like /i in perl
451 return std::regex_match(string, regex_pattern);
452}

Referenced by Slic3r::GUI::SliderCtrl::BUILD().

Here is the caller graph for this function:

◆ label_color()

const wxColour * Slic3r::GUI::UndoValueUIManager::label_color ( ) const
inlineinherited
165{ return m_undo_ui.label_color; }

References m_undo_ui.

Referenced by Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ msw_rescale()

void Slic3r::GUI::PluginField::msw_rescale ( )
overridevirtual

Reimplemented from Slic3r::GUI::Field.

2518{
2520 rebuild_ui();
2521}
virtual void msw_rescale()
Definition Field.cpp:842

References Slic3r::GUI::Field::msw_rescale(), and rebuild_ui().

Here is the call graph for this function:

◆ on_add_clicked()

void Slic3r::GUI::PluginField::on_add_clicked ( )
private
2410{
2411 if (m_opt.readonly)
2412 return;
2413
2414 if (!m_selector)
2415 return;
2416
2417 std::string selected = m_selector();
2418 if (selected.empty())
2419 return;
2420
2421 m_values.push_back(selected);
2422 m_value = m_values;
2423
2424 // Defer: don't destroy the clicked button from inside its own handler.
2425 if(window)
2426 window->CallAfter([this]() {rebuild_ui(); on_change_field();});
2427}
std::function< std::string()> m_selector
Definition Field.hpp:570

References Slic3r::GUI::Field::m_opt, m_selector, Slic3r::GUI::Field::m_value, m_values, Slic3r::GUI::Field::on_change_field(), rebuild_ui(), and window.

Referenced by add_empty_state_row().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_back_to_initial_value()

void Slic3r::GUI::Field::on_back_to_initial_value ( )
inherited

Call the attached m_back_to_initial_value method.

420{
423}
t_back_to_init m_back_to_initial_value
Function object to store callback passed in from owning object.
Definition Field.hpp:223
bool m_is_modified_value
Definition Field.hpp:231

References m_back_to_initial_value, m_is_modified_value, and m_opt_id.

◆ on_back_to_sys_value()

void Slic3r::GUI::Field::on_back_to_sys_value ( )
inherited

Call the attached m_back_to_sys_value method.

426{
427 if (m_back_to_sys_value != nullptr && m_is_nonsys_value)
429}
t_back_to_init m_back_to_sys_value
Definition Field.hpp:224
bool m_is_nonsys_value
Definition Field.hpp:232

References m_back_to_sys_value, m_is_nonsys_value, and m_opt_id.

◆ on_change_field()

void Slic3r::GUI::Field::on_change_field ( )
protectedinherited

Call the attached on_change method.

413{
414// std::cerr << "calling Field::_on_change \n";
415 if (m_on_change != nullptr && !m_disable_change_event)
417}
t_change m_on_change
Function object to store callback passed in from owning object.
Definition Field.hpp:220
bool m_disable_change_event
Definition Field.hpp:230
virtual boost::any & get_value()=0
Gets a boost::any representing this control. subclasses should overload with a specific version.

References get_value(), m_disable_change_event, m_on_change, and m_opt_id.

Referenced by Slic3r::GUI::ColourPicker::apply_user_color(), Slic3r::GUI::CheckBox::BUILD(), Slic3r::GUI::Choice::BUILD(), Slic3r::GUI::PrinterAgentChoice::BUILD(), Slic3r::GUI::SliderCtrl::BUILD(), field_changed(), Slic3r::GUI::PluginField::on_add_clicked(), Slic3r::GUI::PluginField::on_remove_clicked(), Slic3r::GUI::PluginField::on_select_clicked(), Slic3r::GUI::PluginConfigField::open_dialog(), Slic3r::GUI::PointCtrl::propagate_input_value(), Slic3r::GUI::Choice::propagate_value(), Slic3r::GUI::SpinCtrl::propagate_value(), Slic3r::GUI::TextCtrl::propagate_value(), Slic3r::GUI::CheckBox::set_last_meaningful_value(), Slic3r::GUI::Choice::set_last_meaningful_value(), Slic3r::GUI::CheckBox::set_na_value(), Slic3r::GUI::Choice::set_na_value(), and Slic3r::GUI::PluginField::set_value().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_edit_value()

void Slic3r::GUI::Field::on_edit_value ( )
inherited

Call the attached m_fn_edit_value method.

432{
433 if (m_fn_edit_value)
435}
t_back_to_init m_fn_edit_value
Callback function to edit field value.
Definition Field.hpp:227

References m_fn_edit_value, and m_opt_id.

◆ on_kill_focus()

void Slic3r::GUI::Field::on_kill_focus ( )
protectedinherited

Call the attached on_kill_focus method. It's important to use wxEvent instead of wxFocusEvent, in another case we can't unfocused control at all.

406{
407 // call the registered function if it is available
408 if (m_on_kill_focus!=nullptr)
410}
t_kill_focus m_on_kill_focus
Function object to store callback passed in from owning object.
Definition Field.hpp:217

References m_on_kill_focus, and m_opt_id.

Referenced by Slic3r::GUI::PointCtrl::propagate_input_value(), Slic3r::GUI::Choice::propagate_value(), Slic3r::GUI::SpinCtrl::propagate_value(), and Slic3r::GUI::TextCtrl::propagate_value().

Here is the caller graph for this function:

◆ on_remove_clicked()

void Slic3r::GUI::PluginField::on_remove_clicked ( size_t index)
private
2430{
2431 if (m_opt.readonly || index >= m_values.size())
2432 return;
2433
2434 m_values.erase(m_values.begin() + index);
2435 m_value = m_values;
2436
2437 // Defer: don't destroy the clicked button from inside its own handler.
2438 if(window)
2439 window->CallAfter([this]() {rebuild_ui(); on_change_field();});
2440}

References Slic3r::GUI::Field::m_opt, Slic3r::GUI::Field::m_value, m_values, Slic3r::GUI::Field::on_change_field(), rebuild_ui(), and window.

Referenced by add_plugin_row().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ on_select_clicked()

void Slic3r::GUI::PluginField::on_select_clicked ( size_t index)
private
2386{
2387 if (index >= m_rows.size())
2388 return;
2389
2390 if (!m_selector)
2391 return;
2392
2393 std::string selected = m_selector();
2394 if (selected.empty())
2395 return;
2396
2397 if (index >= m_values.size())
2398 m_values.resize(index + 1);
2399
2400 if (m_values[index] == selected)
2401 return;
2402
2403 m_values[index] = selected;
2404 set_row_value(index, display_name_for_value(selected));
2405 m_value = m_values;
2407}
wxString display_name_for_value(const std::string &value) const
Definition Field.cpp:2377
void set_row_value(size_t index, const wxString &value)
Definition Field.cpp:2449

References display_name_for_value(), m_rows, m_selector, Slic3r::GUI::Field::m_value, m_values, Slic3r::GUI::Field::on_change_field(), and set_row_value().

Referenced by add_plugin_row().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ PostInitialize()

void Slic3r::GUI::Field::PostInitialize ( )
protectedvirtualinherited
332{
333 auto color = wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW);
334
335 switch (m_opt.type)
336 {
337 case coPercents:
338 case coFloats:
339 case coStrings:
340 case coBools:
341 case coInts:
342 // BBS
343 case coEnums: {
344 auto tag_pos = m_opt_id.find("#");
345 if (tag_pos != std::string::npos)
346 m_opt_idx = stoi(m_opt_id.substr(tag_pos + 1, m_opt_id.size()));
347 break;
348 }
349 default:
350 break;
351 }
352
353 // initialize m_unit_value
355 parent_is_custom_ctrl = dynamic_cast<OG_CustomCtrl*>(m_parent) != nullptr;
356
357 BUILD();
358
359 // For the mode, when settings are in non-modal dialog, neither dialog nor tabpanel doesn't receive wxEVT_KEY_UP event, when some field is selected.
360 // So, like a workaround check wxEVT_KEY_UP event for the Filed and switch between tabs if Ctrl+(1-4) was pressed
361 if (getWindow()) {
362 if (m_opt.readonly) {
363 this->disable();
364 } else {
365 this->enable();
366 }
367 getWindow()->Bind(wxEVT_KEY_UP, [](wxKeyEvent& evt) {
368 if ((evt.GetModifiers() & wxMOD_CONTROL) != 0) {
369 int tab_id = -1;
370 switch (evt.GetKeyCode()) {
371 case '1': { tab_id = 0; break; }
372 case '2': { tab_id = 1; break; }
373 case '3': { tab_id = 2; break; }
374 case '4': { tab_id = 3; break; }
375#ifdef __APPLE__
376 case 'f':
377#else /* __APPLE__ */
378 case WXK_CONTROL_F:
379#endif /* __APPLE__ */
380 case 'F': {
381 //wxGetApp().plater()->search(false, Preset::TYPE_MODEL, nullptr, nullptr);
382 break;
383 }
384 default: break;
385 }
386 if (tab_id >= 0) {
387 static constexpr const char* kShortcutTabIds[] = {TAB_ID_HOME, TAB_ID_PREPARE, TAB_ID_PREVIEW, TAB_ID_MONITOR};
388 wxGetApp().mainframe->select_tab(kShortcutTabIds[tab_id]);
389 }
390 if (tab_id > 0)
391 // tab panel should be focused for correct navigation between tabs
392 wxGetApp().tab_panel()->SetFocus();
393 }
394
395 evt.Skip();
396 }, getWindow()->GetId());
397 }
398}
#define TAB_ID_PREPARE
Definition MainFrame.hpp:60
#define TAB_ID_HOME
Definition MainFrame.hpp:56
#define TAB_ID_MONITOR
Definition MainFrame.hpp:62
#define TAB_ID_PREVIEW
Definition MainFrame.hpp:61
virtual void BUILD()=0
Finish constructing the Field's wxWidget-related properties, including setting its own sizer,...
virtual wxWindow * getWindow()
Definition Field.hpp:271
int m_em_unit
Definition Field.hpp:304
virtual void disable()=0
bool parent_is_custom_ctrl
Definition Field.hpp:240
int m_opt_idx
{""};
Definition Field.hpp:237
virtual void enable()=0
@ coBools
Definition Config.hpp:212
@ coEnums
Definition Config.hpp:216
int em_unit(wxWindow *win)
Definition wxExtensions.cpp:424

References BUILD(), Slic3r::coBools, Slic3r::coEnums, Slic3r::coFloats, Slic3r::coInts, Slic3r::coPercents, Slic3r::coStrings, disable(), em_unit(), enable(), getWindow(), m_em_unit, m_opt, m_opt_id, m_opt_idx, m_parent, parent_is_custom_ctrl, TAB_ID_HOME, TAB_ID_MONITOR, TAB_ID_PREPARE, and TAB_ID_PREVIEW.

Here is the call graph for this function:

◆ propagate_value()

virtual void Slic3r::GUI::Field::propagate_value ( )
inlinevirtualinherited

◆ rebuild_ui()

void Slic3r::GUI::PluginField::rebuild_ui ( )
private
2309{
2311
2312 if (m_main_sizer) {
2313 m_main_sizer->Clear(true);
2314 }
2315 m_rows.clear();
2316 m_standalone_add_btn = nullptr;
2317
2319 if (!m_values.empty()) {
2320 for (size_t i = 0; i < m_values.size(); ++i)
2322 }
2323
2324 if (window) {
2325 // Report the stacked rows' size so the option-group / OG_CustomCtrl allocate the right height.
2326 window->SetMinSize(m_main_sizer->CalcMin());
2327 window->Layout();
2328 window->Refresh();
2329 }
2330 if (m_parent)
2331 m_parent->Layout();
2332}
void add_empty_state_row()
Definition Field.cpp:2334
void add_plugin_row(const wxString &value=wxEmptyString, bool is_last=false)
Definition Field.cpp:2346
static void remove_empty_plugin_values(std::vector< std::string > &values)
Definition Field.cpp:2298

References add_empty_state_row(), add_plugin_row(), display_name_for_value(), m_main_sizer, Slic3r::GUI::Field::m_parent, m_rows, m_standalone_add_btn, m_values, Slic3r::GUI::remove_empty_plugin_values(), and window.

Referenced by BUILD(), msw_rescale(), on_add_clicked(), on_remove_clicked(), and set_value().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ set_edit_bitmap()

bool Slic3r::GUI::UndoValueUIManager::set_edit_bitmap ( const ScalableBitmap * bmp)
inlineinherited
156{ return m_edit_ui.set_bitmap(bmp); }

References m_edit_ui.

Referenced by Slic3r::GUI::Tab::decorate().

Here is the caller graph for this function:

◆ set_edit_tooltip()

bool Slic3r::GUI::UndoValueUIManager::set_edit_tooltip ( const wxString & tip)
inlineinherited
157{ return m_edit_ui.set_tooltip(tip); }

References m_edit_ui.

◆ set_enter_pressed()

void Slic3r::GUI::Field::set_enter_pressed ( bool pressed)
inlineinherited
289{ bEnterPressed = pressed; }

References bEnterPressed.

◆ set_label_colour()

bool Slic3r::GUI::UndoValueUIManager::set_label_colour ( const wxColour * clr)
inlineinherited
152{ return m_undo_ui.set_label_colour(clr); }

References m_undo_ui.

Referenced by Slic3r::GUI::Tab::create_line_with_widget(), Slic3r::GUI::Tab::decorate(), and Slic3r::GUI::Tab::update_label_colours().

Here is the caller graph for this function:

◆ set_last_meaningful_value()

virtual void Slic3r::GUI::Field::set_last_meaningful_value ( )
inlinevirtualinherited

◆ set_na_value()

virtual void Slic3r::GUI::Field::set_na_value ( )
inlinevirtualinherited

◆ set_row_value()

void Slic3r::GUI::PluginField::set_row_value ( size_t index,
const wxString & value )
private
2450{
2451 if (index >= m_rows.size() || !m_rows[index].display)
2452 return;
2453 m_rows[index].display->SetValue(value);
2454 m_rows[index].display->SetToolTip(get_tooltip_text(value));
2455}

References Slic3r::GUI::Field::get_tooltip_text(), and m_rows.

Referenced by on_select_clicked().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ set_selector()

void Slic3r::GUI::PluginField::set_selector ( std::function< std::string()> selector)
2294{
2295 m_selector = std::move(selector);
2296}

References m_selector.

◆ set_undo_bitmap()

bool Slic3r::GUI::UndoValueUIManager::set_undo_bitmap ( const ScalableBitmap * bmp)
inlineinherited
150{ return m_undo_ui.set_undo_bitmap(bmp); }

References m_undo_ui.

Referenced by Slic3r::GUI::Tab::create_line_with_widget(), and Slic3r::GUI::Tab::decorate().

Here is the caller graph for this function:

◆ set_undo_to_sys_bitmap()

bool Slic3r::GUI::UndoValueUIManager::set_undo_to_sys_bitmap ( const ScalableBitmap * bmp)
inlineinherited
151{ return m_undo_ui.set_undo_to_sys_bitmap(bmp); }

References m_undo_ui.

Referenced by Slic3r::GUI::Tab::create_line_with_widget(), and Slic3r::GUI::Tab::decorate().

Here is the caller graph for this function:

◆ set_undo_to_sys_tooltip()

bool Slic3r::GUI::UndoValueUIManager::set_undo_to_sys_tooltip ( const wxString * tip)
inlineinherited
154{ return m_undo_ui.set_undo_to_sys_tooltip(tip); }

References m_undo_ui.

Referenced by Slic3r::GUI::Tab::create_line_with_widget(), and Slic3r::GUI::Tab::decorate().

Here is the caller graph for this function:

◆ set_undo_tooltip()

bool Slic3r::GUI::UndoValueUIManager::set_undo_tooltip ( const wxString * tip)
inlineinherited
153{ return m_undo_ui.set_undo_tooltip(tip); }

References m_undo_ui.

Referenced by Slic3r::GUI::Tab::create_line_with_widget(), and Slic3r::GUI::Tab::decorate().

Here is the caller graph for this function:

◆ set_value()

void Slic3r::GUI::PluginField::set_value ( const boost::any & value,
bool change_event = false )
overridevirtual

Sets a value for this control. subclasses should overload with a specific version Postcondition: Method does not fire the on_change event.

Implements Slic3r::GUI::Field.

2458{
2459 m_disable_change_event = !change_event;
2460
2461 if (value.empty()) {
2462 m_values.clear();
2463 } else if (value.type() == typeid(std::vector<std::string>)) {
2464 m_values = boost::any_cast<std::vector<std::string>>(value);
2465 } else if (value.type() == typeid(wxString)) {
2466 m_values.clear();
2467 wxString text = boost::any_cast<wxString>(value);
2468 if (!text.IsEmpty())
2469 m_values.push_back(into_u8(text));
2470 } else if (value.type() == typeid(std::string)) {
2471 m_values.clear();
2472 std::string text = boost::any_cast<std::string>(value);
2473 if (!text.empty())
2474 m_values.push_back(text);
2475 }
2476
2477 rebuild_ui();
2478
2479 m_value = m_values;
2480
2481 m_disable_change_event = false;
2482
2483 if (change_event)
2485}

References Slic3r::GUI::into_u8(), Slic3r::GUI::Field::m_disable_change_event, Slic3r::GUI::Field::m_value, m_values, Slic3r::GUI::Field::on_change_field(), and rebuild_ui().

Here is the call graph for this function:

◆ sys_color_changed()

void Slic3r::GUI::Field::sys_color_changed ( )
virtualinherited

Reimplemented in Slic3r::GUI::ColourPicker, and Slic3r::GUI::PointCtrl.

849{
850#ifdef _WIN32
851 if (wxWindow* win = this->getWindow())
852 wxGetApp().UpdateDarkUI(win);
853#endif
854}

References getWindow().

Here is the call graph for this function:

◆ toggle()

void Slic3r::GUI::Field::toggle ( bool en)
inherited

Fires the enable or disable function, based on the input.

439{ en && !m_opt.readonly ? enable() : disable(); }

References disable(), enable(), and m_opt.

Referenced by Slic3r::GUI::Tab::compatible_widget_reload(), Slic3r::GUI::Tab::toggle_option(), Slic3r::GUI::ObjectSettings::update_config_values(), Slic3r::GUI::ObjectTableSettings::update_config_values(), Slic3r::GUI::TabFilament::update_filament_overrides_page(), and Slic3r::GUI::ObjectTableSettings::update_settings_list().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ undo_bitmap()

const ScalableBitmap * Slic3r::GUI::UndoValueUIManager::undo_bitmap ( ) const
inlineinherited
161{ return m_undo_ui.undo_bitmap; }

References m_undo_ui.

Referenced by Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ undo_to_sys_bitmap()

const ScalableBitmap * Slic3r::GUI::UndoValueUIManager::undo_to_sys_bitmap ( ) const
inlineinherited
163{ return m_undo_ui.undo_to_sys_bitmap; }

References m_undo_ui.

Referenced by Slic3r::GUI::OG_CustomCtrl::CtrlLine::render().

Here is the caller graph for this function:

◆ undo_to_sys_tooltip()

const wxString * Slic3r::GUI::UndoValueUIManager::undo_to_sys_tooltip ( ) const
inlineinherited
164{ return m_undo_ui.undo_to_sys_tooltip; }

References m_undo_ui.

◆ undo_tooltip()

const wxString * Slic3r::GUI::UndoValueUIManager::undo_tooltip ( ) const
inlineinherited
162{ return m_undo_ui.undo_tooltip; }

References m_undo_ui.

◆ update_na_value()

virtual void Slic3r::GUI::Field::update_na_value ( const boost::any & value)
inlinevirtualinherited

Reimplemented in Slic3r::GUI::TextCtrl.

249{}

Referenced by Slic3r::GUI::TabFilament::update_filament_overrides_page().

Here is the caller graph for this function:

Member Data Documentation

◆ bEnterPressed

bool Slic3r::GUI::Field::bEnterPressed = false
protectedinherited

◆ m_back_to_initial_value

t_back_to_init Slic3r::GUI::Field::m_back_to_initial_value { nullptr }
inherited

Function object to store callback passed in from owning object.

223{ nullptr };

Referenced by ~Field(), and on_back_to_initial_value().

◆ m_back_to_sys_value

t_back_to_init Slic3r::GUI::Field::m_back_to_sys_value { nullptr }
inherited
224{ nullptr };

Referenced by ~Field(), and on_back_to_sys_value().

◆ m_combine_side_text

◆ m_disable_change_event

◆ m_edit_ui

EditValueUI Slic3r::GUI::UndoValueUIManager::m_edit_ui
privateinherited

◆ m_em_unit

◆ m_fn_edit_value

t_back_to_init Slic3r::GUI::Field::m_fn_edit_value { nullptr }
inherited

Callback function to edit field value.

227{ nullptr };

Referenced by on_edit_value().

◆ m_is_modified_value

bool Slic3r::GUI::Field::m_is_modified_value {false}
inherited

◆ m_is_nonsys_value

bool Slic3r::GUI::Field::m_is_nonsys_value {true}
inherited
232{true};

Referenced by Slic3r::GUI::Tab::decorate(), and on_back_to_sys_value().

◆ m_last_meaningful_value

◆ m_main_sizer

wxBoxSizer* Slic3r::GUI::PluginField::m_main_sizer { nullptr }
private
566{ nullptr };

Referenced by add_empty_state_row(), add_plugin_row(), BUILD(), and rebuild_ui().

◆ m_na_value

wxString Slic3r::GUI::Field::m_na_value = _(L("N/A"))
protectedinherited

◆ m_on_change

t_change Slic3r::GUI::Field::m_on_change {nullptr}
inherited

Function object to store callback passed in from owning object.

220{nullptr};

Referenced by ~Field(), and on_change_field().

◆ m_on_kill_focus

t_kill_focus Slic3r::GUI::Field::m_on_kill_focus {nullptr}
inherited

Function object to store callback passed in from owning object.

217{nullptr};

Referenced by ~Field(), and on_kill_focus().

◆ m_opt

const ConfigOptionDef Slic3r::GUI::Field::m_opt {ConfigOptionDef()}
inherited

Copy of ConfigOption for deduction purposes.

235{ConfigOptionDef()};

Referenced by Field(), Field(), Slic3r::GUI::PluginField::add_plugin_row(), Slic3r::GUI::CheckBox::BUILD(), Slic3r::GUI::Choice::BUILD(), Slic3r::GUI::ColourPicker::BUILD(), Slic3r::GUI::PluginConfigField::BUILD(), Slic3r::GUI::PluginField::BUILD(), Slic3r::GUI::PointCtrl::BUILD(), Slic3r::GUI::PrinterAgentChoice::BUILD(), Slic3r::GUI::SliderCtrl::BUILD(), Slic3r::GUI::SpinCtrl::BUILD(), Slic3r::GUI::StaticText::BUILD(), Slic3r::GUI::TextCtrl::BUILD(), get_tooltip_text(), Slic3r::GUI::CheckBox::get_value(), Slic3r::GUI::Choice::get_value(), Slic3r::GUI::PointCtrl::get_value(), get_value_by_opt_type(), Slic3r::GUI::Choice::msw_rescale(), Slic3r::GUI::ColourPicker::msw_rescale(), Slic3r::GUI::PluginConfigField::msw_rescale(), Slic3r::GUI::PointCtrl::msw_rescale(), Slic3r::GUI::PrinterAgentChoice::msw_rescale(), Slic3r::GUI::StaticText::msw_rescale(), Slic3r::GUI::TextCtrl::msw_rescale(), Slic3r::GUI::PluginField::on_add_clicked(), Slic3r::GUI::PluginField::on_remove_clicked(), PostInitialize(), Slic3r::GUI::Choice::propagate_value(), Slic3r::GUI::TextCtrl::propagate_value(), Slic3r::GUI::CheckBox::set_last_meaningful_value(), Slic3r::GUI::Choice::set_last_meaningful_value(), Slic3r::GUI::CheckBox::set_na_value(), Slic3r::GUI::Choice::set_selection(), Slic3r::GUI::CheckBox::set_value(), Slic3r::GUI::Choice::set_value(), Slic3r::GUI::Choice::set_value(), Slic3r::GUI::PointCtrl::set_value(), Slic3r::GUI::TextCtrl::set_value(), toggle(), Slic3r::GUI::TabPrint::toggle_options(), Slic3r::GUI::PhysicalPrinterDialog::update_host_type(), and Slic3r::GUI::TextCtrl::value_was_changed().

◆ m_opt_id

◆ m_opt_idx

◆ m_parent

◆ m_rows

std::vector<PluginRow> Slic3r::GUI::PluginField::m_rows
private

◆ m_selector

std::function<std::string()> Slic3r::GUI::PluginField::m_selector
private

◆ m_standalone_add_btn

Button* Slic3r::GUI::PluginField::m_standalone_add_btn { nullptr }
private
569{ nullptr };

Referenced by add_empty_state_row(), disable(), enable(), and rebuild_ui().

◆ m_undo_ui

◆ m_value

◆ m_values

std::vector<std::string> Slic3r::GUI::PluginField::m_values
private

◆ opt_height

◆ parent_is_custom_ctrl

◆ window

wxWindow* Slic3r::GUI::PluginField::window { nullptr }
private
565{ nullptr }; // container panel that hosts m_main_sizer

Referenced by add_empty_state_row(), add_plugin_row(), BUILD(), getWindow(), on_add_clicked(), on_remove_clicked(), and rebuild_ui().


The documentation for this class was generated from the following files:
  • /home/runner/work/OrcaSlicer/OrcaSlicer/src/slic3r/GUI/Field.hpp
  • /home/runner/work/OrcaSlicer/OrcaSlicer/src/slic3r/GUI/Field.cpp