クォータニオンを使い始めたばかりですが、クォータニオンを使用して単純な FPS カメラを適切に動作させるのに苦労しています。
基本的に、マウスを動かそうとすると、画面上に描いた三角形が狂ってしまい、目に見えない速さで画面上を移動します。マウスを動かすまで、移動キー (wsad) は期待どおりに機能していますが、その後、すべてが台無しになります。問題はローテーションにあると思いますが、ここ数日間、この問題に頭を悩ませていましたが、役に立ちませんでした。
何が起こっているかのビデオは次のとおりです。Quaternion Test Video
- マウス入力を見るには、最初から見てください。
- キーボード入力 (進む、戻るなど) を表示するには、0:51 秒にスキップします。
参考までに、私が使用している 3 つの主要なクラスを次に示します。
Quaternion.h
CameraSceneNode.h
CameraSceneNode.cpp
最も関連性の高いセクションは、tick()
(回転クォータニオンを更新する場所) とrender()
(シーンの回転と移動で構成される「カメラ」をレンダリングする場所) です。
tick()
メソッドは次のとおりです。
void CameraSceneNode::tick(float32 time) {
// movement direction
if (movement_[MOVE_DIR_FORWARD] == 1)
pos_ += rotation_ * vmath::Vector3f(0, 0, -moveSpeed_ * time);
if (movement_[MOVE_DIR_BACKWARD] == 1)
pos_ += rotation_ * vmath::Vector3f(0, 0, moveSpeed_ * time);
if (movement_[MOVE_DIR_LEFT] == 1)
pos_ += rotation_ * vmath::Vector3f(-moveSpeed_ * time, 0, 0);
if (movement_[MOVE_DIR_RIGHT] == 1)
pos_ += rotation_ * vmath::Vector3f(moveSpeed_ * time, 0, 0);
// rotation
if (xRot_ != 0) {
Quaternion quatRotation = Quaternion();
quatRotation.buildFromAxisAngle(1, 0, 0, (xRot_ * time * rotSpeed_) * math::DEGTORAD);
//quatRotation.normalize();
rotation_ = rotation_ * quatRotation;
xRot_ = 0;
rotation_.normalize();
}
if (yRot_ != 0) {
Quaternion quatRotation = Quaternion();
quatRotation.buildFromAxisAngle(0, 1, 0, (yRot_ * time * rotSpeed_) * math::DEGTORAD);
//quatRotation.normalize();
rotation_ = quatRotation * rotation_;
yRot_ = 0;
rotation_.normalize();
}
}
そしてここにrender()
方法があります:
void CameraSceneNode::render() {
if (isActive()) {
float32 matrix[16];
rotation_.fillMatrix(matrix);
glMultMatrixf(&matrix[0]);
//glRotatef(rotYTest, 0, 1, 0);
//glRotatef(rotXTest, 1, 0, 0);
glTranslatef(-pos_.x, -pos_.y, -pos_.z);
}
}
また、カメラを呼び出す前にrender()
、次のコードを実行します。
glMatrixMode(GL_MODELVIEW);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLoadIdentity();
tick(..)
との両方render()
が、メインのゲーム ループからすべてのフレームで呼び出されます。このクラスには、移動方向とカメラの回転の変更を受け入れる関数がありますCameraSceneNode
(つまり、movement_
バッファ またはxRot_
とを変更しyRot_
ます)。
情報が不十分でしたら申し訳ありません。一部の関数 ( などfillMatrix(..)
) は、上記で参照した 3 つの .h/.cpp ファイルで定義されています。Quaternion クラスを何度か確認しましたが、正しいように見えます。しかし、繰り返しますが、私が使用しているすべてのコードは私には正しいように見えるので、誰が知っていますか:S
私はこれで完全に機知に富んでいます。なぜこれがうまくいかないのか、誰かが光を当てることができれば、とても感謝しています!!
乾杯
ジャレット