nicky

  博客园 :: 首页 :: 博问 :: 闪存 :: 新随笔 :: 联系 :: 订阅 订阅 :: 管理 ::

2004.7.20 对GPU shadow volume construction for non-closed meshes的 思考:

一种方法: 
做GPU SHADOW VOLUME CONSTRUCTION,对于non-closed mesh可以把原mesh不动,判断出edge,再拷贝一个原mesh做back face,仅只将每顶点法向量reverse以下,再对两个mesh构造degenerate quad,并对已判断出的边界将两个mesh在边界用degenerate quad连接.这样就得到了一个封闭的MESH.这样做是有一个隐含约定的:mesh必须面对light,而且不能有缝隙/漏洞;比如一面墙是一个quad,它始终是面朝light,而且是封闭的(这里指相对于他的边界).这样的mesh在场景中一般是static surface: planar surf/bezier patch.

象staic mesh就可以用以前我的方法处理shadow volume construction.

对于skeleton,可以用cpu算,而且我认为做近似的可以不用degenerate quad,效果有待验证.


另一种方法:
对于non-closed mesh可以先用原方法generate一个shadow mesh,这时候一定有一些non-shared edges,如果这些edge可以组成封闭的环,那么可以把这些edge生成一个/几个mesh,这样就相当于把原mesh的non-closed部分补上了.然后,按照原方法把这个/这些mesh与剩下的edge继续生成shadow mesh.如果这些non-shared edge不能组成环,则此方法失效.

这个方法的好处是可以最大限度的节省顶点/索引资源.若按照先前的来做则对于象cylinder这样半封闭的mesh就十分浪费.此方法仍然对planar surf/bezier patch有效.

不知道<<GEMS4>>上是怎么作的,不过这样应该是一种不错的方法:)

事实证明第二种还是不够ROBUST。譬如对于所有的non-closed, _concave_ object都不能构造正确的MESH,因为concave部分利用这种方法会让back face跑到front face前面。用第一种又太费。

顺便说下,dx9.c sdk中提到过第二种方法。

edited on 05-10-17:
今天看了《game programming gems4》的5.2节,文中提到了一种解决方案:
1。预处理过程:
对每个三角面生成三个独立顶点,拥有此面的法向。
对每个面产生三个边,然后对边作两两匹配(拥有相同端点的便匹配)。若有配对则生成degenerate-quad,否则说明此边为open-edge,需要push_back两个顶点,然后生成degenerate-quad。
注意这些退化四边形由indexbuffer存储。
2。渲染
渲染面向光源的面,背光面的剔除可以将输出坐标设为0
渲染延伸的(extruded)面,同上剔除背光面
渲染边(shadow volume),这一步相当于链接了front/back cap
原文并没有用z-pass/z-fail方法。

可以看到文章基本意思就是利用面向光源的面来作vs shadow volume。包括生成front/back cap。不过显而易见这种方法太过于耗费,(需要提交原几何体三次,还是考虑了two-sided stencil)。不太实用。

posted on 2004-12-30 15:21  nicky  阅读(750)  评论(0编辑  收藏  举报