#include "OBAOgreFrameListenerMode.h" namespace OBA { OgreFrameListenerMode::OgreFrameListenerMode(Ogre::RenderWindow *win, unsigned int ogreFrameListenerModeHandle, bool useBufferedInputKeys, bool useBufferedInputMouse) { mOgreFrameListenerModeHandle = ogreFrameListenerModeHandle; mDebugOverlay = Ogre::OverlayManager::getSingleton().getByName("Core/DebugOverlay"); mInputTypeSwitchingOn = useBufferedInputKeys || useBufferedInputMouse; mUseBufferedInputKeys = useBufferedInputKeys; mUseBufferedInputMouse = useBufferedInputMouse; mRotateSpeed = 36; mMoveSpeed = 100; mWindow = win; Ogre::LogManager::getSingleton().logMessage("mWindow.IsClosed->" + Ogre::StringConverter::toString(mWindow->isClosed())); mStatsOn = true; mNumScreenShots = 0; mTimeUntilNextToggle = 0; mSceneDetailIndex = 0; mMoveScale = 0.0f; mRotScale = 0.0f; mTranslateVector = Ogre::Vector3::ZERO; mAniso = 1; mFiltering = Ogre::TFO_BILINEAR; showDebugOverlay(true); } OgreFrameListenerMode::~OgreFrameListenerMode() { } void OgreFrameListenerMode::updateStats(void) { static Ogre::String currFps = "Current FPS: "; static Ogre::String avgFps = "Average FPS: "; static Ogre::String bestFps = "Best FPS: "; static Ogre::String worstFps = "Worst FPS: "; static Ogre::String tris = "Triangle Count: "; // update stats when necessary try { Ogre::OverlayElement* guiAvg = Ogre::OverlayManager::getSingleton().getOverlayElement("Core/AverageFps"); Ogre::OverlayElement* guiCurr = Ogre::OverlayManager::getSingleton().getOverlayElement("Core/CurrFps"); Ogre::OverlayElement* guiBest = Ogre::OverlayManager::getSingleton().getOverlayElement("Core/BestFps"); Ogre::OverlayElement* guiWorst = Ogre::OverlayManager::getSingleton().getOverlayElement("Core/WorstFps"); const Ogre::RenderTarget::FrameStats& stats = mWindow->getStatistics(); guiAvg->setCaption(avgFps + Ogre::StringConverter::toString(stats.avgFPS)); guiCurr->setCaption(currFps + Ogre::StringConverter::toString(stats.lastFPS)); guiBest->setCaption(bestFps + Ogre::StringConverter::toString(stats.bestFPS) +" "+ Ogre::StringConverter::toString(stats.bestFrameTime)+" ms"); guiWorst->setCaption(worstFps + Ogre::StringConverter::toString(stats.worstFPS) +" "+ Ogre::StringConverter::toString(stats.worstFrameTime)+" ms"); Ogre::OverlayElement* guiTris = Ogre::OverlayManager::getSingleton().getOverlayElement("Core/NumTris"); guiTris->setCaption(tris + Ogre::StringConverter::toString(stats.triangleCount)); Ogre::OverlayElement* guiDbg = Ogre::OverlayManager::getSingleton().getOverlayElement("Core/DebugText"); guiDbg->setCaption(mWindow->getDebugText()); } catch(...) { // ignore } } bool OgreFrameListenerMode::processUnbufferedKeyInput(const Ogre::FrameEvent& evt) { if (mInputDevice->isKeyDown(Ogre::KC_A)) { // Move camera left mTranslateVector.x = -mMoveScale; } if (mInputDevice->isKeyDown(Ogre::KC_D)) { // Move camera RIGHT mTranslateVector.x = mMoveScale; } /* Move camera forward by keypress. */ if (mInputDevice->isKeyDown(Ogre::KC_UP) || mInputDevice->isKeyDown(Ogre::KC_W) ) { mTranslateVector.z = -mMoveScale; } /* Move camera backward by keypress. */ if (mInputDevice->isKeyDown(Ogre::KC_DOWN) || mInputDevice->isKeyDown(Ogre::KC_S) ) { mTranslateVector.z = mMoveScale; } if (mInputDevice->isKeyDown(Ogre::KC_PGUP)) { // Move camera up mTranslateVector.y = mMoveScale; } if (mInputDevice->isKeyDown(Ogre::KC_PGDOWN)) { // Move camera down mTranslateVector.y = -mMoveScale; } if (mInputDevice->isKeyDown(Ogre::KC_RIGHT)) { mCamera->yaw(-mRotScale); } if (mInputDevice->isKeyDown(Ogre::KC_LEFT)) { mCamera->yaw(mRotScale); } // see if switching is on, and you want to toggle if (mInputTypeSwitchingOn && mInputDevice->isKeyDown(Ogre::KC_M) && mTimeUntilNextToggle <= 0) { switchMouseMode(); mTimeUntilNextToggle = 1; } if (mInputTypeSwitchingOn && mInputDevice->isKeyDown(Ogre::KC_K) && mTimeUntilNextToggle <= 0) { // must be going from immediate keyboard to buffered keyboard switchKeyMode(); mTimeUntilNextToggle = 1; } if (mInputDevice->isKeyDown(Ogre::KC_F) && mTimeUntilNextToggle <= 0) { mStatsOn = !mStatsOn; showDebugOverlay(mStatsOn); mTimeUntilNextToggle = 1; } if (mInputDevice->isKeyDown(Ogre::KC_T) && mTimeUntilNextToggle <= 0) { switch(mFiltering) { case Ogre::TFO_BILINEAR: mFiltering = Ogre::TFO_TRILINEAR; mAniso = 1; break; case Ogre::TFO_TRILINEAR: mFiltering = Ogre::TFO_ANISOTROPIC; mAniso = 8; break; case Ogre::TFO_ANISOTROPIC: mFiltering = Ogre::TFO_BILINEAR; mAniso = 1; break; default: break; } Ogre::MaterialManager::getSingleton().setDefaultTextureFiltering(mFiltering); Ogre::MaterialManager::getSingleton().setDefaultAnisotropy(mAniso); showDebugOverlay(mStatsOn); mTimeUntilNextToggle = 1; } if (mInputDevice->isKeyDown(Ogre::KC_SYSRQ) && mTimeUntilNextToggle <= 0) { char tmp[20]; sprintf(tmp, "screenshot_%d.png", ++mNumScreenShots); mWindow->writeContentsToFile(tmp); mTimeUntilNextToggle = 0.5; mWindow->setDebugText(Ogre::String("Wrote ") + tmp); } if (mInputDevice->isKeyDown(Ogre::KC_R) && mTimeUntilNextToggle <=0) { mSceneDetailIndex = (mSceneDetailIndex+1)%3 ; switch(mSceneDetailIndex) { case 0 : mCamera->setPolygonMode(Ogre::PM_SOLID) ; break ; case 1 : mCamera->setPolygonMode(Ogre::PM_WIREFRAME) ; break ; case 2 : mCamera->setPolygonMode(Ogre::PM_POINTS) ; break ; } mTimeUntilNextToggle = 0.5; } static bool displayCameraDetails = false; if (mInputDevice->isKeyDown(Ogre::KC_P) && mTimeUntilNextToggle <= 0) { displayCameraDetails = !displayCameraDetails; mTimeUntilNextToggle = 0.5; if (!displayCameraDetails) mWindow->setDebugText(""); } if (displayCameraDetails) { // Print camera details mWindow->setDebugText("P: " + Ogre::StringConverter::toString(mCamera->getDerivedPosition()) + " " + "O: " + Ogre::StringConverter::toString(mCamera->getDerivedOrientation())); } // Return true to continue rendering return true; } bool OgreFrameListenerMode::processUnbufferedMouseInput(const Ogre::FrameEvent& evt) { /* Rotation factors, may not be used if the second mouse button is pressed. */ /* If the second mouse button is pressed, then the mouse movement results in sliding the camera, otherwise we rotate. */ if( mInputDevice->getMouseButton( 1 ) ) { mTranslateVector.x += mInputDevice->getMouseRelativeX() * 0.13; mTranslateVector.y -= mInputDevice->getMouseRelativeY() * 0.13; } else { mRotX = Ogre::Degree(-mInputDevice->getMouseRelativeX() * 0.13); mRotY = Ogre::Degree(-mInputDevice->getMouseRelativeY() * 0.13); } return true; } bool OgreFrameListenerMode::frameEnded(const Ogre::FrameEvent& evt) { updateStats(); return true; } bool OgreFrameListenerMode::frameStarted(const Ogre::FrameEvent& evt, Ogre::InputReader *inputDevice) { mInputDevice = inputDevice; if(mWindow->isClosed()) return false; if ( !mUseBufferedInputMouse || !mUseBufferedInputKeys) { // one of the input modes is immediate, so setup what is needed for immediate mouse/key movement if (mTimeUntilNextToggle >= 0) { mTimeUntilNextToggle -= evt.timeSinceLastFrame; } // If this is the first frame, pick a speed if (evt.timeSinceLastFrame == 0) { mMoveScale = 1; mRotScale = 0.1; } // Otherwise scale movement units by time passed since last frame else { // Move about 100 units per second, mMoveScale = mMoveSpeed * evt.timeSinceLastFrame; // Take about 10 seconds for full rotation mRotScale = mRotateSpeed * evt.timeSinceLastFrame; } mRotX = 0; mRotY = 0; mTranslateVector = Ogre::Vector3::ZERO; } if (mUseBufferedInputKeys) { // no need to do any processing here, it is handled by event processor and // you get the results as KeyEvents } else { if (processUnbufferedKeyInput(evt) == false) { return false; } } if (mUseBufferedInputMouse) { // no need to do any processing here, it is handled by event processor and // you get the results as MouseEvents } else { if (processUnbufferedMouseInput(evt) == false) { return false; } } if ( !mUseBufferedInputMouse || !mUseBufferedInputKeys) { // one of the input modes is immediate, so update the movement vector moveCamera(); } return true; } void OgreFrameListenerMode::moveCamera() { // Make all the changes to the camera // Note that YAW direction is around a fixed axis (freelook style) rather than a natural YAW (e.g. airplane) mCamera->yaw(mRotX); mCamera->pitch(mRotY); mCamera->moveRelative(mTranslateVector); } void OgreFrameListenerMode::showDebugOverlay(bool show) { if (mDebugOverlay) { if (show) { mDebugOverlay->show(); } else { mDebugOverlay->hide(); } } } void OgreFrameListenerMode::switchMouseMode() { mUseBufferedInputMouse = !mUseBufferedInputMouse; mInputDevice->setBufferedInput(mUseBufferedInputKeys, mUseBufferedInputMouse); } void OgreFrameListenerMode::switchKeyMode() { mUseBufferedInputKeys = !mUseBufferedInputKeys; mInputDevice->setBufferedInput(mUseBufferedInputKeys, mUseBufferedInputMouse); } void OgreFrameListenerMode::keyClicked(Ogre::KeyEvent* e) { if (e->getKeyChar() == 'm') { switchMouseMode(); } else if (e->getKeyChar() == 'k') { switchKeyMode(); } } void OgreFrameListenerMode::keyPressed(Ogre::KeyEvent* e) { } void OgreFrameListenerMode::keyReleased(Ogre::KeyEvent* e) { } void OgreFrameListenerMode::chooseSceneManager(void) { // Create the SceneManager, in this case a generic one mSceneMgr = Ogre::Root::getSingleton().createSceneManager(Ogre::ST_GENERIC, "SceneMgr_" + Ogre::StringConverter::toString(mOgreFrameListenerModeHandle)); } Ogre::SceneManager* OgreFrameListenerMode::getSceneManager(void) { return mSceneMgr; } void OgreFrameListenerMode::createCamera(void) { // Create the camera mCamera = mSceneMgr->createCamera("SceneMgr_" + Ogre::StringConverter::toString(mOgreFrameListenerModeHandle) + "_Camera"); // Position it at 200 in Z direction mCamera->setPosition(Ogre::Vector3(0.0, 0.0, 200.0)); // Look back along -Z mCamera->lookAt(Ogre::Vector3(0.0, 0.0, -300.0)); mCamera->setNearClipDistance(2.0); } void OgreFrameListenerMode::createViewports(void) { // Create one viewport, entire window if (mWindow->getNumViewports() == 0) { Ogre::Viewport* vp = mWindow->addViewport(mCamera,mOgreFrameListenerModeHandle); vp->setBackgroundColour(Ogre::ColourValue(0.0, 0.0, 0.0)); } // Alter the camera aspect ratio to match the viewport mCamera->setAspectRatio( Ogre::Real(mWindow->getViewport(0)->getActualWidth()) / Ogre::Real(mWindow->getViewport(0)->getActualHeight())); } unsigned int OgreFrameListenerMode::getHandle() { return mOgreFrameListenerModeHandle; } Ogre::Camera* OgreFrameListenerMode::getCamera() { return mCamera; } void OgreFrameListenerMode::createScene() { } void OgreFrameListenerMode::destroyScene() { } }