#include <CEGUISystem.h>
#include <CEGUISchemeManager.h>
#include <RendererModules/Ogre/CEGUIOgreRenderer.h>
#include "TerrainApp.h"
#include <set>
TerrainApp::TerrainApp() {
}
TerrainApp::~TerrainApp() {
mSceneMgr->destroyQuery(mRaySceneQuery);
}
void TerrainApp::createScene(void)
{
mSceneMgr->setAmbientLight(Ogre::ColourValue(0.5, 0.5, 0.5));
mSceneMgr->setSkyDome(true, "Examples/CloudySky", 5, 8);
mSceneMgr->setWorldGeometry("myTerrain.cfg");
mCamera->setPosition(40, 100, 580);
mCamera->yaw(Ogre::Degree(-45));
mGUIRenderer = &CEGUI::OgreRenderer::bootstrapSystem(); CEGUI::SchemeManager::getSingleton().create((CEGUI::utf8*)"TaharezLook.scheme");
CEGUI::MouseCursor::getSingleton().setImage("TaharezLook", "MouseTarget");
mFlying = false;
}
void TerrainApp::createFrameListener(void)
{
BaseApplication::createFrameListener();
mCount = 0;
mCurrentObject = NULL;
mLMouseDown = false;
mRMouseDown = false;
mRotateSpeed =.1;
mRaySceneQuery = mSceneMgr->createRayQuery(Ogre::Ray());
mOldPosition = mCamera->getPosition();
mRaySceneQuery2 = mSceneMgr->createRayQuery(Ogre::Ray());
mRaySceneQuery2->setSortByDistance(true, 1);
mDirection = Ogre::Vector3::ZERO;
}
void TerrainApp::chooseSceneManager(void)
{
mSceneMgr = mRoot->createSceneManager(Ogre::ST_EXTERIOR_CLOSE);
}
bool TerrainApp::frameRenderingQueued(const Ogre::FrameEvent &evt)
{
if (mWindow->isClosed())
return false;
if (mShutDown)
return false;
mKeyboard->capture();
mMouse->capture();
mTrayMgr->frameRenderingQueued(evt);
mOldPosition = mCamera->getPosition();
Ogre::Vector3 dir = mCamera->getOrientation()*mDirection;
Ogre::Vector3 newCamPos = mOldPosition + (dir * evt.timeSinceLastFrame);
Ogre::Ray cameraRay(Ogre::Vector3(newCamPos.x, 5000.0f, newCamPos.z),
Ogre::Vector3::NEGATIVE_UNIT_Y);
mRaySceneQuery->setRay(cameraRay);
Ogre::RaySceneQueryResult &result = mRaySceneQuery->execute();
Ogre::RaySceneQueryResult::iterator itr = result.begin();
if (itr != result.end() && itr->worldFragment)
{
Ogre::Real terrainHeight = itr->worldFragment->singleIntersection.y;
int newHeight = terrainHeight + COLLIDE_DIST;
if(!mFlying || newCamPos.y < newHeight) {
newCamPos.y = newHeight;
}
}
mCamera->setPosition(newCamPos);
if(dir.length() > CLOSE_TO_ZERO){
dir.normalise();
if(dir.y > CLOSE_TO_ONE)
dir = Ogre::Vector3::UNIT_Y;
else if(dir.y < -1*CLOSE_TO_ONE)
dir = Ogre::Vector3::NEGATIVE_UNIT_Y;
Ogre::Ray directionRay(newCamPos, dir);
mRaySceneQuery2->setRay(directionRay);
mRaySceneQuery2->execute(this);
}
return true;
}
bool TerrainApp::keyPressed( const OIS::KeyEvent& evt ){
switch (evt.key)
{
case OIS::KC_ESCAPE:
mShutDown = true;
break;
case OIS::KC_W:
case OIS::KC_UP:
mDirection.z = -SPEED;
break;
case OIS::KC_S:
case OIS::KC_DOWN:
mDirection.z = SPEED;
break;
case OIS::KC_A:
case OIS::KC_LEFT:
mDirection.x = -SPEED;
break;
case OIS::KC_D:
case OIS::KC_RIGHT:
mDirection.x = SPEED;
break;
case OIS::KC_PGUP:
mDirection.y = SPEED;
break;
case OIS::KC_PGDOWN:
mDirection.y = -SPEED;
break;
default:
break;
}
return true;
}
bool TerrainApp::keyReleased( const OIS::KeyEvent& evt ){
switch (evt.key)
{
case OIS::KC_ESCAPE:
mShutDown = true;
break;
case OIS::KC_W:
case OIS::KC_UP:
mDirection.z = 0;
break;
case OIS::KC_S:
case OIS::KC_DOWN:
mDirection.z = 0;
break;
case OIS::KC_A:
case OIS::KC_LEFT:
mDirection.x = 0;
break;
case OIS::KC_D:
case OIS::KC_RIGHT:
mDirection.x = 0;
break;
case OIS::KC_PGUP:
mDirection.y = 0;
break;
case OIS::KC_PGDOWN:
mDirection.y = 0;
break;
default:
break;
}
return true;
}
bool TerrainApp::mouseMoved(const OIS::MouseEvent &arg)
{
if (mLMouseDown) {
CEGUI::System::getSingleton().injectMouseMove(arg.state.X.rel, arg.state.Y.rel);
}
else if (mRMouseDown)
{
} else {
mCamera->yaw(Ogre::Degree(-arg.state.X.rel * mRotateSpeed));
mCamera->pitch(Ogre::Degree(-arg.state.Y.rel * mRotateSpeed));
}
return true;
}
bool TerrainApp::mousePressed(const OIS::MouseEvent &arg, OIS::MouseButtonID id)
{
if (id == OIS::MB_Left)
{
mLMouseDown = true;
mFlying = !mFlying;
CEGUI::MouseCursor::getSingleton().setVisible(!mFlying);
}
else if (id == OIS::MB_Right)
{
CEGUI::MouseCursor::getSingleton().hide();
mRMouseDown = true;
} return true;
}
bool TerrainApp::mouseReleased(const OIS::MouseEvent &arg, OIS::MouseButtonID id)
{
if (id == OIS::MB_Left)
{
mLMouseDown = false;
}
else if (id == OIS::MB_Right)
{
CEGUI::MouseCursor::getSingleton().show();
mRMouseDown = false;
} return true;
}
bool TerrainApp::queryResult (Ogre::SceneQuery::WorldFragment *fragment, Ogre::Real dist){
if(dist < COLLIDE_DIST)
mCamera->setPosition(mOldPosition);
return true;
}
bool TerrainApp::queryResult (Ogre::MovableObject *object, Ogre::Real dist){
return true;
}
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
#endif
#ifdef __cplusplus
extern "C" {
#endif
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
INT WINAPI WinMain( HINSTANCE hInst, HINSTANCE, LPSTR strCmdLine, INT )
#else
int main(int argc, char *argv[])
#endif
{
TerrainApp app;
try {
app.go();
} catch( Ogre::Exception& e ) {
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
MessageBox( NULL, e.getFullDescription().c_str(), "An exception has occurred!", MB_OK | MB_ICONERROR | MB_TASKMODAL);
#else
std::cerr << "An exception has occurred: " <<
e.getFullDescription().c_str() << std::endl;
#endif
}
return 0;
}
#ifdef __cplusplus
}
#endif