这里回顾GAMES101 Lecture 5,光栅化(三角形的离散化)。

课程主页:

课程作业:

课程视频:

本讲内容:

  • 完成变换
    • 视口(viewpoint)变换
  • 光栅化
    • 不同的光栅显示
    • 光栅化三角形
  • 遮挡和可见性

透视投影

透视投影转换为标准立方体需要知道$l, r,b, t,{f}, {n}$,一般来说说$f, n$为直接给定,而对于$l,r,b,t$,有时人们更喜欢使用垂直视野(field-of-view, fovY)和纵横比(aspect ratio)
(假设对称,即$l = -r, b = -t$),图示如下:

fovY,aspect和$l, r, b,t$的转换关系为:

小结

到目前为止,我们介绍了:

  • 模型变换,model transformation(放置对象)
  • 视图变换,view transformation(放置相机)
  • 投影变换,projection transformation
    • 正交投影(长方体到“规范”立方体$[-1,1]^3$)
    • 透视投影(frustum到“规范”立方体)
  • 下一步是规范立方体到屏幕

规范立方体到屏幕

  • 什么是屏幕?
    • 像素数组
    • 数组大小:分辨率
    • 一种典型的光栅显示
  • 光栅 = 德语屏幕
    • 光栅化 = 在屏幕上绘图
  • 像素(仅供参考,“picture element”的缩写)
    • 到目前为止:一个像素是一个颜色统一的小方块
    • 颜色是(红、绿、蓝)的混合

现在定义屏幕空间:

  • 像素的索引采用$(x, y)$的形式,其中$x$和$y$都是整数
  • 像素的索引从$(0, 0)$到$(width - 1, height - 1)$
  • 像素$(x, y)$以$(x + 0.5, y + 0.5)$为中心
  • 屏幕覆盖范围$(0, 0)$到$(width, height)$

注意到:

  • 屏幕空间和$z$无关
  • 我们的目标是在$xy$平面做变换,将$[-1,1]^2$变换到$[0,width]\times [0, height]$

所以视口(viewpoint)变换为:

图示如下:

下一步:光栅化三角形到像素,即如何在屏幕上画东西。

三角形——形状基元

为什么是三角形?

  • 最基本的多边形
    • 可以分解其他多边形为三角形
  • 独特的属性
    • 保证是平的
    • 明确的内外部
    • 有明确的方法从顶点处插值(重心插值)

接下来的问题是,如何用像素近似三角形:

简单的方式:采样

在一个点上评估函数就是采样,我们可以通过采样来离散化函数:

for (int x = 0; x < xmax; ++x)
	output[x] = f(x);

采样是图形学的核心思想。
我们采样时间(1D)、面积(2D)、方向(2D)、体积(3D)……

对于三角形来说,如果像素中心在三角形内,则采样。定义判断函数inside:

代码:

for (int x = 0; x < xmax; ++x)
    for (int y = 0; y < ymax; ++y)
        image[x][y] = inside(tri, x + 0.5, y + 0.5);

注意到采样点为像素中心。

那么该如何实现inside函数呢?可以利用叉积。对于边界情况,如果一个点在边上,任意选择在三角形内部或者外部都可。

效果:

注意到我们是否要遍历屏幕上所有的点呢?回答是不用,可以找到三角形的bounding box或者每行的bounding box:

光栅化在屏幕上的效果

如果我们在屏幕上展示采样点,那么结果并不是太好,有很明显的锯齿状:

而真实的三角形为:

后续的课程会介绍缓解锯齿问题。