ビューポート変換行列

viewport-matrix.png

正規デバイス座標系1からウィンドウ座標系に変換するための行列
glViewPort(左下x,左下y,width,height)を使っておこなう。大体はこんなかんじで使う

glViewPort(0,0,width,height);

glDepthRange(near,far)という関数でデプスレンジも決められるようだ。デフォルトでは0.0~1.0になっている。
これを使うとデプスバッファへの詰め方が変わるようだ。使ったことないけど。
正規デバイス座標系(NDC)からウィンドウ座標系への変換は線形である。

NDC ウィンドウ座標系 普通はこうする
x -1 x 0
x 1 x+w width
y -1 y 0
y 1 y+h height
z -1 n 0.0
z 1 f 1.0

行列としてまとめるとこうなる

glViewPort(xoff , yoff ,w,h);

と関数の引数を渡したとする

(1)
\begin{align} \left( \begin{array}{c} x_{win}\\ y_{win}\\ z_{win}\\ \end{array} \right) = \left( \begin{array}{cccc} \frac{w}{2}&0&0&(x_{off}+\frac{w}{2})\\ 0&\frac{h}{2}&0&(y_{off}+\frac{h}{2})\\ 0&0&\frac{f-n}{2}&(\frac{f+n}{2})\\ 0&0&0&1 \end{array} \right) \begin{pmatrix} x_{NDC}\\ y_{NDC}\\ z_{NDC}\\ 1 \end{pmatrix} =\begin{pmatrix} \frac{w}{2}x_{NDC}+(x_{off}+\frac{w}{2})\\ \frac{h}{2}y_{NDC}+(y_{off}+\frac{h}{2})\\ \frac{f-n}{2}z_{NDC}+(\frac{f+n}{2})\\ 1 \end{pmatrix} \end{align}

逆変換

(2)
\begin{align} \left[ \begin{array}{cc} x_{ndc} \\ y_{ndc} \\ z_{ndc} \\ w_{ndc}\\ \end{array} \right] = \left[ \begin{array}{cc} \frac{2(x_{win}-x_{off})}{w}-1 \\ \frac{2(y_{win}-y_{off})}{h}-1 \\ \frac{2z_{win}}{f-n}-1 \\ 1\\ \end{array} \right] \end{align}
Bibliography

unproject viewing-pipeline viewport

サポートサイト Wikidot.com unprojectviewing-pipelineviewport