diff --git a/src/slic3r/CMakeLists.txt b/src/slic3r/CMakeLists.txt index 76fd8d989..08dd66d9d 100644 --- a/src/slic3r/CMakeLists.txt +++ b/src/slic3r/CMakeLists.txt @@ -97,6 +97,8 @@ set(SLIC3R_GUI_SOURCES GUI/SavePresetDialog.cpp GUI/PhysicalPrinterDialog.hpp GUI/PhysicalPrinterDialog.cpp + GUI/SimplificationDialog.cpp + GUI/SimplificationDialog.hpp GUI/GUI_Factories.cpp GUI/GUI_Factories.hpp GUI/GUI_ObjectList.cpp diff --git a/src/slic3r/GUI/GUI_Factories.cpp b/src/slic3r/GUI/GUI_Factories.cpp index c4782615c..d2d860286 100644 --- a/src/slic3r/GUI/GUI_Factories.cpp +++ b/src/slic3r/GUI/GUI_Factories.cpp @@ -651,6 +651,15 @@ wxMenuItem* MenuFactory::append_menu_item_fix_through_netfabb(wxMenu* menu) wxMenuItem* menu_item = append_menu_item(menu, wxID_ANY, _L("Fix through the Netfabb"), "", [](wxCommandEvent&) { obj_list()->fix_through_netfabb(); }, "", menu, []() {return plater()->can_fix_through_netfabb(); }, plater()); + + return menu_item; +} + +wxMenuItem* MenuFactory::append_menu_item_simplify(wxMenu* menu) +{ + wxMenuItem* menu_item = append_menu_item(menu, wxID_ANY, _L("Symplify model"), "", + [](wxCommandEvent&) { obj_list()->simplify(); }, "", menu, + []() {return plater()->can_simplify(); }, plater()); menu->AppendSeparator(); return menu_item; @@ -868,6 +877,7 @@ void MenuFactory::create_common_object_menu(wxMenu* menu) append_menu_item_scale_selection_to_fit_print_volume(menu); append_menu_item_fix_through_netfabb(menu); + append_menu_item_simplify(menu); append_menu_items_mirror(menu); } @@ -917,6 +927,7 @@ void MenuFactory::create_part_menu() append_menu_item_replace_with_stl(menu); append_menu_item_export_stl(menu); append_menu_item_fix_through_netfabb(menu); + append_menu_item_simplify(menu); append_menu_items_mirror(menu); append_menu_item(menu, wxID_ANY, _L("Split"), _L("Split the selected object into individual parts"), diff --git a/src/slic3r/GUI/GUI_Factories.hpp b/src/slic3r/GUI/GUI_Factories.hpp index e8928d3ff..e0d091ed5 100644 --- a/src/slic3r/GUI/GUI_Factories.hpp +++ b/src/slic3r/GUI/GUI_Factories.hpp @@ -90,6 +90,7 @@ private: wxMenuItem* append_menu_item_printable(wxMenu* menu); void append_menu_items_osx(wxMenu* menu); wxMenuItem* append_menu_item_fix_through_netfabb(wxMenu* menu); + wxMenuItem* append_menu_item_simplify(wxMenu* menu); void append_menu_item_export_stl(wxMenu* menu); void append_menu_item_reload_from_disk(wxMenu* menu); void append_menu_item_replace_with_stl(wxMenu* menu); diff --git a/src/slic3r/GUI/GUI_ObjectList.cpp b/src/slic3r/GUI/GUI_ObjectList.cpp index 443ef7815..cea5dbcb9 100644 --- a/src/slic3r/GUI/GUI_ObjectList.cpp +++ b/src/slic3r/GUI/GUI_ObjectList.cpp @@ -4,6 +4,7 @@ #include "GUI_Factories.hpp" #include "GUI_ObjectManipulation.hpp" #include "GUI_ObjectLayers.hpp" +#include "SimplificationDialog.hpp" #include "GUI_App.hpp" #include "I18N.hpp" #include "Plater.hpp" @@ -3759,6 +3760,17 @@ void ObjectList::fix_through_netfabb() update_item_error_icon(obj_idx, vol_idx); } +void ObjectList::simplify() +{ + int obj_idx, vol_idx; + get_selected_item_indexes(obj_idx, vol_idx); + + SimplificationDialog dlg(this); + dlg.ShowModal(); + + wxGetApp().plater()->simplify(obj_idx, vol_idx); +} + void ObjectList::update_item_error_icon(const int obj_idx, const int vol_idx) const { const wxDataViewItem item = vol_idx <0 ? m_objects_model->GetItemById(obj_idx) : diff --git a/src/slic3r/GUI/GUI_ObjectList.hpp b/src/slic3r/GUI/GUI_ObjectList.hpp index 36b399e51..291518488 100644 --- a/src/slic3r/GUI/GUI_ObjectList.hpp +++ b/src/slic3r/GUI/GUI_ObjectList.hpp @@ -353,6 +353,7 @@ public: void split_instances(); void rename_item(); void fix_through_netfabb(); + void simplify(); void update_item_error_icon(const int obj_idx, int vol_idx) const ; void copy_layers_to_clipboard(); diff --git a/src/slic3r/GUI/Plater.cpp b/src/slic3r/GUI/Plater.cpp index 49c0359bf..756e74bae 100644 --- a/src/slic3r/GUI/Plater.cpp +++ b/src/slic3r/GUI/Plater.cpp @@ -1730,6 +1730,7 @@ struct Plater::priv void replace_with_stl(); void reload_all_from_disk(); void fix_through_netfabb(const int obj_idx, const int vol_idx = -1); + void simplify(const int obj_idx, const int vol_idx = -1); void set_current_panel(wxPanel* panel); @@ -1782,6 +1783,7 @@ struct Plater::priv bool can_arrange() const; bool can_layers_editing() const; bool can_fix_through_netfabb() const; + bool can_simplify() const; bool can_set_instance_to_object() const; bool can_mirror() const; bool can_reload_from_disk() const; @@ -3593,6 +3595,32 @@ void Plater::priv::fix_through_netfabb(const int obj_idx, const int vol_idx/* = this->schedule_background_process(); } +void Plater::priv::simplify(const int obj_idx, const int vol_idx/* = -1*/) +{ + if (obj_idx < 0) + return; + + // Do not fix anything when a gizmo is open. There might be issues with updates + // and what is worse, the snapshot time would refer to the internal stack. + if (q->canvas3D()->get_gizmos_manager().get_current_type() != GLGizmosManager::Undefined) { + notification_manager->push_notification( + NotificationType::CustomSupportsAndSeamRemovedAfterRepair, + NotificationManager::NotificationLevel::RegularNotification, + _u8L("ERROR: Please close all manipulators available from " + "the left toolbar before fixing the mesh.")); + return; + } + + // size_t snapshot_time = undo_redo_stack().active_snapshot_time(); + Plater::TakeSnapshot snapshot(q, _L("Symplify model")); + + // ToDo + + this->update(); + this->object_list_changed(); + this->schedule_background_process(); +} + void Plater::priv::set_current_panel(wxPanel* panel) { if (std::find(panels.begin(), panels.end(), panel) == panels.end()) @@ -4375,6 +4403,12 @@ bool Plater::priv::can_fix_through_netfabb() const return model.objects[obj_idx]->get_mesh_errors_count() > 0; } + +bool Plater::priv::can_simplify() const +{ + return true; +} + bool Plater::priv::can_increase_instances() const { if (m_ui_jobs.is_any_running() @@ -6309,6 +6343,7 @@ void Plater::suppress_background_process(const bool stop_background_process) } void Plater::fix_through_netfabb(const int obj_idx, const int vol_idx/* = -1*/) { p->fix_through_netfabb(obj_idx, vol_idx); } +void Plater::simplify(const int obj_idx, const int vol_idx/* = -1*/) { p->simplify(obj_idx, vol_idx); } void Plater::mirror(Axis axis) { p->mirror(axis); } void Plater::split_object() { p->split_object(); } void Plater::split_volume() { p->split_volume(); } @@ -6509,6 +6544,7 @@ bool Plater::can_increase_instances() const { return p->can_increase_instances() bool Plater::can_decrease_instances() const { return p->can_decrease_instances(); } bool Plater::can_set_instance_to_object() const { return p->can_set_instance_to_object(); } bool Plater::can_fix_through_netfabb() const { return p->can_fix_through_netfabb(); } +bool Plater::can_simplify() const { return p->can_simplify(); } bool Plater::can_split_to_objects() const { return p->can_split_to_objects(); } bool Plater::can_split_to_volumes() const { return p->can_split_to_volumes(); } bool Plater::can_arrange() const { return p->can_arrange(); } diff --git a/src/slic3r/GUI/Plater.hpp b/src/slic3r/GUI/Plater.hpp index fc4001ba5..d58e6b9b1 100644 --- a/src/slic3r/GUI/Plater.hpp +++ b/src/slic3r/GUI/Plater.hpp @@ -236,6 +236,7 @@ public: bool is_background_process_update_scheduled() const; void suppress_background_process(const bool stop_background_process) ; void fix_through_netfabb(const int obj_idx, const int vol_idx = -1); + void simplify(const int obj_idx, const int vol_idx = -1); void send_gcode(); void eject_drive(); @@ -314,6 +315,7 @@ public: bool can_decrease_instances() const; bool can_set_instance_to_object() const; bool can_fix_through_netfabb() const; + bool can_simplify() const; bool can_split_to_objects() const; bool can_split_to_volumes() const; bool can_arrange() const; diff --git a/src/slic3r/GUI/SimplificationDialog.cpp b/src/slic3r/GUI/SimplificationDialog.cpp new file mode 100644 index 000000000..780fc2407 --- /dev/null +++ b/src/slic3r/GUI/SimplificationDialog.cpp @@ -0,0 +1,91 @@ +#include "SimplificationDialog.hpp" + +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +#include "GUI.hpp" +#include "GUI_App.hpp" +#include "format.hpp" +#include "wxExtensions.hpp" +#include "I18N.hpp" +#include "libslic3r/Utils.hpp" + + +namespace Slic3r { +namespace GUI { + +#define BORDER_W 10 + +SimplificationDialog::SimplificationDialog(wxWindow* parent) : + DPIDialog(parent, wxID_ANY, _L("Name of Dialog"), wxDefaultPosition, wxSize(45 * wxGetApp().em_unit(), -1), wxDEFAULT_DIALOG_STYLE/* | wxRESIZE_BORDER*/) +{ + SetFont(wxGetApp().normal_font()); + + wxStaticText* label_top = new wxStaticText(this, wxID_ANY, _L("Some text") + ":"); + + wxFlexGridSizer* grid_sizer = new wxFlexGridSizer(3, 2, 1, 2); + grid_sizer->AddGrowableCol(1, 1); + grid_sizer->SetFlexibleDirection(wxBOTH); + + for (int i = 0; i < 3; i++) { + auto* text = new wxStaticText(this, wxID_ANY, _L("Text") + " " + std::to_string(i) + " :"); + +#ifdef _WIN32 + long style = wxBORDER_SIMPLE; +#else + long style = 0 +#endif + auto value = new wxTextCtrl(this, wxID_ANY, "Some Value", wxDefaultPosition, wxDefaultSize, style); + + grid_sizer->Add(text, 0, wxALIGN_LEFT | wxALIGN_CENTER_VERTICAL | wxRIGHT, 4); + grid_sizer->Add(value, 1, wxEXPAND | wxBOTTOM, 1); + } + + wxStdDialogButtonSizer* btns = this->CreateStdDialogButtonSizer(wxOK | wxCANCEL); + this->Bind(wxEVT_BUTTON, &SimplificationDialog::OnOK, this, wxID_OK); + + wxBoxSizer* topSizer = new wxBoxSizer(wxVERTICAL); + + topSizer->Add(label_top , 0, wxEXPAND | wxLEFT | wxTOP | wxRIGHT, BORDER_W); + topSizer->Add(grid_sizer, 1, wxEXPAND | wxLEFT | wxTOP | wxRIGHT, BORDER_W); + topSizer->Add(btns , 0, wxEXPAND | wxALL, BORDER_W); + + SetSizer(topSizer); + topSizer->SetSizeHints(this); + + wxGetApp().UpdateDlgDarkUI(this); + + this->CenterOnScreen(); +} + +SimplificationDialog::~SimplificationDialog() +{ +} + +void SimplificationDialog::on_dpi_changed(const wxRect& suggested_rect) +{ + const int& em = em_unit(); + msw_buttons_rescale(this, em, { wxID_OK, wxID_CANCEL }); + + const wxSize& size = wxSize(45 * em, 35 * em); + SetMinSize(size); + + Fit(); + Refresh(); +} + +void SimplificationDialog::OnOK(wxEvent& event) +{ + event.Skip(); +} + +}} // namespace Slic3r::GUI diff --git a/src/slic3r/GUI/SimplificationDialog.hpp b/src/slic3r/GUI/SimplificationDialog.hpp new file mode 100644 index 000000000..4c0210ee8 --- /dev/null +++ b/src/slic3r/GUI/SimplificationDialog.hpp @@ -0,0 +1,25 @@ +#ifndef slic3r_SimplificationDialog_hpp_ +#define slic3r_SimplificationDialog_hpp_ + +#include "GUI_Utils.hpp" + +namespace Slic3r { +namespace GUI { + +class SimplificationDialog : public DPIDialog +{ + void OnOK(wxEvent& event); + +public: + SimplificationDialog(wxWindow* parent); + ~SimplificationDialog(); + +protected: + void on_dpi_changed(const wxRect& suggested_rect) override; +}; + + +} // namespace GUI +} // namespace Slic3r + +#endif //slic3r_SimplificationDialog_hpp_