繁体   English   中英

Unity - object 上具有抗锯齿功能的 2D 圆孔

[英]Unity - 2D circle hole with antialiasing on object

我想在一个空的 object 里面加一个洞,里面有精灵。 这个洞是圆形的。

为此,我将着色器添加到材质,并将材质添加到 Sprite Renderer 组件到空的 object。

这是我的着色器:

Shader "Sprite/Hole Effect"
{
    Properties
    {
        _MainTex ("Base (RGB)", 2D) = "white" {}
        _ObjPos ("Object Position", Vector) = (1,1,1,1)
        _Cutoff ("Alpha cutoff", Range(0,1)) = 0.5
        _Radius ("Hole Radius", Range(0.1,10)) = 2
    }
 
    SubShader
    {
        Pass
        {
            Cull Off
 
            CGPROGRAM
 
            #pragma vertex vert
            #pragma fragment frag
 
            uniform sampler2D _MainTex;
            float _Radius;
            float4 _ObjPos;
 
            struct vertexInput {
                float4 vertex : POSITION;
                float4 texcoord : TEXCOORD0;
            };
            struct vertexOutput {
                float4 pos : SV_POSITION;
                float4 worldPos : POSITION1;
                float4 tex : TEXCOORD0;
            };
 
            vertexOutput vert(vertexInput input)
            {
                vertexOutput output;
 
                output.tex = input.texcoord;
                output.pos = UnityObjectToClipPos(input.vertex);
                output.worldPos = mul(input.vertex, unity_ObjectToWorld);
                return output;
            }
 
            float4 frag(vertexOutput input) : COLOR
            {
                float4 textureColor = tex2D(_MainTex, input.tex.xy);
                float dis = distance(input.worldPos.xyz, _ObjPos);
 
                if (dis > _Radius)
                {
                    discard;
                }
 
                return textureColor;
            }
 
            ENDCG
        }
    }
 
    FallBack "Diffuse"
}

这种方法的问题是圆没有抗锯齿...

所以我尝试在空的 object 中添加一个 Sprite 蒙版,但是没有抗锯齿下界...

我认为着色器是实现这一目标的好解决方案,但真的不知道如何!

任何帮助都是完美的!!!

终于我找到了!!

我将带有着色器的材质应用于 object 的精灵,我想在其中看到圆圈。

这是我的着色器:

Shader "Sprites/XRay Effect"
{
    Properties
    {
        [PerRendererData] _MainTex ("Sprite Texture", 2D) = "white" {}
        
        _PlayerPos ("Player Position", Vector) = (0,0,0,0)
        _Radius ("Hole Radius", Range(0.1,100)) = 2
        _Border ("Border", Range(0.001,1)) = 0.05
    }

    SubShader
    {
        Tags
        { 
            "Queue"="Transparent" 
            "IgnoreProjector"="True" 
            "RenderType"="Transparent" 
            "PreviewType"="Plane"
            "CanUseSpriteAtlas"="True"
        }
        
        Cull Off
        Lighting Off
        ZWrite Off
        ZTest [unity_GUIZTestMode]
        Blend SrcAlpha OneMinusSrcAlpha

        Pass
        {
            CGPROGRAM

            #pragma vertex vert
            #pragma fragment frag

            #include "UnityCG.cginc"
            #include "UnityUI.cginc"
            
            struct vertexInput
            {
                float4 vertex   : POSITION;
                float4 color    : COLOR;
                float2 texCoord : TEXCOORD0;
            };

            struct vertexOutput
            {
                float4 vertex   : SV_POSITION;
                fixed4 color    : COLOR;
                half2 texCoord  : TEXCOORD0;
                float3 worldPosition : TEXCOORD1;
            };
            
            sampler2D _MainTex;
            
            float4 _PlayerPos;
            float _Radius;
            float _Border;

            vertexOutput vert(vertexInput IN)
            {
                vertexOutput OUT;

                OUT.vertex = UnityObjectToClipPos(IN.vertex);
                OUT.texCoord = IN.texCoord;
                OUT.worldPosition = mul(unity_ObjectToWorld, IN.vertex);
                OUT.color = IN.color;

                return OUT;
            }

            fixed4 frag(vertexOutput IN) : SV_Target
            {
                half4 color = tex2D(_MainTex, IN.texCoord) * IN.color;
                
                // Adding the circle hole
                float dis = distance(IN.worldPosition.xyz, _PlayerPos.xyz);
                color.a = lerp(0, color.a, color.a * (dis - _Radius) / _Border);

                return color;
            }
            
            ENDCG
        }
    }
    FallBack "UI/Default"
}

您可以根据需要修改部分lerp(0, color.a, color.a * (dis - _Radius) / _Border)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM