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

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

Inheritance diagram for Slic3r::GUI::Preview:
Collaboration diagram for Slic3r::GUI::Preview:

Public Types

enum class  OptionType : unsigned int {
  Travel , Wipe , Retractions , Unretractions ,
  Seams , ToolChanges , ColorChanges , PausePrints ,
  CustomGCodes , Shells , ToolMarker , Legend
}

Public Member Functions

 Preview (wxWindow *parent, Bed3D &bed, Model *model, DynamicPrintConfig *config, BackgroundSlicingProcess *process, GCodeProcessorResult *gcode_result, std::function< void()> schedule_background_process=[]() {})
virtual ~Preview ()
void update_gcode_result (GCodeProcessorResult *gcode_result)
wxGLCanvas * get_wxglcanvas ()
GLCanvas3D * get_canvas3d ()
void set_as_dirty ()
void bed_shape_changed ()
void select_view (const std::string &direction)
void set_drop_target (wxDropTarget *target)
void load_print (bool keep_z_range=false, bool only_gcode=false)
void reload_print (bool only_gcode=false)
void refresh_belt_view ()
void load_shells (const Print &print, bool force_previewing=false)
void reset_shells ()
void msw_rescale ()
void sys_color_changed ()
bool is_loaded () const
void on_tick_changed (CustomGCode::Type type)
void show_sliders (bool show=true)
void show_moves_sliders (bool show=true)
void show_layers_sliders (bool show=true)
void set_reload_paint_after_background_process_apply (bool flag)
bool get_reload_paint_after_background_process_apply ()

Private Member Functions

bool init (wxWindow *parent, Bed3D &bed, Model *model)
void bind_event_handlers ()
void unbind_event_handlers ()
void on_size (wxSizeEvent &evt)
void check_layers_slider_values (std::vector< CustomGCode::Item > &ticks_from_model, const std::vector< double > &layers_z)
void update_layers_slider (const std::vector< double > &layers_z, bool keep_z_range=false)
void update_layers_slider_mode ()
void load_print_as_fff (bool keep_z_range=false, bool only_gcode=false)

Private Attributes

wxGLCanvas * m_canvas_widget { nullptr }
GLCanvas3D * m_canvas { nullptr }
DynamicPrintConfig * m_config
BackgroundSlicingProcess * m_process
GCodeProcessorResult * m_gcode_result
std::function< void()> m_schedule_background_process
unsigned int m_number_extruders { 1 }
bool m_keep_current_preview_type { false }
const Slic3r::PrintBase * m_loaded_print { nullptr }
bool m_only_gcode { false }
bool m_reload_paint_after_background_process_apply {false}

Detailed Description

Member Enumeration Documentation

◆ OptionType

enum class Slic3r::GUI::Preview::OptionType : unsigned int
strong
Enumerator
Travel 
Wipe 
Retractions 
Unretractions 
Seams 
ToolChanges 
ColorChanges 
PausePrints 
CustomGCodes 
Shells 
ToolMarker 
Legend 
117 {
118 Travel,
119 Wipe,
122 Seams,
127 Shells,
128 ToolMarker,
129 Legend
130 };
@ Travel
Definition ExclusionVolumePathCheck.hpp:17
@ Wipe
Definition GCodeProcessor.hpp:63
@ ToolChanges
Definition Types.hpp:183
@ Seams
Definition Types.hpp:182
@ ColorChanges
Definition Types.hpp:184
@ CustomGCodes
Definition Types.hpp:186
@ Unretractions
Definition Types.hpp:181
@ Retractions
Definition Types.hpp:180
@ PausePrints
Definition Types.hpp:185

Constructor & Destructor Documentation

◆ Preview()

Slic3r::GUI::Preview::Preview ( wxWindow * parent,
Bed3D & bed,
Model * model,
DynamicPrintConfig * config,
BackgroundSlicingProcess * process,
GCodeProcessorResult * gcode_result,
std::function< void()> schedule_background_process = []() {} )
255 : m_config(config)
256 , m_process(process)
257 , m_gcode_result(gcode_result)
258 , m_schedule_background_process(schedule_background_process_func)
259{
260 if (init(parent, bed, model))
261 load_print();
262}
GCodeProcessorResult * m_gcode_result
Definition GUI_Preview.hpp:100
std::function< void()> m_schedule_background_process
Definition GUI_Preview.hpp:103
void load_print(bool keep_z_range=false, bool only_gcode=false)
Definition GUI_Preview.cpp:350
DynamicPrintConfig * m_config
Definition GUI_Preview.hpp:98
BackgroundSlicingProcess * m_process
Definition GUI_Preview.hpp:99
bool init(wxWindow *parent, Bed3D &bed, Model *model)
Definition GUI_Preview.cpp:271

References init(), load_print(), m_config, m_gcode_result, m_process, and m_schedule_background_process.

Here is the call graph for this function:

◆ ~Preview()

Slic3r::GUI::Preview::~Preview ( )
virtual
316{
318
319 if (m_canvas != nullptr)
320 delete m_canvas;
321
322 if (m_canvas_widget != nullptr)
323 delete m_canvas_widget;
324}
wxGLCanvas * m_canvas_widget
Definition GUI_Preview.hpp:96
void unbind_event_handlers()
Definition GUI_Preview.cpp:432
GLCanvas3D * m_canvas
Definition GUI_Preview.hpp:97

References m_canvas, m_canvas_widget, and unbind_event_handlers().

Here is the call graph for this function:

Member Function Documentation

◆ bed_shape_changed()

void Slic3r::GUI::Preview::bed_shape_changed ( )
333{
334 if (m_canvas != nullptr)
335 m_canvas->bed_shape_changed();
336}

References m_canvas.

◆ bind_event_handlers()

void Slic3r::GUI::Preview::bind_event_handlers ( )
private
428{
429 this->Bind(wxEVT_SIZE, &Preview::on_size, this);
430}
void on_size(wxSizeEvent &evt)
Definition GUI_Preview.cpp:454

References on_size().

Referenced by init().

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

◆ check_layers_slider_values()

void Slic3r::GUI::Preview::check_layers_slider_values ( std::vector< CustomGCode::Item > & ticks_from_model,
const std::vector< double > & layers_z )
private
461{
462 // All ticks that would end up outside the slider range should be erased.
463 // TODO: this should be placed into more appropriate part of code,
464 // this function is e.g. not called when the last object is deleted
465 unsigned int old_size = ticks_from_model.size();
466 ticks_from_model.erase(std::remove_if(ticks_from_model.begin(), ticks_from_model.end(),
467 [layers_z](CustomGCode::Item val)
468 {
469 auto it = std::lower_bound(layers_z.begin(), layers_z.end(), val.print_z - epsilon());
470 return it == layers_z.end();
471 }),
472 ticks_from_model.end());
473 if (ticks_from_model.size() != old_size)
475}

References m_schedule_background_process.

Referenced by update_layers_slider().

Here is the caller graph for this function:

◆ get_canvas3d()

GLCanvas3D * Slic3r::GUI::Preview::get_canvas3d ( )
inline
140{ return m_canvas; }

References m_canvas.

Referenced by msw_rescale().

Here is the caller graph for this function:

◆ get_reload_paint_after_background_process_apply()

bool Slic3r::GUI::Preview::get_reload_paint_after_background_process_apply ( )
inline
bool m_reload_paint_after_background_process_apply
Definition GUI_Preview.hpp:113

References m_reload_paint_after_background_process_apply.

◆ get_wxglcanvas()

wxGLCanvas * Slic3r::GUI::Preview::get_wxglcanvas ( )
inline
139{ return m_canvas_widget; }

References m_canvas_widget.

◆ init()

bool Slic3r::GUI::Preview::init ( wxWindow * parent,
Bed3D & bed,
Model * model )
private
272{
273 if (!Create(parent, wxID_ANY, wxDefaultPosition, wxDefaultSize, 0 /* disable wxTAB_TRAVERSAL */))
274 return false;
275
276 // to match the background of the sliders
277#ifdef _WIN32
278 wxGetApp().UpdateDarkUI(this);
279#else
280 SetBackgroundColour(GetParent()->GetBackgroundColour());
281#endif // _WIN32
282
284#endif // ENABLE_OPENGL_AUTO_AA_SAMPLES
285 if (m_canvas_widget == nullptr)
286 return false;
287
288 m_canvas = new GLCanvas3D(m_canvas_widget, bed);
289 m_canvas->set_context(wxGetApp().init_glcontext(*m_canvas_widget));
290 m_canvas->allow_multisample(OpenGLManager::can_multisample());
291 m_canvas->set_config(m_config);
292 m_canvas->set_model(model);
293 m_canvas->set_process(m_process);
295 m_canvas->get_gcode_viewer().enable_legend(true);
296 //BBS: GUI refactor: GLToolbar
297 if (wxGetApp().is_editor()) {
298 m_canvas->enable_select_plate_toolbar(true);
299 }
300 m_canvas->enable_assemble_view_toolbar(false);
301
302 // sizer, m_canvas_widget
303 wxBoxSizer *main_sizer = new wxBoxSizer(wxVERTICAL);
304 main_sizer->Add(m_canvas_widget, 1, wxALL | wxEXPAND, 0);
305
306 SetSizer(main_sizer);
307 SetMinSize(GetSize());
308 GetSizer()->SetSizeHints(this);
309
311
312 return true;
313}
@ CanvasPreview
Definition GLCanvas3D.hpp:627
static bool can_multisample()
Definition OpenGLManager.hpp:100
static wxGLCanvas * create_wxglcanvas(wxWindow &parent)
Definition OpenGLManager.cpp:432
void bind_event_handlers()
Definition GUI_Preview.cpp:427

References bind_event_handlers(), Slic3r::GUI::OpenGLManager::can_multisample(), Slic3r::GUI::GLCanvas3D::CanvasPreview, Slic3r::GUI::OpenGLManager::create_wxglcanvas(), m_canvas, m_canvas_widget, m_config, and m_process.

Referenced by Preview().

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

◆ is_loaded()

bool Slic3r::GUI::Preview::is_loaded ( ) const
inline
161{ return (m_loaded_print != nullptr); }
const Slic3r::PrintBase * m_loaded_print
Definition GUI_Preview.hpp:110

References m_loaded_print.

◆ load_print()

void Slic3r::GUI::Preview::load_print ( bool keep_z_range = false,
bool only_gcode = false )
351{
352 PrinterTechnology tech = m_process->current_printer_technology();
353 if (tech == ptFFF)
354 load_print_as_fff(keep_z_range, only_gcode);
355
356 Layout();
357}
void load_print_as_fff(bool keep_z_range=false, bool only_gcode=false)
Definition GUI_Preview.cpp:643
PrinterTechnology
Definition Config.hpp:229
@ ptFFF
Definition Config.hpp:231

References load_print_as_fff(), m_process, and Slic3r::ptFFF.

Referenced by Preview(), refresh_belt_view(), and reload_print().

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

◆ load_print_as_fff()

void Slic3r::GUI::Preview::load_print_as_fff ( bool keep_z_range = false,
bool only_gcode = false )
private
644{
645 if (wxGetApp().mainframe == nullptr || wxGetApp().is_recreating_gui())
646 // avoid processing while mainframe is being constructed
647 return;
648
649 //BBS: add m_loaded_print logic
650 const Print *print = m_process->fff_print();
651 BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(" %1%: previous print %2%, new print %3%")%__LINE__ %m_loaded_print %print;
652 if ((m_loaded_print&&(m_loaded_print == print)) || m_process->current_printer_technology() != ptFFF) {
653 BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(" %1%: already loaded before, return directly")%__LINE__;
654 return;
655 }
656
657 // we require that there's at least one object and the posSlice step
658 // is performed on all of them(this ensures that _shifted_copies was
659 // populated and we know the number of layers)
660 bool has_layers = false;
661 //BBS: always load shell at preview
662 load_shells(*print, true);
663 BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(" %1%: print: %2%, gcode_result %3%, check started")%__LINE__ %print %m_gcode_result;
664 BOOST_LOG_TRIVIAL(info) << __FUNCTION__ << boost::format(" %1%: print is step done, posSlice %2%, posSupportMaterial %3%, psGCodeExport %4%") % __LINE__ % print->is_step_done(posSlice) %print->is_step_done(posSupportMaterial) % print->is_step_done(psGCodeExport);
665 if (print->is_step_done(posSlice)) {
666 for (const PrintObject* print_object : print->objects())
667 if (! print_object->layers().empty()) {
668 has_layers = true;
669 break;
670 }
671 }
672 if (print->is_step_done(posSupportMaterial)) {
673 for (const PrintObject* print_object : print->objects())
674 if (! print_object->support_layers().empty()) {
675 has_layers = true;
676 break;
677 }
678 }
679
680 //BBS: support preview gcode directly even if no slicing
681 bool directly_preview = print->is_step_done(psGCodeExport) && !m_gcode_result->moves.empty();
682 BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(": directly_preview: %1%, gcode_result moves %2%, has_layers %3%") % directly_preview % m_gcode_result->moves.size() %has_layers;
683 if (wxGetApp().is_editor() && !has_layers && !directly_preview) {
684 show_sliders(false);
685 m_canvas_widget->Refresh();
686 return;
687 }
688 //BBS: for direct preview, don't keep z range
689 else if (directly_preview && !has_layers)
690 keep_z_range = false;
691
692 libvgcode::EViewType gcode_view_type = m_canvas->get_gcode_view_type();
693 const bool gcode_preview_data_valid = !m_gcode_result->moves.empty();
694 const bool is_pregcode_preview = !gcode_preview_data_valid && wxGetApp().is_editor();
695
696 const std::vector<std::string> tool_colors = wxGetApp().plater()->get_extruder_colors_from_plater_config(m_gcode_result);
697 const std::vector<CustomGCode::Item>& color_print_values = wxGetApp().is_editor() ?
698 wxGetApp().plater()->model().get_curr_plate_custom_gcodes().gcodes : m_gcode_result->custom_gcode_per_print_z;
699 std::vector<std::string> color_print_colors;
700 if (!color_print_values.empty()) {
701 color_print_colors = wxGetApp().plater()->get_colors_for_color_print(m_gcode_result);
702 color_print_colors.push_back("#808080"); // gray color for pause print or custom G-code
703 }
704
705 std::vector<double> zs;
706
707 if (IsShown()) {
708 m_canvas->set_selected_extruder(0);
709 bool is_slice_result_valid = wxGetApp().plater()->get_partplate_list().get_curr_plate()->is_slice_result_valid();
710 if (gcode_preview_data_valid && (is_slice_result_valid || only_gcode)) {
711 // Load the real G-code preview.
712 //BBS: add more log
713 BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(": will load gcode_preview from result, moves count %1%") % m_gcode_result->moves.size();
714 //BBS: add only gcode mode
715 m_canvas->load_gcode_preview(*m_gcode_result, tool_colors, color_print_colors, only_gcode);
716 // the view type may have been changed by the call m_canvas->load_gcode_preview()
717 gcode_view_type = m_canvas->get_gcode_view_type();
718 //BBS show sliders
720
721 //Orca: keep shell preview on but make it more transparent
722 m_canvas->set_shells_on_previewing(true);
723 m_canvas->set_shell_transparence();
724 Refresh();
725 zs = m_canvas->get_gcode_layers_zs();
726 //BBS: add m_loaded_print logic
727 //m_loaded = true;
728 m_loaded_print = print;
729 }
730 else if (is_pregcode_preview) {
731 // Load the initial preview based on slices, not the final G-code.
732 //BBS: only display shell before slicing result out
733 //m_canvas->load_preview(colors, color_print_values);
734 show_moves_sliders(false);
735 Refresh();
736 //zs = m_canvas->get_volumes_print_zs(true);
737 }
738
739 if (!zs.empty() && !m_keep_current_preview_type) {
740 unsigned int number_extruders = wxGetApp().is_editor() ?
741 (unsigned int)print->extruders().size() :
742 m_canvas->get_gcode_extruders_count();
743 std::vector<CustomGCode::Item> gcodes = wxGetApp().is_editor() ?
744 //BBS
745 wxGetApp().plater()->model().get_curr_plate_custom_gcodes().gcodes :
746 m_gcode_result->custom_gcode_per_print_z;
747 const wxString choice = !gcodes.empty() ?
748 _L("Multicolor Print") :
749 (number_extruders > 1) ? _L("Filaments") : _L("Line Type");
750 }
751
752 if (zs.empty()) {
753 // all layers filtered out
754 //BBS
755 show_layers_sliders(false);
756 m_canvas_widget->Refresh();
757 }
758 else
759 update_layers_slider(zs, keep_z_range);
760 }
761}
#define _L(s)
Definition OBJ.cpp:34
void show_moves_sliders(bool show=true)
Definition GUI_Preview.cpp:443
void load_shells(const Print &print, bool force_previewing=false)
Definition GUI_Preview.cpp:392
void show_layers_sliders(bool show=true)
Definition GUI_Preview.cpp:448
void update_layers_slider(const std::vector< double > &layers_z, bool keep_z_range=false)
Definition GUI_Preview.cpp:545
void show_sliders(bool show=true)
Definition GUI_Preview.cpp:437
bool m_keep_current_preview_type
Definition GUI_Preview.hpp:106
@ psGCodeExport
Definition Print.hpp:118
@ posSlice
Definition Print.hpp:124
@ posSupportMaterial
Definition Print.hpp:125
EViewType
Definition Types.hpp:91

References _L, Slic3r::Print::extruders(), Slic3r::Print::is_step_done(), load_shells(), m_canvas, m_canvas_widget, m_gcode_result, m_keep_current_preview_type, m_loaded_print, m_process, Slic3r::Print::objects(), Slic3r::posSlice, Slic3r::posSupportMaterial, Slic3r::psGCodeExport, Slic3r::ptFFF, show_layers_sliders(), show_moves_sliders(), show_sliders(), and update_layers_slider().

Referenced by load_print().

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

◆ load_shells()

void Slic3r::GUI::Preview::load_shells ( const Print & print,
bool force_previewing = false )
393{
394 m_canvas->load_shells(print, force_previewing);
395}

References m_canvas.

Referenced by load_print_as_fff(), and Slic3r::GUI::Plater::priv::update_fff_scene_only_shells().

Here is the caller graph for this function:

◆ msw_rescale()

void Slic3r::GUI::Preview::msw_rescale ( )
404{
405 // rescale warning legend on the canvas
407
408 // rescale legend
410}
void msw_rescale()
Definition GLCanvas3D.hpp:1383
GLCanvas3D * get_canvas3d()
Definition GUI_Preview.hpp:140
bool m_only_gcode
Definition GUI_Preview.hpp:112
void reload_print(bool only_gcode=false)
Definition GUI_Preview.cpp:360

References get_canvas3d(), m_only_gcode, Slic3r::GUI::GLCanvas3D::msw_rescale(), and reload_print().

Here is the call graph for this function:

◆ on_size()

void Slic3r::GUI::Preview::on_size ( wxSizeEvent & evt)
private
455{
456 evt.Skip();
457 Refresh();
458}

Referenced by bind_event_handlers(), and unbind_event_handlers().

Here is the caller graph for this function:

◆ on_tick_changed()

void Slic3r::GUI::Preview::on_tick_changed ( CustomGCode::Type type)
419{
420 //if (type == Type::PausePrint) {
421 // m_schedule_background_process();
422 //}
424 reload_print(false);
425}

References m_keep_current_preview_type, and reload_print().

Here is the call graph for this function:

◆ refresh_belt_view()

void Slic3r::GUI::Preview::refresh_belt_view ( )
373{
374 // Re-run the G-code preview conversion so the belt "designed view" toggle takes effect
375 // (the back-transform is baked into the toolpath geometry in GCodeViewer::load_as_gcode,
376 // whose same-result cache also keys on the view state, so the re-convert runs).
377 // Reset m_loaded_print to bypass the "already loaded" guard the way reload_print does, but
378 // keep the current layer range and only-gcode mode so the view doesn't jump on toggle.
379 // The layer Z values differ between the designed and the raw view (the raw view's are
380 // machine-frame heights), so keep_z_range alone cannot find the old span: carry the
381 // slider over by layer index instead.
382 IMSlider *layers_slider = m_canvas->get_gcode_viewer().get_layers_slider();
383 const int lower = layers_slider->GetLowerValue();
384 const int higher = layers_slider->GetHigherValue();
385 m_loaded_print = nullptr;
386 load_print(true /*keep_z_range*/, m_only_gcode);
387 if (higher <= layers_slider->GetMaxValue())
388 layers_slider->SetSelectionSpan(lower, higher);
389}

References Slic3r::GUI::IMSlider::GetHigherValue(), Slic3r::GUI::IMSlider::GetLowerValue(), load_print(), m_canvas, m_loaded_print, m_only_gcode, and Slic3r::GUI::IMSlider::SetSelectionSpan().

Here is the call graph for this function:

◆ reload_print()

void Slic3r::GUI::Preview::reload_print ( bool only_gcode = false)
361{
362 BOOST_LOG_TRIVIAL(debug) << __FUNCTION__ << boost::format(" %1%: enter")%__LINE__;
363
364 //BBS: add m_loaded_print logic
365 //m_loaded = false;
366 m_loaded_print = nullptr;
367
368 load_print(false, only_gcode);
369 m_only_gcode = only_gcode;
370}

References load_print(), m_loaded_print, and m_only_gcode.

Referenced by msw_rescale(), Slic3r::GUI::Plater::priv::on_process_completed(), Slic3r::GUI::Plater::priv::on_slicing_update(), on_tick_changed(), Slic3r::GUI::Plater::priv::set_current_panel(), Slic3r::GUI::Plater::priv::update(), Slic3r::GUI::Plater::priv::update_fff_scene(), and Slic3r::GUI::Plater::priv::update_restart_background_process().

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

◆ reset_shells()

void Slic3r::GUI::Preview::reset_shells ( )
399{
400 m_canvas->reset_shells();
401}

References m_canvas.

◆ select_view()

void Slic3r::GUI::Preview::select_view ( const std::string & direction)
339{
340 m_canvas->select_view(direction);
341}

References m_canvas.

◆ set_as_dirty()

void Slic3r::GUI::Preview::set_as_dirty ( )
327{
328 if (m_canvas != nullptr)
329 m_canvas->set_as_dirty();
330}

References m_canvas.

◆ set_drop_target()

void Slic3r::GUI::Preview::set_drop_target ( wxDropTarget * target)
344{
345 if (target != nullptr)
346 SetDropTarget(target);
347}

◆ set_reload_paint_after_background_process_apply()

void Slic3r::GUI::Preview::set_reload_paint_after_background_process_apply ( bool flag)
inline

◆ show_layers_sliders()

void Slic3r::GUI::Preview::show_layers_sliders ( bool show = true)
449{
450 ;//TODO
451}

Referenced by load_print_as_fff(), and show_sliders().

Here is the caller graph for this function:

◆ show_moves_sliders()

void Slic3r::GUI::Preview::show_moves_sliders ( bool show = true)
444{
445 ;//TODO
446}

Referenced by load_print_as_fff(), and show_sliders().

Here is the caller graph for this function:

◆ show_sliders()

void Slic3r::GUI::Preview::show_sliders ( bool show = true)
438{
439 show_moves_sliders(show);
441}

References show_layers_sliders(), and show_moves_sliders().

Referenced by load_print_as_fff().

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

◆ sys_color_changed()

void Slic3r::GUI::Preview::sys_color_changed ( )
413{
414 //TODO
415 // m_layers_slider->sys_color_changed();
416}

◆ unbind_event_handlers()

void Slic3r::GUI::Preview::unbind_event_handlers ( )
private
433{
434 this->Unbind(wxEVT_SIZE, &Preview::on_size, this);
435}

References on_size().

Referenced by ~Preview().

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

◆ update_gcode_result()

void Slic3r::GUI::Preview::update_gcode_result ( GCodeProcessorResult * gcode_result)
265{
266 m_gcode_result = gcode_result;
267
268 return;
269}

References m_gcode_result.

Referenced by Slic3r::GUI::Plater::priv::load_files(), Slic3r::GUI::Plater::priv::reload_from_disk(), Slic3r::GUI::Plater::priv::undo_redo_to(), and Slic3r::GUI::Plater::priv::update_background_process().

Here is the caller graph for this function:

◆ update_layers_slider()

void Slic3r::GUI::Preview::update_layers_slider ( const std::vector< double > & layers_z,
bool keep_z_range = false )
private
546{
547 IMSlider *m_layers_slider = m_canvas->get_gcode_viewer().get_layers_slider();
548 // Save the initial slider span.
549 double z_low = m_layers_slider->GetLowerValueD();
550 double z_high = m_layers_slider->GetHigherValueD();
551 bool was_empty = m_layers_slider->GetMaxValue() == 0;
552
553 bool force_sliders_full_range = was_empty;
554 if (!keep_z_range) {
555 bool span_changed = layers_z.empty() || std::abs(layers_z.back() - m_layers_slider->GetMaxValueD()) > epsilon() /*1e-6*/;
556 force_sliders_full_range |= span_changed;
557 }
558 bool snap_to_min = force_sliders_full_range || m_layers_slider->is_lower_at_min();
559 bool snap_to_max = force_sliders_full_range || m_layers_slider->is_higher_at_max();
560
561 // Detect and set manipulation mode for double slider
563
564 Plater* plater = wxGetApp().plater();
565 //BBS: replace model custom gcode with current plate custom gcode
566 CustomGCode::Info ticks_info_from_curr_plate;
567 if (wxGetApp().is_editor())
568 ticks_info_from_curr_plate = plater->model().get_curr_plate_custom_gcodes();
569 else {
570 ticks_info_from_curr_plate.mode = CustomGCode::Mode::SingleExtruder;
571 ticks_info_from_curr_plate.gcodes = m_gcode_result->custom_gcode_per_print_z;
572 }
573 check_layers_slider_values(ticks_info_from_curr_plate.gcodes, layers_z);
574
575 // first of all update extruder colors to avoid crash, when we are switching printer preset from MM to SM
576 m_layers_slider->SetExtruderColors(plater->get_extruder_colors_from_plater_config(wxGetApp().is_editor() ? nullptr : m_gcode_result));
577 m_layers_slider->SetSliderValues(layers_z);
578 assert(m_layers_slider->GetMinValue() == 0);
579 m_layers_slider->SetMaxValue(layers_z.empty() ? 0 : layers_z.size() - 1);
580
581 int idx_low = 0;
582 int idx_high = m_layers_slider->GetMaxValue();
583 if (!layers_z.empty()) {
584 if (!snap_to_min) {
585 int idx_new = find_close_layer_idx(layers_z, z_low, epsilon() /*1e-6*/);
586 if (idx_new != -1) idx_low = idx_new;
587 }
588 if (!snap_to_max) {
589 int idx_new = find_close_layer_idx(layers_z, z_high, epsilon() /*1e-6*/);
590 if (idx_new != -1) idx_high = idx_new;
591 }
592 }
593 m_layers_slider->SetSelectionSpan(idx_low, idx_high);
594
595 auto curr_plate = wxGetApp().plater()->get_partplate_list().get_curr_plate();
596 auto curr_print_seq = curr_plate->get_real_print_seq();
597 bool sequential_print = (curr_print_seq == PrintSequence::ByObject);
598 m_layers_slider->SetDrawMode(sequential_print);
599
600 m_layers_slider->SetTicksValues(ticks_info_from_curr_plate);
601
602 auto print_mode_stat = m_gcode_result->print_statistics.modes.front();
603 m_layers_slider->SetLayersTimes(m_canvas->get_gcode_layers_times_cache(), print_mode_stat.time);
604
605 // Suggest the auto color change, if model looks like sign
606 if (m_layers_slider->IsNewPrint()) {
607 const Print &print = wxGetApp().plater()->fff_print();
608
609 // bool is_possible_auto_color_change = false;
610 for (auto object : print.objects()) {
611 double object_x = double(object->size().x());
612 double object_y = double(object->size().y());
613
614 // if it's sign, than object have not to be a too height
615 double height = object->height();
616 coord_t longer_side = std::max(object_x, object_y);
617 auto num_layers = int(object->layers().size());
618 if (height / longer_side > 0.3 || num_layers < 2) continue;
619
620 const ExPolygons &bottom = object->get_layer(0)->lslices;
621 double bottom_area = area(bottom);
622
623 // at least 25% of object's height have to be a solid
624 int i, min_solid_height = int(0.25 * num_layers);
625 for (i = 1; i <= min_solid_height; ++i) {
626 double cur_area = area(object->get_layer(i)->lslices);
627 if (!equivalent_areas(bottom_area, cur_area)) {
628 // but due to the elephant foot compensation, the first layer may be slightly smaller than the others
629 if (i == 1 && fabs(cur_area - bottom_area) / bottom_area < 0.1) {
630 // So, let process this case and use second layer as a bottom
631 bottom_area = cur_area;
632 continue;
633 }
634 break;
635 }
636 }
637 if (i < min_solid_height) continue;
638 }
639 }
640}
std::vector< std::string > get_extruder_colors_from_plater_config(const GCodeProcessorResult *const result=nullptr) const
Definition Plater.cpp:21797
const Model & model() const
Definition Plater.cpp:16047
void update_layers_slider_mode()
Definition GUI_Preview.cpp:499
void check_layers_slider_values(std::vector< CustomGCode::Item > &ticks_from_model, const std::vector< double > &layers_z)
Definition GUI_Preview.cpp:460
const CustomGCode::Info get_curr_plate_custom_gcodes() const
Definition Model.hpp:1745
int64_t coord_t
Definition libslic3r.h:48
@ SingleExtruder
Definition CustomGCode.hpp:56
static Plater * plater()
Definition GUI_Factories.cpp:400
static int find_close_layer_idx(const std::vector< double > &zs, double &z, double eps)
Definition GCodeViewer.cpp:208
bool equivalent_areas(const double &bottom_area, const double &top_area)
Definition IMSlider.cpp:81
@ Plater
Definition Shortcuts.hpp:21
constexpr double epsilon()
Definition IMSlider.hpp:31
coord_t height(const BoundingBox &box)
Definition Arrange.cpp:1185
std::vector< ExPolygon > ExPolygons
Definition ExPolygon.hpp:20
double area(const ExPolygon &poly)
Definition ExPolygon.hpp:511
@ ByObject
Definition PrintConfig.hpp:312

References Slic3r::area(), Slic3r::ByObject, check_layers_slider_values(), Slic3r::GUI::epsilon(), Slic3r::GUI::equivalent_areas(), Slic3r::GUI::find_close_layer_idx(), Slic3r::CustomGCode::Info::gcodes, Slic3r::GUI::IMSlider::GetHigherValueD(), Slic3r::GUI::IMSlider::GetLowerValueD(), Slic3r::GUI::IMSlider::GetMaxValue(), Slic3r::GUI::IMSlider::GetMaxValueD(), Slic3r::GUI::IMSlider::GetMinValue(), Slic3r::GUI::IMSlider::is_higher_at_max(), Slic3r::GUI::IMSlider::is_lower_at_min(), Slic3r::GUI::IMSlider::IsNewPrint(), m_canvas, m_gcode_result, Slic3r::CustomGCode::Info::mode, Slic3r::Print::objects(), Slic3r::GUI::plater(), Slic3r::GUI::IMSlider::SetDrawMode(), Slic3r::GUI::IMSlider::SetExtruderColors(), Slic3r::GUI::IMSlider::SetLayersTimes(), Slic3r::GUI::IMSlider::SetMaxValue(), Slic3r::GUI::IMSlider::SetSelectionSpan(), Slic3r::GUI::IMSlider::SetSliderValues(), Slic3r::GUI::IMSlider::SetTicksValues(), Slic3r::CustomGCode::SingleExtruder, and update_layers_slider_mode().

Referenced by load_print_as_fff().

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

◆ update_layers_slider_mode()

void Slic3r::GUI::Preview::update_layers_slider_mode ( )
private
500{
501 // true -> single-extruder printer profile OR
502 // multi-extruder printer profile , but whole model is printed by only one extruder
503 // false -> multi-extruder printer profile , and model is printed by several extruders
504 bool one_extruder_printed_model = true;
505 bool can_change_color = true;
506 // extruder used for whole model for multi-extruder printer profile
507 int only_extruder = -1;
508
509 // BBS
510 if (wxGetApp().filaments_cnt() > 1) {
511 //const ModelObjectPtrs& objects = wxGetApp().plater()->model().objects;
512 auto plate_extruders = wxGetApp().plater()->get_partplate_list().get_curr_plate()->get_extruders_without_support();
513 for (auto extruder : plate_extruders) {
514 if (extruder != plate_extruders[0])
515 can_change_color = false;
516 }
517 // check if whole model uses just only one extruder
518 if (!plate_extruders.empty()) {
519 //const int extruder = objects[0]->config.has("extruder") ? objects[0]->config.option("extruder")->getInt() : 0;
520 only_extruder = plate_extruders[0];
521 // auto is_one_extruder_printed_model = [objects, extruder]() {
522 // for (ModelObject *object : objects) {
523 // if (object->config.has("extruder") && object->config.option("extruder")->getInt() != extruder) /*return false*/;
524
525 // for (ModelVolume *volume : object->volumes)
526 // if ((volume->config.has("extruder") && volume->config.option("extruder")->getInt() != extruder) || !volume->mmu_segmentation_facets.empty()) return false;
527
528 // for (const auto &range : object->layer_config_ranges)
529 // if (range.second.has("extruder") && range.second.option("extruder")->getInt() != extruder) return false;
530 // }
531 // return true;
532 // };
533
534 // if (is_one_extruder_printed_model())
535 // only_extruder = extruder;
536 // else
537 // one_extruder_printed_model = false;
538 }
539 }
540
541 IMSlider *m_layers_slider = m_canvas->get_gcode_viewer().get_layers_slider();
542 m_layers_slider->SetModeAndOnlyExtruder(one_extruder_printed_model, only_extruder, can_change_color);
543}

References m_canvas, and Slic3r::GUI::IMSlider::SetModeAndOnlyExtruder().

Referenced by update_layers_slider().

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

Member Data Documentation

◆ m_canvas

◆ m_canvas_widget

wxGLCanvas* Slic3r::GUI::Preview::m_canvas_widget { nullptr }
private
96{ nullptr };

Referenced by ~Preview(), get_wxglcanvas(), init(), and load_print_as_fff().

◆ m_config

DynamicPrintConfig* Slic3r::GUI::Preview::m_config
private

Referenced by Preview(), and init().

◆ m_gcode_result

GCodeProcessorResult* Slic3r::GUI::Preview::m_gcode_result
private

◆ m_keep_current_preview_type

bool Slic3r::GUI::Preview::m_keep_current_preview_type { false }
private
106{ false };

Referenced by load_print_as_fff(), and on_tick_changed().

◆ m_loaded_print

const Slic3r::PrintBase* Slic3r::GUI::Preview::m_loaded_print { nullptr }
private
110{ nullptr };

Referenced by is_loaded(), load_print_as_fff(), refresh_belt_view(), and reload_print().

◆ m_number_extruders

unsigned int Slic3r::GUI::Preview::m_number_extruders { 1 }
private
105{ 1 };

◆ m_only_gcode

bool Slic3r::GUI::Preview::m_only_gcode { false }
private
112{ false };

Referenced by msw_rescale(), refresh_belt_view(), and reload_print().

◆ m_process

BackgroundSlicingProcess* Slic3r::GUI::Preview::m_process
private

◆ m_reload_paint_after_background_process_apply

bool Slic3r::GUI::Preview::m_reload_paint_after_background_process_apply {false}
private

◆ m_schedule_background_process

std::function<void()> Slic3r::GUI::Preview::m_schedule_background_process
private

The documentation for this class was generated from the following files: