win32-add Pad To Integer view menu option, for help when maximizing or fullscreening to keep from distorting the image non-integerly

This commit is contained in:
zeromus 2013-05-24 08:47:31 +00:00
parent 7a160accc7
commit a093258ec2
3 changed files with 101 additions and 21 deletions

View File

@ -500,6 +500,7 @@ bool romloaded = false;
void SetScreenGap(int gap); void SetScreenGap(int gap);
bool ForceRatio = true; bool ForceRatio = true;
bool PadToInteger = false;
bool SeparationBorderDrag = true; bool SeparationBorderDrag = true;
int ScreenGapColor = 0xFFFFFF; int ScreenGapColor = 0xFFFFFF;
float DefaultWidth; float DefaultWidth;
@ -1093,6 +1094,65 @@ template<typename T> static void doRotate(void* dst)
} }
} }
struct DisplayLayoutInfo
{
int vx,vy,vw,vh;
float widthScale, heightScale;
int bufferWidth, bufferHeight;
};
//performs aspect ratio letterboxing correction and integer clamping
DisplayLayoutInfo CalculateDisplayLayout(RECT rcClient, bool maintainAspect, bool maintainInteger, int targetWidth, int targetHeight)
{
DisplayLayoutInfo ret;
//do maths on the viewport and the native resolution and the user settings to get a display rectangle
SIZE sz = { rcClient.right - rcClient.left, rcClient.bottom - rcClient.top };
float widthScale = (float)sz.cx / targetWidth;
float heightScale = (float)sz.cy / targetHeight;
if(maintainAspect)
{
if(widthScale > heightScale) widthScale = heightScale;
if(heightScale > widthScale) heightScale = widthScale;
}
if(maintainInteger)
{
widthScale = floorf(widthScale);
heightScale = floorf(heightScale);
}
ret.vw = (int)(widthScale * targetWidth);
ret.vh = (int)(heightScale * targetHeight);
ret.vx = (sz.cx - ret.vw)/2;
ret.vy = (sz.cy - ret.vh)/2;
ret.widthScale = widthScale;
ret.heightScale = heightScale;
ret.bufferWidth = sz.cx;
ret.bufferHeight = sz.cy;
return ret;
}
//reformulates CalculateDisplayLayout() into a format more convenient for this purpose
RECT CalculateDisplayLayoutWrapper(RECT rcClient, int targetWidth, int targetHeight, int tbHeight, bool maximized)
{
bool maintainInteger = !!PadToInteger;
bool maintainAspect = !!ForceRatio;
if(maintainInteger) maintainAspect = true;
//nothing to do here if maintain aspect isnt chosen
if(!maintainAspect) return rcClient;
RECT rc = { rcClient.left, rcClient.top + tbHeight, rcClient.right, rcClient.bottom };
DisplayLayoutInfo dli = CalculateDisplayLayout(rc, maintainAspect, maintainInteger, targetWidth, targetHeight);
rc.left = rcClient.left + dli.vx;
rc.top = rcClient.top + dli.vy;
rc.right = rc.left + dli.vw;
rc.bottom = rc.top + dli.vh + tbHeight;
return rc;
}
void UpdateWndRects(HWND hwnd) void UpdateWndRects(HWND hwnd)
{ {
POINT ptClient; POINT ptClient;
@ -1115,9 +1175,10 @@ void UpdateWndRects(HWND hwnd)
tbheight = MainWindowToolbar->GetHeight(); tbheight = MainWindowToolbar->GetHeight();
if (video.layout == 1) //horizontal
if (video.layout == 1)
{ {
rc = CalculateDisplayLayoutWrapper(rc, 512, 192, tbheight, maximized);
wndWidth = (rc.bottom - rc.top) - tbheight; wndWidth = (rc.bottom - rc.top) - tbheight;
wndHeight = (rc.right - rc.left); wndHeight = (rc.right - rc.left);
@ -1150,8 +1211,9 @@ void UpdateWndRects(HWND hwnd)
SubScreenRect.bottom = ptClient.y; SubScreenRect.bottom = ptClient.y;
} }
else else
if (video.layout == 2) if (video.layout == 2) //one screen
{ {
rc = CalculateDisplayLayoutWrapper(rc, 256, 192, tbheight, maximized);
wndWidth = (rc.bottom - rc.top) - tbheight; wndWidth = (rc.bottom - rc.top) - tbheight;
wndHeight = (rc.right - rc.left); wndHeight = (rc.right - rc.left);
@ -1172,8 +1234,18 @@ void UpdateWndRects(HWND hwnd)
MainScreenRect.bottom = ptClient.y; MainScreenRect.bottom = ptClient.y;
} }
else else
if (video.layout == 0) if (video.layout == 0) //vertical
{ {
//apply logic to correct things if forced integer is selected
if((video.rotation == 90) || (video.rotation == 270))
{
rc = CalculateDisplayLayoutWrapper(rc, 384 + video.screengap, 256, tbheight, maximized);
}
else
{
rc = CalculateDisplayLayoutWrapper(rc, 256, 384 + video.screengap, tbheight, maximized);
}
if((video.rotation == 90) || (video.rotation == 270)) if((video.rotation == 90) || (video.rotation == 270))
{ {
wndWidth = (rc.bottom - rc.top) - tbheight; wndWidth = (rc.bottom - rc.top) - tbheight;
@ -1186,6 +1258,7 @@ void UpdateWndRects(HWND hwnd)
} }
ratio = ((float)wndHeight / (float)defHeight); ratio = ((float)wndHeight / (float)defHeight);
oneScreenHeight = (int)((video.height/2) * ratio); oneScreenHeight = (int)((video.height/2) * ratio);
gapHeight = (wndHeight - (oneScreenHeight * 2)); gapHeight = (wndHeight - (oneScreenHeight * 2));
@ -1226,6 +1299,8 @@ void UpdateWndRects(HWND hwnd)
} }
else else
{ {
// Main screen // Main screen
ptClient.x = rc.left; ptClient.x = rc.left;
ptClient.y = rc.top; ptClient.y = rc.top;
@ -2381,14 +2456,16 @@ static BOOL LoadROM(const char * filename, const char * physicalName, const char
Pause(); Pause();
//if (strcmp(filename,"")!=0) INFO("Attempting to load ROM: %s\n",filename); //if (strcmp(filename,"")!=0) INFO("Attempting to load ROM: %s\n",filename);
//since loading a rom can take a long time and happens in the main thread, forcibly display a message here so users dont think it froze
video.clear(); video.clear();
osd->clear(); osd->clear();
osd->addFixed(90, 80, "Loading ROM."); osd->addFixed(70, 80, "Loading ROM.");
osd->addFixed(90, 100, "Please, wait..."); osd->addFixed(70, 100, "Please wait...");
osd->addFixed(90, 192 + 80, "Loading ROM."); osd->addFixed(70, 192 + 80, "Loading ROM.");
osd->addFixed(90, 192 + 100, "Please, wait..."); osd->addFixed(70, 192 + 100, "Please wait...");
bRefreshDisplay = true; bRefreshDisplay = true;
Display(); Display();
if (NDS_LoadROM(filename, physicalName, logicalName) > 0) if (NDS_LoadROM(filename, physicalName, logicalName) > 0)
{ {
INFO("Loading %s was successful\n",logicalName); INFO("Loading %s was successful\n",logicalName);
@ -2938,6 +3015,7 @@ int _main()
video.rotation = GetPrivateProfileInt("Video","Window Rotate", 0, IniName); video.rotation = GetPrivateProfileInt("Video","Window Rotate", 0, IniName);
video.rotation_userset = GetPrivateProfileInt("Video","Window Rotate Set", video.rotation, IniName); video.rotation_userset = GetPrivateProfileInt("Video","Window Rotate Set", video.rotation, IniName);
ForceRatio = GetPrivateProfileBool("Video","Window Force Ratio", 1, IniName); ForceRatio = GetPrivateProfileBool("Video","Window Force Ratio", 1, IniName);
PadToInteger = GetPrivateProfileBool("Video","Window Pad To Integer", 0, IniName);
WndX = GetPrivateProfileInt("Video","WindowPosX", CW_USEDEFAULT, IniName); WndX = GetPrivateProfileInt("Video","WindowPosX", CW_USEDEFAULT, IniName);
WndY = GetPrivateProfileInt("Video","WindowPosY", CW_USEDEFAULT, IniName); WndY = GetPrivateProfileInt("Video","WindowPosY", CW_USEDEFAULT, IniName);
if(WndX < -10000) WndX = CW_USEDEFAULT; // fix for missing window problem if(WndX < -10000) WndX = CW_USEDEFAULT; // fix for missing window problem
@ -4397,6 +4475,7 @@ LRESULT CALLBACK WindowProcedure (HWND hwnd, UINT message, WPARAM wParam, LPARAM
MainWindow->checkMenu(ID_LCDS_SUBGPU, video.swap == 3); MainWindow->checkMenu(ID_LCDS_SUBGPU, video.swap == 3);
//Force Maintain Ratio //Force Maintain Ratio
MainWindow->checkMenu(IDC_FORCERATIO, ((ForceRatio))); MainWindow->checkMenu(IDC_FORCERATIO, ((ForceRatio)));
MainWindow->checkMenu(IDC_VIEW_PADTOINTEGER, ((PadToInteger)));
//Screen rotation //Screen rotation
MainWindow->checkMenu(IDC_ROTATE0, ((video.rotation_userset==0))); MainWindow->checkMenu(IDC_ROTATE0, ((video.rotation_userset==0)));
MainWindow->checkMenu(IDC_ROTATE90, ((video.rotation_userset==90))); MainWindow->checkMenu(IDC_ROTATE90, ((video.rotation_userset==90)));
@ -5941,18 +6020,18 @@ DOKEYDOWN:
WritePrivateProfileInt("Video","Window Size",windowSize,IniName); WritePrivateProfileInt("Video","Window Size",windowSize,IniName);
break; break;
case IDC_FORCERATIO: case IDC_VIEW_PADTOINTEGER:
if (ForceRatio) { PadToInteger = (!PadToInteger)?TRUE:FALSE;
ForceRatio = FALSE; WritePrivateProfileInt("Video","Window Pad To Integer",PadToInteger,IniName);
WritePrivateProfileInt("Video","Window Force Ratio",0,IniName); UpdateWndRects(hwnd);
}
else {
ForceRatio = TRUE;
FixAspectRatio();
WritePrivateProfileInt("Video","Window Force Ratio",1,IniName);
}
break; break;
case IDC_FORCERATIO:
ForceRatio = (!ForceRatio)?TRUE:FALSE;
if(ForceRatio)
FixAspectRatio();
WritePrivateProfileInt("Video","Window Force Ratio",ForceRatio,IniName);
break;
case IDM_DEFSIZE: case IDM_DEFSIZE:
{ {

View File

@ -914,6 +914,7 @@
#define ID_DISPLAYMETHOD_OPENGL_FILTER 40104 #define ID_DISPLAYMETHOD_OPENGL_FILTER 40104
#define IDM_AUTODETECTSAVETYPE_FROMDATABASE 40105 #define IDM_AUTODETECTSAVETYPE_FROMDATABASE 40105
#define ID_DISPLAYMETHOD_FILTER 40106 #define ID_DISPLAYMETHOD_FILTER 40106
#define IDC_VIEW_PADTOINTEGER 40107
#define ID_LABEL_HK3b 44670 #define ID_LABEL_HK3b 44670
#define ID_LABEL_HK3c 44671 #define ID_LABEL_HK3c 44671
#define ID_LABEL_HK3d 44672 #define ID_LABEL_HK3d 44672
@ -1019,7 +1020,7 @@
#ifdef APSTUDIO_INVOKED #ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS #ifndef APSTUDIO_READONLY_SYMBOLS
#define _APS_NEXT_RESOURCE_VALUE 128 #define _APS_NEXT_RESOURCE_VALUE 128
#define _APS_NEXT_COMMAND_VALUE 40106 #define _APS_NEXT_COMMAND_VALUE 40108
#define _APS_NEXT_CONTROL_VALUE 1054 #define _APS_NEXT_CONTROL_VALUE 1054
#define _APS_NEXT_SYMED_VALUE 101 #define _APS_NEXT_SYMED_VALUE 101
#endif #endif

Binary file not shown.