码迷,mamicode.com
首页 > 移动开发 > 详细

Unity3D手游开发日记(4) - 适合移动平台的热浪扭曲

时间:2016-08-18 23:25:54      阅读:840      评论:0      收藏:0      [点我收藏+]

标签:

热浪扭曲效果的实现,分两部分,一是抓图,二是扭曲扰动.其中难点在于抓图的处理,网上的解决方案有两种,在移动平台都有很多问题,只好自己实现了一种新的方案,效果还不错.

 

网上方案1. 用GrabPass抓图

GrabPass在有的手机上是不支持的...效率也是问题,所以...

代码可以看看:

 

[csharp] view plain copy
 
  1. Shader "Luoyinan/Distortion/HeatDistortion"   
  2. {  
  3.     Properties  
  4.     {  
  5.         _NoiseTex ("Noise Texture (RG)", 2D) = "white" {}  
  6.         _MainTex ("Alpha (A)", 2D) = "white" {}  
  7.         _HeatTime  ("Heat Time", range (0,1.5)) = 1  
  8.         _HeatForce  ("Heat Force", range (0,0.1)) = 0.1  
  9.     }  
  10.   
  11.     Category   
  12.     {  
  13.         Tags { "Queue"="Transparent+1" "RenderType"="Transparent" }  
  14.   
  15.         Blend SrcAlpha OneMinusSrcAlpha  
  16.         AlphaTest Greater .01  
  17.         Cull Off   
  18.         Lighting Off   
  19.         ZWrite Off  
  20.       
  21.         SubShader   
  22.         {  
  23.             GrabPass   
  24.             {                             
  25.                 Name "BASE"  
  26.                 Tags { "LightMode" = "Always" }  
  27.             }  
  28.   
  29.             Pass   
  30.             {  
  31.                 Name "BASE"  
  32.                 Tags { "LightMode" = "Always" }  
  33.               
  34.                 CGPROGRAM  
  35.                 #pragma vertex vert  
  36.                 #pragma fragment frag  
  37.                 #pragma fragmentoption ARB_precision_hint_fastest  
  38.                 #include "UnityCG.cginc"  
  39.   
  40.                 struct appdata_t   
  41.                 {  
  42.                     float4 vertex : POSITION;  
  43.                     fixed4 color : COLOR;  
  44.                     float2 texcoord: TEXCOORD0;  
  45.                 };  
  46.   
  47.                 struct v2f   
  48.                 {  
  49.                     float4 vertex : POSITION;  
  50.                     float4 uvgrab : TEXCOORD0;  
  51.                     float2 uvmain : TEXCOORD1;  
  52.                 };  
  53.   
  54.                 float _HeatForce;  
  55.                 float _HeatTime;  
  56.                 float4 _MainTex_ST;  
  57.                 float4 _NoiseTex_ST;  
  58.                 sampler2D _NoiseTex;  
  59.                 sampler2D _MainTex;  
  60.   
  61.                 v2f vert (appdata_t v)  
  62.                 {  
  63.                     v2f o;  
  64.                     o.vertex = mul(UNITY_MATRIX_MVP, v.vertex);  
  65.                     o.uvgrab = ComputeGrabScreenPos(o.vertex);  
  66.                     o.uvmain = TRANSFORM_TEX( v.texcoord, _MainTex );  
  67.                     return o;  
  68.                 }  
  69.   
  70.                 sampler2D _GrabTexture;  
  71.   
  72.                 half4 frag( v2f i ) : COLOR  
  73.                 {  
  74.                     // noise effect  
  75.                     half4 offsetColor1 = tex2D(_NoiseTex, i.uvmain + _Time.xz*_HeatTime);  
  76.                     half4 offsetColor2 = tex2D(_NoiseTex, i.uvmain - _Time.yx*_HeatTime);  
  77.                     i.uvgrab.x += ((offsetColor1.r + offsetColor2.r) - 1) * _HeatForce;  
  78.                     i.uvgrab.y += ((offsetColor1.g + offsetColor2.g) - 1) * _HeatForce;  
  79.       
  80.                     half4 col = tex2Dproj(_GrabTexture, UNITY_PROJ_COORD(i.uvgrab));  
  81.                     // Skybox‘s alpha is zero, don‘t know why.  
  82.                     col.a = 1.0f;  
  83.                     half4 tint = tex2D( _MainTex, i.uvmain);  
  84.   
  85.                     return col*tint;  
  86.                 }  
  87.   
  88.                 ENDCG  
  89.             }  
  90.         }  
  91.   
  92.         // ------------------------------------------------------------------  
  93.         // Fallback for older cards and Unity non-Pro  
  94.         SubShader   
  95.         {  
  96.             Blend DstColor Zero  
  97.             Pass   
  98.             {  
  99.                 Name "BASE"  
  100.                 SetTexture [_MainTex] { combine texture }  
  101.             }  
  102.         }  
  103.     }  
  104. }  


网上方案2:用RenderTexture来代替抓图

 

这种方法很坑爹,把场景再渲染一次?想想就很恐怖

我的方案: 后处理

换种思路,后处理其实就已经有了我们需要抓取的图,我们只需要渲染一个掩码图,就能实现局部的扭曲了,以前做次世代引擎的开发,很多特效都是后处理的实现的,比如人在水里面走水面泛起的涟漪,其实热浪扭曲也可以用类似的方法.

 

原理:

1.先用后处理实现全屏的扰动

技术分享

2.用RenderTexture做实时的掩码图.

技术分享技术分享

这样的话,效率开销只在两部分,一是后处理,二是把扭曲面片渲染到掩码图,

优化:

1.掩码图RenderTexture尽可能简单,关掉深度,抗锯齿等,用最简单的格式RenderTextureFormat.RGB565,黑白掩码图,不要alpha通道,掩码面片的shader可以用粒子的add shader

2.不需要扭曲的时候应该关闭掉扭曲用的后处理.不要一直开着.这个实现起来需要对掩码面片的存在有一个计数统计,才知道什么时候能关掉.

3.掩码图的比例一定要和屏幕保持一致,大小可设置为屏幕宽高的1/2或者1/4,

 

后处理的脚本:

技术分享

后处理shader:

 

[csharp] view plain copy
 
    1. Shader "Luoyinan/ImageEffect/HeatDistortion"   
    2. {  
    3.     Properties   
    4.     {  
    5.         _MainTex ("Base (RGB)", 2D) = "white" {}  
    6.         _NoiseTex ("Noise Texture (RG)", 2D) = "white" {}  
    7.         _MaskTex ("Mask Texture", 2D) = "white" {}  
    8.         _HeatTime  ("Heat Time", range (0,1.5)) = 1  
    9.         _HeatForce  ("Heat Force", range (0,0.1)) = 0.1  
    10.     }  
    11.       
    12.     SubShader   
    13.     {  
    14.         Pass  
    15.         {  
    16.             CGPROGRAM  
    17.             #pragma vertex vert_img  
    18.             #pragma fragment frag  
    19.             #pragma fragmentoption ARB_precision_hint_fastest  
    20.             #include "UnityCG.cginc"  
    21.               
    22.             float _HeatForce;  
    23.             float _HeatTime;  
    24.   
    25.             uniform sampler2D _MainTex;  
    26.             uniform sampler2D _NoiseTex;  
    27.             uniform sampler2D _MaskTex;  
    28.   
    29.             fixed4 frag(v2f_img i) : COLOR  
    30.             {  
    31.                 // 为了效率,掩码图是黑白的,so...  
    32.                 fixed mask = tex2D(_MaskTex, i.uv).r;  
    33.   
    34.                 // 扭曲效果  
    35.                 half4 offsetColor1 = tex2D(_NoiseTex, i.uv + _Time.xz*_HeatTime);  
    36.                 half4 offsetColor2 = tex2D(_NoiseTex, i.uv - _Time.yx*_HeatTime);  
    37.                 i.uv.x += ((offsetColor1.r + offsetColor2.r) - 1) * _HeatForce * mask;  
    38.                 i.uv.y += ((offsetColor1.g + offsetColor2.g) - 1) * _HeatForce * mask;  
    39.   
    40.                 fixed4 renderTex = tex2D(_MainTex, i.uv);  
    41.           
    42.                 return renderTex;  
    43.             }  
    44.       
    45.             ENDCG  
    46.         }  
    47.     }   
    48.     FallBack off  
    49. }  

Unity3D手游开发日记(4) - 适合移动平台的热浪扭曲

标签:

原文地址:http://www.cnblogs.com/czaoth/p/5785632.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!