Я сейчас работаю над трехмерным моделированием гравитации. У меня есть два вектора для представления нормальных векторов верхней и верхней граней куба.
Как чтобы получить эйлеровое вращение этого куба?
Я попытался спроецировать u
и v
на те плоскости, которые используют ось XYZ в качестве нормального вектора и получить угол между осью XYZ и этими спроецированный вектор, чтобы получить вращение вместе с осью XYZ.
rotation.x = Vector.projectOnPlane(
new Vector3f(gravityVec).negate(), //pointing upward
new Vector3f(1, 0, 0)).normalize() //project onto yz-plane
.angle(new Vector3f(0, 1, 0)) //angle to y-axis
rotation.y = Vector.projectOnPlane(
new Vector3f(zDir).negate(), //pointing forward
new Vector3f(0, 1, 0)).normalize() //project onto xz-plane
.angle(new Vector3f(1, 0, 0)) //angle to x-axis
rotation.z = Vector.projectOnPlane(
new Vector3f(gravityVec).negate(), //pointing upward
new Vector3f(0, 0, 1)).normalize() //project onto xy-plane
.angle(new Vector3f(0, 1, 0)) //angle to y-axis
где функция projectOnPlane
равна
public static Vector3f projectOnPlane(Vector3f vec, Vector3f planeNormal)
{//project vec on a plane that use planeNormal as normal vector
return new Vector3f(vec).sub(new Vector3f(vec).mul(new Vector3f(planeNormal))
.div(planeNormal.length() * planeNormal.length()).mul(planeNormal)).normalize();
}
Но это не соответствует моим ожиданиям.
Работает, когда x и z близки к 0 Но когда я переехал в другое место, все пошло не так.
Мои ожидания