mirror of
https://git.mirrors.martin98.com/https://github.com/prusa3d/PrusaSlicer.git
synced 2025-08-14 06:15:58 +08:00
Implemented BulkExportDialog
This commit is contained in:
parent
ab58ccff60
commit
8f7b2b2259
@ -78,16 +78,15 @@ src/slic3r/GUI/GUI_ObjectSettings.cpp
|
||||
src/slic3r/GUI/GUI_Preview.cpp
|
||||
src/slic3r/GUI/HintNotification.cpp
|
||||
src/slic3r/GUI/ImGuiWrapper.cpp
|
||||
src/slic3r/GUI/Jobs/ArrangeJob.cpp
|
||||
src/slic3r/GUI/Jobs/ArrangeJob2.cpp
|
||||
src/slic3r/GUI/Jobs/EmbossJob.cpp
|
||||
src/slic3r/GUI/Jobs/FillBedJob.cpp
|
||||
src/slic3r/GUI/Jobs/PlaterWorker.hpp
|
||||
src/slic3r/GUI/Jobs/RotoptimizeJob.hpp
|
||||
src/slic3r/GUI/Jobs/RotoptimizeJob.cpp
|
||||
src/slic3r/GUI/Jobs/SLAImportDialog.hpp
|
||||
src/slic3r/GUI/Jobs/SLAImportJob.cpp
|
||||
src/slic3r/GUI/KBShortcutsDialog.cpp
|
||||
src/slic3r/GUI/BulkExportDialog.cpp
|
||||
src/slic3r/GUI/LoginDialog.cpp
|
||||
src/slic3r/GUI/MainFrame.cpp
|
||||
src/slic3r/GUI/Mouse3DController.cpp
|
||||
|
@ -151,6 +151,8 @@ set(SLIC3R_GUI_SOURCES
|
||||
GUI/EditGCodeDialog.cpp
|
||||
GUI/SavePresetDialog.hpp
|
||||
GUI/SavePresetDialog.cpp
|
||||
GUI/BulkExportDialog.hpp
|
||||
GUI/BulkExportDialog.cpp
|
||||
GUI/PhysicalPrinterDialog.hpp
|
||||
GUI/PhysicalPrinterDialog.cpp
|
||||
GUI/GUI_Factories.cpp
|
||||
|
219
src/slic3r/GUI/BulkExportDialog.cpp
Normal file
219
src/slic3r/GUI/BulkExportDialog.cpp
Normal file
@ -0,0 +1,219 @@
|
||||
///|/ Copyright (c) Prusa Research 2020 - 2023 Oleksandra Iushchenko @YuSanka, David Kocík @kocikdav, Enrico Turri @enricoturri1966, Vojtěch Bubník @bubnikv
|
||||
///|/
|
||||
///|/ PrusaSlicer is released under the terms of the AGPLv3 or higher
|
||||
///|/
|
||||
#include "BulkExportDialog.hpp"
|
||||
|
||||
#include <cstddef>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
#include <boost/algorithm/string.hpp>
|
||||
|
||||
#include <wx/sizer.h>
|
||||
#include <wx/stattext.h>
|
||||
#include <wx/textctrl.h>
|
||||
|
||||
#include "libslic3r/PresetBundle.hpp"
|
||||
|
||||
#include "GUI.hpp"
|
||||
#include "GUI_App.hpp"
|
||||
#include "format.hpp"
|
||||
#include "Tab.hpp"
|
||||
|
||||
using Slic3r::GUI::format_wxstr;
|
||||
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
constexpr auto BORDER_W = 10;
|
||||
|
||||
//-----------------------------------------------
|
||||
// BulkExportDialog::Item
|
||||
//-----------------------------------------------
|
||||
|
||||
|
||||
void BulkExportDialog::Item::init_input_name_ctrl(wxBoxSizer* input_path_sizer, const std::string path)
|
||||
{
|
||||
#ifdef _WIN32
|
||||
long style = wxBORDER_SIMPLE;
|
||||
#else
|
||||
long style = 0L;
|
||||
#endif
|
||||
m_text_ctrl = new wxTextCtrl(m_parent, wxID_ANY, from_u8(path), wxDefaultPosition, wxSize(45 * wxGetApp().em_unit(), -1), style);
|
||||
wxGetApp().UpdateDarkUI(m_text_ctrl);
|
||||
m_text_ctrl->Bind(wxEVT_TEXT, [this](wxCommandEvent&) { update(); });
|
||||
|
||||
input_path_sizer->Add(m_text_ctrl, 1, wxEXPAND, BORDER_W);
|
||||
}
|
||||
|
||||
BulkExportDialog::Item::Item(wxWindow* parent, wxBoxSizer* sizer, PrintToExport& pte):
|
||||
m_parent(parent),
|
||||
m_print_to_export(&pte),
|
||||
m_valid_bmp(new wxStaticBitmap(m_parent, wxID_ANY, *get_bmp_bundle("tick_mark"))),
|
||||
m_valid_label(new wxStaticText(m_parent, wxID_ANY, ""))
|
||||
{
|
||||
m_valid_label->SetFont(wxGetApp().bold_font());
|
||||
|
||||
wxBoxSizer* input_path_sizer = new wxBoxSizer(wxHORIZONTAL);
|
||||
input_path_sizer->Add(m_valid_bmp, 0, wxALIGN_CENTER_VERTICAL | wxRIGHT, BORDER_W);
|
||||
init_input_name_ctrl(input_path_sizer, pte.output_path.filename().string());
|
||||
|
||||
sizer->Add(input_path_sizer,0, wxEXPAND | wxTOP, BORDER_W);
|
||||
sizer->Add(m_valid_label, 0, wxEXPAND | wxLEFT, 3*BORDER_W);
|
||||
|
||||
update();
|
||||
}
|
||||
|
||||
void BulkExportDialog::Item::update()
|
||||
{
|
||||
m_path = into_u8(m_text_ctrl->GetValue());
|
||||
|
||||
m_valid_type = ValidationType::Valid;
|
||||
wxString info_line;
|
||||
|
||||
const char* unusable_symbols = "<>[]:/\\|?*\"";
|
||||
|
||||
for (size_t i = 0; i < std::strlen(unusable_symbols); i++) {
|
||||
if (m_path.find_first_of(unusable_symbols[i]) != std::string::npos) {
|
||||
info_line = _L("The following characters are not allowed in the name") + ": " + unusable_symbols;
|
||||
m_valid_type = ValidationType::NoValid;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
bool existing = false;// is_existing(m_path);
|
||||
if (m_valid_type == ValidationType::Valid && existing) {
|
||||
info_line = _L("This name is already used, use another.");
|
||||
m_valid_type = ValidationType::Warning;
|
||||
}
|
||||
|
||||
if (m_valid_type == ValidationType::Valid && m_path.empty()) {
|
||||
info_line = _L("The name cannot be empty.");
|
||||
m_valid_type = ValidationType::NoValid;
|
||||
}
|
||||
|
||||
#ifdef __WXMSW__
|
||||
const int max_path_length = MAX_PATH;
|
||||
#else
|
||||
const int max_path_length = 255;
|
||||
#endif
|
||||
|
||||
if (m_valid_type == ValidationType::Valid && m_path.length() >= max_path_length) {
|
||||
info_line = _L("The name is too long.");
|
||||
m_valid_type = ValidationType::NoValid;
|
||||
}
|
||||
|
||||
if (m_valid_type == ValidationType::Valid && m_path.find_first_of(' ') == 0) {
|
||||
info_line = _L("The name cannot start with space character.");
|
||||
m_valid_type = ValidationType::NoValid;
|
||||
}
|
||||
|
||||
if (m_valid_type == ValidationType::Valid && m_path.find_last_of(' ') == m_path.length()-1) {
|
||||
info_line = _L("The name cannot end with space character.");
|
||||
m_valid_type = ValidationType::NoValid;
|
||||
}
|
||||
|
||||
m_valid_label->SetLabel(info_line);
|
||||
m_valid_label->Show(!info_line.IsEmpty());
|
||||
|
||||
update_valid_bmp();
|
||||
|
||||
if (is_valid()) {
|
||||
boost::filesystem::path field = m_print_to_export->output_path.parent_path();
|
||||
m_print_to_export->output_path = field / m_path;
|
||||
}
|
||||
|
||||
m_parent->Layout();
|
||||
}
|
||||
|
||||
void BulkExportDialog::Item::update_valid_bmp()
|
||||
{
|
||||
std::string bmp_name = m_valid_type == ValidationType::Warning ? "exclamation_manifold" :
|
||||
m_valid_type == ValidationType::NoValid ? "exclamation" : "tick_mark" ;
|
||||
m_valid_bmp->SetBitmap(*get_bmp_bundle(bmp_name));
|
||||
}
|
||||
|
||||
//-----------------------------------------------
|
||||
// BulkExportDialog
|
||||
//-----------------------------------------------
|
||||
|
||||
BulkExportDialog::BulkExportDialog(wxWindow* parent, std::vector<PrintToExport>& exports)
|
||||
: DPIDialog(parent, wxID_ANY, exports.size() == 1 ? _L("Save bed") : _L("Save beds"),
|
||||
wxDefaultPosition, wxSize(45 * wxGetApp().em_unit(), 5 * wxGetApp().em_unit()), wxDEFAULT_DIALOG_STYLE | wxICON_WARNING)
|
||||
{
|
||||
this->SetFont(wxGetApp().normal_font());
|
||||
|
||||
#ifndef __WXMSW__
|
||||
SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW));
|
||||
#endif // __WXMSW__
|
||||
|
||||
wxBoxSizer* topSizer = new wxBoxSizer(wxVERTICAL);
|
||||
|
||||
m_sizer = new wxBoxSizer(wxVERTICAL);
|
||||
|
||||
for (PrintToExport& exp : exports)
|
||||
AddItem(exp);
|
||||
|
||||
// Add dialog's buttons
|
||||
wxStdDialogButtonSizer* btns = this->CreateStdDialogButtonSizer(wxOK | wxCANCEL);
|
||||
wxButton* btnOK = static_cast<wxButton*>(this->FindWindowById(wxID_OK, this));
|
||||
btnOK->Bind(wxEVT_UPDATE_UI, [this](wxUpdateUIEvent& evt) { evt.Enable(enable_ok_btn()); });
|
||||
|
||||
topSizer->Add(m_sizer, 0, wxEXPAND | wxALL, BORDER_W);
|
||||
|
||||
topSizer->Add(btns, 0, wxEXPAND | wxALL, BORDER_W);
|
||||
|
||||
SetSizer(topSizer);
|
||||
topSizer->SetSizeHints(this);
|
||||
|
||||
this->CenterOnScreen();
|
||||
|
||||
#ifdef _WIN32
|
||||
wxGetApp().UpdateDlgDarkUI(this);
|
||||
#endif
|
||||
}
|
||||
|
||||
BulkExportDialog::~BulkExportDialog()
|
||||
{
|
||||
for (auto item : m_items)
|
||||
delete item;
|
||||
}
|
||||
|
||||
void BulkExportDialog::AddItem(PrintToExport& pte)
|
||||
{
|
||||
m_items.emplace_back(new Item{ this, m_sizer, pte });
|
||||
}
|
||||
|
||||
bool BulkExportDialog::enable_ok_btn() const
|
||||
{
|
||||
for (const Item* item : m_items)
|
||||
if (!item->is_valid())
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool BulkExportDialog::Layout()
|
||||
{
|
||||
const bool ret = DPIDialog::Layout();
|
||||
this->Fit();
|
||||
return ret;
|
||||
}
|
||||
|
||||
void BulkExportDialog::on_dpi_changed(const wxRect& suggested_rect)
|
||||
{
|
||||
const int& em = em_unit();
|
||||
|
||||
msw_buttons_rescale(this, em, { wxID_OK, wxID_CANCEL });
|
||||
|
||||
for (Item* item : m_items)
|
||||
item->update_valid_bmp();
|
||||
|
||||
const wxSize& size = wxSize(65 * em, 35 * em);
|
||||
SetMinSize(size);
|
||||
|
||||
Fit();
|
||||
Refresh();
|
||||
}
|
||||
|
||||
}} // namespace Slic3r::GUI
|
94
src/slic3r/GUI/BulkExportDialog.hpp
Normal file
94
src/slic3r/GUI/BulkExportDialog.hpp
Normal file
@ -0,0 +1,94 @@
|
||||
///|/ Copyright (c) Prusa Research 2020 - 2023 Oleksandra Iushchenko @YuSanka, David Kocík @kocikdav, Lukáš Matěna @lukasmatena
|
||||
///|/
|
||||
///|/ PrusaSlicer is released under the terms of the AGPLv3 or higher
|
||||
///|/
|
||||
#pragma once
|
||||
|
||||
//#include <wx/gdicmn.h>
|
||||
|
||||
#include <boost/filesystem/path.hpp>
|
||||
#include "wxExtensions.hpp"
|
||||
#include "GUI_Utils.hpp"
|
||||
|
||||
class wxString;
|
||||
class wxStaticText;
|
||||
class wxTextCtrl;
|
||||
class wxStaticBitmap;
|
||||
|
||||
namespace Slic3r {
|
||||
|
||||
class Print;
|
||||
struct GCodeProcessorResult;
|
||||
|
||||
namespace GUI {
|
||||
|
||||
struct PrintToExport {
|
||||
std::reference_wrapper<Slic3r::Print> print;
|
||||
std::reference_wrapper<Slic3r::GCodeProcessorResult> processor_result;
|
||||
boost::filesystem::path output_path;
|
||||
};
|
||||
|
||||
class BulkExportDialog : public DPIDialog
|
||||
{
|
||||
public:
|
||||
struct Item
|
||||
{
|
||||
enum class ValidationType
|
||||
{
|
||||
Valid,
|
||||
NoValid,
|
||||
Warning
|
||||
};
|
||||
|
||||
// Item as a separate control(f.e. as a part of ConfigWizard to check name of the new custom priter)
|
||||
Item(wxWindow* parent, wxBoxSizer* sizer, PrintToExport& path);
|
||||
|
||||
void update_valid_bmp();
|
||||
bool is_valid() const { return m_valid_type != ValidationType::NoValid; }
|
||||
|
||||
private:
|
||||
std::string m_path;
|
||||
PrintToExport* m_print_to_export { nullptr };
|
||||
|
||||
ValidationType m_valid_type {ValidationType::NoValid};
|
||||
wxWindow* m_parent {nullptr};
|
||||
wxStaticBitmap* m_valid_bmp {nullptr};
|
||||
wxTextCtrl* m_text_ctrl {nullptr};
|
||||
wxStaticText* m_valid_label {nullptr};
|
||||
|
||||
|
||||
void init_input_name_ctrl(wxBoxSizer *input_name_sizer, std::string path);
|
||||
void update();
|
||||
};
|
||||
|
||||
private:
|
||||
std::vector<Item*> m_items;
|
||||
|
||||
std::vector<PrintToExport>* m_exports {nullptr};
|
||||
|
||||
wxBoxSizer* m_sizer {nullptr};
|
||||
wxStaticText* m_label {nullptr};
|
||||
|
||||
std::string m_ph_printer_name;
|
||||
std::string m_old_preset_name;
|
||||
wxString m_info_line_extention{wxEmptyString};
|
||||
|
||||
public:
|
||||
|
||||
BulkExportDialog(wxWindow* parent, std::vector<PrintToExport>& exports);
|
||||
~BulkExportDialog() override;
|
||||
bool Layout() override;
|
||||
|
||||
void AddItem(PrintToExport& pte);
|
||||
|
||||
protected:
|
||||
void on_dpi_changed(const wxRect& suggested_rect) override;
|
||||
void on_sys_color_changed() override {}
|
||||
|
||||
private:
|
||||
bool enable_ok_btn() const;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
}
|
@ -133,6 +133,7 @@
|
||||
#include "WebViewPanel.hpp"
|
||||
#include "ConfigWizardWebViewPage.hpp"
|
||||
#include "PresetArchiveDatabase.hpp"
|
||||
#include "BulkExportDialog.hpp"
|
||||
|
||||
#ifdef __APPLE__
|
||||
#include "Gizmos/GLGizmosManager.hpp"
|
||||
@ -5922,11 +5923,6 @@ void Plater::export_gcode_to_path(
|
||||
appconfig.update_last_output_dir(output_path.parent_path().string(), path_on_removable_media);
|
||||
}
|
||||
|
||||
struct PrintToExport{ std::reference_wrapper<Print> print;
|
||||
std::reference_wrapper<GCodeProcessorResult> processor_result;
|
||||
fs::path output_path;
|
||||
};
|
||||
|
||||
void Plater::export_all_gcodes(bool prefer_removable) {
|
||||
const auto optional_default_output_file{this->get_default_output_file()};
|
||||
if (!optional_default_output_file) {
|
||||
@ -5958,11 +5954,10 @@ void Plater::export_all_gcodes(bool prefer_removable) {
|
||||
prints_to_export.push_back({*print, this->p->gcode_results[print_index], output_file});
|
||||
}
|
||||
|
||||
//BulkExportDialog dialog{prints_to_export};
|
||||
//if (dialog.ShowModal() != wxID_OK) {
|
||||
// return;
|
||||
//}
|
||||
//prints_to_export = dialog.get_prints_to_export();
|
||||
BulkExportDialog dialog(nullptr, prints_to_export);
|
||||
if (dialog.ShowModal() != wxID_OK) {
|
||||
return;
|
||||
}
|
||||
|
||||
bool path_on_removable_media{false};
|
||||
for (const PrintToExport &print_to_export : prints_to_export) {
|
||||
|
Loading…
x
Reference in New Issue
Block a user