基於法線的邊緣檢測

來源:互聯網
上載者:User

在邊緣高亮效果中我提到過兩種方法, 各有優缺點吧

 

映像空間域的邊緣檢測效果比較好, 中間沒有多餘的線條. 缺點是PS中計算比較慢

第二種把模型"放大"(其實是變胖)的做法, 可以在VS中完成, 不需要額外的RenderTarget, 適合低端顯卡使用, 適應性好. 不如果模型法線資訊不對的話, 會造成畫面錯亂. 實際使用時可以根據W值(不用Z深度)來畫出遠近粗細一樣的線條

 

這次提到的基於法線的方法, 其實跟2D的空間域邊緣檢測很相似, 如果要求結果是繪製物體的線條圖而不僅僅是一個邊緣輪廓時, 它就派上用場了. (還是要用PS去算, 實際使用時要注意效能問題)

 

基本的渲染流程(2 pass):

第一個pass用於產生法線圖到一張RenderTarget上, 第二個pass跟據這張法線圖來做邊緣檢測.

實際使用時可以採用Multi-RenderTarget來加速

 

法線資訊要在pixel shader裡進行向量化, 不然會在一些面上出塊很淡的顏色. 如果對品質要求不高, 可以在VS中進行向量化.

RenderTarget要Clear成單位化的值, 我用的(0,0,1), 即純藍色

/*********************VS*********************/<br />float4x4 matViewProjection;</p><p>struct VS_INPUT<br />{<br /> float4 Position : POSITION0;<br /> float3 Normal : NORMAL0;<br />};</p><p>struct VS_OUTPUT<br />{<br /> float4 Position : POSITION0;<br /> float3 Normal : TEXCOORD0;<br />};</p><p>VS_OUTPUT vs_main( VS_INPUT Input )<br />{<br /> VS_OUTPUT Output;</p><p> Output.Position = mul( Input.Position, matViewProjection );<br /> Output.Normal = mul( Input.Normal, matViewProjection );</p><p> return( Output );</p><p>}<br />/*********************PS*********************/<br />float4 ps_main(float3 normal : TEXCOORD0) : COLOR0<br />{<br /> return(float4(normalize(normal), 1.0f));<br />}<br />

注意法線圖的格式是浮點數格式, 我用的是D3DFMT_A16B16G16R16F(因為法線有負值, 你也可以自己壓縮到[0,1]再解開)

 

有了這張法線圖就很好辦了, 對每個像素計算它與周圍像素的法線夾角餘弦值的和, 再取反(1-degree), 這樣就能計算出來邊緣了

依據就是邊緣處的法線夾角比較大, 餘弦值更接近0甚至為負值.

sampler TexNormal;<br />float2 fInverseViewportDimensions;</p><p>float2 PixelKernel[4] =<br />{<br /> { 0, 1},<br /> { 1, 0},<br /> { 0, -1},<br /> {-1, 0}<br />};</p><p>float4 ps_main(float2 texCoord : TEXCOORD0) : COLOR0<br />{<br /> float4 origin = tex2D(TexNormal, texCoord);<br /> float3 sum = 0;<br /> for (int i = 0; i < 4; i++)<br /> {<br /> float2 texel = texCoord + PixelKernel[i] * fInverseViewportDimensions;<br /> sum += saturate(1.0f - dot(origin.xyz, tex2D(TexNormal, texel).xyz));<br /> }</p><p> return float4(sum, 1.0f);<br />}<br />

最終效果:

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.