13歳のときからAMOS3Dで遊んでいたので、3Dグラフィックスのコーディング方法を学びたいと思っていました。さて、10年後、私はついにそれを実行するのに十分な数学を蓄積したと思います。
私はさまざまなチュートリアルに従い、screenX(および同等にscreenY)を次のように定義しました。
screenX = (pointX * cameraX) / distance
(さらにオフセットとスケーリング。)
私の問題は、距離変数が実際に何を参照しているかにあります。距離は、カメラとポイントの間のzの差として定義されているのを見てきました。ただし、xとyは、カメラからポイントまでの実際の距離にzと同じ影響を与えるため、これは完全に正しいわけではありません。距離を実際の距離として実装しましたが、結果として、「多すぎる」視点があるかのように、多少歪んだ視点が得られます。
私の「実際の距離」の実装は、次のようなものでした。
distance = new Vector(pointX, pointY, cameraZ - pointZ).magnitude()
コードをいじって、方程式に次のようにperspectiveCoefficientという変数を追加しました。
distance = new Vector(pointX * perspectiveCoefficient,
pointY * perspectiveCoefficient, cameraZ - pointZ).magnitude()
何らかの理由で、それは私を超えています。perspectiveCoefficientを1 / sqrt(2)に設定すると、最良の結果が得られる傾向があります。
私の3Dテストキューブはhttp://vega.soi.city.ac.uk/~abdv866/3dcubetest/3dtest.svgにあります。(SafariとFFでテスト済み。)perspectiveCoefficientの入力を求められます。ここで、0はx / y距離を考慮しないパースペクティブを示し、1はx、y、z距離を等しく考慮したパースペクティブを示します。デフォルトは1/sqrt(2)です。立方体は、矢印キーを使用してxとyを中心に回転できます。(興味のある人は、関連するコードがView.jsファイルのupdate()にあります。)
これに関するアイデアに感謝します。