0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

Unity UIエフェクトシェーダ ノイズテクスチャ合成

Posted at

Unity BuildinUIShader 拡張

こんな感じの見た目のUIImage表現ができます

  • スクロール
    UI_cutomdefault_02.gif
  • スクロール + 多重スクロール有効
    UI_cutomdefault_01.gif

ビルトインのUI-Defaultを拡張し、ノイズテクスチャを合成できるようにしています。
_EmissionX、_EmissionYでノイズテクスチャのスクロールスピードを調整。
_MultiplySubEmissionMapで多重スクロールを行うかハンドリングできます。

使用する場合はマテリアルでこのシェーダーを参照し、
Imageコンポーネントのマテリアルで参照させてください。
スクリーンショット 2023-10-22 013842.jpg

スクリーンショット 2023-10-22 013929.jpg

// Unity built-in shader source. Copyright (c) 2016 Unity Technologies. MIT license (see license.txt)

Shader "UI/CustomDefault"
{
    Properties
    {
        [PerRendererData] _MainTex("Sprite Texture", 2D) = "white" {}
        _EmissionTex("Emission Sprite Texture", 2D) = "white" {}
        [HDR]_Color("Tint", Color) = (1,1,1,1)
        [HDR]_EmissionColor("Emission Color", Color) = (0,0,0,1)

        _StencilComp("Stencil Comparison", Float) = 8
        _Stencil("Stencil ID", Float) = 0
        _StencilOp("Stencil Operation", Float) = 0
        _StencilWriteMask("Stencil Write Mask", Float) = 255
        _StencilReadMask("Stencil Read Mask", Float) = 255

        _ColorMask("Color Mask", Float) = 15
        
        _EmissionX("_Emission X", Float) = 0
        _EmissionY("_Emission Y", Float) = 0

        [Toggle]_MultiplySubEmissionMap("Mutiply Emission", Int) = 0

        [Toggle(UNITY_UI_ALPHACLIP)] _UseUIAlphaClip("Use Alpha Clip", Float) = 0

        [Enum(UnityEngine.Rendering.BlendMode)]_SrcBlend("SrcBlend", Int) = 1
        [Enum(UnityEngine.Rendering.BlendMode)]_DstBlend("DstBlend", Int) = 0
        [Enum(UnityEngine.Rendering.BlendMode)]_SrcBlendAlpha("SrcBlendAlpha", Int) = 1
        [Enum(UnityEngine.Rendering.BlendMode)]_DstBlendAlpha("DstBlendAlpha", Int) = 10
        [Enum(UnityEngine.Rendering.BlendOp)]_BlendOp("BlendOp", Int) = 0
        [Enum(UnityEngine.Rendering.BlendOp)]_BlendOpAlpha("BlendOpAlpha", Int) = 0
    }

        SubShader
        {
            Tags
            {
                "Queue" = "Transparent"
                "IgnoreProjector" = "True"
                "RenderType" = "Transparent"
                "PreviewType" = "Plane"
                "CanUseSpriteAtlas" = "True"
            }

            Stencil
            {
                Ref[_Stencil]
                Comp[_StencilComp]
                Pass[_StencilOp]
                ReadMask[_StencilReadMask]
                WriteMask[_StencilWriteMask]
            }

            Cull Off
            Lighting Off
            ZWrite Off
            ZTest[unity_GUIZTestMode]
            //Blend One OneMinusSrcAlpha
            BlendOp[_BlendOp],[_BlendOpAlpha]
            Blend[_SrcBlend][_DstBlend],[_SrcBlendAlpha][_DstBlendAlpha]
            ColorMask[_ColorMask]

            Pass
            {
                Name "Default"
            CGPROGRAM
                #pragma vertex vert
                #pragma fragment frag
                #pragma target 2.0

                #include "UnityCG.cginc"
                #include "UnityUI.cginc"

                #pragma multi_compile_local _ UNITY_UI_CLIP_RECT
                #pragma multi_compile_local _ UNITY_UI_ALPHACLIP


                struct appdata_t
                {
                    float4 vertex   : POSITION;
                    float4 color    : COLOR;
                    float2 texcoord : TEXCOORD0;
                    UNITY_VERTEX_INPUT_INSTANCE_ID
                };

                struct v2f
                {
                    float4 vertex   : SV_POSITION;
                    fixed4 color : COLOR;
                    float2 texcoord  : TEXCOORD0;
                    float4 worldPosition : TEXCOORD1;
                    float4  mask : TEXCOORD2;
                    UNITY_VERTEX_OUTPUT_STEREO
                };

                sampler2D _MainTex;
                sampler2D _EmissionTex;
                fixed4 _Color;
                fixed4 _EmissionColor;
                fixed4 _TextureSampleAdd;
                float4 _ClipRect;
                float4 _MainTex_ST;
                float4 _EmissionTex_ST;
                float _UIMaskSoftnessX;
                float _UIMaskSoftnessY;
                float _EmissionX;
                float _EmissionY;
                int _UIVertexColorAlwaysGammaSpace;
                int _MultiplySubEmissionMap;

                v2f vert(appdata_t v)
                {
                    v2f OUT;
                    UNITY_SETUP_INSTANCE_ID(v);
                    UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(OUT);
                    float4 vPosition = UnityObjectToClipPos(v.vertex);
                    OUT.worldPosition = v.vertex;
                    OUT.vertex = vPosition;

                    float2 pixelSize = vPosition.w;
                    pixelSize /= float2(1, 1) * abs(mul((float2x2)UNITY_MATRIX_P, _ScreenParams.xy));

                    float4 clampedRect = clamp(_ClipRect, -2e10, 2e10);
                    float2 maskUV = (v.vertex.xy - clampedRect.xy) / (clampedRect.zw - clampedRect.xy);
                    OUT.texcoord = TRANSFORM_TEX(v.texcoord.xy, _MainTex);
                    OUT.mask = float4(v.vertex.xy * 2 - clampedRect.xy - clampedRect.zw, 0.25 / (0.25 * half2(_UIMaskSoftnessX, _UIMaskSoftnessY) + abs(pixelSize.xy)));


                    if (_UIVertexColorAlwaysGammaSpace)
                    {
                        if (!IsGammaSpace())
                        {
                            v.color.rgb = UIGammaToLinear(v.color.rgb);
                        }
                    }

                    OUT.color = v.color * _Color;
                    return OUT;
                }

                fixed4 frag(v2f IN) : SV_Target
                {
                    //Round up the alpha color coming from the interpolator (to 1.0/256.0 steps)
                    //The incoming alpha could have numerical instability, which makes it very sensible to
                    //HDR color transparency blend, when it blends with the world's texture.
                    const half alphaPrecision = half(0xff);
                    const half invAlphaPrecision = half(1.0 / alphaPrecision);
                    IN.color.a = round(IN.color.a * alphaPrecision) * invAlphaPrecision;

                    half4 color = IN.color * (tex2D(_MainTex, IN.texcoord) + _TextureSampleAdd);

                    half4 emissionColor = tex2D(_EmissionTex, (IN.texcoord * _EmissionTex_ST.xy + _EmissionTex_ST.zw) + half2(_EmissionX * _Time.y, _EmissionY * _Time.y)) * _EmissionColor;

                    emissionColor *= _MultiplySubEmissionMap ? tex2D(_EmissionTex, (IN.texcoord * _EmissionTex_ST.xy + _EmissionTex_ST.zw) - half2(_EmissionX * _Time.y, _EmissionY * _Time.y)) : 1;

                    color.rgb += emissionColor.rgb;
                    color.a *= max(emissionColor.a, color.a);
                    
                    #ifdef UNITY_UI_CLIP_RECT
                    half2 m = saturate((_ClipRect.zw - _ClipRect.xy - abs(IN.mask.xy)) * IN.mask.zw);
                    color.a *= m.x * m.y;
                    #endif

                    #ifdef UNITY_UI_ALPHACLIP
                    clip(color.a - 0.001);
                    #endif

                    color.rgb *= color.a;

                    return color;
                }
            ENDCG
            }
        }
}

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?