http://www.insomniacgames.com/tech/articles/0409/files/water.pdf
链接下面还有source code,实现的挺优雅,艺术品欣赏下不错(直接导致有段时间变成变量命名变成c风格了)。
但是算法上看文章了解比较好,代码最核心部分是spu汇编,看得累。
题外话:
insomnic这篇论文非常具有理论和实战价值。
但是真正让我感叹的是这本身是很不错的技术,本应成为insomniac的宝贵财产,而insomniac却share了出来。
比较之下,也只有carmack open source quake代码能更胜一筹了。
再次表达敬意
现在fps游戏中的水大抵这几个方面需要考虑:
- grid的分布----由于可见范围过大,需要project grid这类技术来让grid分布尽可能合理,近密远疏。
- ambient wave----这部分基本是达成共识fft,至于bioshock,hydrobophia这种迎面扑来的是another story
- interaction----交互时候的波动
- 光学效果----reflection, refraction, fresnel都是last gen考虑过的问题了,虽然重要,但是insomniac唯一提到的是他们hack了reflection,使用正面render target直接反一下。
grid和ambient wave这里前人已经给了不错的答案了,这部分也不是这个paper的核心所在。
不过lod那里在算ambient wave时候有个优化,很古怪的,没太看懂。。。留着以后慢慢品吧。
convolution based interaction
这里基本原理是convolution based algorithm for animated water waves的原理。
但是insomniac走的更远,首先是以overlap save的方法来优化convolution。
时域中的convolution在频域中是个乘法操作。
这个道理在巨早的时候就被大家知道了,但是知道fft算法发明出来才具有实际应用价值。
在fft的情况下,把interaction tile的heightmap转到频域,然后和convolution的kernel(频域)相乘,然后ifft变回来就是结果了。
insomniac得以把fft的汇编代码在convolution阶段又用了一遍。
另外一点觉得是一个理解很好的点是,把convolution和interaction都看作是在随时间更新相位的spectrum component。
这里本来我想扩展一下,做更大范围的卷积的快速算法(overlap save)但是失败,因为overlap save的前提是函数是周期函数。
所以如果在一个area下边加一个impulse,然后全area fft_convolution,会发现波会从area的顶部散下来,orz。
所以insomniac的interaction都是每一个interaction生成一个tile,在tile中心开始impulse,然后去convolution,由于是tile中心,所以不用担心波会越过下界,进而就不会下进上出了。
最后觉得insomniac带来的理论和推导非常的棒,但是由于是在ps3上,spu的计算能力逆天,所以其他平台上不适合直接复制。
还是根据平台特性,来从原始理论推导出合适算法比较好。