From 19bf2b9eb6c6d92a31a864313f6434dd693f83a1 Mon Sep 17 00:00:00 2001 From: Alejandro Marzini Date: Fri, 3 Sep 2010 03:23:46 +0000 Subject: OPENGL: Improve scaling, aspect ratio correction and display(GFX) modes. Now the previous aspect ratio modes are handled as GFX modes. The previous GFX modes were for scaling, but are removed now. A new 4/3 display mode added. Added Ctrl-Shift-A for backward switching through display modes, and Ctrl-Alt- for switching to a specific GFX mode. Window resizing now is available for all display modes, and will automatically change the scale factor as well as maintain the aspect ratio when needed. svn-id: r52501 --- backends/graphics/opengl/opengl-graphics.cpp | 170 +++++------ backends/graphics/opengl/opengl-graphics.h | 34 +-- backends/graphics/openglsdl/openglsdl-graphics.cpp | 316 ++++++++++++--------- backends/graphics/openglsdl/openglsdl-graphics.h | 15 +- 4 files changed, 284 insertions(+), 251 deletions(-) (limited to 'backends/graphics') diff --git a/backends/graphics/opengl/opengl-graphics.cpp b/backends/graphics/opengl/opengl-graphics.cpp index f1b6cdd410..a920aaffbf 100644 --- a/backends/graphics/opengl/opengl-graphics.cpp +++ b/backends/graphics/opengl/opengl-graphics.cpp @@ -48,17 +48,16 @@ OpenGLGraphicsManager::OpenGLGraphicsManager() _cursorVisible(false), _cursorKeyColor(0), _cursorTargetScale(1), _formatBGR(false), - _aspectX(0), _aspectY(0), _aspectWidth(0), _aspectHeight(0) { + _displayX(0), _displayY(0), _displayWidth(0), _displayHeight(0) { memset(&_oldVideoMode, 0, sizeof(_oldVideoMode)); memset(&_videoMode, 0, sizeof(_videoMode)); memset(&_transactionDetails, 0, sizeof(_transactionDetails)); - _videoMode.mode = OpenGL::GFX_DOUBLESIZE; + _videoMode.mode = OpenGL::GFX_NORMAL; _videoMode.scaleFactor = 2; _videoMode.fullscreen = ConfMan.getBool("fullscreen"); _videoMode.antialiasing = false; - _videoMode.aspectRatioCorrection = ConfMan.getBool("aspect_ratio") ? kAspectRatioConserve : kAspectRatioNone; _gamePalette = (byte *)calloc(sizeof(byte) * 4, 256); _cursorPalette = (byte *)calloc(sizeof(byte) * 4, 256); @@ -96,7 +95,7 @@ bool OpenGLGraphicsManager::hasFeature(OSystem::Feature f) { void OpenGLGraphicsManager::setFeatureState(OSystem::Feature f, bool enable) { switch (f) { case OSystem::kFeatureAspectRatioCorrection: - setAspectRatioCorrection(enable ? -1 : 0); + setGraphicsMode(enable ? OpenGL::GFX_CONSERVE : OpenGL::GFX_NORMAL); break; default: break; @@ -112,11 +111,10 @@ bool OpenGLGraphicsManager::getFeatureState(OSystem::Feature f) { // static const OSystem::GraphicsMode s_supportedGraphicsModes[] = { - {"gl1x", _s("OpenGL Normal"), OpenGL::GFX_NORMAL}, -#ifdef USE_SCALERS - {"gl2x", "OpenGL 2x", OpenGL::GFX_DOUBLESIZE}, - {"gl3x", "OpenGL 3x", OpenGL::GFX_TRIPLESIZE}, -#endif + {"gl1", _s("OpenGL Normal"), OpenGL::GFX_NORMAL}, + {"gl2", _s("OpenGL Conserve"), OpenGL::GFX_CONSERVE}, + {"gl3", _s("OpenGL 4/3"), OpenGL::GFX_4_3}, + {"gl4", _s("OpenGL Original"), OpenGL::GFX_ORIGINAL}, {0, 0, 0} }; @@ -138,32 +136,19 @@ bool OpenGLGraphicsManager::setGraphicsMode(int mode) { if (_oldVideoMode.setup && _oldVideoMode.mode == mode) return true; - int newScaleFactor = 1; - switch (mode) { case OpenGL::GFX_NORMAL: - newScaleFactor = 1; - break; -#ifdef USE_SCALERS - case OpenGL::GFX_DOUBLESIZE: - newScaleFactor = 2; + case OpenGL::GFX_CONSERVE: + case OpenGL::GFX_4_3: + case OpenGL::GFX_ORIGINAL: break; - case OpenGL::GFX_TRIPLESIZE: - newScaleFactor = 3; - break; -#endif default: warning("unknown gfx mode %d", mode); return false; } - if (_oldVideoMode.setup && _oldVideoMode.scaleFactor != newScaleFactor) - _transactionDetails.needRefresh = true; - - _transactionDetails.needUpdatescreen = true; - _videoMode.mode = mode; - _videoMode.scaleFactor = newScaleFactor; + _transactionDetails.needRefresh = true; return true; } @@ -248,10 +233,6 @@ OSystem::TransactionError OpenGLGraphicsManager::endGFXTransaction() { errors |= OSystem::kTransactionFullscreenFailed; _videoMode.fullscreen = _oldVideoMode.fullscreen; - } else if (_videoMode.aspectRatioCorrection != _oldVideoMode.aspectRatioCorrection) { - errors |= OSystem::kTransactionAspectRatioFailed; - - _videoMode.aspectRatioCorrection = _oldVideoMode.aspectRatioCorrection; } else if (_videoMode.mode != _oldVideoMode.mode) { errors |= OSystem::kTransactionModeSwitchFailed; @@ -274,7 +255,6 @@ OSystem::TransactionError OpenGLGraphicsManager::endGFXTransaction() { } if (_videoMode.fullscreen == _oldVideoMode.fullscreen && - _videoMode.aspectRatioCorrection == _oldVideoMode.aspectRatioCorrection && _videoMode.mode == _oldVideoMode.mode && _videoMode.screenWidth == _oldVideoMode.screenWidth && _videoMode.screenHeight == _oldVideoMode.screenHeight) { @@ -818,7 +798,7 @@ void OpenGLGraphicsManager::refreshCursorScale() { _videoMode.hardwareHeight * 10000 / _videoMode.screenHeight); // Do not scale cursor if original size is used - if (_videoMode.aspectRatioCorrection == kAspectRatioOriginal) + if (_videoMode.mode == OpenGL::GFX_ORIGINAL) screenScaleFactor = _videoMode.scaleFactor * 10000; if ((uint)_cursorTargetScale * 10000 >= screenScaleFactor && (uint)_videoMode.scaleFactor * 10000 >= screenScaleFactor) { @@ -845,27 +825,31 @@ void OpenGLGraphicsManager::refreshCursorScale() { _cursorState.vHotY = (int16)(_cursorState.hotY * screenScaleFactor / 10000); } -void OpenGLGraphicsManager::refreshAspectRatio() { - if (_videoMode.aspectRatioCorrection == kAspectRatioOriginal) { - _aspectWidth = _videoMode.overlayWidth; - _aspectHeight = _videoMode.overlayHeight; +void OpenGLGraphicsManager::calculateDisplaySize(int &width, int &height) { + if (_videoMode.mode == OpenGL::GFX_ORIGINAL) { + width = _videoMode.overlayWidth; + height = _videoMode.overlayHeight; } else { - _aspectWidth = _videoMode.hardwareWidth; - _aspectHeight = _videoMode.hardwareHeight; + width = _videoMode.hardwareWidth; + height = _videoMode.hardwareHeight; - uint aspectRatio = _videoMode.hardwareWidth * 10000 / _videoMode.hardwareHeight; + uint aspectRatio = (_videoMode.hardwareWidth * 10000 + 5000) / _videoMode.hardwareHeight; uint desiredAspectRatio = getAspectRatio(); // Adjust one screen dimension for mantaining the aspect ratio if (aspectRatio < desiredAspectRatio) - _aspectHeight = _aspectWidth * 10000 / desiredAspectRatio; + height = (width * 10000 + 5000) / desiredAspectRatio; else if (aspectRatio > desiredAspectRatio) - _aspectWidth = _aspectHeight * desiredAspectRatio / 10000; + width = (height * desiredAspectRatio + 5000) / 10000; } +} + +void OpenGLGraphicsManager::refreshDisplaySize() { + calculateDisplaySize(_displayWidth, _displayHeight); // Adjust x and y for centering the screen - _aspectX = (_videoMode.hardwareWidth - _aspectWidth) / 2; - _aspectY = (_videoMode.hardwareHeight - _aspectHeight) / 2; + _displayX = (_videoMode.hardwareWidth - _displayWidth) / 2; + _displayY = (_videoMode.hardwareHeight - _displayHeight) / 2; } void OpenGLGraphicsManager::getGLPixelFormat(Graphics::PixelFormat pixelFormat, byte &bpp, GLenum &intFormat, GLenum &glFormat, GLenum &gltype) { @@ -969,7 +953,7 @@ void OpenGLGraphicsManager::internUpdateScreen() { glTranslatef(0, _shakePos * scaleFactor, 0); CHECK_GL_ERROR(); // Draw the game screen - _gameTexture->drawTexture(_aspectX, _aspectY, _aspectWidth, _aspectHeight); + _gameTexture->drawTexture(_displayX, _displayY, _displayWidth, _displayHeight); glPopMatrix(); @@ -979,7 +963,7 @@ void OpenGLGraphicsManager::internUpdateScreen() { refreshOverlay(); // Draw the overlay - _overlayTexture->drawTexture(_aspectX, _aspectY, _aspectWidth, _aspectHeight); + _overlayTexture->drawTexture(_displayX, _displayY, _displayWidth, _displayHeight); } if (_cursorVisible) { @@ -1146,7 +1130,7 @@ bool OpenGLGraphicsManager::loadGFXMode() { refreshCursorScale(); - refreshAspectRatio(); + refreshDisplaySize(); internUpdateScreen(); @@ -1161,52 +1145,15 @@ void OpenGLGraphicsManager::setScale(int newScale) { if (newScale == _videoMode.scaleFactor) return; - switch (newScale - 1) { - case OpenGL::GFX_NORMAL: - _videoMode.mode = OpenGL::GFX_NORMAL; - break; - case OpenGL::GFX_DOUBLESIZE: - _videoMode.mode = OpenGL::GFX_DOUBLESIZE; - break; - case OpenGL::GFX_TRIPLESIZE: - _videoMode.mode = OpenGL::GFX_TRIPLESIZE; - break; - } - _videoMode.scaleFactor = newScale; _transactionDetails.sizeChanged = true; } -void OpenGLGraphicsManager::setAspectRatioCorrection(int mode) { - if (_oldVideoMode.setup && _oldVideoMode.aspectRatioCorrection == mode) - return; - - if (_transactionMode == kTransactionActive) { - if (mode == -1) - // If -1, switch to next mode - _videoMode.aspectRatioCorrection = (_videoMode.aspectRatioCorrection + 1) % 3; - else - _videoMode.aspectRatioCorrection = mode; - _transactionDetails.needRefresh = true; - } -} - -Common::String OpenGLGraphicsManager::getAspectRatioName() { - switch (_videoMode.aspectRatioCorrection) { - case kAspectRatioNone: - return "None"; - case kAspectRatioConserve: - return "Conserve"; - case kAspectRatioOriginal: - return "Original"; - default: - return ""; - } -} - uint OpenGLGraphicsManager::getAspectRatio() { - if (_videoMode.aspectRatioCorrection == kAspectRatioNone) + if (_videoMode.mode == OpenGL::GFX_NORMAL) return _videoMode.hardwareWidth * 10000 / _videoMode.hardwareHeight; + else if (_videoMode.mode == OpenGL::GFX_4_3) + return 13333; else return _videoMode.screenWidth * 10000 / _videoMode.screenHeight; } @@ -1216,7 +1163,7 @@ void OpenGLGraphicsManager::adjustMouseEvent(const Common::Event &event) { Common::Event newEvent(event); newEvent.synthetic = true; - if (!_videoMode.aspectRatioCorrection) { + if (_videoMode.mode == OpenGL::GFX_NORMAL) { if (_videoMode.hardwareWidth != _videoMode.overlayWidth) newEvent.mouse.x = newEvent.mouse.x * _videoMode.overlayWidth / _videoMode.hardwareWidth; if (_videoMode.hardwareHeight != _videoMode.overlayHeight) @@ -1228,19 +1175,19 @@ void OpenGLGraphicsManager::adjustMouseEvent(const Common::Event &event) { } } else { - newEvent.mouse.x -= _aspectX; - newEvent.mouse.y -= _aspectY; + newEvent.mouse.x -= _displayX; + newEvent.mouse.y -= _displayY; if (_overlayVisible) { - if (_aspectWidth != _videoMode.overlayWidth) - newEvent.mouse.x = newEvent.mouse.x * _videoMode.overlayWidth / _aspectWidth; - if (_aspectHeight != _videoMode.overlayHeight) - newEvent.mouse.y = newEvent.mouse.y * _videoMode.overlayHeight / _aspectHeight; + if (_displayWidth != _videoMode.overlayWidth) + newEvent.mouse.x = newEvent.mouse.x * _videoMode.overlayWidth / _displayWidth; + if (_displayHeight != _videoMode.overlayHeight) + newEvent.mouse.y = newEvent.mouse.y * _videoMode.overlayHeight / _displayHeight; } else { - if (_aspectWidth != _videoMode.screenWidth) - newEvent.mouse.x = newEvent.mouse.x * _videoMode.screenWidth / _aspectWidth; - if (_aspectHeight != _videoMode.screenHeight) - newEvent.mouse.y = newEvent.mouse.y * _videoMode.screenHeight / _aspectHeight; + if (_displayWidth != _videoMode.screenWidth) + newEvent.mouse.x = newEvent.mouse.x * _videoMode.screenWidth / _displayWidth; + if (_displayHeight != _videoMode.screenHeight) + newEvent.mouse.y = newEvent.mouse.y * _videoMode.screenHeight / _displayHeight; } } @@ -1320,4 +1267,33 @@ bool OpenGLGraphicsManager::saveScreenshot(const char *filename) { return true; } +const char *OpenGLGraphicsManager::getCurrentModeName() { + const char *modeName = 0; + const OSystem::GraphicsMode *g = getSupportedGraphicsModes(); + while (g->name) { + if (g->id == _videoMode.mode) { + modeName = g->description; + break; + } + g++; + } + return modeName; +} + +void OpenGLGraphicsManager::switchDisplayMode(int mode) { + if (_oldVideoMode.setup && _oldVideoMode.mode == mode) + return; + + if (_transactionMode == kTransactionActive) { + if (mode == -1) // If -1, switch to next mode + _videoMode.mode = (_videoMode.mode + 1) % 4; + else if (mode == -2) // If -2, switch to previous mode + _videoMode.mode = (_videoMode.mode + 3) % 4; + else + _videoMode.mode = mode; + + _transactionDetails.needRefresh = true; + } +} + #endif diff --git a/backends/graphics/opengl/opengl-graphics.h b/backends/graphics/opengl/opengl-graphics.h index 715f85dd6a..f4e26f43ec 100644 --- a/backends/graphics/opengl/opengl-graphics.h +++ b/backends/graphics/opengl/opengl-graphics.h @@ -38,8 +38,9 @@ namespace OpenGL { // do not clash with the SDL GFX modes. enum { GFX_NORMAL = 0, - GFX_DOUBLESIZE = 1, - GFX_TRIPLESIZE = 2 + GFX_CONSERVE = 1, + GFX_4_3 = 2, + GFX_ORIGINAL = 3 }; } @@ -141,18 +142,11 @@ protected: TransactionDetails _transactionDetails; int _transactionMode; - enum { - kAspectRatioNone, - kAspectRatioConserve, - kAspectRatioOriginal - }; - struct VideoState { bool setup; bool fullscreen; int activeFullscreenMode; - int aspectRatioCorrection; int mode; int scaleFactor; @@ -178,20 +172,22 @@ protected: virtual void setScale(int newScale); - // Drawing coordinates for the current aspect ratio - int _aspectX; - int _aspectY; - int _aspectWidth; - int _aspectHeight; + // Drawing coordinates for the current display mode and scale + int _displayX; + int _displayY; + int _displayWidth; + int _displayHeight; /** - * Sets the aspect ratio mode. - * @mode the aspect ratio mode, if -1 it will switch to next mode. + * Sets the dispaly mode. + * @mode the dispaly mode, if -1 it will switch to next mode. If -2 to previous mode. */ - virtual void setAspectRatioCorrection(int mode); + virtual void switchDisplayMode(int mode); + + virtual const char *getCurrentModeName(); - virtual void refreshAspectRatio(); - virtual Common::String getAspectRatioName(); + virtual void calculateDisplaySize(int &width, int &height); + virtual void refreshDisplaySize(); /** * Returns the current target aspect ratio x 10000 diff --git a/backends/graphics/openglsdl/openglsdl-graphics.cpp b/backends/graphics/openglsdl/openglsdl-graphics.cpp index 0018d0115d..c10dbf0d8f 100644 --- a/backends/graphics/openglsdl/openglsdl-graphics.cpp +++ b/backends/graphics/openglsdl/openglsdl-graphics.cpp @@ -191,7 +191,7 @@ void OpenGLSdlGraphicsManager::warpMouse(int x, int y) { int scaledX = x; int scaledY = y; - if (!_videoMode.aspectRatioCorrection) { + if (_videoMode.mode == OpenGL::GFX_NORMAL) { if (_videoMode.hardwareWidth != _videoMode.overlayWidth) scaledX = scaledX * _videoMode.hardwareWidth / _videoMode.overlayWidth; if (_videoMode.hardwareHeight != _videoMode.overlayHeight) @@ -203,19 +203,19 @@ void OpenGLSdlGraphicsManager::warpMouse(int x, int y) { } } else { if (_overlayVisible) { - if (_aspectWidth != _videoMode.overlayWidth) - scaledX = scaledX * _aspectWidth / _videoMode.overlayWidth; - if (_aspectHeight != _videoMode.overlayHeight) - scaledY = scaledY * _aspectHeight / _videoMode.overlayHeight; + if (_displayWidth != _videoMode.overlayWidth) + scaledX = scaledX * _displayWidth / _videoMode.overlayWidth; + if (_displayHeight != _videoMode.overlayHeight) + scaledY = scaledY * _displayHeight / _videoMode.overlayHeight; } else { - if (_aspectWidth != _videoMode.screenWidth) - scaledX = scaledX * _aspectWidth / _videoMode.screenWidth; - if (_aspectHeight != _videoMode.screenHeight) - scaledY = scaledY * _aspectHeight / _videoMode.screenHeight; + if (_displayWidth != _videoMode.screenWidth) + scaledX = scaledX * _displayWidth / _videoMode.screenWidth; + if (_displayHeight != _videoMode.screenHeight) + scaledY = scaledY * _displayHeight / _videoMode.screenHeight; } - scaledX += _aspectX; - scaledY += _aspectY; + scaledX += _displayX; + scaledY += _displayY; } SDL_WarpMouse(scaledX, scaledY); @@ -356,7 +356,7 @@ bool OpenGLSdlGraphicsManager::loadGFXMode() { if (_videoMode.fullscreen) flags |= SDL_FULLSCREEN; - else if (_videoMode.aspectRatioCorrection == kAspectRatioNone) + else flags |= SDL_RESIZABLE; // Create our window @@ -406,85 +406,30 @@ void OpenGLSdlGraphicsManager::internUpdateScreen() { SDL_GL_SwapBuffers(); } -bool OpenGLSdlGraphicsManager::handleScalerHotkeys(Common::KeyCode key) { - - // Ctrl-Alt-a toggles aspect ratio correction - if (key == 'a') { - beginGFXTransaction(); - setAspectRatioCorrection(-1); - endGFXTransaction(); #ifdef USE_OSD +void OpenGLSdlGraphicsManager::displayModeChangedMsg() { + const char *newModeName = getCurrentModeName(); + if (newModeName) { char buffer[128]; - sprintf(buffer, "Current aspect ratio mode: %s\n%d x %d -> %d x %d", - getAspectRatioName().c_str(), + sprintf(buffer, "Current display mode: %s\n%d x %d -> %d x %d", + newModeName, _videoMode.screenWidth * _videoMode.scaleFactor, _videoMode.screenHeight * _videoMode.scaleFactor, _hwscreen->w, _hwscreen->h ); displayMessageOnOSD(buffer); -#endif - internUpdateScreen(); - return true; - } - - // Ctrl-Alt-f toggles antialiasing - if (key == 'f') { - beginGFXTransaction(); - _videoMode.antialiasing = !_videoMode.antialiasing; - _transactionDetails.filterChanged = true; - endGFXTransaction(); -#ifdef USE_OSD - if (_videoMode.antialiasing) - displayMessageOnOSD("Active filter mode: Linear"); - else - displayMessageOnOSD("Active filter mode: Nearest"); -#endif - return true; - } - - SDLKey sdlKey = (SDLKey)key; - - // Increase/decrease the scale factor - if (sdlKey == SDLK_EQUALS || sdlKey == SDLK_PLUS || sdlKey == SDLK_MINUS || - sdlKey == SDLK_KP_PLUS || sdlKey == SDLK_KP_MINUS) { - int factor = _videoMode.scaleFactor; - factor += (sdlKey == SDLK_MINUS || sdlKey == SDLK_KP_MINUS) ? -1 : +1; - if (0 < factor && factor < 4) { - // Check if the desktop resolution has been detected - if (_desktopWidth > 0 && _desktopHeight > 0) - // If the new scale factor is too big, do not scale - if (_videoMode.screenWidth * factor > _desktopWidth || - _videoMode.screenHeight * factor > _desktopHeight) - return false; - - beginGFXTransaction(); - setScale(factor); - endGFXTransaction(); -#ifdef USE_OSD - const char *newScalerName = 0; - const OSystem::GraphicsMode *g = getSupportedGraphicsModes(); - while (g->name) { - if (g->id == _videoMode.mode) { - newScalerName = g->description; - break; - } - g++; - } - if (newScalerName) { - char buffer[128]; - sprintf(buffer, "Active graphics mode: %s\n%d x %d -> %d x %d", - newScalerName, - _videoMode.screenWidth, _videoMode.screenHeight, - _hwscreen->w, _hwscreen->h - ); - displayMessageOnOSD(buffer); - } -#endif - return true; - } } - return false; } +void OpenGLSdlGraphicsManager::displayScaleChangedMsg() { + char buffer[128]; + sprintf(buffer, "Current scale: x%d\n%d x %d -> %d x %d", + _videoMode.scaleFactor, + _videoMode.screenWidth, _videoMode.screenHeight, + _videoMode.overlayWidth, _videoMode.overlayHeight + ); + displayMessageOnOSD(buffer); +} +#endif void OpenGLSdlGraphicsManager::setFullscreenMode(bool enable) { if (_oldVideoMode.setup && _oldVideoMode.fullscreen == enable && @@ -497,12 +442,17 @@ void OpenGLSdlGraphicsManager::setFullscreenMode(bool enable) { } } -bool OpenGLSdlGraphicsManager::isScalerHotkey(const Common::Event &event) { +bool OpenGLSdlGraphicsManager::isHotkey(const Common::Event &event) { if ((event.kbd.flags & (Common::KBD_CTRL|Common::KBD_ALT)) == (Common::KBD_CTRL|Common::KBD_ALT)) { - const bool isScaleKey = (event.kbd.keycode == Common::KEYCODE_EQUALS || event.kbd.keycode == Common::KEYCODE_PLUS || event.kbd.keycode == Common::KEYCODE_MINUS || - event.kbd.keycode == Common::KEYCODE_KP_PLUS || event.kbd.keycode == Common::KEYCODE_KP_MINUS); - - return (isScaleKey || event.kbd.keycode == 'a' || event.kbd.keycode == 'f'); + if (event.kbd.keycode == Common::KEYCODE_PLUS || event.kbd.keycode == Common::KEYCODE_MINUS || + event.kbd.keycode == Common::KEYCODE_KP_PLUS || event.kbd.keycode == Common::KEYCODE_KP_MINUS || + event.kbd.keycode == 'a' || event.kbd.keycode == 'f') + return true; + } else if ((event.kbd.flags & (Common::KBD_CTRL|Common::KBD_SHIFT)) == (Common::KBD_CTRL|Common::KBD_SHIFT)) { + if (event.kbd.keycode == 'a' || event.kbd.keycode == 'f') + return true; + } else if ((event.kbd.flags & (Common::KBD_ALT)) == (Common::KBD_ALT) && event.kbd.keycode == 's') { + return true; } return false; } @@ -538,71 +488,171 @@ void OpenGLSdlGraphicsManager::toggleFullScreen(int loop) { bool OpenGLSdlGraphicsManager::notifyEvent(const Common::Event &event) { switch ((int)event.type) { case Common::EVENT_KEYDOWN: - // Alt-Return and Alt-Enter toggle full screen mode - if (event.kbd.hasFlags(Common::KBD_ALT) && - (event.kbd.keycode == Common::KEYCODE_RETURN || - event.kbd.keycode == (Common::KeyCode)SDLK_KP_ENTER)) { - toggleFullScreen(0); - return true; - } + if (event.kbd.hasFlags(Common::KBD_ALT)) { + // Alt-Return and Alt-Enter toggle full screen mode + if (event.kbd.keycode == Common::KEYCODE_RETURN || + event.kbd.keycode == (Common::KeyCode)SDLK_KP_ENTER) { + toggleFullScreen(0); + return true; + } - // Ctrl-Alt-Return and Ctrl-Alt-Enter switches between full screen modes - if (event.kbd.hasFlags(Common::KBD_CTRL|Common::KBD_ALT) && - (event.kbd.keycode == Common::KEYCODE_RETURN || - event.kbd.keycode == (Common::KeyCode)SDLK_KP_ENTER)) { - toggleFullScreen(1); - return true; - } + // Alt-S create a screenshot + if (event.kbd.keycode == 's') { + char filename[20]; - // Ctrl-Shift-Return and Ctrl-Shift-Enter switches backwards between full screen modes - if (event.kbd.hasFlags(Common::KBD_CTRL|Common::KBD_SHIFT) && - (event.kbd.keycode == Common::KEYCODE_RETURN || - event.kbd.keycode == (Common::KeyCode)SDLK_KP_ENTER)) { - toggleFullScreen(-1); - return true; + for (int n = 0;; n++) { + SDL_RWops *file; + + sprintf(filename, "scummvm%05d.bmp", n); + file = SDL_RWFromFile(filename, "r"); + if (!file) + break; + SDL_RWclose(file); + } + if (saveScreenshot(filename)) + printf("Saved '%s'\n", filename); + else + printf("Could not save screenshot!\n"); + return true; + } } - // Alt-S: Create a screenshot - if (event.kbd.hasFlags(Common::KBD_ALT) && event.kbd.keycode == 's') { - char filename[20]; + if (event.kbd.hasFlags(Common::KBD_CTRL|Common::KBD_ALT)) { + // Ctrl-Alt-Return and Ctrl-Alt-Enter switch between full screen modes + if (event.kbd.keycode == Common::KEYCODE_RETURN || + event.kbd.keycode == (Common::KeyCode)SDLK_KP_ENTER) { + toggleFullScreen(1); + return true; + } + + // Ctrl-Alt-a switch between display modes + if (event.kbd.keycode == 'a') { + beginGFXTransaction(); + switchDisplayMode(-1); + endGFXTransaction(); +#ifdef USE_OSD + displayModeChangedMsg(); +#endif + internUpdateScreen(); + return true; + } - for (int n = 0;; n++) { - SDL_RWops *file; + // Ctrl-Alt-f toggles antialiasing + if (event.kbd.keycode == 'f') { + beginGFXTransaction(); + _videoMode.antialiasing = !_videoMode.antialiasing; + _transactionDetails.filterChanged = true; + endGFXTransaction(); +#ifdef USE_OSD + if (_videoMode.antialiasing) + displayMessageOnOSD("Active filter mode: Linear"); + else + displayMessageOnOSD("Active filter mode: Nearest"); +#endif + return true; + } - sprintf(filename, "scummvm%05d.bmp", n); - file = SDL_RWFromFile(filename, "r"); - if (!file) - break; - SDL_RWclose(file); + SDLKey sdlKey = (SDLKey)event.kbd.keycode; + + // Ctrl+Alt+Plus/Minus Increase/decrease the scale factor + if ((sdlKey == SDLK_EQUALS || sdlKey == SDLK_PLUS || sdlKey == SDLK_MINUS || + sdlKey == SDLK_KP_PLUS || sdlKey == SDLK_KP_MINUS)) { + int factor = _videoMode.scaleFactor; + factor += (sdlKey == SDLK_MINUS || sdlKey == SDLK_KP_MINUS) ? -1 : +1; + if (0 < factor && factor < 4) { + // Check if the desktop resolution has been detected + if (_desktopWidth > 0 && _desktopHeight > 0) + // If the new scale factor is too big, do not scale + if (_videoMode.screenWidth * factor > _desktopWidth || + _videoMode.screenHeight * factor > _desktopHeight) + return false; + + beginGFXTransaction(); + setScale(factor); + endGFXTransaction(); +#ifdef USE_OSD + displayScaleChangedMsg(); +#endif + return true; + } + } + + const bool isNormalNumber = (SDLK_1 <= sdlKey && sdlKey <= SDLK_4); + const bool isKeypadNumber = (SDLK_KP1 <= sdlKey && sdlKey <= SDLK_KP4); + + // Ctrl-Alt- will change the GFX mode + if (isNormalNumber || isKeypadNumber) { + if (sdlKey - (isNormalNumber ? SDLK_1 : SDLK_KP1) <= 4) { + int lastMode = _videoMode.mode; + beginGFXTransaction(); + _videoMode.mode = sdlKey - (isNormalNumber ? SDLK_1 : SDLK_KP1); + _transactionDetails.needRefresh = true; + endGFXTransaction(); +#ifdef USE_OSD + if (lastMode != _videoMode.mode) + displayModeChangedMsg(); +#endif + internUpdateScreen(); + } } - if (saveScreenshot(filename)) - printf("Saved '%s'\n", filename); - else - printf("Could not save screenshot!\n"); - return true; } - // Ctrl-Alt- will change the GFX mode - if (event.kbd.hasFlags(Common::KBD_CTRL|Common::KBD_ALT)) { - if (handleScalerHotkeys(event.kbd.keycode)) + if (event.kbd.hasFlags(Common::KBD_CTRL|Common::KBD_SHIFT)) { + // Ctrl-Shift-Return and Ctrl-Shift-Enter switch backwards between full screen modes + if (event.kbd.keycode == Common::KEYCODE_RETURN || + event.kbd.keycode == (Common::KeyCode)SDLK_KP_ENTER) { + toggleFullScreen(-1); + return true; + } + + // Ctrl-Shift-a switch backwards between display modes + if (event.kbd.keycode == 'a') { + beginGFXTransaction(); + switchDisplayMode(-2); + endGFXTransaction(); +#ifdef USE_OSD + displayModeChangedMsg(); +#endif + internUpdateScreen(); return true; + } } + break; case Common::EVENT_KEYUP: - return isScalerHotkey(event); - /*case OSystem_SDL::kSdlEventExpose: - break;*/ - // HACK: Handle special SDL event + return isHotkey(event); + // HACK: Handle special SDL event + // The new screen size is saved on the mouse event as part of HACK, + // there is no common resize event. case OSystem_SDL::kSdlEventResize: // Do not resize if ignoring resize events. - if (!_ignoreResizeFrames) { + if (!_ignoreResizeFrames && !_videoMode.fullscreen) { + bool scaleChanged = false; beginGFXTransaction(); - // Set the new screen size. It is saved on the mouse event as part of HACK, - // there is no common resize event _videoMode.hardwareWidth = event.mouse.x; _videoMode.hardwareHeight = event.mouse.y; - _screenResized = true; + + if (_videoMode.mode != OpenGL::GFX_ORIGINAL) { + _screenResized = true; + calculateDisplaySize(_videoMode.hardwareWidth, _videoMode.hardwareHeight); + } + + int scale = MIN(_videoMode.hardwareWidth / _videoMode.screenWidth, + _videoMode.hardwareHeight / _videoMode.screenHeight); + if (_videoMode.scaleFactor != scale) { + scaleChanged = true; + _videoMode.scaleFactor = MAX(MIN(scale, 3), 1); + } + + if (_videoMode.mode == OpenGL::GFX_ORIGINAL) { + calculateDisplaySize(_videoMode.hardwareWidth, _videoMode.hardwareHeight); + } + _transactionDetails.sizeChanged = true; endGFXTransaction(); +#ifdef USE_OSD + if (scaleChanged) + displayScaleChangedMsg(); +#endif } return true; diff --git a/backends/graphics/openglsdl/openglsdl-graphics.h b/backends/graphics/openglsdl/openglsdl-graphics.h index fdf7bf6e08..0854872315 100644 --- a/backends/graphics/openglsdl/openglsdl-graphics.h +++ b/backends/graphics/openglsdl/openglsdl-graphics.h @@ -63,8 +63,7 @@ protected: virtual void setFullscreenMode(bool enable); - virtual bool handleScalerHotkeys(Common::KeyCode key); - virtual bool isScalerHotkey(const Common::Event &event); + virtual bool isHotkey(const Common::Event &event); #ifdef USE_RGB_COLOR Common::List _supportedFormats; @@ -104,6 +103,18 @@ protected: // from its borders, but in some cases a resize event can be generated // after a fullscreen change. int _ignoreResizeFrames; + +#ifdef USE_OSD + /** + * Displays a mode change message in OSD + */ + void displayModeChangedMsg(); + + /** + * Displays a scale change message in OSD + */ + void displayScaleChangedMsg(); +#endif }; #endif -- cgit v1.2.3