http://game.ceeger.com/forum/read.php?tid=23209&fid=2

由于最近要做一个冰系的角色,就想能不能做一些冰霜效果。那么就试试吧,先弄一张原图:

 

1.常规的冰霜,最简单的要数霜冻的颜色变化,只需要减少亮度,增加蓝色分量。 

片段着色器: 

texcol *= fixed4(0.9, 0.9, 0.9, 1f); 
 texcol.b += 0.2; 

效果如下: 
 
虽然简单,但效果也十分一般。 

2.如果你玩过冰火围城,它里面的冰冻效果则是更加金属化,给人的感觉是一层灰色滤镜再增加一点蓝色,然后顶部会更亮。 

首先,我们要计算法线夹角,方便处理顶部更亮这部分。 

顶点着色器: 

float3 normal = mul(SCALED_NORMAL, (float3x3)_World2Object); 
 fixed dotProduct = dot(normal, fixed3(0, 1, 0)) / 2; 
if(dotProduct <= 0) 
 { 
         dotProduct = 0; 

  o.color = dotProduct.xxx; 

然后灰化整个角色,并且增加顶部亮度。 

片段着色器: 

float grey = dot(texcol.rgb, float3(0.299, 0.587, 0.114)) + i.color.x; 
texcol = fixed4(grey, grey, grey, texcol.a); 
texcol.r -= 0.15; 
 texcol.b += 0.15; 
效果如下: 
 
不过由于这个模型本身比较暗,所以看上去有点像雕像。但这似乎不是我们想要的效果呢,于是我打算换一个思路,让材质先变成霜。 

增加了一张贴图,看看霜的效果: 
 
哈哈,有点像冰棍了呢。但霜应该要亮一些,我打算增加下亮度,同时增加外发光。 

顶点着色器: 

fixed3 viewDir = normalize(ObjSpaceViewDir(v.vertex)); 
 fixed dotProduct = 1 - dot(v.normal, viewDir); 
o.color = smoothstep(0, 1, dotProduct);     
o.color *= _RimColor; 

片段着色器: 

texcol.rgb += i.color; 

效果: 
 
可是这样就完全是冰棍了呢,我想要混合一下原始的像素,于是增加一个变量,控制一下混合。 

片段着色器: 

texcol = texcol * _Frezz +  alpha * (1 - _Frezz); 

设置效果: 
 
通过控制滚动条可以调整混合比例,这个大概是64开的比例,看着还行吧。 

但这样就结束的话还是差强人意,因为冰霜的变化太过规则了,我们很多时候希望的是随机变化,显得更自然。 

再增加一张噪点贴图,通过获得贴图的值调整混合比例。 

 float ClipTex = tex2D (_RandomTex, i.uv).r ; 
float ClipAmount = (_Frezz - ClipTex) / 2 + 0.5; 
 if(ClipAmount < 0) 
 { 
          ClipAmount = 0; 

if(ClipAmount > 1) 
 { 
           ClipAmount = 1; 
 } 

效果如下: 
 
这样马马虎虎吧,如果还要继续就需要法线贴图,遗憾的是这个模型没有法线贴图。 

如果有法线贴图,我们可以再法线贴图层面上增加冰霜的颜色变化。 

最后 的完整shader代码: 

本部分设定了隐藏,您已回复过了,以下是隐藏的内容
// Upgrade NOTE: replaced 'PositionFog()' with multiply of UNITY_MATRIX_MVP by position 

// Upgrade NOTE: replaced 'V2F_POS_FOG' with 'float4 pos : SV_POSITION' 

Shader "Custom/CharactorShaderCullOff" { 

    Properties { 

        _MainTex ("Base (RGB)", 2D) = "white" {} 

        _AlphaTex ("Base (RGB)", 2D) = "white" {} 

        _RandomTex ("Base (RGB)", 2D) = "white" {} 

        _RimColor ("Rim Color", Color) = (1, 0, 0, 1) 

        _Color("_Color", Color) = (0.5,0.5,0.5,1) 

        _Rampage("_Rampage", Float) = 0 

        _Frezz("_Frezz", Range(0, 1)) = 0 

    } 

   

    SubShader { 

     //Tags {"Queue"="Transparent" "IgnoreProjector"="True" "RenderType"="Transparent"} 

        Pass { 

            cull off 

            Blend SrcAlpha OneMinusSrcAlpha 

            CGPROGRAM 

// Upgrade NOTE: excluded shader from DX11 and Xbox360; has structs without semantics (struct v2f members pos1) 

#pragma exclude_renderers d3d11 xbox360 

                #pragma vertex vert 

                #pragma fragment frag 

                #include "UnityCG.cginc" 

                 

                struct appdata { 

                    float4 vertex : POSITION; 

                    float3 normal : NORMAL; 

                    float2 texcoord : TEXCOORD0; 

                }; 

                struct v2f { 

                    half4 pos : SV_POSITION; 

                    half2 uv : TEXCOORD0; 

                    fixed3 color : COLOR; 

                }; 

                uniform fixed4 _RimColor; 

                uniform fixed _Rampage; 

                uniform fixed _Frezz; 

         

                v2f vert (appdata_base v) { 

                    v2f o; 

                    o.pos = mul (UNITY_MATRIX_MVP, v.vertex); 

                    if(_Rampage == 1) 

                    { 

                        fixed3 viewDir = normalize(ObjSpaceViewDir(v.vertex)); 

                        fixed dotProduct = 1 - dot(v.normal, viewDir); 

                            o.color = smoothstep(0, 1, dotProduct);     

                        o.color *= _RimColor; 

                    } 

                    float3 normal = mul(SCALED_NORMAL, (float3x3)_World2Object); 

                    fixed dotProduct = dot(normal, fixed3(0, 1, 0)) / 2; 

                    if(dotProduct <= 0) 

                    { 

                        dotProduct = 0; 

                    } 

                    o.color += dotProduct.xxx; 

                    o.uv = v.texcoord.xy; 

                    return o; 

                } 

                uniform sampler2D _MainTex; 

                uniform sampler2D _AlphaTex; 

                uniform sampler2D _RandomTex; 

                uniform fixed4 _Color; 

                fixed4 frag(v2f i) : COLOR { 

                    fixed4 texcol = tex2D(_MainTex, i.uv); 

                    fixed4 alpha = tex2D(_AlphaTex, i.uv); 

                    float ClipTex = tex2D (_RandomTex, i.uv).r ; 

                    float ClipAmount = (_Frezz - ClipTex) / 2 + 0.5; 

                    if(ClipAmount < 0) 

                    { 

                        ClipAmount = 0; 

                    } 

                    if(ClipAmount > 1) 

                    { 

                        ClipAmount = 1; 

                    } 

                    if(_Rampage == 1) 

                    { 

                        texcol.rgb += i.color; 

                    } 

                    texcol = texcol * ClipAmount +  alpha * (1 - ClipAmount); 

                    texcol.a = alpha.a; 

                    clip(texcol.a - 0.5); 

                    texcol *= _Color; 

                    return texcol; 

                } 

            ENDCG 

        } 

         

    } 

[Shader 着色器]冰霜效果的思考和实现的更多相关文章

  1. Unity Shader着色器优化

    https://mp.weixin.qq.com/s?__biz=MzU5MjQ1NTEwOA==&mid=2247493518&idx=1&sn=c51b92e9300bcf ...

  2. Unity3D学习笔记(三十四):Shader着色器(1)

    一.GPU:图形处理器,Graphics Processing Unit 显卡的处理器就是图形处理器.与CPU类似.   GPU和CPU的区别? 1.CPU主要是为了串行指令设计,GPU则是为了大规模 ...

  3. [Unity] Shader(着色器)输入输出和语义

    在Unity5.x后, 已经支持了基于物理的光照模型,也就是常说的次时代引擎所必须具备的功能. 如果在Properties使用2D,CG里要用sampler2D,代表使用的是2维纹理 如果在Prope ...

  4. [Unity] Shader(着色器)之纹理贴图

    在Shader中,我们除了可以设定各种光线处理外,还可以增加纹理贴图. 使用 settexture 命令可以为着色器指定纹理. 示例代码: Shader "Sbin/ff2" { ...

  5. OpenGL之shader着色器的应用,三色渐变的三角形

    学习自: https://learnopengl-cn.github.io/01%20Getting%20started/05%20Shaders/#_7 首先放一张效果图: 本次教程,将着色器单独定 ...

  6. Unity3D学习笔记(三十五):Shader着色器(2)- 顶点片元着色器

    Alpha测试 AlphaTest Great:大于 AlphaTest Less:小于 AlphaTest Equal:等于 AlphaTest GEqual:大于等于 AlphaTest LEqu ...

  7. osg Shader 着色器

    #ifdef _WIN32 #include <Windows.h> #endif // _WIN32 #include <osg/Group> #include <os ...

  8. [Unity] Shader(着色器)之固定管线

    在Unity中,固定管线Shader的性能是最好的. 什么是固定管线呢? 固定渲染管线 —— 这是标准的几何&光照(T&L)管线,功能是固定的,它控制着世界.视.投影变换及固定光照控制 ...

  9. Unity3D学习笔记(三十六):Shader着色器(3)- 光照

    光照模型:用数学的方法模拟现实世界中的光照效果.   场景中模型身上的光反射到相机中的光线: 1.漫反射:产生明暗效果 2.高光反射:产生镜面反射,物体中有最亮且比较耀眼的一部分 3.自发光: 4.环 ...

随机推荐

  1. 封装算法: 模板方法(Template Method)模式

    template method(模板方法)模式是一种行为型设计模式.它在一个方法中定义了算法的骨架(这种方法被称为template method.模板方法),并将算法的详细步骤放到子类中去实现.tem ...

  2. 释放SQL Server占用的内存 .Net 读取xml UrlReWriter 在web.config中简单的配置

    释放SQL Server占用的内存   由于Sql Server对于系统内存的管理策略是有多少占多少,除非系统内存不够用了(大约到剩余内存为4M左右),Sql Server才会释放一点点内存.所以很多 ...

  3. TinyXML中类分析

    TiXmlElement: 对应于XML的元素,定义了对element的相关操作 成员函数: TiXmlElement (const char * in_value); TiXmlElement( c ...

  4. vue的安装以及语法介绍

    #需要用到一个vue文件,还有一个自己的js文件main.js<!DOCTYPE html> <html lang="en"> <head> & ...

  5. Dell服务器相关操作

    1. Raid相关: # 删除已有的Raid配置 MegaCli64 -CfgLdDel -LALL -aALL # 获取设备ID和槽号 MegaCli64 -PDList -aALL|egrep ' ...

  6. sqlldr的用法

    在 Oracle 数据库中,我们通常在不同数据库的表间记录进行复制或迁移时会用以下几种方法: 1. A 表的记录导出为一条条分号隔开的 insert 语句,然后执行插入到 B 表中2. 建立数据库间的 ...

  7. NBUT 1222 English Game(trie树+DP)

    [1222] English Game 时间限制: 1000 ms 内存限制: 131072 K 问题描写叙述 This English game is a simple English words ...

  8. BusyBox下ftpget的使用方法

    在终端输入ftpget命令,可以得到以下帮助信息: BusyBox v1.17.4 (2010-12-22 10:59:18 CST) multi-call binary. Usage: ftpget ...

  9. 动态预览Xib的实现

    写一个TestView继承于UIView,然后写个对应的xib,把xib的名字设置成TestView,这是标准的用xib加载这个view必须得条件 然后xib里把这个View的backgroundCo ...

  10. 【Nginx安装】CentOS7安装Nginx及配置

    [Nginx安装]CentOS7安装Nginx及配置 2018年03月05日 11:07:21 阅读数:7073 Nginx是一款轻量级的网页服务器.反向代理服务器.相较于Apache.lighttp ...