Shading(2) Texture和插值

插值

三角形内部点的表达

\[\begin{aligned}(x,y)=\alpha A+\beta B+\gamma C\end{aligned} \]

\[\begin{aligned}\alpha+\beta+\gamma&=1\end{aligned} \]

表示在三角形ABC所在平面上
\(\alpha\)\(\beta\)\(\gamma\) 都是非负的时,点(x,y)在三角形内部

三角形重心是均分三角形面积的点。

在顶点的线性插值:
这里还有一个注意点是应该注意坐标系,如果要插的值是三维坐标系中的,那就应该在三维坐标系插值,而不是投影后。

Bilinear 插值

当纹理过大,对应的采样像素区域过小时怎么办?

首先会出现问题:

这个现象的原因有些难以理解,应该是在远处的一个像素其实对应了纹理上的一大块区域【在很小的一块像素上表达了高频的纹理信息】

下面这幅图可以比较好的解释:

可以理解为,在远处的部分,其实在uv纹理上对应了很大的一部分信息,那么这一大块我要怎么取才合理呢?

那么接下来就要找到如何将高频的纹理信息表达(常规来看是平均)出来。

这其实转化为了一个重要问题——范围查询。也有一些解决方法:mipmap(针对正方形)、(金字塔应该也是这个思想)等。

Mipmap

有一个非常重要的前提是正方形
【why,应该是定义就是这么定义的,后面取得也是一个近似的正方形,当取得是一个近似的长方形时,可以用各向异性的】

也就是提前把(长/2N)×(宽/2N)分辨率给计算出来,然后查询就可以了,提前计算的这部分总和占之前面积的1/3:

对于某一像素,在纹理上计算一个近似的正方形,然后取对应层的一个像素表达。

当层数计算出来是非整数时,也可以再进行一次层与层之间的插值:

这样的话就能插值出来一个比较连续的结果,但是会出现一个问题就是overblur:


原因是因为采样的时候,按照和相邻顶点近似为正方形去获得像素。如果形状和正方形相差过大,就会造成这种现象。例如将下面的蓝色框取为正方形近似,就会平均了更多的纹素。针对红色框圈住的长方形形状,设计了Anisotropic Filtering

Anisotropic Filtering

Ripmaps and summed area tables

纹理的使用

In modern GPUs, texture = memory + range query (filtering)

  • General method to bring data to fragment calculations
    我理解这里贴图其实只是一块内存,重要的是定义映射【交给美工】,这样的话,可以进行各种计算。
    Many applications
  • Environment lighting
  • Store microgeometry
  • Procedural textures
  • Solid modeling
  • Volume rendering

环境光:

Spherical Map:

球星环境光展开会像地球仪展开成二维平面一样,但是这有一个问题就是越靠近两级的地方就会越扭曲。

这样就有人提出Cube Map:

这减少了扭曲的位置,但是增加了对应面的计算

高度贴图、凹凸贴图、位移贴图

假如这个贴图中存储的是高度信息,就可以模拟表面的几何信息,但是并不真正改变几何

凹凸贴图(Bump Map):

对每一个像素沿着法线位置进行一个高度的扰动。这其实相当于改变了几何,但是并没有增加更多的三角面片。这样的话,就需要计算新的法线:

  • Original surface normal n(p) = (0, 1)
  • Derivative at p is dp = c * [h(p+1) - h(p)]
  • Perturbed normal is then n(p) = (-dp, 1).normalized()

同理,3D空间下的新法线计算:

但是,因为不移动顶点,所以在边缘处的渲染可能并不真实。(只是计算了新法线)

假如移动了顶点,就是位移贴图,会形成:(就是移动了顶点,并且计算了新法线)

预计算Shading

这就相当于提前化了高光和阴影。

posted @ 2024-03-21 13:40  小帆敲代码  阅读(3)  评论(0编辑  收藏  举报