mirror of
https://github.com/SoftFever/OrcaSlicer.git
synced 2025-07-25 15:44:12 -06:00
Merge branch 'master' into tm_zero_elev_ui
This commit is contained in:
commit
92e1649606
7 changed files with 125 additions and 70 deletions
|
@ -27,49 +27,57 @@ namespace GUI {
|
|||
|
||||
void GLTexture::Compressor::reset()
|
||||
{
|
||||
if (m_is_compressing)
|
||||
{
|
||||
// force compression completion, if any
|
||||
if (m_thread.joinable()) {
|
||||
m_abort_compressing = true;
|
||||
// wait for compression completion, if any
|
||||
while (m_is_compressing) {}
|
||||
}
|
||||
|
||||
m_levels.clear();
|
||||
}
|
||||
|
||||
void GLTexture::Compressor::add_level(unsigned int w, unsigned int h, const std::vector<unsigned char>& data)
|
||||
{
|
||||
m_levels.emplace_back(w, h, data);
|
||||
m_thread.join();
|
||||
m_levels.clear();
|
||||
m_num_levels_compressed = 0;
|
||||
m_abort_compressing = false;
|
||||
}
|
||||
assert(m_levels.empty());
|
||||
assert(m_abort_compressing == false);
|
||||
assert(m_num_levels_compressed == 0);
|
||||
}
|
||||
|
||||
void GLTexture::Compressor::start_compressing()
|
||||
{
|
||||
std::thread t(&GLTexture::Compressor::compress, this);
|
||||
t.detach();
|
||||
// The worker thread should be stopped already.
|
||||
assert(! m_thread.joinable());
|
||||
assert(! m_levels.empty());
|
||||
assert(m_abort_compressing == false);
|
||||
assert(m_num_levels_compressed == 0);
|
||||
if (! m_levels.empty()) {
|
||||
std::thread thrd(&GLTexture::Compressor::compress, this);
|
||||
m_thread = std::move(thrd);
|
||||
}
|
||||
}
|
||||
|
||||
bool GLTexture::Compressor::unsent_compressed_data_available() const
|
||||
{
|
||||
for (const Level& level : m_levels)
|
||||
{
|
||||
if (!level.sent_to_gpu && level.compressed)
|
||||
if (m_levels.empty())
|
||||
return false;
|
||||
// Querying the atomic m_num_levels_compressed value synchronizes processor caches, so that the dat of m_levels modified by the worker thread are accessible to the calling thread.
|
||||
unsigned int num_compressed = m_num_levels_compressed;
|
||||
for (unsigned int i = 0; i < num_compressed; ++ i)
|
||||
if (! m_levels[i].sent_to_gpu && ! m_levels[i].compressed_data.empty())
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void GLTexture::Compressor::send_compressed_data_to_gpu()
|
||||
{
|
||||
// this method should be called inside the main thread of Slicer or a new OpenGL context (sharing resources) would be needed
|
||||
if (m_levels.empty())
|
||||
return;
|
||||
|
||||
glsafe(::glPixelStorei(GL_UNPACK_ALIGNMENT, 1));
|
||||
glsafe(::glBindTexture(GL_TEXTURE_2D, m_texture.m_id));
|
||||
for (int i = 0; i < (int)m_levels.size(); ++i)
|
||||
// Querying the atomic m_num_levels_compressed value synchronizes processor caches, so that the dat of m_levels modified by the worker thread are accessible to the calling thread.
|
||||
int num_compressed = (int)m_num_levels_compressed;
|
||||
for (int i = 0; i < num_compressed; ++ i)
|
||||
{
|
||||
Level& level = m_levels[i];
|
||||
if (!level.sent_to_gpu && level.compressed)
|
||||
if (! level.sent_to_gpu && ! level.compressed_data.empty())
|
||||
{
|
||||
glsafe(::glCompressedTexSubImage2D(GL_TEXTURE_2D, (GLint)i, 0, 0, (GLsizei)level.w, (GLsizei)level.h, GL_COMPRESSED_RGBA_S3TC_DXT5_EXT, (GLsizei)level.compressed_data.size(), (const GLvoid*)level.compressed_data.data()));
|
||||
glsafe(::glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, i));
|
||||
|
@ -77,29 +85,21 @@ void GLTexture::Compressor::send_compressed_data_to_gpu()
|
|||
level.sent_to_gpu = true;
|
||||
// we are done with the compressed data, we can discard it
|
||||
level.compressed_data.clear();
|
||||
level.compressed = false;
|
||||
}
|
||||
}
|
||||
glsafe(::glBindTexture(GL_TEXTURE_2D, 0));
|
||||
}
|
||||
|
||||
bool GLTexture::Compressor::all_compressed_data_sent_to_gpu() const
|
||||
{
|
||||
for (const Level& level : m_levels)
|
||||
{
|
||||
if (!level.sent_to_gpu)
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
if (num_compressed == (unsigned int)m_levels.size())
|
||||
// Finalize the worker thread, close it.
|
||||
this->reset();
|
||||
}
|
||||
|
||||
void GLTexture::Compressor::compress()
|
||||
{
|
||||
// reference: https://github.com/Cyan4973/RygsDXTc
|
||||
|
||||
m_is_compressing = true;
|
||||
m_abort_compressing = false;
|
||||
assert(m_num_levels_compressed == 0);
|
||||
assert(m_abort_compressing == false);
|
||||
|
||||
for (Level& level : m_levels)
|
||||
{
|
||||
|
@ -115,11 +115,8 @@ void GLTexture::Compressor::compress()
|
|||
|
||||
// we are done with the source data, we can discard it
|
||||
level.src_data.clear();
|
||||
level.compressed = true;
|
||||
++ m_num_levels_compressed;
|
||||
}
|
||||
|
||||
m_is_compressing = false;
|
||||
m_abort_compressing = false;
|
||||
}
|
||||
|
||||
GLTexture::Quad_UVs GLTexture::FullTextureUVs = { { 0.0f, 1.0f }, { 1.0f, 1.0f }, { 1.0f, 0.0f }, { 0.0f, 0.0f } };
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <thread>
|
||||
|
||||
class wxImage;
|
||||
|
||||
|
@ -19,30 +20,34 @@ namespace GUI {
|
|||
unsigned int h;
|
||||
std::vector<unsigned char> src_data;
|
||||
std::vector<unsigned char> compressed_data;
|
||||
bool compressed;
|
||||
bool sent_to_gpu;
|
||||
|
||||
Level(unsigned int w, unsigned int h, const std::vector<unsigned char>& data) : w(w), h(h), src_data(data), compressed(false), sent_to_gpu(false) {}
|
||||
Level(unsigned int w, unsigned int h, const std::vector<unsigned char>& data) : w(w), h(h), src_data(data), sent_to_gpu(false) {}
|
||||
};
|
||||
|
||||
GLTexture& m_texture;
|
||||
std::vector<Level> m_levels;
|
||||
bool m_is_compressing;
|
||||
bool m_abort_compressing;
|
||||
std::thread m_thread;
|
||||
// Does the caller want the background thread to stop?
|
||||
// This atomic also works as a memory barrier for synchronizing the cancel event with the worker thread.
|
||||
std::atomic<bool> m_abort_compressing;
|
||||
// How many levels were compressed since the start of the background processing thread?
|
||||
// This atomic also works as a memory barrier for synchronizing results of the worker thread with the calling thread.
|
||||
std::atomic<unsigned int> m_num_levels_compressed;
|
||||
|
||||
public:
|
||||
explicit Compressor(GLTexture& texture) : m_texture(texture), m_is_compressing(false), m_abort_compressing(false) {}
|
||||
explicit Compressor(GLTexture& texture) : m_texture(texture), m_abort_compressing(false), m_num_levels_compressed(0) {}
|
||||
~Compressor() { reset(); }
|
||||
|
||||
void reset();
|
||||
|
||||
void add_level(unsigned int w, unsigned int h, const std::vector<unsigned char>& data);
|
||||
void add_level(unsigned int w, unsigned int h, const std::vector<unsigned char>& data) { m_levels.emplace_back(w, h, data); }
|
||||
|
||||
void start_compressing();
|
||||
|
||||
bool unsent_compressed_data_available() const;
|
||||
void send_compressed_data_to_gpu();
|
||||
bool all_compressed_data_sent_to_gpu() const;
|
||||
bool all_compressed_data_sent_to_gpu() const { return m_levels.empty(); }
|
||||
|
||||
private:
|
||||
void compress();
|
||||
|
|
|
@ -6,23 +6,23 @@
|
|||
#include "GUI_App.hpp"
|
||||
#include "wxExtensions.hpp"
|
||||
|
||||
namespace Slic3r {
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
KBShortcutsDialog::KBShortcutsDialog()
|
||||
: DPIDialog(NULL, wxID_ANY, wxString(SLIC3R_APP_NAME) + " - " + _(L("Keyboard Shortcuts")),
|
||||
: DPIDialog(NULL, wxID_ANY, wxString(SLIC3R_APP_NAME) + " - " + _(L("Keyboard Shortcuts")),
|
||||
wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER)
|
||||
{
|
||||
SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW));
|
||||
SetBackgroundColour(wxSystemSettings::GetColour(wxSYS_COLOUR_WINDOW));
|
||||
|
||||
auto main_sizer = new wxBoxSizer(wxVERTICAL);
|
||||
auto main_sizer = new wxBoxSizer(wxVERTICAL);
|
||||
|
||||
// logo
|
||||
m_logo_bmp = ScalableBitmap(this, "PrusaSlicer_32px.png", 32);
|
||||
|
||||
// fonts
|
||||
const wxFont& font = wxGetApp().normal_font();
|
||||
const wxFont& bold_font = wxGetApp().bold_font();
|
||||
const wxFont& bold_font = wxGetApp().bold_font();
|
||||
SetFont(font);
|
||||
|
||||
wxFont head_font = bold_font;
|
||||
|
@ -78,17 +78,17 @@ KBShortcutsDialog::KBShortcutsDialog()
|
|||
grid_sizer->Add(description, -1, wxALIGN_CENTRE_VERTICAL);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
wxStdDialogButtonSizer* buttons = this->CreateStdDialogButtonSizer(wxOK);
|
||||
|
||||
this->SetEscapeId(wxID_OK);
|
||||
this->Bind(wxEVT_BUTTON, &KBShortcutsDialog::onCloseDialog, this, wxID_OK);
|
||||
main_sizer->Add(buttons, 0, wxEXPAND | wxRIGHT | wxBOTTOM, 15);
|
||||
|
||||
|
||||
this->Bind(wxEVT_LEFT_DOWN, &KBShortcutsDialog::onCloseDialog, this);
|
||||
|
||||
SetSizer(main_sizer);
|
||||
main_sizer->SetSizeHints(this);
|
||||
SetSizer(main_sizer);
|
||||
main_sizer->SetSizeHints(this);
|
||||
}
|
||||
|
||||
void KBShortcutsDialog::fill_shortcuts()
|
||||
|
@ -132,6 +132,7 @@ void KBShortcutsDialog::fill_shortcuts()
|
|||
plater_shortcuts.reserve(20);
|
||||
|
||||
plater_shortcuts.push_back(Shortcut("A", L("Arrange")));
|
||||
plater_shortcuts.push_back(Shortcut("Shift+A", L("Arrange selection")));
|
||||
plater_shortcuts.push_back(Shortcut(ctrl+"A", L("Select All objects")));
|
||||
plater_shortcuts.push_back(Shortcut("Del", L("Delete selected")));
|
||||
plater_shortcuts.push_back(Shortcut(ctrl+"Del", L("Delete All")));
|
||||
|
@ -163,10 +164,10 @@ void KBShortcutsDialog::fill_shortcuts()
|
|||
|
||||
// Shortcuts gizmo_shortcuts;
|
||||
// gizmo_shortcuts.reserve(2);
|
||||
//
|
||||
//
|
||||
// gizmo_shortcuts.push_back(Shortcut("Shift+", L("Press to snap by 5% in Gizmo Scale\n or by 1mm in Gizmo Move")));
|
||||
// gizmo_shortcuts.push_back(Shortcut(alt, L("Press to scale or rotate selected objects around their own center")));
|
||||
//
|
||||
//
|
||||
// m_full_shortcuts.push_back(std::make_pair(_(L("Gizmo Shortcuts")), std::make_pair(gizmo_shortcuts, 1)));
|
||||
|
||||
|
||||
|
|
|
@ -1758,6 +1758,17 @@ void TabFilament::reload_config()
|
|||
Tab::reload_config();
|
||||
}
|
||||
|
||||
void TabFilament::update_volumetric_flow_preset_hints()
|
||||
{
|
||||
wxString text;
|
||||
try {
|
||||
text = from_u8(PresetHints::maximum_volumetric_flow_description(*m_preset_bundle));
|
||||
} catch (std::exception &ex) {
|
||||
text = _(L("Volumetric flow hints not available\n\n")) + from_u8(ex.what());
|
||||
}
|
||||
m_volumetric_speed_description_line->SetText(text);
|
||||
}
|
||||
|
||||
void TabFilament::update()
|
||||
{
|
||||
if (m_preset_bundle->printers.get_selected_preset().printer_technology() == ptSLA)
|
||||
|
@ -1765,10 +1776,9 @@ void TabFilament::update()
|
|||
|
||||
m_update_cnt++;
|
||||
|
||||
wxString text = from_u8(PresetHints::cooling_description(m_presets->get_edited_preset()));
|
||||
m_cooling_description_line->SetText(text);
|
||||
text = from_u8(PresetHints::maximum_volumetric_flow_description(*m_preset_bundle));
|
||||
m_volumetric_speed_description_line->SetText(text);
|
||||
wxString text = from_u8(PresetHints::cooling_description(m_presets->get_edited_preset()));
|
||||
m_cooling_description_line->SetText(text);
|
||||
this->update_volumetric_flow_preset_hints();
|
||||
Layout();
|
||||
|
||||
bool cooling = m_config->opt_bool("cooling", 0);
|
||||
|
@ -1790,8 +1800,8 @@ void TabFilament::update()
|
|||
|
||||
void TabFilament::OnActivate()
|
||||
{
|
||||
m_volumetric_speed_description_line->SetText(from_u8(PresetHints::maximum_volumetric_flow_description(*m_preset_bundle)));
|
||||
Tab::OnActivate();
|
||||
this->update_volumetric_flow_preset_hints();
|
||||
Tab::OnActivate();
|
||||
}
|
||||
|
||||
wxSizer* Tab::description_line_widget(wxWindow* parent, ogStaticText* *StaticText)
|
||||
|
|
|
@ -340,6 +340,7 @@ class TabFilament : public Tab
|
|||
|
||||
void add_filament_overrides_page();
|
||||
void update_filament_overrides_page();
|
||||
void update_volumetric_flow_preset_hints();
|
||||
|
||||
std::map<std::string, wxCheckBox*> m_overrides_options;
|
||||
public:
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue