张春成

V2

2022/06/30阅读:16主题:默认主题

三个火枪手

三个火枪手

立体渲染是一个充斥着工程师卓越智慧的领域。它的科学问题不多,但工程上的困难几乎无处不在。因此,这也是一个大坑。


这是我扩展的一个渲染样例,尝试用它来说明一些已知的坑和解决方案。 本文的代码和全部内容都可见我的前端主页 home-page-2[1]

main
main

【视频样例】

它需要解决以下问题,在此只把问题罗列出来,以后慢慢填坑。

三维环境

简单来说,三维环境就是贴图。但这个贴图比较奇怪,大概是如下这样很扭曲的结果。它并不是平面图,而是以相机为中心,匀速旋转 360 度摄影得到的图像。如果你的想象力足够好的话,或者可以拿起手机拍一个全景图像,大概就能明白我的意思。

hdr-1
hdr-1

线框架与法线

下面需要把三维模型放在这个场景中。三维模型有无数种组织方式,目前最常用的是 MESH 模型,也就是框线模型,如下图所示。简单来说它是把物体的表面拆分成大量的三角或多边形,再将多边形组合起来就得到了整个立体。

wareframe
wareframe

有了表面多面体就立即得到了它们的法线,如下图所示

computeNorm
computeNorm

但这样简单的法线虽然能够表现大致的方向,但无法展示细节纹理。还记得吗,每个小多边形其实是在表面采样得到的,采样就有失真,在法线方向上的失真会导致模型表面损失大量的细节。为了解决这个问题,可以通过更精细的模型贴图来解决这个问题。

normTexture
normTexture

材质与纹理

既然说到了材质贴图,为了让我们的模型的表面有颜色,最常用的方法是使用表面贴图,它类似下图这样,可以从图中看出模型各个部位的纹理和颜色。

colorPaper
colorPaper

但是有了纹理贴图就能唯一地为模型染色了吗?显然不能。因为还要考虑到如何将这些颜色块“放置”在模型表面。下面三张图就是用上图的纹理,但采用三种截然不同的染色方案,不同点在于染色的方向和反射参数等。

color-1
color-1
color-2
color-2
color-3
color-3

如果你放大一些,可以看到表面的黑漆材质是十足的金属,能够在一定程度上反射周围的场景。

color-2-detail
color-2-detail

镜面反射

那么,我们能够用上面的方法制作一面镜子,或镜面的材质吗?其实答案是不能。这里面的原因非常复杂,简单来说就是用材质渲染的方法“画”镜面的计算开销过大,十分的不明智。所以一个最简洁的方法是在镜面处放置一个相机,再将相机的视野“投射”到镜面表面,这样呈现的图像不仅干净,它的计算开销也是相当经济的。

Mirror-1
Mirror-1
Mirror-2
Mirror-2

水体

另外,我们还希望能够渲染水体的动态效果。说实在话,这个东西很麻烦。因为将水体拆解来看,它就是一个褶皱密度的透光面。天哪透明度,这个玩意就不在这里展开了,也许之后有时间再细说吧。

Water
Water

参考资料

[1]

home-page-2: https://listenzcc.github.io/home-page-2/gunRender/

分类:

后端

标签:

后端

作者介绍

张春成
V2