Graphenix

 
 
昵称:linyizsh
园龄:5年3个月
粉丝:11
关注:0

搜索

 
 

常用链接

  • 我的随笔
  • 我的评论
  • 我的参与
  • 最新评论
  • 我的标签

随笔分类

  • Algorithm(3) (rss)
  • Engine(2) (rss)
  • GI(2) (rss)
  • Misc(6) (rss)
  • Optimization(2) (rss)
  • Shadow (rss)

随笔档案

  • 2011年3月 (1)
  • 2010年12月 (1)
  • 2010年10月 (2)
  • 2010年8月 (1)
  • 2010年5月 (1)
  • 2010年2月 (2)
  • 2009年5月 (1)
  • 2008年10月 (2)
  • 2008年3月 (1)
  • 2008年1月 (2)
  • 2007年5月 (1)
  • 2007年4月 (3)
  • 2007年3月 (1)
  • 2007年2月 (1)
  • 2007年1月 (1)
  • 2006年10月 (11)

好友链接

  • cp的小屋
  • sixwater
  • 猎狼者
  • 流逝的时光
  • 向往的程序人生

最新评论

阅读排行榜

评论排行榜

推荐排行榜


Powered by: 博客园
模板提供:沪江博客
博客园 | 首页 | 发新随笔 | 发新文章 | 联系 | 订阅订阅 | 管理

2011年3月22日

t&h

    老久没更新,发点吧,让前面一篇降下去。

 

    * 在D9下,SetStreamSource/DrawIndexedPrimitive,这几个参数的意思,久了经常忘记。
    OffsetInBytes: 设置VB的数据从哪一个位置开始,即IB里的第0个顶点,从这个地址开始算起。
    BaseVertexIndex: IB里的每个索引,加上这个数值,比如设置了2,则IB里的5会变成7。。。不太常用,但有时候会有意想不到的作用。
    MinVertexIndex: 告诉D3D,使用到的顶点从VB里的第几个开始,设置之后,对渲染无影响,只是帮助D3D在某些时候改进性能。。。
    NumVertices: 告诉D3D,本次DP,用了多少个顶点,设置之后,对渲染无影响,要注意的是这个跟MinVertexIndex没啥关系,并不是从MinVertexIndex开始算起的,只是帮助D3D在某些时候改进性能。。。
    startIndex: 与OffsetInBytes类型,设置IB的数据从哪一个开始读起。

 

    * Cry的地形并不是用一张图来算每一层的Alpha,而是用顶点中的color的256级来表示,每一个数值表示一个层。因此它不能表示半透明的层,只能在边缘1格的地方由1降到0。

 

    * D3DFORMAT MAKEFOURCC('N', 'U', 'L', 'L')格式的Target并没有必要设置成1x1(cry中是这么搞的)的大小。这个target无论多大,都不会消耗显存,并且draw的时候写入的像素也是0,速度也没啥变化。

 

    * 简易骨骼动画:

    Mesh当前帧顶点 = Mesh绑定时顶点 * 绑定时骨骼的变换到本帧骨骼的变换的改变量。

                           = Mesh绑定时顶点 * 绑定时骨骼的变换的逆矩阵 * 本帧的骨骼变换。

                           = Mesh绑定时顶点 * 绑定时骨骼的变换的逆矩阵 * 本帧的骨骼相对父节点的变换 * 本帧父骨骼的变换。

    其中,

    Mesh绑定时顶点:由Max导出。

    绑定时骨骼的变换的逆矩阵:从Max的Skin Modifier的GetBoneInitTM中取得(或者Physique Modifier的GetInitNodeTM中取得)矩阵。

    本帧的骨骼相对父节点的变换:从Max的骨骼的NodeTM和父骨骼的NodeTM得到,注意对于行矩阵,矩阵顺序是 ParentToChild = ChildToWorld * Inverse(ParentToWorld)。列矩阵则相反,根节点则直接保存NodeTM即可。帧之间的插值也主要是对这些数据做插值,在两帧之间没有很大变化的时候,四元数加向量和矩阵视觉上并没有很大差别。

    本帧父骨骼的变换:由前面从根节点累加。

 

    * deferred shading中light画volume的简单方法。
    眼睛在volume外,用CCW直接画volume;眼睛即将进入volume或在volume中时,用CW画,并且将volume轻微放大一些包含住camera。除了修改下cullmode,渲染流程完全不用变。

 

    * CSM中,如果shadowmap用atlas放到一张图中的时候,比如4个slice放到一张图的时候,计算shadow receive时,可以用一张很小的(64x64)的图,来选择slice的UV。比直接计算快。

posted @ 2011-03-22 13:43 linyizsh 阅读(1109) 评论(0) 编辑
 

2010年12月5日

MTE

posted @ 2010-12-05 14:26 linyizsh 阅读(269) 评论(7) 编辑
 

2010年10月23日

Best fit gbuffer normal

    http://advances.realtimerendering.com/。crytek总是能发现一些别人没发现的东西。

之前我也发过http://www.cnblogs.com/linyizsh/archive/2009/05/30/1492314.html

说过些packnormal的东西。但是从直觉上,无论哪种方法,总是觉得不怎么完美,一个是计算量太大,

一个是存储bit数太多,如果使用类似deferred lighting的方式,存深度,normal和specular power,

如果希望只用64bit来存,在pc d3d上不考虑扩展情况下,深度通常32bit不可少(当然16bit不是不可以,就像sc2

,但是sc2情况特殊,它没有太远的场景,500米内,16bit通常够用,但是如果希望能够看到更远,16bit

就不够了,如果做ssao之类深度效果,在远处影响就很大),剩下normal和specularpower,specularpower

至少也要8bit,剩下24bit给normal,如果按之前的pack方式,这是很难的,直接存取更不用说,质量太差。

    无数人做过无数方法去弄这个pack问题,但是都忽视一个非常简单的问题,24bit能够存的是一个volume,

有256*256*256个可能的值,直觉上这么多的值,应该是可以保证精度才是,为什么直接存却不行呢,因为

pack都是按照normalized之后的向量去pack的,相当于xyz的关系是确定的,这些xyz构成的是一个球面,

这样给自己下了一个限制,这个球面的空间占这个volume的比例还不到2%。。。浪费了其它n多的空间,精度

当然是相当低的,best fit的方式就是利用这些空间,先把所有256*256*256的各个方向的

向量长度bake到一个图里,去掉对称的和重复的,之后放入一个2d图里。在生成gbuffer的时候,通过normal来查找到

最接近的texel,也就是找到对应的向量长度,然后直接将这个长度的normal,scale到0-1就行了,使用的时候只要scale

回来,然后normalize一下就可以了,可谓方便之极,完全可以到处使用。

    这种方法给存储normal指了另一条明路,如何来利用这256*256*256个值,crytek的方式感觉上还是有些麻烦,

压缩normal的过程在ps3.0下需要18条指令,也许以后还有更简单的方式。

    个人觉得,只有normal能够存入24bit并保证精度,deferredlighting才能真正比较实用,best fit的方式应该是最好的

办法了。

posted @ 2010-10-23 22:03 linyizsh 阅读(314) 评论(0) 编辑
 

2010年10月17日

Mipmap不连续问题。

一个容易疏忽的问题。

图:

    模型的边缘有个碍眼的白边,这个是由于计算水下的caustic的时候用了深度来计算某个tex的uv,结果产生这个白边。(图压缩后变难看了。。。)

这个不是算法错,也不是什么数据问题。而是由于使用的tex带有mipmap,但由于uv从深度算来,因此在ps里,边缘相邻两个像素的uv有个跳变,使gpu在这个地方出现lod计算错误,因此取了一个错误的值。

    解决的办法有两个,一个是自己计算lod,可以通过采样边缘的像素,在xy方向选深度差最小的那个相邻像素来计算ddx ddy。

另一个办法是tex如果尺寸比较小的话可以不要用mipmap,总是用0层,则不会出现问题。

解决后的图:

    这个问题其实存在的地方并不少,只要使用有突然跳跃的数值(比如这里的深度)来计算mipmap tex的uv,则都有可能会出现,不过有些情况下这个问题不太明显。

不解决其实也没啥问题,作为游戏来讲用户也不一定注意,所以这个问题也容易被疏忽,不过如果追求完美的图像的话,就总觉得有些别扭。

posted @ 2010-10-17 15:41 linyizsh 阅读(225) 评论(0) 编辑
 

2010年8月30日

MLAA(Morphological Antialiasing)

    试了mlaa,后处理的aa。

    最初的文档是intel发布http://visual-computing.intel-research.net/publications/papers/2009/mlaa/mlaa.pdf,只有cpu实现。

    后来有人做了gpu版本http://igm.univ-mlv.fr/~biri/mlaa-gpu/,有篇paper,不过跟没有差不多,似乎还有个siggraph的talk,但是网上找不到,总之这个版本

有一定的简化,Z shape简化为L shape。不过对于一般游戏来讲效果已经足够。

    mlaa应该是后处理方式的aa,能达到的最好的效果了,越来越多的游戏用了这个东西,包括战神3,不过它用的是ps3的spu。

    我刚开始看上面那个gpu版本被他那些flag弄迷糊了。于是自己根据intel那个山寨了一个,回头再来看终于容易多了。。。

    gpu实现,不过在我的垃圾显卡(9400)上要花将近10ms,相信在最新的机器上应该可以勉强跑的起来,因为效果确实不错。

    先看看效果,上面没开,下面开:

 

对比可以看到,下面的边缘平滑的非常好,而且对于整体的颜色粗糙部分也有一定的改善,但这种改善会造成原有的信息有一些偏差,不过对于游戏通常这个偏差可以忽略。

 

过程如下:

首先第一步生成边缘图,红线是横线,绿线是竖线,那个gpu版本是将颜色转换到lab空间判断,我这里直接用rgb分别判断:

 

第二步分别生成横线和竖线的长度信息,我没有按照上面那篇gpu版本的方法分level做,而是直接做几次循环来取:

 

然后根据上面几张图判断shape类型,生成上下左右四个像素的比例图:

最后一步就blend到最终target上,也就是上面的效果了。

   

    虽然mlaa目前来讲耗的时间还是比较多,但是在延迟渲染上,比起硬件msaa和ssaa(supersample),还是要快很多,估计以后应该会有些变形,提高些速度。

    mlaa对于边缘的过滤非常漂亮了,但是缺点是由于是后处理,因此在光栅化的时候丢弃的信息就无能为力了,比如屏幕上的断断续续的细线之类。

posted @ 2010-08-30 23:36 linyizsh 阅读(405) 评论(1) 编辑
 

2010年5月8日

Volumetric Obscurance
摘要: 原文为了看起来像一个论文,所以写的洋洋洒洒,引经据典,其实在我看来SSAO本身就只是一种tip,没必要那么啰嗦,关键的东西说来就两句话,在每个像素为中心的球体内,发射与屏幕垂直的n条线,计算每条线在这个球体范围内有多少被zbuffer遮挡,再按比例加起来作为AO。放点图,10次sample,但只做了一次2x2的blur,所以质量不太好,但速度确实比以前的方法快,提高blur的kernel可以提高质...阅读全文
posted @ 2010-05-08 02:58 linyizsh 阅读(414) 评论(0) 编辑
 

2010年2月3日

ao propagation volume...
摘要: 这个是名字是我乱起的:)。。。发了上一篇之后突然想到,既然radiance volume可以做能量传递,那或许也可以做为ao的传递,因为ao信息也是低频的,于是有这个名字。。。 改一下lpv的过程,不要生成rsm,而是直接将mesh写入volume,生成的时候关掉ztest和zwrite,直接写入到对应的位置。只需用位置和normal即可,同样把信息投影到sh。propagation 过程一样,只...阅读全文
posted @ 2010-02-03 22:01 linyizsh 阅读(331) 评论(0) 编辑
 
lpv
摘要: 测试了Light Propagation Volumes,全实时没有任何预处理的GI,而且可以适用任意场景。文档很长,不过基本原理还是比较直白的: 生成reflect shadow map(rsm)。 将rsm信息用SH系数方式注入一个volumetexture中。 在volumetexture中进行propagation(大概叫传递或者传播的意思)。 最后将propagation完的volume...阅读全文
posted @ 2010-02-03 00:12 linyizsh 阅读(714) 评论(5) 编辑
 

2009年5月30日

说下pack/unpack normal的问题
摘要: 现在很多延迟光照算法,都有保存normal的pass,为了节约资源,很多有把normal三个分量pack为两个分量的算法,以d3d的左手坐标为例,normal在camera空间。 最开始有:pack:xy = norm.xy; unpack:norm.xy = xy; norm.z = -sqrt(1 - x^2 - y^2); 这个方法开始用的很广泛,但它是错的,因为由于透视投影的关系,有些面...阅读全文
posted @ 2009-05-30 17:03 linyizsh 阅读(431) 评论(1) 编辑
 

2008年10月11日

CheckPoint
摘要: 到今天为止,我已经实现了一个比较完整的延迟着色(ds)渲染器,包括各种各样的类型的处理和融合opaque,translucent,mirror reflect,cube reflect, terrain,sky,particle,primitive,ui,postprocess(hdr,dof,lightshaft, ssao)等。国内很少有人做基于ds的渲染,导致我找不到人讨论,一直都只好到国外...阅读全文
posted @ 2008-10-11 02:16 linyizsh 阅读(656) 评论(2) 编辑
 
仅列出标题  下一页