Reorder two billboard rotations, so they work together correctly.

Fixes #126

# Conflicts:
#	src/gl/scene/gl_sprite.cpp
This commit is contained in:
Christopher Bruns 2016-04-30 16:08:13 -04:00
parent b320787102
commit 5a33005303

View file

@ -282,39 +282,35 @@ void GLSprite::Draw(int pass)
Matrix3x4 mat; Matrix3x4 mat;
mat.MakeIdentity(); mat.MakeIdentity();
mat.Translate(xcenter, zcenter, ycenter); // move to sprite center
// Order of rotations matters. Perform yaw rotation (Y, face camera) before pitch (X, tilt up/down).
if (drawBillboardFacingCamera) {
// [CMB] Rotate relative to camera XY position, not just camera direction,
// which is nicer in VR
float xrel = xcenter - FIXED2FLOAT(GLRenderer->mViewActor->X());
float yrel = ycenter - FIXED2FLOAT(GLRenderer->mViewActor->Y());
float absAngleDeg = RAD2DEG(atan2(-yrel, xrel));
float counterRotationDeg = 270. - float(GLRenderer->mAngles.Yaw); // counteracts existing sprite rotation
float relAngleDeg = counterRotationDeg + absAngleDeg;
mat.Rotate(0, 1, 0, relAngleDeg);
}
if (drawWithXYBillboard) if (drawWithXYBillboard)
{ {
// Rotate the sprite about the vector starting at the center of the sprite // Rotate the sprite about the vector starting at the center of the sprite
// triangle strip and with direction orthogonal to where the player is looking // triangle strip and with direction orthogonal to where the player is looking
// in the x/y plane. // in the x/y plane.
mat.Translate(xcenter, zcenter, ycenter);
mat.Rotate(-sin(angleRad), 0, cos(angleRad), -GLRenderer->mAngles.Pitch.Degrees); mat.Rotate(-sin(angleRad), 0, cos(angleRad), -GLRenderer->mAngles.Pitch.Degrees);
mat.Translate(-xcenter, -zcenter, -ycenter);
} }
mat.Translate(-xcenter, -zcenter, -ycenter); // retreat from sprite center
if (drawBillboardFacingCamera) {
// [CMB] Rotate relative to camera XY position, not just camera direction,
// which is nicer in VR
float xrel = xcenter - FIXED2FLOAT(GLRenderer->mViewActor->X());
float yrel = ycenter - FIXED2FLOAT(GLRenderer->mViewActor->Y());
float zrel = zcenter - FIXED2FLOAT(GLRenderer->mViewActor->Z());
float absAngleDeg = RAD2DEG(atan2(-yrel, xrel));
float counterRotationDeg = 270. - float(GLRenderer->mAngles.Yaw); // counteracts existing sprite rotation
float relAngleDeg = counterRotationDeg + absAngleDeg;
mat.Translate(xcenter, zcenter, ycenter);
mat.Rotate(0, 1, 0, relAngleDeg);
mat.Translate(-xcenter, -zcenter, -ycenter);
}
v1 = mat * Vector(x1, z1, y1); v1 = mat * Vector(x1, z1, y1);
v2 = mat * Vector(x2, z1, y2); v2 = mat * Vector(x2, z1, y2);
v3 = mat * Vector(x1, z2, y1); v3 = mat * Vector(x1, z2, y1);
v4 = mat * Vector(x2, z2, y2); v4 = mat * Vector(x2, z2, y2);
} }
else else // traditional "Y" billboard mode
{ {
v1 = Vector(x1, z1, y1); v1 = Vector(x1, z1, y1);
v2 = Vector(x2, z1, y2); v2 = Vector(x2, z1, y2);