From 14f4f09f834b4d5f7c1d840de8b3be18ff66943e Mon Sep 17 00:00:00 2001 From: scrawl Date: Mon, 28 May 2012 09:19:25 +0200 Subject: [PATCH] proper resolution switching (reposition GUI & adjust mouse clipping region) --- apps/openmw/mwgui/console.cpp | 5 +++++ apps/openmw/mwgui/console.hpp | 2 ++ apps/openmw/mwgui/hud.cpp | 5 +++++ apps/openmw/mwgui/hud.hpp | 1 + apps/openmw/mwgui/settingswindow.cpp | 5 +++++ apps/openmw/mwgui/window_base.cpp | 10 +++++++++- apps/openmw/mwgui/window_manager.cpp | 21 +++++++++++++++++++++ apps/openmw/mwinput/inputmanager.cpp | 23 ++++++++++++++++++++++- apps/openmw/mwinput/inputmanager.hpp | 4 ++++ apps/openmw/mwrender/renderingmanager.cpp | 23 +++++++++++++++++++---- libs/mangle/input/servers/ois_driver.cpp | 7 +++++++ libs/mangle/input/servers/ois_driver.hpp | 2 ++ libs/openengine/gui/events.cpp | 18 +++--------------- libs/openengine/gui/events.hpp | 2 -- libs/openengine/ogre/renderer.cpp | 6 +----- libs/openengine/ogre/renderer.hpp | 2 +- 16 files changed, 107 insertions(+), 29 deletions(-) diff --git a/apps/openmw/mwgui/console.cpp b/apps/openmw/mwgui/console.cpp index 8e15abddd..bf80a77b2 100644 --- a/apps/openmw/mwgui/console.cpp +++ b/apps/openmw/mwgui/console.cpp @@ -370,4 +370,9 @@ namespace MWGui /* All keywords match with the shortest. Append it to the output string and return it. */ return output.append(matches.front()); } + + void Console::onResChange(int width, int height) + { + setCoord(10,10, width-10, height/2); + } } diff --git a/apps/openmw/mwgui/console.hpp b/apps/openmw/mwgui/console.hpp index 6974d8333..117285847 100644 --- a/apps/openmw/mwgui/console.hpp +++ b/apps/openmw/mwgui/console.hpp @@ -58,6 +58,8 @@ namespace MWGui void setFont(const std::string &fntName); + void onResChange(int width, int height); + void clearHistory(); // Print a message to the console. Messages may contain color diff --git a/apps/openmw/mwgui/hud.cpp b/apps/openmw/mwgui/hud.cpp index d3d7696b4..31952e993 100644 --- a/apps/openmw/mwgui/hud.cpp +++ b/apps/openmw/mwgui/hud.cpp @@ -347,3 +347,8 @@ void HUD::onFrame(float dt) if (mCellNameTimer < 0) mCellNameBox->setVisible(false); } + +void HUD::onResChange(int width, int height) +{ + setCoord(0, 0, width, height); +} diff --git a/apps/openmw/mwgui/hud.hpp b/apps/openmw/mwgui/hud.hpp index f7131a39c..531dd7020 100644 --- a/apps/openmw/mwgui/hud.hpp +++ b/apps/openmw/mwgui/hud.hpp @@ -26,6 +26,7 @@ namespace MWGui void setFpsLevel(const int level); void onFrame(float dt); + void onResChange(int width, int height); void setCellName(const std::string& cellName); diff --git a/apps/openmw/mwgui/settingswindow.cpp b/apps/openmw/mwgui/settingswindow.cpp index 0e0815228..c8337d74c 100644 --- a/apps/openmw/mwgui/settingswindow.cpp +++ b/apps/openmw/mwgui/settingswindow.cpp @@ -11,6 +11,7 @@ #include "../mwbase/environment.hpp" #include "../mwworld/world.hpp" #include "../mwsound/soundmanager.hpp" +#include "../mwinput/inputmanager.hpp" #include "window_manager.hpp" #include "confirmationdialog.hpp" @@ -144,7 +145,10 @@ namespace MWGui } if (_sender == mFullscreenButton) + { Settings::Manager::setBool("fullscreen", "Video", newState); + apply(); + } else if (_sender == mVSyncButton) { Settings::Manager::setBool("vsync", "Video", newState); @@ -188,5 +192,6 @@ namespace MWGui MWBase::Environment::get().getWorld()->processChangedSettings(changed); MWBase::Environment::get().getSoundManager()->processChangedSettings(changed); MWBase::Environment::get().getWindowManager()->processChangedSettings(changed); + MWBase::Environment::get().getInputManager()->processChangedSettings(changed); } } diff --git a/apps/openmw/mwgui/window_base.cpp b/apps/openmw/mwgui/window_base.cpp index 45206214b..433057931 100644 --- a/apps/openmw/mwgui/window_base.cpp +++ b/apps/openmw/mwgui/window_base.cpp @@ -1,6 +1,8 @@ #include "window_base.hpp" #include "window_manager.hpp" +#include + using namespace MWGui; WindowBase::WindowBase(const std::string& parLayout, WindowManager& parWindowManager) @@ -25,7 +27,13 @@ void WindowBase::setVisible(bool visible) void WindowBase::center() { // Centre dialog - MyGUI::IntSize gameWindowSize = MyGUI::RenderManager::getInstance().getViewSize(); + + // MyGUI::IntSize gameWindowSize = MyGUI::RenderManager::getInstance().getViewSize(); + // Note by scrawl: The following works more reliably in the case when the window was _just_ + // resized and MyGUI RenderManager doesn't know about the new size yet + MyGUI::IntSize gameWindowSize = MyGUI::IntSize(Settings::Manager::getInt("resolution x", "Video"), + Settings::Manager::getInt("resolution y", "Video")); + MyGUI::IntCoord coord = mMainWidget->getCoord(); coord.left = (gameWindowSize.width - coord.width)/2; coord.top = (gameWindowSize.height - coord.height)/2; diff --git a/apps/openmw/mwgui/window_manager.cpp b/apps/openmw/mwgui/window_manager.cpp index a6d236136..891f85ca2 100644 --- a/apps/openmw/mwgui/window_manager.cpp +++ b/apps/openmw/mwgui/window_manager.cpp @@ -605,6 +605,27 @@ void WindowManager::onRetrieveTag(const MyGUI::UString& _tag, MyGUI::UString& _r void WindowManager::processChangedSettings(const Settings::CategorySettingVector& changed) { hud->setFpsLevel(Settings::Manager::getInt("fps", "HUD")); + + bool changeRes = false; + for (Settings::CategorySettingVector::const_iterator it = changed.begin(); + it != changed.end(); ++it) + { + if (it->first == "Video" && ( + it->second == "resolution x" + || it->second == "resolution y")) + { + changeRes = true; + } + } + + if (changeRes) + { + int x = Settings::Manager::getInt("resolution x", "Video"); + int y = Settings::Manager::getInt("resolution y", "Video"); + hud->onResChange(x, y); + console->onResChange(x, y); + mSettingsWindow->center(); + } } void WindowManager::pushGuiMode(GuiMode mode) diff --git a/apps/openmw/mwinput/inputmanager.cpp b/apps/openmw/mwinput/inputmanager.cpp index 9b6a1d39b..a2bafcbf7 100644 --- a/apps/openmw/mwinput/inputmanager.cpp +++ b/apps/openmw/mwinput/inputmanager.cpp @@ -92,7 +92,12 @@ namespace MWInput /* InputImpl Methods */ - +public: + void adjustMouseRegion(int width, int height) + { + input.adjustMouseClippingSize(width, height); + } +private: void toggleSpell() { if (windows.isGuiMode()) return; @@ -450,4 +455,20 @@ namespace MWInput { impl->changeInputMode(guiMode); } + + void MWInputManager::processChangedSettings(const Settings::CategorySettingVector& changed) + { + bool changeRes = false; + for (Settings::CategorySettingVector::const_iterator it = changed.begin(); + it != changed.end(); ++it) + { + if (it->first == "Video" && ( + it->second == "resolution x" + || it->second == "resolution y")) + changeRes = true; + } + + if (changeRes) + impl->adjustMouseRegion(Settings::Manager::getInt("resolution x", "Video"), Settings::Manager::getInt("resolution y", "Video")); + } } diff --git a/apps/openmw/mwinput/inputmanager.hpp b/apps/openmw/mwinput/inputmanager.hpp index b8d98ed56..4ef3df137 100644 --- a/apps/openmw/mwinput/inputmanager.hpp +++ b/apps/openmw/mwinput/inputmanager.hpp @@ -3,6 +3,8 @@ #include "../mwgui/mode.hpp" +#include + namespace OEngine { namespace Render @@ -52,6 +54,8 @@ namespace MWInput void changeInputMode(bool guiMode); + void processChangedSettings(const Settings::CategorySettingVector& changed); + void setDragDrop(bool dragDrop); }; } diff --git a/apps/openmw/mwrender/renderingmanager.cpp b/apps/openmw/mwrender/renderingmanager.cpp index e5ce6b0dd..46e274ff5 100644 --- a/apps/openmw/mwrender/renderingmanager.cpp +++ b/apps/openmw/mwrender/renderingmanager.cpp @@ -22,6 +22,9 @@ #include "water.hpp" #include "compositors.hpp" +#include "../mwgui/window_manager.hpp" // FIXME +#include "../mwinput/inputmanager.hpp" // FIXME + using namespace MWRender; using namespace Ogre; @@ -591,9 +594,13 @@ void RenderingManager::processChangedSettings(const Settings::CategorySettingVec if (changeRes) { - int x = Settings::Manager::getInt("resolution x", "Video"); - int y = Settings::Manager::getInt("resolution y", "Video"); - mRendering.getWindow()->resize(x, y); + unsigned int x = Settings::Manager::getInt("resolution x", "Video"); + unsigned int y = Settings::Manager::getInt("resolution y", "Video"); + + if (x != mRendering.getWindow()->getWidth() || y != mRendering.getWindow()->getHeight()) + { + mRendering.getWindow()->resize(x, y); + } mRendering.getWindow()->setFullscreen(Settings::Manager::getBool("fullscreen", "Video"), x, y); } } @@ -610,9 +617,17 @@ void RenderingManager::setMenuTransparency(float val) void RenderingManager::windowResized(Ogre::RenderWindow* rw) { - mCompositors->setViewport(mRendering.recreateViewport()); + Settings::Manager::setInt("resolution x", "Video", rw->getWidth()); + Settings::Manager::setInt("resolution y", "Video", rw->getHeight()); + + + mRendering.adjustViewport(); mCompositors->recreate(); mWater->assignTextures(); + + const Settings::CategorySettingVector& changed = Settings::Manager::apply(); + MWBase::Environment::get().getInputManager()->processChangedSettings(changed); //FIXME + MWBase::Environment::get().getWindowManager()->processChangedSettings(changed); // FIXME } void RenderingManager::windowClosed(Ogre::RenderWindow* rw) diff --git a/libs/mangle/input/servers/ois_driver.cpp b/libs/mangle/input/servers/ois_driver.cpp index 2071b91ea..acca69df4 100644 --- a/libs/mangle/input/servers/ois_driver.cpp +++ b/libs/mangle/input/servers/ois_driver.cpp @@ -146,3 +146,10 @@ bool OISDriver::isDown(int index) // TODO: Extend to mouse buttons as well return keyboard->isKeyDown((OIS::KeyCode)index); } + +void OISDriver::adjustMouseClippingSize(int width, int height) +{ + const OIS::MouseState &ms = mouse->getMouseState(); + ms.width = width; + ms.height = height; +} diff --git a/libs/mangle/input/servers/ois_driver.hpp b/libs/mangle/input/servers/ois_driver.hpp index ba780c39e..81633542f 100644 --- a/libs/mangle/input/servers/ois_driver.hpp +++ b/libs/mangle/input/servers/ois_driver.hpp @@ -31,6 +31,8 @@ namespace Mangle OISDriver(Ogre::RenderWindow *window, bool exclusive=true); ~OISDriver(); + void adjustMouseClippingSize(int width, int height); + void capture(); bool isDown(int index); /// Not currently supported. diff --git a/libs/openengine/gui/events.cpp b/libs/openengine/gui/events.cpp index 3e52c6435..a19c247c2 100644 --- a/libs/openengine/gui/events.cpp +++ b/libs/openengine/gui/events.cpp @@ -8,18 +8,9 @@ using namespace OIS; using namespace OEngine::GUI; EventInjector::EventInjector(MyGUI::Gui *g) - : gui(g), mouseX(0), mouseY(0), enabled(true) + : gui(g), enabled(true) { assert(gui); - maxX = MyGUI::RenderManager::getInstance().getViewSize().width; - maxY = MyGUI::RenderManager::getInstance().getViewSize().height; -} - -template -void setRange(X &x, X min, X max) -{ - if(x < min) x = min; - else if(x > max) x = max; } void EventInjector::event(Type type, int index, const void *p) @@ -64,11 +55,8 @@ void EventInjector::event(Type type, int index, const void *p) MyGUI::MouseButton id = MyGUI::MouseButton::Enum(index); // Update mouse position - mouseX += mouse->state.X.rel; - mouseY += mouse->state.Y.rel; - - setRange(mouseX,0,maxX); - setRange(mouseY,0,maxY); + int mouseX = mouse->state.X.abs; + int mouseY = mouse->state.Y.abs; if(type == EV_MouseDown) MyGUI::InputManager::getInstance().injectMousePress(mouseX, mouseY, id); diff --git a/libs/openengine/gui/events.hpp b/libs/openengine/gui/events.hpp index 6ca83cf75..1f506cffa 100644 --- a/libs/openengine/gui/events.hpp +++ b/libs/openengine/gui/events.hpp @@ -16,8 +16,6 @@ namespace GUI class EventInjector : public Mangle::Input::Event { MyGUI::Gui *gui; - int mouseX, mouseY; - int maxX, maxY; public: bool enabled; diff --git a/libs/openengine/ogre/renderer.cpp b/libs/openengine/ogre/renderer.cpp index 579ba3dd7..7a01ffce7 100644 --- a/libs/openengine/ogre/renderer.cpp +++ b/libs/openengine/ogre/renderer.cpp @@ -145,14 +145,10 @@ void OgreRenderer::createScene(const std::string camName, float fov, float nearC mFader = new Fader(); } -Ogre::Viewport* OgreRenderer::recreateViewport() +void OgreRenderer::adjustViewport() { - mWindow->removeViewport(mView->getZOrder()); - mView = mWindow->addViewport(mCamera); - // Alter the camera aspect ratio to match the viewport mCamera->setAspectRatio(Real(mView->getActualWidth()) / Real(mView->getActualHeight())); - return mView; } void OgreRenderer::setWindowEventListener(Ogre::WindowEventListener* listener) diff --git a/libs/openengine/ogre/renderer.hpp b/libs/openengine/ogre/renderer.hpp index 7a0fd11df..9d1d0122d 100644 --- a/libs/openengine/ogre/renderer.hpp +++ b/libs/openengine/ogre/renderer.hpp @@ -157,7 +157,7 @@ namespace OEngine /// Viewport Ogre::Viewport *getViewport() { return mView; } - Ogre::Viewport* recreateViewport(); + void adjustViewport(); }; } }