Fix a rounding bug that effected screenshots and resolutions.
Previously, you may have gotten values like 639x480 (4:3) or 853x480 (16:9). These are due to rounding errors caused by lrintf; ceilf does what we really want. [RageDisplay.cpp] modified screenshot function [ScreenDimensions] modified SCREEN_WIDTH and SCREEN_HEIGHT algorithms (no longer do you need to SCREEN_WIDTH+1 for 16:9 support) [StepMania.cpp] modified windowed mode width calculation
This commit is contained in:
+25
-29
@@ -15,9 +15,7 @@
|
|||||||
#include "DisplayResolutions.h"
|
#include "DisplayResolutions.h"
|
||||||
#include "arch/ArchHooks/ArchHooks.h"
|
#include "arch/ArchHooks/ArchHooks.h"
|
||||||
|
|
||||||
//
|
|
||||||
// Statistics stuff
|
// Statistics stuff
|
||||||
//
|
|
||||||
RageTimer g_LastCheckTimer;
|
RageTimer g_LastCheckTimer;
|
||||||
int g_iNumVerts;
|
int g_iNumVerts;
|
||||||
int g_iFPS, g_iVPF, g_iCFPS;
|
int g_iFPS, g_iVPF, g_iCFPS;
|
||||||
@@ -145,7 +143,7 @@ void RageDisplay::ResetStats()
|
|||||||
RString RageDisplay::GetStats() const
|
RString RageDisplay::GetStats() const
|
||||||
{
|
{
|
||||||
RString s;
|
RString s;
|
||||||
/* If FPS == 0, we don't have stats yet. */
|
// If FPS == 0, we don't have stats yet.
|
||||||
if( !GetFPS() )
|
if( !GetFPS() )
|
||||||
s = "-- FPS\n-- av FPS\n-- VPF";
|
s = "-- FPS\n-- av FPS\n-- VPF";
|
||||||
|
|
||||||
@@ -182,7 +180,7 @@ void RageDisplay::StatsAddVerts( int iNumVertsRendered ) { g_iVertsRenderedSince
|
|||||||
* angle of the line. */
|
* angle of the line. */
|
||||||
void RageDisplay::DrawPolyLine(const RageSpriteVertex &p1, const RageSpriteVertex &p2, float LineWidth )
|
void RageDisplay::DrawPolyLine(const RageSpriteVertex &p1, const RageSpriteVertex &p2, float LineWidth )
|
||||||
{
|
{
|
||||||
/* soh cah toa strikes strikes again! */
|
// soh cah toa strikes strikes again!
|
||||||
float opp = p2.p.x - p1.p.x;
|
float opp = p2.p.x - p1.p.x;
|
||||||
float adj = p2.p.y - p1.p.y;
|
float adj = p2.p.y - p1.p.y;
|
||||||
float hyp = powf(opp*opp + adj*adj, 0.5f);
|
float hyp = powf(opp*opp + adj*adj, 0.5f);
|
||||||
@@ -215,13 +213,13 @@ void RageDisplay::DrawLineStripInternal( const RageSpriteVertex v[], int iNumVer
|
|||||||
{
|
{
|
||||||
ASSERT( iNumVerts >= 2 );
|
ASSERT( iNumVerts >= 2 );
|
||||||
|
|
||||||
/* Draw a line strip with rounded corners using polys. This is used on
|
/* Draw a line strip with rounded corners using polys. This is used on
|
||||||
* cards that have strange allergic reactions to antialiased points and
|
* cards that have strange allergic reactions to antialiased points and
|
||||||
* lines. */
|
* lines. */
|
||||||
for( int i = 0; i < iNumVerts-1; ++i )
|
for( int i = 0; i < iNumVerts-1; ++i )
|
||||||
DrawPolyLine(v[i], v[i+1], LineWidth);
|
DrawPolyLine(v[i], v[i+1], LineWidth);
|
||||||
|
|
||||||
/* Join the lines with circles so we get rounded corners. */
|
// Join the lines with circles so we get rounded corners.
|
||||||
for( int i = 0; i < iNumVerts; ++i )
|
for( int i = 0; i < iNumVerts; ++i )
|
||||||
DrawCircle( v[i], LineWidth/2 );
|
DrawCircle( v[i], LineWidth/2 );
|
||||||
}
|
}
|
||||||
@@ -246,7 +244,6 @@ void RageDisplay::DrawCircleInternal( const RageSpriteVertex &p, float radius )
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void RageDisplay::SetDefaultRenderStates()
|
void RageDisplay::SetDefaultRenderStates()
|
||||||
{
|
{
|
||||||
SetLighting( false );
|
SetLighting( false );
|
||||||
@@ -261,9 +258,7 @@ void RageDisplay::SetDefaultRenderStates()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//
|
|
||||||
// Matrix stuff
|
// Matrix stuff
|
||||||
//
|
|
||||||
class MatrixStack
|
class MatrixStack
|
||||||
{
|
{
|
||||||
vector<RageMatrix> stack;
|
vector<RageMatrix> stack;
|
||||||
@@ -279,14 +274,14 @@ public:
|
|||||||
void Pop()
|
void Pop()
|
||||||
{
|
{
|
||||||
stack.pop_back();
|
stack.pop_back();
|
||||||
ASSERT( stack.size() > 0 ); // underflow
|
ASSERT( stack.size() > 0 ); // underflow
|
||||||
}
|
}
|
||||||
|
|
||||||
// Pushes the stack by one, duplicating the current matrix.
|
// Pushes the stack by one, duplicating the current matrix.
|
||||||
void Push()
|
void Push()
|
||||||
{
|
{
|
||||||
stack.push_back( stack.back() );
|
stack.push_back( stack.back() );
|
||||||
ASSERT( stack.size() < 100 ); // overflow
|
ASSERT( stack.size() < 100 ); // overflow
|
||||||
}
|
}
|
||||||
|
|
||||||
// Loads identity in the current matrix.
|
// Loads identity in the current matrix.
|
||||||
@@ -555,7 +550,7 @@ void RageDisplay::TextureTranslate( float x, float y )
|
|||||||
|
|
||||||
void RageDisplay::LoadMenuPerspective( float fovDegrees, float fWidth, float fHeight, float fVanishPointX, float fVanishPointY )
|
void RageDisplay::LoadMenuPerspective( float fovDegrees, float fWidth, float fHeight, float fVanishPointX, float fVanishPointY )
|
||||||
{
|
{
|
||||||
/* fovDegrees == 0 gives ortho projection. */
|
// fovDegrees == 0 gives ortho projection.
|
||||||
if( fovDegrees == 0 )
|
if( fovDegrees == 0 )
|
||||||
{
|
{
|
||||||
float left = 0, right = fWidth, bottom = fHeight, top = 0;
|
float left = 0, right = fWidth, bottom = fHeight, top = 0;
|
||||||
@@ -575,8 +570,7 @@ void RageDisplay::LoadMenuPerspective( float fovDegrees, float fWidth, float fHe
|
|||||||
fVanishPointX -= fWidth/2;
|
fVanishPointX -= fWidth/2;
|
||||||
fVanishPointY -= fHeight/2;
|
fVanishPointY -= fHeight/2;
|
||||||
|
|
||||||
|
// It's the caller's responsibility to push first.
|
||||||
/* It's the caller's responsibility to push first. */
|
|
||||||
g_ProjectionStack.LoadMatrix(
|
g_ProjectionStack.LoadMatrix(
|
||||||
GetFrustumMatrix(
|
GetFrustumMatrix(
|
||||||
(fVanishPointX-fWidth/2)/fDistCameraFromImage,
|
(fVanishPointX-fWidth/2)/fDistCameraFromImage,
|
||||||
@@ -608,14 +602,14 @@ void RageDisplay::CameraPopMatrix()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* gluLookAt. The result is pre-multiplied to the matrix (M = L * M) instead of
|
/* gluLookAt. The result is pre-multiplied to the matrix (M = L * M) instead of
|
||||||
* post-multiplied. */
|
* post-multiplied. */
|
||||||
void RageDisplay::LoadLookAt( float fFOV, const RageVector3 &Eye, const RageVector3 &At, const RageVector3 &Up )
|
void RageDisplay::LoadLookAt( float fFOV, const RageVector3 &Eye, const RageVector3 &At, const RageVector3 &Up )
|
||||||
{
|
{
|
||||||
float fAspect = GetActualVideoModeParams().fDisplayAspectRatio;
|
float fAspect = GetActualVideoModeParams().fDisplayAspectRatio;
|
||||||
g_ProjectionStack.LoadMatrix( GetPerspectiveMatrix(fFOV, fAspect, 1, 1000) );
|
g_ProjectionStack.LoadMatrix( GetPerspectiveMatrix(fFOV, fAspect, 1, 1000) );
|
||||||
|
|
||||||
/* Flip the Y coordinate, so positive numbers go down. */
|
// Flip the Y coordinate, so positive numbers go down.
|
||||||
g_ProjectionStack.Scale( 1, -1, 1 );
|
g_ProjectionStack.Scale( 1, -1, 1 );
|
||||||
|
|
||||||
g_ViewStack.LoadMatrix( RageLookAt(Eye.x, Eye.y, Eye.z, At.x, At.y, At.z, Up.x, Up.y, Up.z) );
|
g_ViewStack.LoadMatrix( RageLookAt(Eye.x, Eye.y, Eye.z, At.x, At.y, At.z, Up.x, Up.y, Up.z) );
|
||||||
@@ -624,12 +618,12 @@ void RageDisplay::LoadLookAt( float fFOV, const RageVector3 &Eye, const RageVect
|
|||||||
|
|
||||||
RageMatrix RageDisplay::GetPerspectiveMatrix(float fovy, float aspect, float zNear, float zFar)
|
RageMatrix RageDisplay::GetPerspectiveMatrix(float fovy, float aspect, float zNear, float zFar)
|
||||||
{
|
{
|
||||||
float ymax = zNear * tanf(fovy * PI / 360.0f);
|
float ymax = zNear * tanf(fovy * PI / 360.0f);
|
||||||
float ymin = -ymax;
|
float ymin = -ymax;
|
||||||
float xmin = ymin * aspect;
|
float xmin = ymin * aspect;
|
||||||
float xmax = ymax * aspect;
|
float xmax = ymax * aspect;
|
||||||
|
|
||||||
return GetFrustumMatrix(xmin, xmax, ymin, ymax, zNear, zFar);
|
return GetFrustumMatrix(xmin, xmax, ymin, ymax, zNear, zFar);
|
||||||
}
|
}
|
||||||
|
|
||||||
RageSurface *RageDisplay::CreateSurfaceFromPixfmt( PixelFormat pixfmt,
|
RageSurface *RageDisplay::CreateSurfaceFromPixfmt( PixelFormat pixfmt,
|
||||||
@@ -663,9 +657,9 @@ PixelFormat RageDisplay::FindPixelFormat( int iBPP, int iRmask, int iGmask, int
|
|||||||
return PixelFormat_Invalid;
|
return PixelFormat_Invalid;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* These convert to OpenGL's coordinate system: -1,-1 is the bottom-left, +1,+1 is the
|
/* These convert to OpenGL's coordinate system: -1,-1 is the bottom-left,
|
||||||
* top-right, and Z goes from -1 (viewer) to +1 (distance). It's a little odd, but
|
* +1,+1 is the top-right, and Z goes from -1 (viewer) to +1 (distance).
|
||||||
* very well-defined. */
|
* It's a little odd, but very well-defined. */
|
||||||
RageMatrix RageDisplay::GetOrthoMatrix( float l, float r, float b, float t, float zn, float zf )
|
RageMatrix RageDisplay::GetOrthoMatrix( float l, float r, float b, float t, float zn, float zf )
|
||||||
{
|
{
|
||||||
RageMatrix m(
|
RageMatrix m(
|
||||||
@@ -693,20 +687,20 @@ RageMatrix RageDisplay::GetFrustumMatrix( float l, float r, float b, float t, fl
|
|||||||
|
|
||||||
void RageDisplay::ResolutionChanged()
|
void RageDisplay::ResolutionChanged()
|
||||||
{
|
{
|
||||||
/* The centering matrix depends on the resolution. */
|
// The centering matrix depends on the resolution.
|
||||||
UpdateCentering();
|
UpdateCentering();
|
||||||
}
|
}
|
||||||
|
|
||||||
void RageDisplay::CenteringPushMatrix()
|
void RageDisplay::CenteringPushMatrix()
|
||||||
{
|
{
|
||||||
g_CenteringStack.push_back( g_CenteringStack.back() );
|
g_CenteringStack.push_back( g_CenteringStack.back() );
|
||||||
ASSERT( g_CenteringStack.size() < 100 ); // overflow
|
ASSERT( g_CenteringStack.size() < 100 ); // overflow
|
||||||
}
|
}
|
||||||
|
|
||||||
void RageDisplay::CenteringPopMatrix()
|
void RageDisplay::CenteringPopMatrix()
|
||||||
{
|
{
|
||||||
g_CenteringStack.pop_back();
|
g_CenteringStack.pop_back();
|
||||||
ASSERT( g_CenteringStack.size() > 0 ); // underflow
|
ASSERT( g_CenteringStack.size() > 0 ); // underflow
|
||||||
UpdateCentering();
|
UpdateCentering();
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -761,10 +755,12 @@ bool RageDisplay::SaveScreenshot( RString sPath, GraphicsFileFormat format )
|
|||||||
* screenshots in a strange (non-1) sample aspect ratio. */
|
* screenshots in a strange (non-1) sample aspect ratio. */
|
||||||
if( format != SAVE_LOSSLESS && format != SAVE_LOSSLESS_SENSIBLE )
|
if( format != SAVE_LOSSLESS && format != SAVE_LOSSLESS_SENSIBLE )
|
||||||
{
|
{
|
||||||
/* Maintain the DAR. */
|
// Maintain the DAR.
|
||||||
ASSERT( GetActualVideoModeParams().fDisplayAspectRatio > 0 );
|
ASSERT( GetActualVideoModeParams().fDisplayAspectRatio > 0 );
|
||||||
int iHeight = 480;
|
int iHeight = 480;
|
||||||
int iWidth = lrintf( iHeight * GetActualVideoModeParams().fDisplayAspectRatio );
|
// This used to be lrintf. However, lrintf causes odd resolutions like
|
||||||
|
// 639x480 (4:3) and 853x480 (16:9). ceilf gives correct values. -aj
|
||||||
|
int iWidth = ceilf( iHeight * GetActualVideoModeParams().fDisplayAspectRatio );
|
||||||
timer.Touch();
|
timer.Touch();
|
||||||
RageSurfaceUtils::Zoom( surface, iWidth, iHeight );
|
RageSurfaceUtils::Zoom( surface, iWidth, iHeight );
|
||||||
// LOG->Trace( "%ix%i -> %ix%i (%.3f) in %f seconds", surface->w, surface->h, iWidth, iHeight, GetActualVideoModeParams().fDisplayAspectRatio, timer.GetDeltaTime() );
|
// LOG->Trace( "%ix%i -> %ix%i (%.3f) in %f seconds", surface->w, surface->h, iWidth, iHeight, GetActualVideoModeParams().fDisplayAspectRatio, timer.GetDeltaTime() );
|
||||||
|
|||||||
@@ -25,6 +25,9 @@ float ScreenDimensions::GetThemeAspectRatio()
|
|||||||
return THEME_NATIVE_ASPECT;
|
return THEME_NATIVE_ASPECT;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ceilf was originally lrintf. However, lrintf causes odd resolutions like
|
||||||
|
// 639x480 (4:3) and 853x480 (16:9). ceilf gives the correct values of 640x480
|
||||||
|
// and 854x480 respectively. -aj
|
||||||
float ScreenDimensions::GetScreenWidth()
|
float ScreenDimensions::GetScreenWidth()
|
||||||
{
|
{
|
||||||
float fAspect = PREFSMAN->m_fDisplayAspectRatio;
|
float fAspect = PREFSMAN->m_fDisplayAspectRatio;
|
||||||
@@ -32,7 +35,7 @@ float ScreenDimensions::GetScreenWidth()
|
|||||||
if( fAspect > THEME_NATIVE_ASPECT )
|
if( fAspect > THEME_NATIVE_ASPECT )
|
||||||
fScale = fAspect / THEME_NATIVE_ASPECT;
|
fScale = fAspect / THEME_NATIVE_ASPECT;
|
||||||
ASSERT( fScale >= 1 );
|
ASSERT( fScale >= 1 );
|
||||||
return (float) lrintf(THEME_SCREEN_WIDTH * fScale);
|
return (float) ceilf(THEME_SCREEN_WIDTH * fScale);
|
||||||
}
|
}
|
||||||
|
|
||||||
float ScreenDimensions::GetScreenHeight()
|
float ScreenDimensions::GetScreenHeight()
|
||||||
@@ -42,7 +45,7 @@ float ScreenDimensions::GetScreenHeight()
|
|||||||
if( fAspect < THEME_NATIVE_ASPECT )
|
if( fAspect < THEME_NATIVE_ASPECT )
|
||||||
fScale = THEME_NATIVE_ASPECT / fAspect;
|
fScale = THEME_NATIVE_ASPECT / fAspect;
|
||||||
ASSERT( fScale >= 1 );
|
ASSERT( fScale >= 1 );
|
||||||
return (float) lrintf(THEME_SCREEN_HEIGHT * fScale);
|
return (float) ceilf(THEME_SCREEN_HEIGHT * fScale);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ScreenDimensions::ReloadScreenDimensions()
|
void ScreenDimensions::ReloadScreenDimensions()
|
||||||
|
|||||||
+3
-5
@@ -103,11 +103,9 @@ void StepMania::GetPreferredVideoModeParams( VideoModeParams ¶msOut )
|
|||||||
int iWidth = PREFSMAN->m_iDisplayWidth;
|
int iWidth = PREFSMAN->m_iDisplayWidth;
|
||||||
if( PREFSMAN->m_bWindowed )
|
if( PREFSMAN->m_bWindowed )
|
||||||
{
|
{
|
||||||
/*
|
//float fRatio = PREFSMAN->m_iDisplayWidth / PREFSMAN->m_iDisplayHeight;
|
||||||
float fRatio = PREFSMAN->m_iDisplayWidth / PREFSMAN->m_iDisplayHeight;
|
//iWidth = PREFSMAN->m_iDisplayHeight * fRatio;
|
||||||
iWidth = PREFSMAN->m_iDisplayHeight * fRatio;
|
iWidth = ceilf(PREFSMAN->m_iDisplayHeight * PREFSMAN->m_fDisplayAspectRatio);
|
||||||
*/
|
|
||||||
iWidth = PREFSMAN->m_iDisplayHeight * PREFSMAN->m_fDisplayAspectRatio;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
paramsOut = VideoModeParams(
|
paramsOut = VideoModeParams(
|
||||||
|
|||||||
Reference in New Issue
Block a user