第N次重新推到Camera变换矩阵后的总结

本文总结了Camera变换矩阵的推导过程,包括从View到Orthogonal、Perspective变换,以及从view space到non-NDC orthogonal space的转换。通过详细描述目的和实现方法,帮助理解在DirectX中如何将3D空间的坐标映射到屏幕上的NDC空间,涉及关键步骤如平移、缩放以及视锥台空间的处理。
摘要由CSDN通过智能技术生成

这个轮回我已经做过3次了:写DirectX的API driver,然后纠结几个小时把ViewPerspective给推导一遍。可能还有第4或这第5次,既然如此这次就留点东西,让下次再轮回时少浪费点时间。

前面的废话

这里就不记WorldView了。

orthogonal 变换

  • 目的(简单描述版):把view空间的一个AABB变换到graphics API所处理的NDC(normalized device coordinate)里,不要近大远小,平行的线看起来距离一直不变。
  • 目的(详细描述版,以DX为例):把view空间一个AABB[Min=(-w/2, -h/2, zNear), Max=(w/2,h/2,zFar)]用一个matrix4x4变到DirectX所规定的NDC space[Min=(-1,-1,0),Max=(1,1,1)]里
  • 实现(简单描述版):对AABB先做平移,让原来AABB在zNear的那个面对齐到z=0,然后再缩放,把AABB和NDC的大小对上。结束
  • 实现(详细描述版):对输入坐标(view space坐标)。先乘一个Translate(0, 0, -zNear),再乘一个Scale(2/w,2/h,1/(f-n))。结束

perspective 变换

  • 目的(简单版描述):把view space的AABB变换到graphics API所处理的NDC里,但是有近大远小,也就是说:沿着视线方向直线上的2个点会在屏幕上处于相同位置

  • 目的(详细版):使用一个matrix4x4对输入坐标做变换,具体来说要让输出结果的x/w和y/w对于在同一条视线上的2个点是相同的,并且z/w仍然是随z增大而单调递增,并且视锥台(因为要切掉近平面和eye之间的空间)要能被map到NDC.视锥台空间[Min=(-w/2,-h/2,zNear), Max=(zFarw/(2zNear),zFarh/(2zNear),zFar)]
    -3个空间

  • 实现:perspective变换可以分成2个步骤(1)view space->non-NDC orthogonal space(2)non-NDC orthogonal space->NDC.所谓的non-NDC orthognal space是一个正交空间。所以第2步可以直接用一个orthogonal矩阵,第一步需要另外推算

view space->non-NDC orthogonal space变换

  • 目的(简略版):把view space的视锥台空间变换到AABB space
  • 目的(详细版):znear、zfar的值都不变。视锥台空间的znear到了AABB space还是znear,视锥台空间的zfar到了AABB space 还是zfar。另外视锥台空间的znear完全不变地进入AABB space。变化地地方在于:视锥台空间地zfar平面(以及视锥台内处znear平面上的其他点)都要根据z值来scale XY坐标。要使得同一视线上的点在变换后x/w和y/w都相同.
  • 实现
    • 对于输入点的xy坐标,考虑到z轴上的点(0,0,z)仍然是(0,0,?),所以对于xy坐标的变换是x’ = zNear * x / depth和y’ = zNear * y / depth。由于变换的方式是乘上Matrix4x4再xyz分别除w。所以Matrix4x4上对应xy的scale应该是zNear,所以x’ = zNear * x, y’ = zNear * y. 此时w的计算公式是w’= z
    • 如果矩阵上z的scale是1,那z/w的结果是1,这样深度信息就全没了。由于是Matrix4x4,所以对于z能做的变换顶多是z’ = a * z + b, 此时z’/w’ = a + b/z,这个有2个问题:(1)和z是反相关(2)不再NDC要求的[0,1] range 里。所以要求得一个g(z) = a + b/z,要能让g(zNear) = 0, g(zFar) = 1。求解结果是 a = -f / (n-f), b = f*n/(n-f)
    • 如此便有了view space->non-NDC orthogonal space的变换矩阵

主要推导过程
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值