通过Alpha混合精灵查看着色器的轮廓


12

我想在Unity中实现类似于以下示例中的透视效果:

在我的特定情况下,有两个要求:

  • 子画面使用Alpha混合,并且子画面具有透明区域。
  • 遮挡字符有2种元素。一个应创建轮廓效果,而另一个应具有正常的行为。

对于遮挡创建轮廓的元素,我启用了ZWrite,并为没有轮廓的元素禁用了它。

对于角色,我尝试将着色器的队列设置为transparent + 1,并添加了此步骤:

Pass
{
    ZTest Greater
    Lighting Off
    Color [_Color]
}

效果部分起作用:

  • 轮廓绘制在整个角色上,甚至透明的部分。透明的部分不应创建轮廓。

  • 当角色在精灵后面时,即使该精灵的那部分是透明的,也会创建轮廓。在精灵的透明部分后面不应创建轮廓。

  • 角色出现在其余元素的前面,即使它位于它们的后面。我猜这是因为将队列设置为“透明+1”。但是,如果我将其保留为“透明”,则会以正确的顺序绘制角色,但永远不会看到轮廓。

我尝试遵循某人给我的这些提示,但无法使其正常工作:

1)保留渲染精灵的过程。

2)添加一个写入z缓冲区的通道,但是具有一个着色器,该着色器使用clip()丢弃基于alpha的像素。如果不使用MSAA和alpha-to coverage,则不能使用z缓冲区进行软性z测试。这样的质量不会很好,但是这是您可以做到的最好的。更快的替代方法是图案或噪声抖动,或者,如果您的精灵都具有相当尖锐的边缘,则可以使用老式的阈值。

3)向使用z测试绘制遮挡颜色的可遮挡对象添加第三遍,并确保将其绘制为最终遍。

我是着色器的新手,尤其是在Unity中,我只是想不出如何使其正常工作。


您的第二个示例仅看起来是放置在角色上方的半透明绿色精灵。如果您正在寻找它,那么您可能想要摆脱那个而只留下第二个。
史蒂夫·哈丁,

Answers:


1

该视频介绍基本知识吗?这是从人们已经发布的着色器创建几种不同样式的轮廓和轮廓的例证。

https://www.youtube.com/watch?v=00qMZlacZQo

这是一个使用Unity Wiki中发布的着色器来完成您所需要的工作的示例。着色器的内容在下面,尽管我认为着色器的概述部分可能未按U5的预期运行。

Shader "Outlined/Silhouetted Diffuse" {
Properties {
    _Color ("Main Color", Color) = (.5,.5,.5,1)
    _OutlineColor ("Outline Color", Color) = (0,0,0,1)
    _Outline ("Outline width", Range (0.0, 0.03)) = .005
    _MainTex ("Base (RGB)", 2D) = "white" { }
}

CGINCLUDE
#include "UnityCG.cginc"

struct appdata {
    float4 vertex : POSITION;
    float3 normal : NORMAL;
};

struct v2f {
    float4 pos : POSITION;
    float4 color : COLOR;
};

uniform float _Outline;
uniform float4 _OutlineColor;

v2f vert(appdata v) {
// just make a copy of incoming vertex data but scaled according to normal direction
    v2f o;
    o.pos = mul(UNITY_MATRIX_MVP, v.vertex);

    float3 norm   = mul ((float3x3)UNITY_MATRIX_IT_MV, v.normal);
    float2 offset = TransformViewToProjection(norm.xy);

    o.pos.xy += offset * o.pos.z * _Outline;
    o.color = _OutlineColor;
    return o;
}
ENDCG

SubShader {
    Tags { "Queue" = "Transparent" }

    // note that a vertex shader is specified here but its using the one above
    Pass {
        Name "OUTLINE"
        Tags { "LightMode" = "Always" }
        Cull Off
        ZWrite Off
        ZTest Always
        ColorMask RGB // alpha not used

        // you can choose what kind of blending mode you want for the outline
        Blend SrcAlpha OneMinusSrcAlpha // Normal
        //Blend One One // Additive
        //Blend One OneMinusDstColor // Soft Additive
        //Blend DstColor Zero // Multiplicative
        //Blend DstColor SrcColor // 2x Multiplicative

CGPROGRAM
#pragma vertex vert
#pragma fragment frag

half4 frag(v2f i) :COLOR {
    return i.color;
}
ENDCG
    }

    Pass {
        Name "BASE"
        ZWrite On
        ZTest LEqual
        Blend SrcAlpha OneMinusSrcAlpha
        Material {
            Diffuse [_Color]
            Ambient [_Color]
        }
        Lighting On
        SetTexture [_MainTex] {
            ConstantColor [_Color]
            Combine texture * constant
        }
        SetTexture [_MainTex] {
            Combine previous * primary DOUBLE
        }
    }
}

SubShader {
    Tags { "Queue" = "Transparent" }

    Pass {
        Name "OUTLINE"
        Tags { "LightMode" = "Always" }
        Cull Front
        ZWrite Off
        ZTest Always
        ColorMask RGB

        // you can choose what kind of blending mode you want for the outline
        Blend SrcAlpha OneMinusSrcAlpha // Normal
        //Blend One One // Additive
        //Blend One OneMinusDstColor // Soft Additive
        //Blend DstColor Zero // Multiplicative
        //Blend DstColor SrcColor // 2x Multiplicative

        CGPROGRAM
        #pragma vertex vert
        #pragma exclude_renderers gles xbox360 ps3
        ENDCG
        SetTexture [_MainTex] { combine primary }
    }

    Pass {
        Name "BASE"
        ZWrite On
        ZTest LEqual
        Blend SrcAlpha OneMinusSrcAlpha
        Material {
            Diffuse [_Color]
            Ambient [_Color]
        }
        Lighting On
        SetTexture [_MainTex] {
            ConstantColor [_Color]
            Combine texture * constant
        }
        SetTexture [_MainTex] {
            Combine previous * primary DOUBLE
        }
    }
}

Fallback "Diffuse"
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.