diff --git a/apps/openmw/engine.cpp b/apps/openmw/engine.cpp index 5b6aea3c2..ecee8c446 100644 --- a/apps/openmw/engine.cpp +++ b/apps/openmw/engine.cpp @@ -3,6 +3,7 @@ #include #include +#include #include #include @@ -70,6 +71,15 @@ bool OMW::Engine::frameStarted(const Ogre::FrameEvent& evt) // update actors mEnvironment.mMechanicsManager->update(); + if (focusFrameCounter++ == focusUpdateFrame) + { + std::pair handle = mEnvironment.mWorld->getMWScene()->getFacedHandle(); + + std::cout << "Object: " << handle.first << ", distance: " << handle.second << std::endl; + + focusFrameCounter = 0; + } + return true; } @@ -233,6 +243,8 @@ void OMW::Engine::go() MWInput::MWInputManager input(mOgre, mEnvironment.mWorld->getPlayerPos(), *mEnvironment.mWindowManager, mDebug); + focusFrameCounter = 0; + std::cout << "\nPress Q/ESC or close window to exit.\n"; mOgre.getRoot()->addFrameListener (this); diff --git a/apps/openmw/engine.hpp b/apps/openmw/engine.hpp index 9923f4990..412c4fa73 100644 --- a/apps/openmw/engine.hpp +++ b/apps/openmw/engine.hpp @@ -65,6 +65,9 @@ namespace OMW Compiler::Context *mScriptContext; OEngine::GUI::MyGUIManager *mGuiManager; + int focusFrameCounter; + static const int focusUpdateFrame = 10; + // not implemented Engine (const Engine&); Engine& operator= (const Engine&); diff --git a/apps/openmw/mwinput/inputmanager.cpp b/apps/openmw/mwinput/inputmanager.cpp index f32e207dc..f851b43b2 100644 --- a/apps/openmw/mwinput/inputmanager.cpp +++ b/apps/openmw/mwinput/inputmanager.cpp @@ -41,6 +41,8 @@ namespace MWInput A_MoveForward, // Forward / Backward A_MoveBackward, + A_Activate, + A_LAST // Marker for the last item }; @@ -133,6 +135,11 @@ namespace MWInput else setGuiMode(GM_Console); } + void activate() + { + + } + // Exit program now button (which is disabled in GUI mode) void exitNow() { @@ -170,6 +177,8 @@ namespace MWInput "Toggle inventory screen"); disp->funcs.bind(A_Console, boost::bind(&InputImpl::toggleConsole, this), "Toggle console"); + disp->funcs.bind(A_Activate, boost::bind(&InputImpl::activate, this), + "Activate"); // Add the exit listener @@ -212,6 +221,7 @@ namespace MWInput disp->bind(A_Screenshot, KC_SYSRQ); disp->bind(A_Inventory, KC_I); disp->bind(A_Console, KC_F1); + disp->bind(A_Activate, KC_SPACE); // Key bindings for polled keys @@ -257,6 +267,7 @@ namespace MWInput if(moveX != 0 || moveY != 0 || moveZ != 0) player.moveRel(moveX, moveY, moveZ); + return true; } }; diff --git a/apps/openmw/mwrender/mwscene.cpp b/apps/openmw/mwrender/mwscene.cpp index 489b5f242..15163d7a2 100644 --- a/apps/openmw/mwrender/mwscene.cpp +++ b/apps/openmw/mwrender/mwscene.cpp @@ -31,4 +31,53 @@ MWScene::MWScene(OEngine::Render::OgreRenderer &_rend) SceneNode *rt = rend.getScene()->getRootSceneNode(); mwRoot = rt->createChildSceneNode(); mwRoot->pitch(Degree(-90)); + + //used to obtain ingame information of ogre objects (which are faced or selected) + mRaySceneQuery = rend.getScene()->createRayQuery(Ray()); } + +std::pair MWScene::getFacedHandle() +{ + std::string handle = ""; + float distance = -1; + + //get a ray pointing to the center of the viewport + Ray centerRay = getCamera()->getCameraToViewportRay( + getViewport()->getWidth()/2, + getViewport()->getHeight()/2); + + // get all objects touched by the ray + getRaySceneQuery()->setRay (centerRay ); + RaySceneQueryResult &result = getRaySceneQuery()->execute(); + + RaySceneQueryResult::iterator nearest = result.end(); + + for (RaySceneQueryResult::iterator itr = result.begin(); + itr != result.end(); itr++ ) + { + // there seem to be omnipresent objects like the caelum sky dom, + // the distance of these objects is always 0 so this if excludes these + // TODO: Check if the object can be focused (ignore walls etc.. + // in this state of openmw not possible) + if ( itr->movable && itr->distance >= 0.1) + { + if ( nearest == result.end() ) //if no object is set + { + nearest = itr; + } + else if ( itr->distance < nearest->distance ) + { + nearest = itr; + } + } + } + + if ( nearest != result.end() ) + { + handle = nearest->movable->getParentSceneNode()->getName(); + distance = nearest->distance; + } + + return std::pair(handle, distance); +} + diff --git a/apps/openmw/mwrender/mwscene.hpp b/apps/openmw/mwrender/mwscene.hpp index a7339e1c8..ce04efc92 100644 --- a/apps/openmw/mwrender/mwscene.hpp +++ b/apps/openmw/mwrender/mwscene.hpp @@ -1,6 +1,7 @@ #ifndef _GAME_RENDER_MWSCENE_H #define _GAME_RENDER_MWSCENE_H +#include #include namespace Ogre @@ -9,6 +10,7 @@ namespace Ogre class Viewport; class SceneManager; class SceneNode; + class RaySceneQuery; } namespace MWRender @@ -26,6 +28,7 @@ namespace MWRender // that the OGRE coordinate system matches that used internally in // Morrowind. Ogre::SceneNode *mwRoot; + Ogre::RaySceneQuery *mRaySceneQuery; public: MWScene(OEngine::Render::OgreRenderer &_rend); @@ -34,6 +37,13 @@ namespace MWRender Ogre::SceneNode *getRoot() { return mwRoot; } Ogre::SceneManager *getMgr() { return rend.getScene(); } Ogre::Viewport *getViewport() { return rend.getViewport(); } + Ogre::RaySceneQuery *getRaySceneQuery() { return mRaySceneQuery; } + + //gets the handle of the object the player is looking at + //pair + //name is empty and distance = -1 if there is no object which + //can be faced + std::pair getFacedHandle(); }; } diff --git a/apps/openmw/mwworld/world.hpp b/apps/openmw/mwworld/world.hpp index 9030b0c1b..354c3603c 100644 --- a/apps/openmw/mwworld/world.hpp +++ b/apps/openmw/mwworld/world.hpp @@ -83,6 +83,8 @@ namespace MWWorld ~World(); + MWRender::MWScene* getMWScene() { return &mScene; } + MWRender::PlayerPos& getPlayerPos(); ESMS::ESMStore& getStore();