github unity 图片切换效果_[Unity+shader]模拟一个三棱柱广告牌(上)

d452ec745b014deffbdf8da23f15d880.png

三面翻广告牌(Trivision, Triangular Billboard,https://en.wikipedia.org/wiki/Trivision)

是由一组并排定位的三棱柱构成,通过旋转三棱柱,利用其三个侧面形成三幅画面的广告牌,在LED广告牌大规模出现之前是个很常见的东西。

fd18f122bff3d542424d56af63741e66.png
就是这个东西,图片随便搜的,应该是某厂的产品展示

在这篇文章里,我们就讲一下如何制作一个棱柱翻转切换图片的效果。

模拟棱柱翻转的基本,就在于将同时显示的两张贴图分割,之后按一定比例缩放。

1b22de323e94e3330079b66316da519b.png

ac65411acea518b10f898475221d5a7d.gif
三棱柱依次旋转的效果

先从基础的功能开始:

//AnimationEffects2D-->sakuraplus-->https://sakuraplus.github.io/make-terrain-with-google-elevation/index.html
Shader "TUT/TriangularBillboard01" {
	Properties {
		_MainTex ("Texture A", 2D) = "white" {}
		_MainTexB ("Texture B", 2D) = "black" {}
		[Space(10)]
		_Progress("Progress", Range(0,1))=0
	}

	SubShader {
		Tags {"Queue"="Transparent" }
		CGINCLUDE
		#include "UnityCG.cginc"
		sampler2D _MainTex;  
		sampler2D _MainTexB;  
		uniform half4 _MainTex_ST;
		uniform half4 _MainTexB_ST;
		fixed _Progress;

		struct v2f {
			float4 pos : SV_POSITION;
			half2 uvTA: TEXCOORD0;
			half2 uvTB: TEXCOORD1;
			half2 uvORI: TEXCOORD2;//original
		};
		  
		v2f vert(appdata_img v) {
			v2f o;
			o.pos = mul(UNITY_MATRIX_MVP, v.vertex);
			o.uvTA=(v.texcoord-_MainTex_ST.zw)*_MainTex_ST.xy ;
			o.uvTB=(v.texcoord-_MainTexB_ST.zw)*_MainTexB_ST.xy ;
			o.uvORI=v.texcoord;
			o.uvORI=v.texcoord;

			return o;
		}

		fixed4 frag(v2f i) : SV_Target {
			fixed4 texA;
			fixed4 texB ;
			fixed4 color;
			float posmod;

			texA = tex2D(_MainTex, i.uvTA).rgba ;
			texB = tex2D(_MainTexB, i.uvTB).rgba ;

			if(i.uvORI.x>_Progress){
					color=texA;
			}else{
					color=texB;
			}
			return color;
		}
		    
		ENDCG
		Pass {
			//ZWrite Off
			Blend SrcAlpha OneMinusSrcAlpha
			CGPROGRAM
			#pragma vertex vert  
			#pragma fragment frag
			#pragma target 3.0
			ENDCG  
		}
	} 
	FallBack "Diffuse"
}

首先定义两章贴图,和一个propert,_progress作为控制三棱柱旋转的参数。

在frag 函数中,以progress 为依据判断绘制哪张贴图。

这样我们得到了一个使用progress控制切换两张贴图的效果。

32ae81d7c6a6387fd7c4b73b27cd22e3.png
单个棱柱旋转切图的效果

但是一个三棱柱广告牌不应该只有一个棱柱,于是加上一个width的property,来设置每个棱柱的宽度。

		_Width("Width",Float )=0.5

虽然可能用不到,但是这个宽度其实是可以超过uv的范围的,所以不需要限定成Range(0,1)。

修改一下这个部分,计算当前uv与width属性的余数:

   			float	posmod= fmod(i.uvORI.x,_Width);
			if(posmod/_Width>_Progress){
					color=texA;
			}else{
					color=texB;
			}

就实现了一个简单的百叶窗效果,把这里的uvORI.x换成y,百叶窗就可以变成横向打开的啦。

c78ae2b575ac64bf6a074d4f5509cfff.png
像不像我们熟悉的ppt百叶窗

作为一个模拟棱柱,图片旋转造成的压缩效果必不可少,接下来我们来计算压缩部分。

两张贴图uv的y坐标不变,x根据自身的位置和progress计算。

 			fixed2	uvA=fixed2(i.uvTA.x+(posmod-_Width)* _Progress/(1-_Progress), i.uvTA.y);
			fixed2	uvB=fixed2(i.uvTB.x+(1-_Progress)*posmod /_Progress, i.uvTB.y);
			texA = tex2D(_MainTex, uvA).rgba ;
			texB = tex2D(_MainTexB, uvB).rgba ;	

公式其实很简单,只是平面几何的程度。

e56da9be20c1c2060548e291011a4928.png
以左侧texB为例:(posmod +(新UV - 原本的UV))与 width的比值等于posmod和(width*progress)的比值。

接下来给它添加一个假的阴影。先添加一个表示阴影基础强度的property。

		_ShadowStrength("Shadow",  Range(0,2)) = 1.0

之后,让棱柱的两个面都有显示的时候,加上一个从内侧向外逐步减淡的阴影,即让最终的颜色乘以一个小于1的数。

658f874b8190ef27dd26d95f2fab49c2.png

以左侧texB为例:

首先,让阴影强度随着progress 变化,在面所占的比例变大时,这个数逐渐接近1,比例变小的时候,逐渐接近0。

		fixed shadowOnTexB=_ShadowStrength*abs(_Progress-1);

接着,让uv越接近progress位置时,阴影越淡。

		shadowOnTexB *= (_Width*_Progress- posmod)/(_Width*_Progress);

这时,shadowOnTexB和我们所期待的正好相反,于是,

 		texB.rgb*=1-shadowOnTexB;

而针对在右侧texA区域的点,也是同样方法计算。

		fixed shadowOnTexA=_ShadowStrength*_Progress;
		shadowOnTexA *= (posmod-_Width*_Progress)/(_Width*(1-_Progress));
		texA.rgb*=1-shadowOnTexA;

dcc0d3ed39e8f29082370e7eb1e5e6d0.png

至此,一个所有三棱柱同时旋转以切换图片的模拟三棱柱广告牌就完成了。下一章会讲一下更多的三棱柱翻转方式。

这一章中所用到的内容在这里,真的很尴尬到现在才发现忘了加链接:

sakuraplus/make-terrain-with-google-elevation​github.com

其中上篇所讲到的内容为01,02,03

希望观看更多效果,去sakuraplus/make-terrain-with-google-elevation希望观看更多效果,去

Unity Web Player | SlideshowEffect​sakuraplus.github.io

作为摄像机特效也可以使用

Unity Web Player |SlideshowEffect CamEffect​sakuraplus.github.io

Buy me a coffee: http://u3d.as/1jVq

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值