【Unity Shader】渲染纹理实现镜子效果
1 基本概念
1.1 什么是渲染到紋理?
全稱是Render To Texture,《入門精要》好像又把渲染目標(biāo)紋理,即Render Target Texture也叫做RTT,但我認(rèn)為《入門精要》的RTT更多的是“中間緩沖區(qū)”這個(gè)緩沖區(qū),而Render To Texture這個(gè)RTT更多的是指渲染到紋理這一個(gè)操作,為了避免混亂接下來我說的RTT都是指Render To Texture這個(gè)渲染操作。
在我們學(xué)習(xí)渲染過程基礎(chǔ)的時(shí)候,一個(gè)Camera的渲染結(jié)果通常會(huì)說“輸出并儲(chǔ)存在顏色緩沖中”,再等待最后出現(xiàn)在屏幕上。當(dāng)然,這也是常規(guī)的渲染操作。至于為什么會(huì)是渲染到紋理?有時(shí)候渲染會(huì)想要實(shí)現(xiàn)一些特效,那么此時(shí)RTT也像常規(guī)渲染操作一樣渲染一個(gè)場(chǎng)景,但這次并不是儲(chǔ)存在幀緩沖(雙緩沖則是儲(chǔ)存在后緩沖)中,而是渲染出一張紋理并在之后進(jìn)行使用。
關(guān)于RTT更專業(yè)點(diǎn)的敘述:現(xiàn)代圖形處理單元(GPU)允許我們將3D場(chǎng)景先渲染到中間緩沖區(qū)中,也就是說不會(huì)直接到達(dá)默認(rèn)的幀緩沖或者后緩沖(關(guān)于各種緩沖我在【技術(shù)美術(shù)圖形部分】圖形渲染管線3.0-光柵化和像素處理階段末尾有做簡(jiǎn)單的介紹)。
1.2 什么是渲染紋理?
全稱Render Texture,簡(jiǎn)稱RT,也就是上述提到的渲染出的那張紋理,這是Unity為渲染目標(biāo)紋理專門定義的一種紋理類型。
1.3?RTT的應(yīng)用范圍
上面說了,是為了實(shí)現(xiàn)一些特效效果。一般是在游戲的攝像機(jī)進(jìn)行設(shè)置,使得攝像機(jī)渲染的結(jié)果能存到Render Texture中。
1.4 什么是多重渲染目標(biāo)?
Multiple Render Target, 簡(jiǎn)稱MRT,也叫做多目標(biāo)渲染,是一個(gè)意思。多重渲染目標(biāo)允許我們同時(shí)把場(chǎng)景渲染到多個(gè)渲染目標(biāo)紋理中,不用再是渲染整個(gè)場(chǎng)景后才儲(chǔ)存。在【技術(shù)美術(shù)圖形部分】關(guān)于前向渲染和延遲渲染中我在Unity實(shí)現(xiàn)延遲渲染中,提到了“RT0、RT1、RT2、RT3”這四個(gè)渲染紋理,就是延遲渲染使用到MRT的體現(xiàn)。
2 模擬鏡子效果
2.1 原理
就是創(chuàng)建除了MainCamera之外的另一個(gè)Camera:用于渲染鏡子想要反射的場(chǎng)景,同時(shí)這個(gè)Camera的Render Target選擇創(chuàng)建的一個(gè)Render Texture,這樣的話選中的Camera渲染的場(chǎng)景將不會(huì)到屏幕上,而是存到的選中的渲染紋理RT中。同時(shí)要注意,既然是鏡像效果,畫面肯定是要反轉(zhuǎn)一下。
2.2?效果展示
這里我為了練習(xí)自己搜索紋理的能力沒有用《入門精要》提供的一些紋理圖片,而是在網(wǎng)上搜索(推薦一個(gè)免費(fèi)的紋理貼圖網(wǎng)站:Texture Ninja,如果有更好的歡迎分享!)自己想要效果的紋理圖片當(dāng)作Texture,然后在PS里獲得Texuture的法線圖,再分別給場(chǎng)景中的Wall、Sphere、Cube們賦予想要的材質(zhì)。?
2.3?實(shí)現(xiàn)過程
2.3.1 準(zhǔn)備場(chǎng)景
首先是搭建場(chǎng)景,創(chuàng)建6個(gè)立方體把MainCamera包圍住,場(chǎng)景中放置一些物體,再加上3個(gè)Point Light,賦予對(duì)應(yīng)的材質(zhì),Shader用的是標(biāo)準(zhǔn)光照Shader。
2.3.2 創(chuàng)建RT/Camera/“鏡子”
Project視圖下右鍵,Create -> Render Texture創(chuàng)建一個(gè)MirrorTexture渲染紋理;
Scene視圖下右鍵,創(chuàng)建一個(gè)Camera,并將Render Target選中剛才創(chuàng)建的RT:
我們的鏡子就用一個(gè)Quad平面代替,還需要?jiǎng)?chuàng)建MirrorMat材質(zhì)以及MirrorShader。
2.3.3 用于“鏡子”平面的Shader
這個(gè)Shader輸入的texture是剛才創(chuàng)建的RenderTexuture,整個(gè)結(jié)構(gòu)非常簡(jiǎn)單,這里就直接貼上代碼了:
Shader "Unity Shaders Book/Chapter 10/Mirror" {Properties{_MainTex ("Texture", 2D) = "white" {}}SubShader{Pass{Tags {"LightMode"="ForwardBase"}CGPROGRAM#pragma vertex vert#pragma fragment fragsampler2D _MainTex;struct a2v {//必不可少的,object->clipspacefloat4 vertex : POSITION;//要使用uv?那要先存著float4 texcoord : TEXCOORD0; };struct v2f {float4 pos : SV_POSITION;float2 uv : TEXCOORD0; };v2f vert(a2v v) {v2f o;o.pos = UnityObjectToClipPos(v.vertex);o.uv = v.texcoord; //什么都不需要做,就是獲取個(gè)紋理而已//還需要左右翻轉(zhuǎn)一下,關(guān)于x=0.5對(duì)稱:o.uv.x = 1 - o.uv.x;return o;}fixed4 frag(v2f i) : SV_Target {return tex2D(_MainTex, i.uv);}ENDCG}}FallBack OFF }2.4 特點(diǎn)及應(yīng)用
2.4.1 “鏡子”清晰度與什么有關(guān)?
清晰度完全取決于這個(gè)Render Texture的分辨率,上述效果中我的分辨率選擇的是默認(rèn)的256x256,看上去會(huì)比較模糊,如果改成1024x1024,則會(huì)清晰很多,但會(huì)消耗更多的性能,必要時(shí)注意清晰度和性能二者的取舍:
2.4.2 應(yīng)用
游戲里的鏡子是怎么做出來的? - 知乎 (zhihu.com)
想了解更多可以自行搜索“游戲中怎么做鏡子效果”等等,這里我只是貼了一個(gè)知乎的問題,16年的時(shí)候就有人回答了用渲染紋理實(shí)現(xiàn)鏡子效果的方法。
總結(jié)
以上是生活随笔為你收集整理的【Unity Shader】渲染纹理实现镜子效果的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 如何把excel中的多行数据按行数拆分成
- 下一篇: 线上编辑器推荐