diff --git a/resources/shaders/110/gouraud.fs b/resources/shaders/110/gouraud.fs index 0742f6cc88..cf3163fa37 100644 --- a/resources/shaders/110/gouraud.fs +++ b/resources/shaders/110/gouraud.fs @@ -26,8 +26,6 @@ struct SlopeDetection uniform vec4 uniform_color; uniform SlopeDetection slope; -uniform bool offset_depth_buffer; - #ifdef ENABLE_ENVIRONMENT_MAP uniform sampler2D environment_tex; uniform bool use_environment_tex; @@ -78,9 +76,4 @@ void main() else #endif gl_FragColor = vec4(vec3(intensity.y) + color * intensity.x, alpha); - - // In the support painting gizmo and the seam painting gizmo are painted triangles rendered over the already - // rendered object. To resolved z-fighting between previously rendered object and painted triangles, values - // inside the depth buffer are offset by small epsilon for painted triangles inside those gizmos. - gl_FragDepth = gl_FragCoord.z - (offset_depth_buffer ? EPSILON : 0.0); } diff --git a/resources/shaders/110/mm_contour.fs b/resources/shaders/110/mm_contour.fs index 14477a59e6..ab656998df 100644 --- a/resources/shaders/110/mm_contour.fs +++ b/resources/shaders/110/mm_contour.fs @@ -1,13 +1,8 @@ #version 110 -const float EPSILON = 0.0001; - uniform vec4 uniform_color; void main() { gl_FragColor = uniform_color; - // Values inside depth buffer for fragments of the contour of a selected area are offset - // by small epsilon to solve z-fighting between painted triangles and contour lines. - gl_FragDepth = gl_FragCoord.z - EPSILON; } diff --git a/resources/shaders/110/mm_contour.vs b/resources/shaders/110/mm_contour.vs index d9063f0c70..b37394b619 100644 --- a/resources/shaders/110/mm_contour.vs +++ b/resources/shaders/110/mm_contour.vs @@ -2,10 +2,14 @@ uniform mat4 view_model_matrix; uniform mat4 projection_matrix; +uniform float offset; attribute vec3 v_position; void main() { - gl_Position = projection_matrix * view_model_matrix * vec4(v_position, 1.0); + // Add small epsilon to z to solve z-fighting between painted triangles and contour lines. + vec4 clip_position = projection_matrix * view_model_matrix * vec4(v_position, 1.0); + clip_position.z -= offset * abs(clip_position.w); + gl_Position = clip_position; } diff --git a/resources/shaders/140/gouraud.fs b/resources/shaders/140/gouraud.fs index beb3a947bb..273779ca84 100644 --- a/resources/shaders/140/gouraud.fs +++ b/resources/shaders/140/gouraud.fs @@ -26,8 +26,6 @@ struct SlopeDetection uniform vec4 uniform_color; uniform SlopeDetection slope; -uniform bool offset_depth_buffer; - #ifdef ENABLE_ENVIRONMENT_MAP uniform sampler2D environment_tex; uniform bool use_environment_tex; @@ -78,9 +76,4 @@ void main() else #endif gl_FragColor = vec4(vec3(intensity.y) + color * intensity.x, alpha); - - // In the support painting gizmo and the seam painting gizmo are painted triangles rendered over the already - // rendered object. To resolved z-fighting between previously rendered object and painted triangles, values - // inside the depth buffer are offset by small epsilon for painted triangles inside those gizmos. - gl_FragDepth = gl_FragCoord.z - (offset_depth_buffer ? EPSILON : 0.0); } diff --git a/resources/shaders/140/mm_contour.fs b/resources/shaders/140/mm_contour.fs index 3681d76c18..e74124dcae 100644 --- a/resources/shaders/140/mm_contour.fs +++ b/resources/shaders/140/mm_contour.fs @@ -1,13 +1,8 @@ #version 140 -const float EPSILON = 0.0001; - uniform vec4 uniform_color; void main() { gl_FragColor = uniform_color; - // Values inside depth buffer for fragments of the contour of a selected area are offset - // by small epsilon to solve z-fighting between painted triangles and contour lines. - gl_FragDepth = gl_FragCoord.z - EPSILON; } diff --git a/resources/shaders/140/mm_contour.vs b/resources/shaders/140/mm_contour.vs index 7042671de2..679291ba6d 100644 --- a/resources/shaders/140/mm_contour.vs +++ b/resources/shaders/140/mm_contour.vs @@ -2,10 +2,14 @@ uniform mat4 view_model_matrix; uniform mat4 projection_matrix; +uniform float offset; in vec3 v_position; void main() { - gl_Position = projection_matrix * view_model_matrix * vec4(v_position, 1.0); + // Add small epsilon to z to solve z-fighting between painted triangles and contour lines. + vec4 clip_position = projection_matrix * view_model_matrix * vec4(v_position, 1.0); + clip_position.z -= offset * abs(clip_position.w); + gl_Position = clip_position; } diff --git a/resources/shaders/gouraud.fs b/resources/shaders/gouraud.fs index 511faf4c00..1657fc0513 100644 --- a/resources/shaders/gouraud.fs +++ b/resources/shaders/gouraud.fs @@ -26,8 +26,6 @@ struct SlopeDetection uniform vec4 uniform_color; uniform SlopeDetection slope; -uniform bool offset_depth_buffer; - #ifdef ENABLE_ENVIRONMENT_MAP uniform sampler2D environment_tex; uniform bool use_environment_tex; @@ -78,9 +76,4 @@ void main() else #endif gl_FragColor = vec4(vec3(intensity.y) + color * intensity.x, alpha); - - // In the support painting gizmo and the seam painting gizmo are painted triangles rendered over the already - // rendered object. To resolved z-fighting between previously rendered object and painted triangles, values - // inside the depth buffer are offset by small epsilon for painted triangles inside those gizmos. - gl_FragDepth = gl_FragCoord.z - (offset_depth_buffer ? EPSILON : 0.0); } diff --git a/resources/shaders/mm_contour.fs b/resources/shaders/mm_contour.fs index 8ccf5b832c..14c18dcf16 100644 --- a/resources/shaders/mm_contour.fs +++ b/resources/shaders/mm_contour.fs @@ -1,11 +1,6 @@ #version 110 -const float EPSILON = 0.0001; - void main() { gl_FragColor = vec4(1.0, 1.0, 1.0, 1.0); - // Values inside depth buffer for fragments of the contour of a selected area are offset - // by small epsilon to solve z-fighting between painted triangles and contour lines. - gl_FragDepth = gl_FragCoord.z - EPSILON; } diff --git a/resources/shaders/mm_contour.vs b/resources/shaders/mm_contour.vs index d0d3ee42a9..8423362e46 100644 --- a/resources/shaders/mm_contour.vs +++ b/resources/shaders/mm_contour.vs @@ -1,6 +1,11 @@ #version 110 +uniform float offset; + void main() { - gl_Position = ftransform(); + // Add small epsilon to z to solve z-fighting between painted triangles and contour lines. + vec4 clip_position = gl_ModelViewProjectionMatrix * gl_Vertex; + clip_position.z -= offset * abs(clip_position.w); + gl_Position = clip_position; } diff --git a/src/slic3r/GUI/GLCanvas3D.cpp b/src/slic3r/GUI/GLCanvas3D.cpp index afb24185d6..2bbeb14f0d 100644 --- a/src/slic3r/GUI/GLCanvas3D.cpp +++ b/src/slic3r/GUI/GLCanvas3D.cpp @@ -5351,7 +5351,7 @@ void GLCanvas3D::_picking_pass() #if !ENABLE_GL_SHADERS_ATTRIBUTES m_camera_clipping_plane = m_gizmos.get_clipping_plane(); if (m_camera_clipping_plane.is_active()) { - ::glClipPlane(GL_CLIP_PLANE0, (GLdouble*)m_camera_clipping_plane.get_data()); + ::glClipPlane(GL_CLIP_PLANE0, (GLdouble*)m_camera_clipping_plane.get_data().data()); ::glEnable(GL_CLIP_PLANE0); } #endif // !ENABLE_GL_SHADERS_ATTRIBUTES diff --git a/src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp b/src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp index c5d5405275..b6861254a9 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp @@ -9,6 +9,7 @@ #include "slic3r/GUI/format.hpp" #include "slic3r/GUI/GUI_ObjectList.hpp" #include "slic3r/GUI/NotificationManager.hpp" +#include "slic3r/GUI/OpenGLManager.hpp" #include "libslic3r/PresetBundle.hpp" #include "libslic3r/Model.hpp" #include "slic3r/Utils/UndoRedo.hpp" @@ -627,11 +628,8 @@ void TriangleSelectorMmGui::render(ImGuiWrapper *imgui) auto *contour_shader = wxGetApp().get_shader("mm_contour"); contour_shader->start_using(); - - glsafe(::glDepthFunc(GL_LEQUAL)); + contour_shader->set_uniform("offset", OpenGLManager::get_gl_info().is_mesa() ? 0.0005 : 0.00001); m_paint_contour.render(); - glsafe(::glDepthFunc(GL_LESS)); - contour_shader->stop_using(); } #endif // ENABLE_LEGACY_OPENGL_REMOVAL diff --git a/src/slic3r/GUI/Gizmos/GLGizmoPainterBase.cpp b/src/slic3r/GUI/Gizmos/GLGizmoPainterBase.cpp index 01dc595148..0cba59c6d8 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoPainterBase.cpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoPainterBase.cpp @@ -8,6 +8,7 @@ #include "slic3r/GUI/GUI_App.hpp" #include "slic3r/GUI/Camera.hpp" #include "slic3r/GUI/Plater.hpp" +#include "slic3r/GUI/OpenGLManager.hpp" #include "slic3r/Utils/UndoRedo.hpp" #include "libslic3r/Model.hpp" #include "libslic3r/PresetBundle.hpp" @@ -284,9 +285,11 @@ void GLGizmoPainterBase::render_cursor_sphere(const Transform3d& trafo) const #endif // ENABLE_LEGACY_OPENGL_REMOVAL } +#if ENABLE_LEGACY_OPENGL_REMOVAL GLShaderProgram* shader = wxGetApp().get_shader("flat"); if (shader == nullptr) return; +#endif // ENABLE_LEGACY_OPENGL_REMOVAL const Transform3d complete_scaling_matrix_inverse = Geometry::Transformation(trafo).get_matrix(true, true, false, true).inverse(); const bool is_left_handed = Geometry::Transformation(trafo).is_left_handed(); @@ -918,8 +921,6 @@ void TriangleSelectorGUI::render(ImGuiWrapper* imgui) assert(shader->get_name() == "gouraud"); - ScopeGuard guard([shader]() { if (shader) shader->set_uniform("offset_depth_buffer", false);}); - shader->set_uniform("offset_depth_buffer", true); for (auto iva : {std::make_pair(&m_iva_enforcers, enforcers_color), std::make_pair(&m_iva_blockers, blockers_color)}) { #if ENABLE_LEGACY_OPENGL_REMOVAL @@ -967,11 +968,8 @@ void TriangleSelectorGUI::render(ImGuiWrapper* imgui) auto *contour_shader = wxGetApp().get_shader("mm_contour"); contour_shader->start_using(); - - glsafe(::glDepthFunc(GL_LEQUAL)); + contour_shader->set_uniform("offset", OpenGLManager::get_gl_info().is_mesa() ? 0.0005 : 0.00001); m_paint_contour.render(); - glsafe(::glDepthFunc(GL_LESS)); - contour_shader->stop_using(); } #endif // ENABLE_LEGACY_OPENGL_REMOVAL @@ -1014,6 +1012,9 @@ void TriangleSelectorGUI::update_render_data() iva.release_geometry(); #endif // ENABLE_LEGACY_OPENGL_REMOVAL + // small value used to offset triangles along their normal to avoid z-fighting + static const float offset = 0.001f; + for (const Triangle &tr : m_triangles) { if (!tr.valid() || tr.is_split() || (tr.get_state() == EnforcerBlockerType::NONE && !tr.is_selected_by_seed_fill())) continue; @@ -1037,15 +1038,17 @@ void TriangleSelectorGUI::update_render_data() //FIXME the normal may likely be pulled from m_triangle_selectors, but it may not be worth the effort // or the current implementation may be more cache friendly. const Vec3f n = (v1 - v0).cross(v2 - v1).normalized(); + // small value used to offset triangles along their normal to avoid z-fighting + const Vec3f offset_n = offset * n; #if ENABLE_LEGACY_OPENGL_REMOVAL - iva.add_vertex(v0, n); - iva.add_vertex(v1, n); - iva.add_vertex(v2, n); + iva.add_vertex(v0 + offset_n, n); + iva.add_vertex(v1 + offset_n, n); + iva.add_vertex(v2 + offset_n, n); iva.add_triangle((unsigned int)cnt, (unsigned int)cnt + 1, (unsigned int)cnt + 2); #else - iva.push_geometry(v0, n); - iva.push_geometry(v1, n); - iva.push_geometry(v2, n); + iva.push_geometry(v0 + offset_n, n); + iva.push_geometry(v1 + offset_n, n); + iva.push_geometry(v2 + offset_n, n); iva.push_triangle(cnt, cnt + 1, cnt + 2); #endif // ENABLE_LEGACY_OPENGL_REMOVAL cnt += 3; @@ -1361,16 +1364,14 @@ void TriangleSelectorGUI::render_paint_contour() if (contour_shader != nullptr) { contour_shader->start_using(); + contour_shader->set_uniform("offset", OpenGLManager::get_gl_info().is_mesa() ? 0.0005 : 0.00001); #if ENABLE_GL_SHADERS_ATTRIBUTES const Camera& camera = wxGetApp().plater()->get_camera(); contour_shader->set_uniform("view_model_matrix", camera.get_view_matrix() * matrix); contour_shader->set_uniform("projection_matrix", camera.get_projection_matrix()); #endif // ENABLE_GL_SHADERS_ATTRIBUTES - glsafe(::glDepthFunc(GL_LEQUAL)); m_paint_contour.render(); - glsafe(::glDepthFunc(GL_LESS)); - contour_shader->stop_using(); } diff --git a/src/slic3r/GUI/Gizmos/GLGizmoSimplify.cpp b/src/slic3r/GUI/Gizmos/GLGizmoSimplify.cpp index 157a44b2ba..fcdd56c6a5 100644 --- a/src/slic3r/GUI/Gizmos/GLGizmoSimplify.cpp +++ b/src/slic3r/GUI/Gizmos/GLGizmoSimplify.cpp @@ -7,6 +7,7 @@ #include "slic3r/GUI/NotificationManager.hpp" #include "slic3r/GUI/Plater.hpp" #include "slic3r/GUI/format.hpp" +#include "slic3r/GUI/OpenGLManager.hpp" #include "libslic3r/AppConfig.hpp" #include "libslic3r/Model.hpp" #include "libslic3r/QuadricEdgeCollapse.hpp" @@ -756,6 +757,7 @@ void GLGizmoSimplify::on_render() if (m_show_wireframe) { auto *contour_shader = wxGetApp().get_shader("mm_contour"); contour_shader->start_using(); + contour_shader->set_uniform("offset", OpenGLManager::get_gl_info().is_mesa() ? 0.0005 : 0.00001); #if ENABLE_GL_SHADERS_ATTRIBUTES contour_shader->set_uniform("view_model_matrix", view_model_matrix); contour_shader->set_uniform("projection_matrix", camera.get_projection_matrix()); diff --git a/src/slic3r/GUI/OpenGLManager.cpp b/src/slic3r/GUI/OpenGLManager.cpp index 41a11cff6e..3bf0b1b270 100644 --- a/src/slic3r/GUI/OpenGLManager.cpp +++ b/src/slic3r/GUI/OpenGLManager.cpp @@ -65,6 +65,11 @@ const std::string& OpenGLManager::GLInfo::get_renderer() const return m_renderer; } +bool OpenGLManager::GLInfo::is_mesa() const +{ + return boost::icontains(m_version, "mesa"); +} + int OpenGLManager::GLInfo::get_max_tex_size() const { if (!m_detected) diff --git a/src/slic3r/GUI/OpenGLManager.hpp b/src/slic3r/GUI/OpenGLManager.hpp index 72a4e6bc07..0b505c6455 100644 --- a/src/slic3r/GUI/OpenGLManager.hpp +++ b/src/slic3r/GUI/OpenGLManager.hpp @@ -40,6 +40,8 @@ public: const std::string& get_vendor() const; const std::string& get_renderer() const; + bool is_mesa() const; + int get_max_tex_size() const; float get_max_anisotropy() const;