摘要:Hi Tessellation
Hi 大家好久不見
我把這些日子研究Tessellation的過程做個記錄
之前做好的Tessellation屬於Polygon再細分而已, 並沒有對輪廓平滑有任何加強
例如:
經過Tessellation之後
但是, 輪廓還是一樣方方的, 多出來的面, 可以用Displacement Map來拉出一些細節
可是理想中, Tessellation 應該可以做到這樣:
要如何達到呢?
名詞解譯:
Patch:(布片)
一小片面積的表面, 可以是三角形(Triangle),四角形(Quad)
平常我們的MODEL包含了Face或稱Polygon, 但在Tessellation中這一小塊布片可以用一些三次曲線或spline變成曲面
我約略把Subdivision的技術分為兩種(注意: 此處為閒聊漫談, 非正式的學術分類)
- 直接平滑
- 1-Ring 平滑
直接平滑和1-Ring平滑的差別在於
1-Ring要事先分析每一個Patch(布片)周圍相接的第一環結構, 比如說有幾個面, 每個點接幾個邊, 直接平滑只把該Patch直接處理而已
兩者的效果差異是顯而易見的(Phong Tessellation和 PN-Triangle是直接平滑, QAS和BFT是 1-Ring平滑)
1-Ring的作法最最有名的就是
Catmull-Clark
艾德文·厄爾·卡特姆,美國計算機科學家,迪士尼動畫工作室和皮克斯動畫工作室現任總裁,皮克斯的創始人之一。作為計算機科學家,卡特姆為計算機圖形學作出了許多重大的貢獻。 維基百科
他的論文被拿來延伸, 修改應用在無數的電影動畫軟體中
但是他的演算法牽涉到較多的數學運算, 所以比較少用在即時3D與遊戲上
所以不少人把它拿來做"近似"處理 並且希望能用到最新的DX11 GPU硬體加速的功能
泛稱為ACC (Approximation Catmull Clark)
但想到我們一般遊戲美術做的都是三角面, 所以就希望能找到以三角面為Patch的演算法
在網路上搜尋到一位SIGGRAPH的常客
Tamy Boubekeur
http://perso.telecom-paristech.fr/~boubek/papers/GPUSub/
這篇論文就是以三角面為主的演算法, 我也找到他的同事網頁
http://graphics.tudelft.nl/~matthias/common/home.php
公開的原始碼 http://graphics.tudelft.nl/~matthias/bft/BFTDemo.zip
可惜, 它是用OpenGL寫成的, 而且, 沒有辦法看出來, 它是否用到了DX11的Tessellation硬體加速
嘗試一
那麼先來試用直接平滑的效果如何
在DirectX 2010 JUNE 中有PNTriangles11範例, 我把它的SHADER拿來改, 放到OGRE的架構底下
於是結果如下: 左邊只有一般的Tessellation, 右邊是PN-Triangle的Tessellation
雖然, 右邊的輪廓線比左邊平滑, 但是效果還是不夠理想, 比如魚的眼睛比較低的面數之類的
嘗試二
回過頭來, 在DirectX中的其他範例如 Charles Loop的SDK root\Samples\C++\Direct3D11\SubD11
論文: http://research.microsoft.com/pubs/70432/tr-2007-44.pdf
拿到了它的HLSL Shader Code 落落長一千多行
可是, 它專案引入的模型檔, .SDKMESH本身就已經附了1-Ring的資料, 這個資料怎麼產生的
卻沒有解釋, 而且它的理論基礎主要針對Quad(四角面)
嘗試三
在nVidia的SDK11中有一個Gregory Patch的範例
https://developer.nvidia.com/nvidia-graphics-sdk-11-direct3d
它使用的論文是
http://research.microsoft.com/en-us/um/people/cloop/sga09.pdf
HLSL Shader 也是一千多行
因為Gregory Patch可以同時用在三角面和四角面上
但問題又來了 它使用的模型檔是nVidia的BZR檔, 要了解這個檔案架構
就要了解nVidia SDK mesh tools
https://code.google.com/p/nvidia-mesh-tools/
但是工程有點大
於是就此打住
以下是運用這個技術成功的Matt Davidson
http://www.gamedev.net/page/community/iotd/index.html/_/gregory-patches-and-character-stuff-r128
他在文章下方提到他的做法, 可惜也是工程浩大
![]() |
|








