I am currently working on the wireframe shaders which is working. I managed to have some sort of dashed wire whenever the the edges is hidden from the view but I am having problem with certain views of the camera where some supposed to be visible edges would be rendered as dashed lines and the dashed lines itself is not in constant sizes and spacing between the lines.

enter image description here

I am also troubled at removing the unnecessary diagonals since the script supposed to remove it but, probably the shader does not recognize it as a diagonal lines.

enter image description here

Above image is the opposite view from the first image btw.

Here is the shader:

Shader "Custom/Geometry/WireframeSample"
{
    Properties
    {
        [PowerSlider(3.0)]
        _WireframeVal ("Wireframe width", Range(0., 0.5)) = 0.05
        _RepeatCount("Repeat Count", float) = 5
		_Spacing("Spacing", float) = 0.5
		_Offset("Offset", float) = 0
        _FrontColor ("Front color", color) = (1., 1., 1., 1.)
        _BackColor ("Back color", color) = (1., 1., 1., 1.)
        [Toggle] _RemoveDiag("Remove diagonals?", Float) = 0.
    }
    SubShader
    {
        Tags { "Queue"="Geometry" "RenderType"="Opaque" }
       
        Pass
        {
            Cull Front
            CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #pragma geometry geom
 
            // Change "shader_feature" with "pragma_compile" if you want set this keyword from c# code
            #pragma shader_feature __ _REMOVEDIAG_ON
 
            #include "UnityCG.cginc"

            float _RepeatCount;
	        float _Spacing;
	        float _Offset;
 
            struct v2g {
                float4 worldPos : SV_POSITION;
            };
 
            struct g2f {
                float4 pos : SV_POSITION;
                float3 bary : TEXCOORD0;
            };
 
            v2g vert(appdata_base v) {
                v2g o;
                o.worldPos = mul(unity_ObjectToWorld, v.vertex);
                return o;
            }
 
            [maxvertexcount(3)]
            void geom(triangle v2g IN[3], inout TriangleStream<g2f> triStream) {
                float3 param = float3(0., 0., 0.);
 
                #if _REMOVEDIAG_ON
                float EdgeA = length(IN[0].worldPos - IN[1].worldPos);
                float EdgeB = length(IN[1].worldPos - IN[2].worldPos);
                float EdgeC = length(IN[2].worldPos - IN[0].worldPos);
               
                if(EdgeA > EdgeB && EdgeA > EdgeC)
                    param.y = 1.;
                else if (EdgeB > EdgeC && EdgeB > EdgeA)
                    param.x = 1.;
                else
                    param.z = 1.;
                #endif
 
                g2f o;

                o.pos = mul(UNITY_MATRIX_VP, IN[0].worldPos);
                o.bary = float3(1.+ _Offset, 0., 0.)* _RepeatCount * (1.0f + _Spacing) + param;
                triStream.Append(o);
                o.pos = mul(UNITY_MATRIX_VP, IN[1].worldPos);
                o.bary = float3(0., 0., 1.+ _Offset)* _RepeatCount * (1.0f + _Spacing) + param;
                triStream.Append(o);
                o.pos = mul(UNITY_MATRIX_VP, IN[2].worldPos);
                o.bary = float3(0., 1.+ _Offset, 0.)* _RepeatCount * (1.0f + _Spacing) + param;
                triStream.Append(o);
            }
 
            float _WireframeVal;
            fixed4 _BackColor;
 
            fixed4 frag(g2f i) : SV_Target {
            
            if(!any(bool3(i.bary.x < _WireframeVal, i.bary.y < _WireframeVal, i.bary.z < _WireframeVal)))
                 discard;

                return _BackColor;
            }
 
            ENDCG
        }
 
        Pass
        {
            Cull Back
            CGPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #pragma geometry geom
 
            // Change "shader_feature" with "pragma_compile" if you want set this keyword from c# code
            #pragma shader_feature __ _REMOVEDIAG_ON
 
            #include "UnityCG.cginc"
 
            struct v2g {
                float4 worldPos : SV_POSITION;
            };
 
            struct g2f {
                float4 pos : SV_POSITION;
                float3 bary : TEXCOORD0;
            };
 
            v2g vert(appdata_base v) {
                v2g o;
                o.worldPos = mul(unity_ObjectToWorld, v.vertex);
                return o;
            }
 
            [maxvertexcount(3)]
            void geom(triangle v2g IN[3], inout TriangleStream<g2f> triStream) {
                float3 param = float3(0., 0., 0.);
 
                #if _REMOVEDIAG_ON
                float EdgeA = length(IN[0].worldPos - IN[1].worldPos);
                float EdgeB = length(IN[1].worldPos - IN[2].worldPos);
                float EdgeC = length(IN[2].worldPos - IN[0].worldPos);
               
                if(EdgeA > EdgeB && EdgeA > EdgeC)
                    param.y = 1.;
                else if (EdgeB > EdgeC && EdgeB > EdgeA)
                    param.x = 1.;
                else
                    param.z = 1.;
                #endif
 
                g2f o;
                o.pos = mul(UNITY_MATRIX_VP, IN[0].worldPos);
                o.bary = float3(1., 0., 0.) + param;
                triStream.Append(o);
                o.pos = mul(UNITY_MATRIX_VP, IN[1].worldPos);
                o.bary = float3(0., 0., 1.) + param;
                triStream.Append(o);
                o.pos = mul(UNITY_MATRIX_VP, IN[2].worldPos);
                o.bary = float3(0., 1., 0.) + param;
                triStream.Append(o);
            }
 
            float _WireframeVal;
            fixed4 _FrontColor;
 
            fixed4 frag(g2f i) : SV_Target {
            if(!any(bool3(i.bary.x <= _WireframeVal, i.bary.y <= _WireframeVal, i.bary.z <= _WireframeVal)))
                 discard;
 
                return _FrontColor;
            }
 
            ENDCG
        }
    }
}

Sorry for the long post. Any ideas? Thanks a bunch.

  • 1
    I've yet to find a satisfactory way of removing the "internal" diagonal edges of a mesh. Nothing I've ever tried has worked. The only things I haven't tried are things not supported by Unity (geometry shader using TRIANGLES_ADJACENT 6-vert input). I'm certain I could do it if I had triangle adjacency information. – Draco18s Dec 6 at 20:35
  • Aw :'( , I wish Unity would take this issue asap to support it on future version. Thanks for the reply btw. – Mira 2 days ago
  • I think adj tris in shaders aren't supported due to the cross-platform nature of the compilation. i.e. it might be a Direct-X only thing. I've wanted access to adjacent triangles for another shader as well. – Draco18s 2 days ago
  • I'm glad I'm not the only one who trying to solve this issue, but I'm not a 3D modeler, but is it possible to remove that diagonals from within 3D software before exported it to Unity? Or am I asking the ridiculous answer here lmao. – Mira 2 days ago
  • No, that's not possible. While some 3D modeling software will happily let you have n-sided faces, its just doing the triangulation under the hood for you and those edges will still be there when imported into unity. – Draco18s 2 days ago

Your Answer

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Browse other questions tagged or ask your own question.