在Unity3D中,如何使整个场景在黑暗中,但某些区域不在黑暗中

时间:2015-06-19 06:48:32

标签: unity3d

我不想用UGUI制作一些教学水平,所以需要整体处于黑暗中,但是一些矩形区域不是在黑暗中。

我可以通过添加带有图像组件的游戏对象来使整个场景变暗,并将其控制为黑暗。

但我不知道如何制作一些矩形区域,而矩形区域会在不同的教学水平上发生变化。并且具有不同分辨率的不同设备也将改变rec的笨蛋。

Picutre3就是我想要的,只有矩形区域就可以了。

Picture1中 P1

图片2

P2

图片2

P3

图片4 P4

1 个答案:

答案 0 :(得分:3)

我将解释如何使用简单的着色器和一些设置来实现这一目标。我是在记忆中说话,所以如果出现问题,请问。

所以你可以做的是:

  • 创建一个用于渲染蒙版的新图层。假设我们将此图层称为MaskLayer。

  • 复制主相机。我们称之为旧的主摄像机camA和新的摄像机。

  • 设置camA的剔除遮罩以包含除MaskLayer以外的所有内容。
  • 将camB的剔除蒙版设置为仅包含MaskLayer。
  • 创建一个新的渲染纹理(比方说MaskRT)并将其设置为camB的渲染目标。
  • 现在创建任何游戏对象。让它成为一个纯色(白色)的精灵。
  • 将精灵图层设置为MaskLayer。

此时你应该注意到游戏窗口或camA预览中不再显示精灵。只有场景的其余部分可见。选择camB时,预览中只能看到平面。 camB的输出表示“孔”的位置。

现在我们继续这样做:

  • 创建一个与视口一样大的新精灵。
  • 确保此精灵具有默认标记。
  • 创建新着色器和新材质。称之为MaskMaterial。该 创建的默认着色器模板应该足够好。我不记得它提供了什么,但它至少应该有一个纹理输入。
  • 让我们说你的着色器参数叫做DIFFUSE。在像素中 着色器,将输出颜色设置为:

    fixed4 frag (v2f i) : SV_Target
    {
        fixed4 texcol = tex2D (DIFFUSE, i.uv);
        fixed4 outputColor = fixed4(0,0,0, 0.8-texcol.r);
        return outputColor ;
    }
    

所以我们在简单的英文着色器中说的是: 我的颜色是纯黑色,略有透明度(0.8),除非我的输入纹理在同一位置有白色,在这种情况下我更透明(-texcol.r)。

我们在这里使用r组件,但您可以轻松使用任何颜色组件。

现在将这个新材质和着色器分配给全屏精灵,并将MaskRT渲染纹理设置为Mask Shader的输入纹理DIFFUSE。

如果一切顺利(大声笑),那么你现在应该有你想要的效果。移动蒙版现在就像移动场景中用MaskLayer图层标记的任何对象一样简单。所以你可以有很多面具。

注意:

  • 精灵可能会让你有些困难,也许可能会开始 面对镜头的飞机以防万一。

  • 以下是关于着色器的文档,以防您需要阅读:http://docs.unity3d.com/Manual/ShaderTut2.html这值得研究,但这次你可能会试错。

    • 在着色器中,默认情况下可能会有颜色输入。您可以在片段着色器中使用它而不是说(0,0,0 ..),以便更容易地控制生成的蒙版。这将允许您像往常一样使用材质的滑块更改蒙版外观。例如:

    fixed4 outputColor = fixed4(InputColor.Albedo,InputColor.a-texcol)

编辑: 您可以在此处查看“在Cg代码中使用着色器属性”部分:http://docs.unity3d.com/Manual/ShaderTut2.html如果您正在努力,可以复制粘贴整个片段并更改片段着色器(抱歉,我不知道什么级别的体验你有它。)

编辑: 这是要求的着色器。另请阅读以下注释。

Shader "Tutorial/Textured Colored" {
    Properties {
        _Color ("Main Color", Color) = (1,1,1,0.5)
        _MainTex ("Texture", 2D) = "white" { }
    }
    SubShader {
        Tags
        {
          "Queue" = "Transparent"
        }

        Blend One OneMinusSrcAlpha

        Pass {

        CGPROGRAM
        #pragma vertex vert
        #pragma fragment frag

        #include "UnityCG.cginc"

        fixed4 _Color;
        sampler2D _MainTex;

        struct v2f {
            float4 pos : SV_POSITION;
            float2 uv : TEXCOORD0;
        };

        float4 _MainTex_ST;

        v2f vert (appdata_base v)
        {
            v2f o;
            o.pos = mul (UNITY_MATRIX_MVP, v.vertex);
            o.uv = TRANSFORM_TEX (v.texcoord, _MainTex);
            return o;
        }

         fixed4 frag (v2f i) : SV_Target
        {
            fixed4 texcol = tex2D (_MainTex, i.uv);
            fixed4 outputColor = _Color;
            outputColor.a -= texcol.r;
            return outputColor ;
        }
        ENDCG

        }
    }
}

注意:

  • 此着色器应该在全屏四边形上显示。
  • 请注意着色器属性名称的区别(而不是DIFFUSE,现在它更清晰_Color和_MainTex。
  • 逻辑基本保持不变。
  • 此代码未经过测试。
  • 有更有效的方法可以做到这一点,例如只将屏蔽对象深度写入单个通道RenderTexture,但这种方式更容易学习。
  • 一旦你完成这项半工作,就会有一些改进。第一种方法是使用未点亮的纯色着色器将蒙版矩形的材质更改为一个。

更新:

我遗漏了着色器的关键部分。请参阅标签部分和添加到着色器的混合操作。另请注意,对于全屏四边形,您应该使用平面而不是精灵,因为着色器与此状态下的精灵不兼容。

另请注意,在此处的示例项目中:https://drive.google.com/file/d/0Bw8X8yAt21AiYjRyVkxJUkhreVU/view?usp=sharing

平面在x和z轴上都被翻转。

至于我之前错过的UGUI部分 - 这个解决方案很可行。我没有检查过。如果掩码位于UI后面,您可以尝试将着色器中的“Queue”标记设置为“Overlay”。