From 65a9e655cfa30e45d59946e152cb1978bf071181 Mon Sep 17 00:00:00 2001 From: yw4z Date: Fri, 3 Jul 2026 23:27:30 +0300 Subject: [PATCH] Add wireframe toggle to canvas menu and fix keyboard shortcut (#14469) --- src/slic3r/GUI/GLCanvas3D.cpp | 48 +++++++++++++++++++++++++++++++++++ src/slic3r/GUI/GLCanvas3D.hpp | 1 + 2 files changed, 49 insertions(+) diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index 8ffac135ff..4237632393 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -2062,6 +2062,7 @@ void GLCanvas3D::render(bool only_init) _render_sla_slices(); _render_selection(); _render_objects(GLVolumeCollection::ERenderType::Transparent, !m_gizmos.is_running()); + _render_wireframe_overlay(); } /* preview render */ else if (m_canvas_type == ECanvasType::CanvasPreview && m_render_preview) { @@ -2087,6 +2088,7 @@ void GLCanvas3D::render(bool only_init) //_render_selection(); // BBS: add outline logic _render_objects(GLVolumeCollection::ERenderType::Transparent, !m_gizmos.is_running()); + _render_wireframe_overlay(); } _render_sequential_clearance(); @@ -8237,6 +8239,46 @@ void GLCanvas3D::_render_objects(GLVolumeCollection::ERenderType type, bool with m_camera_clipping_plane = ClippingPlane::ClipsNothing(); } +void GLCanvas3D::_render_wireframe_overlay() +{ + if (!wxGetApp().plater()->is_show_wireframe()) + return; + if (m_volumes.empty()) + return; + +#if SLIC3R_OPENGL_ES + GLShaderProgram* shader = wxGetApp().get_shader("wireframe"); +#else + GLShaderProgram* shader = wxGetApp().get_shader("mm_contour"); +#endif + if (shader == nullptr) + return; + + const Camera& camera = wxGetApp().plater()->get_camera(); + const Transform3d& view_matrix = camera.get_view_matrix(); + const Transform3d& proj_matrix = camera.get_projection_matrix(); + const Size sz = get_canvas_size(); + + shader->start_using(); + shader->set_uniform("offset", OpenGLManager::get_gl_info().is_mesa() ? 0.0005 : 0.00001); + shader->set_uniform("view_model_matrix", view_matrix); + shader->set_uniform("projection_matrix", proj_matrix); + + glsafe(::glEnable(GL_DEPTH_TEST)); +#if !SLIC3R_OPENGL_ES + if (!OpenGLManager::get_gl_info().is_core_profile()) + glsafe(::glLineWidth(1.0f)); + glsafe(::glPolygonMode(GL_FRONT_AND_BACK, GL_LINE)); +#endif + + m_volumes.render(GLVolumeCollection::ERenderType::Opaque, false, view_matrix, proj_matrix, sz); + +#if !SLIC3R_OPENGL_ES + glsafe(::glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)); +#endif + shader->stop_using(); +} + //BBS: GUI refactor: add canvas size as parameters void GLCanvas3D::_render_gcode(int canvas_width, int canvas_height) { @@ -9275,6 +9317,12 @@ void GLCanvas3D::_render_canvas_toolbar() [this]{wxGetApp().toggle_show_outline();} ); + create_menu_item( _utf8(L("Wireframe")), + m_canvas_type != ECanvasType::CanvasPreview, // not work on preview + p->is_show_wireframe(), + [this, p]{p->toggle_show_wireframe(); m_dirty = true;} + ); + create_menu_item( _utf8(L("Realistic View")), true, cfg->get_bool(SETTING_OPENGL_REALISTIC_MODE), diff --git a/src/slic3r/GUI/GLCanvas3D.hpp b/src/slic3r/GUI/GLCanvas3D.hpp index 72e7f1f8e2..a3209dcc1c 100644 --- a/src/slic3r/GUI/GLCanvas3D.hpp +++ b/src/slic3r/GUI/GLCanvas3D.hpp @@ -1256,6 +1256,7 @@ private: void _render_platelist(const Transform3d& view_matrix, const Transform3d& projection_matrix, bool bottom, bool only_current, bool only_body = false, int hover_id = -1, bool render_cali = false, bool show_grid = true); //BBS: add outline drawing logic void _render_objects(GLVolumeCollection::ERenderType type, bool with_outline = true); + void _render_wireframe_overlay(); //BBS: GUI refactor: add canvas size as parameters void _render_gcode(int canvas_width, int canvas_height); //BBS: render a plane for assemble