Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/FICN/src/orxonox/orxonox.cc @ 569

Last change on this file since 569 was 568, checked in by scheusso, 17 years ago

added capability for presentation mode

File size: 13.6 KB
RevLine 
[74]1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
3 *
4 *
5 *   License notice:
6 *
[462]7 *   This program is free software; you can redistribute it and/or
8 *   modify it under the terms of the GNU General Public License
9 *   as published by the Free Software Foundation; either version 2
10 *   of the License, or (at your option) any later version.
[74]11 *
12 *   This program is distributed in the hope that it will be useful,
13 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
14 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 *   GNU General Public License for more details.
16 *
17 *   You should have received a copy of the GNU General Public License
[462]18 *   along with this program; if not, write to the Free Software
19 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
[74]20 *
21 *   Author:
22 *      Benjamin Knecht <beni_at_orxonox.net>, (C) 2007
23 *   Co-authors:
24 *      ...
25 *
26 */
27
[142]28/**
29 @file  orxonox.cc
[462]30 @brief Orxonox Main Class
[142]31 */
32
[462]33#include "orxonox.h"
34#include "graphicsEngine.h"
35
[379]36//#include <Ogre.h>
37// 40% speed up: (instead of Ogre.h)
38#include <OgreSceneNode.h>
39#include <OgreSceneManager.h>
40#include <OgreRoot.h>
41#include <OgreFrameListener.h>
42#include <OgreConfigFile.h>
43#include <OgreTextureManager.h>
44#include <OgreEntity.h>
45#include <OgreRenderWindow.h>
46
[137]47#include <OIS/OIS.h>
[346]48//#include <CEGUI/CEGUI.h>
49//#include <OgreCEGUIRenderer.h>
[74]50
[164]51#include <string>
52#include <iostream>
53
[496]54#include "objects/Tickable.h"
55#include "objects/Timer.h"
[542]56#include "core/ArgReader.h"
[496]57#include "core/Factory.h"
[568]58#include "core/Debug.h"
[496]59
[462]60#include "../loader/LevelLoader.h"
61#include "../audio/AudioManager.h"
[164]62
[337]63#include "spaceship_steering.h"
[164]64
[535]65#include "particle/ParticleInterface.h"
[337]66
[459]67//network stuff
[462]68#include "../network/Server.h"
69#include "../network/Client.h"
[473]70#include "../network/NetworkFrameListener.h"
[459]71
[142]72
[337]73namespace orxonox
74{
[462]75  using namespace Ogre;
[74]76
[462]77   // put this in seperate Class or solve the problem in another fashion
78  class OrxListener : public FrameListener, public OIS::MouseListener
79  {
80    public:
[519]81      OrxListener(OIS::Keyboard *keyboard, OIS::Mouse *mouse, audio::AudioManager*  auMan, SpaceshipSteering* steering)
[462]82      : mKeyboard(keyboard), mMouse(mouse)
83      {
[530]84
85
86
[462]87        speed = 250;
88        loop = 100;
89        rotate = 10;
90        mouseX = 0;
91        mouseY = 0;
92        maxMouseX = 0;
93        minMouseX = 0;
[337]94        moved = false;
[530]95
[519]96        steering_ = steering;
97
98        steering_->brakeRotate(rotate*10);
99        steering_->brakeLoop(loop);
100
[530]101
[462]102        mMouse->setEventCallback(this);
103        auMan_ = auMan;
[265]104      }
[462]105      bool frameStarted(const FrameEvent& evt)
106      {
[135]107
[462]108        auMan_->update();
[74]109
[462]110        mKeyboard->capture();
111        mMouse->capture();
112        if (mKeyboard->isKeyDown(OIS::KC_UP) || mKeyboard->isKeyDown(OIS::KC_W))
[519]113          steering_->moveForward(speed);
[462]114        else
[519]115          steering_->moveForward(0);
[462]116        if(mKeyboard->isKeyDown(OIS::KC_DOWN) || mKeyboard->isKeyDown(OIS::KC_S))
[519]117          steering_->brakeForward(speed);
[462]118        else
[519]119          steering_->brakeForward(speed/10);
[462]120        if (mKeyboard->isKeyDown(OIS::KC_RIGHT) || mKeyboard->isKeyDown(OIS::KC_D))
[519]121          steering_->loopRight(loop);
[462]122        else
[519]123          steering_->loopRight(0);
[462]124        if (mKeyboard->isKeyDown(OIS::KC_LEFT) || mKeyboard->isKeyDown(OIS::KC_A))
[519]125          steering_->loopLeft(loop);
[462]126        else
[519]127          steering_->loopLeft(0);
[337]128
[462]129        if(moved) {
[512]130          if (mouseY<=0)
[519]131            steering_->rotateUp(-mouseY*rotate);
[462]132          if (mouseY>0)
[519]133            steering_->rotateDown(mouseY*rotate);
[462]134          if (mouseX>0)
[519]135            steering_->rotateRight(mouseX*rotate);
[512]136          if (mouseX<=0)
[519]137            steering_->rotateLeft(-mouseX*rotate);
[512]138          mouseY = 0;
139          mouseX = 0;
[462]140          moved = false;
141        }
142        else {
[519]143          steering_->rotateUp(0);
144          steering_->rotateDown(0);
145          steering_->rotateRight(0);
146          steering_->rotateLeft(0);
[462]147        }
[337]148
[519]149                steering_->tick(evt.timeSinceLastFrame);
[530]150
151
152
[462]153//      scenemanager->spacehip->tick(evt.timesincelastframe);
[542]154        //if(mKeyboard->isKeyDown(OIS::KC_ESCAPE))
155          //cout << "maximal MouseX: " << maxMouseX << "\tminMouseX: " << minMouseX << endl;
[565]156        usleep(10);
[462]157        return !mKeyboard->isKeyDown(OIS::KC_ESCAPE);
158      }
[337]159
[462]160      bool mouseMoved(const OIS::MouseEvent &e)
[265]161      {
[511]162        mouseX += e.state.X.rel;
163        mouseY += e.state.Y.rel;
[462]164        if(mouseX>maxMouseX) maxMouseX = mouseX;
165        if(mouseX<minMouseX) minMouseX = mouseX;
[542]166        //cout << "mouseX: " << mouseX << "\tmouseY: " << mouseY << endl;
[462]167        moved = true;
168        return true;
[265]169      }
[74]170
[462]171      bool mousePressed(const OIS::MouseEvent &e, OIS::MouseButtonID id) { return true; }
172      bool mouseReleased(const OIS::MouseEvent &e, OIS::MouseButtonID id) { return true; }
[137]173
[265]174    private:
[462]175      float speed;
176      float rotate;
177      float loop;
178      float mouseY;
179      float mouseX;
180      float maxMouseX;
181      float minMouseX;
182      bool moved;
[265]183      OIS::Keyboard *mKeyboard;
184      OIS::Mouse *mMouse;
[462]185      audio::AudioManager*  auMan_;
[519]186      SpaceshipSteering* steering_;
[462]187  };
188  // init static singleton reference of Orxonox
189  Orxonox* Orxonox::singletonRef_ = NULL;
[137]190
[462]191  /**
192   * create a new instance of Orxonox
193   */
194  Orxonox::Orxonox()
195  {
196    ogre_ = new GraphicsEngine();
[546]197    dataPath_ = "";
[462]198  }
[74]199
[462]200  /**
201   * destruct Orxonox
202   */
203  Orxonox::~Orxonox()
204  {
205    // nothing to delete as for now
206  }
[265]207
[462]208  /**
209   * initialization of Orxonox object
210   * @param argc argument counter
211   * @param argv list of arguments
212   * @param path path to config (in home dir or something)
213   */
214  void Orxonox::init(int argc, char **argv, std::string path)
215  {
216    //TODO: find config file (assuming executable directory)
217    //TODO: read config file
218    //TODO: give config file to Ogre
[568]219    std::string mode;
220    if(argc>=2)
221      mode = std::string(argv[1]);
222    else
223      mode = "";
[542]224    ArgReader ar = ArgReader(argc, argv);
225    ar.checkArgument("mode", mode, false);
[546]226    ar.checkArgument("data", this->dataPath_, false);
[542]227    if(ar.errorHandling()) die();
[534]228
[542]229    if(mode == std::string("server"))
[462]230    {
231      serverInit(path);
[568]232      mode = SERVER;
[462]233    }
[542]234    else if(mode == std::string("client"))
[462]235    {
236      clientInit(path);
[568]237      mode = CLIENT;
[534]238    }
[542]239    else if(mode == std::string("presentation"))
[531]240    {
[568]241      serverInit(path);
242      mode = PRESENTATION;
[534]243    }
[568]244    else{
245      standaloneInit(path);
246      mode = STANDALONE;
247    }
[462]248  }
[263]249
[462]250  /**
251   * start modules
252   */
253  void Orxonox::start()
254  {
255    //TODO: start modules
[534]256    ogre_->startRender();
[462]257    //TODO: run engine
[534]258    createScene();
259    setupScene();
260    setupInputSystem();
261    createFrameListener();
262    Factory::createClassHierarchy();
[568]263    switch(mode_){
264    case PRESENTATION:
265      server_g->open();
266      break;
267    case SERVER:
268    case CLIENT:
269    case STANDALONE:
270    default:
271      break;
272    }
[534]273    startRenderLoop();
[462]274  }
[74]275
[462]276  /**
277   * @return singleton object
278   */
279  Orxonox* Orxonox::getSingleton()
280  {
281    if (!singletonRef_)
282      singletonRef_ = new Orxonox();
283    return singletonRef_;
284  }
[74]285
[462]286  /**
287   * error kills orxonox
288   */
289  void Orxonox::die(/* some error code */)
290  {
291    //TODO: destroy and destruct everything and print nice error msg
[542]292    delete this;
[462]293  }
[74]294
[568]295  void Orxonox::standaloneInit(std::string path)
[462]296  {
297    ogre_->setConfigPath(path);
298    ogre_->setup();
[473]299    root_ = ogre_->getRoot();
[534]300    if(!ogre_->load()) die(/* unable to load */);
[473]301
[534]302    //defineResources();
303    //setupRenderSystem();
304    //createRenderWindow();
305    //initializeResourceGroups();
306    /*createScene();
[473]307    setupScene();
308    setupInputSystem();
309    createFrameListener();
[496]310    Factory::createClassHierarchy();
[534]311    startRenderLoop();*/
[462]312  }
[534]313
[531]314  void Orxonox::playableServer(std::string path)
315  {
316    ogre_->setConfigPath(path);
317    ogre_->setup();
318    root_ = ogre_->getRoot();
319    defineResources();
320    setupRenderSystem();
321    createRenderWindow();
322    initializeResourceGroups();
323    createScene();
324    setupScene();
325    setupInputSystem();
326    Factory::createClassHierarchy();
327    createFrameListener();
328    try{
[534]329      server_g = new network::Server(); // add port and bindadress
330      server_g->open(); // open server and create listener thread
331      if(ogre_ && ogre_->getRoot())
332        ogre_->getRoot()->addFrameListener(new network::ServerFrameListener()); // adds a framelistener for the server
[560]333      COUT(3) << "Info: network framelistener added" << std::endl;
[534]334    }
[531]335    catch(exception &e)
336    {
[560]337      COUT(1) << "Error: There was a problem initialising the server :(" << std::endl;
[531]338    }
339    startRenderLoop();
340  }
[568]341 
342  void Orxonox::standalone(){
343   
344   
345   
346  }
[74]347
[462]348  void Orxonox::serverInit(std::string path)
349  {
350    ogre_->setConfigPath(path);
351    ogre_->setup();
[473]352    server_g = new network::Server(); // add some settings if wanted
[462]353    if(!ogre_->load()) die(/* unable to load */);
[568]354    // add network framelistener
[505]355    ogre_->getRoot()->addFrameListener(new network::ServerFrameListener());
[462]356  }
[164]357
[462]358  void Orxonox::clientInit(std::string path)
359  {
360    ogre_->setConfigPath(path);
361    ogre_->setup();
[473]362    client_g = new network::Client(); // address here
[462]363    if(!ogre_->load()) die(/* unable to load */);
[505]364    ogre_->getRoot()->addFrameListener(new network::ClientFrameListener());
[462]365  }
[258]366
[473]367  void Orxonox::defineResources()
368  {
369    Ogre::String secName, typeName, archName;
370    Ogre::ConfigFile cf;
371#if OGRE_PLATFORM == OGRE_PLATFORM_APPLE
372    cf.load(macBundlePath() + "/Contents/Resources/resources.cfg");
373#else
[546]374    cf.load(dataPath_ + "resources.cfg");
[473]375#endif
376
377    Ogre::ConfigFile::SectionIterator seci = cf.getSectionIterator();
378    while (seci.hasMoreElements())
379    {
380      secName = seci.peekNextKey();
381      Ogre::ConfigFile::SettingsMultiMap *settings = seci.getNext();
382      Ogre::ConfigFile::SettingsMultiMap::iterator i;
383      for (i = settings->begin(); i != settings->end(); ++i)
384      {
385        typeName = i->first;
386        archName = i->second;
387#if OGRE_PLATFORM == OGRE_PLATFORM_APPLE
388        Ogre::ResourceGroupManager::getSingleton().addResourceLocation( String(macBundlePath() + "/" + archName), typeName, secName);
389#else
390        Ogre::ResourceGroupManager::getSingleton().addResourceLocation( archName, typeName, secName);
391#endif
392      }
393    }
394  }
395
396  void Orxonox::setupRenderSystem()
397  {
[546]398    if (/*!root_->restoreConfig() &&*/ !root_->showConfigDialog())
[473]399      throw Exception(52, "User canceled the config dialog!", "OrxApplication::setupRenderSystem()");
400  }
401
402  void Orxonox::createRenderWindow()
403  {
404    root_->initialise(true, "OrxonoxV2");
405  }
406
407  void Orxonox::initializeResourceGroups()
408  {
409    TextureManager::getSingleton().setDefaultNumMipmaps(5);
410    ResourceGroupManager::getSingleton().initialiseAllResourceGroups();
411  }
412
[537]413  /**
414   *
415   * @param
416   */
[462]417  void Orxonox::createScene(void)
418  {
[480]419        // Init audio
[462]420    auMan_ = new audio::AudioManager();
[487]421
[480]422    // load this file from config
423    loader_ = new loader::LevelLoader("sample.oxw");
424    loader_->loadLevel();
[337]425
[480]426        /*
[462]427    auMan_->ambientAdd("a1");
428    auMan_->ambientAdd("a2");
429    auMan_->ambientAdd("a3");
430                                //auMan->ambientAdd("ambient1");
431    auMan_->ambientStart();
[480]432        */
[462]433  }
[337]434
435
[537]436  /**
437   *
438   */
[462]439  void Orxonox::setupScene()
440  {
441    SceneManager *mgr = ogre_->getSceneManager();
[512]442
[515]443
[525]444    SceneNode* node = (SceneNode*)mgr->getRootSceneNode()->getChild("OgreHeadNode");
[541]445//     SceneNode *node = mgr->getRootSceneNode()->createChildSceneNode("OgreHeadNode", Vector3(0,0,0));
[515]446
[337]447
[525]448    steering_ = new SpaceshipSteering(500, 200, 200, 200);
449    steering_->addNode(node);
[74]450
[537]451
452    particle::ParticleInterface *e = new particle::ParticleInterface(mgr,"engine","Orxonox/strahl");
[535]453    e->particleSystem_->setParameter("local_space","true");
[537]454    e->setPositionOfEmitter(0, Vector3(0,-10,200));
455    e->setDirection(Vector3(0,0,-1));
456    e->addToSceneNode(node);
[535]457
[537]458    particle::ParticleInterface *w = new particle::ParticleInterface(mgr,"schuss","Orxonox/schuss");
459    w->particleSystem_->setParameter("local_space","true");
460    w->newEmitter();
461    w->setDirection(Vector3(0,0,1));
462    w->setPositionOfEmitter(0, Vector3(10,10,0));
463    w->setPositionOfEmitter(1, Vector3(-10,10,0));
464    w->addToSceneNode(node);
[462]465  }
[137]466
467
[462]468  void Orxonox::setupInputSystem()
469  {
470    size_t windowHnd = 0;
471    std::ostringstream windowHndStr;
472    OIS::ParamList pl;
473    Ogre::RenderWindow *win = ogre_->getRoot()->getAutoCreatedWindow();
[137]474
[462]475    win->getCustomAttribute("WINDOW", &windowHnd);
476    windowHndStr << windowHnd;
477    pl.insert(std::make_pair(std::string("WINDOW"), windowHndStr.str()));
478    inputManager_ = OIS::InputManager::createInputSystem(pl);
[265]479
[462]480    try
[337]481    {
[462]482      keyboard_ = static_cast<OIS::Keyboard*>(inputManager_->createInputObject(OIS::OISKeyboard, false));
483      mouse_ = static_cast<OIS::Mouse*>(inputManager_->createInputObject(OIS::OISMouse, true));
[337]484    }
[462]485    catch (const OIS::Exception &e)
[459]486    {
[462]487      throw new Ogre::Exception(42, e.eText, "OrxApplication::setupInputSystem");
[459]488    }
[462]489  }
[137]490
[462]491  // we actually want to do this differently...
492  void Orxonox::createFrameListener()
[137]493  {
[496]494    TickFrameListener* TickFL = new TickFrameListener();
495    ogre_->getRoot()->addFrameListener(TickFL);
496
497    TimerFrameListener* TimerFL = new TimerFrameListener();
498    ogre_->getRoot()->addFrameListener(TimerFL);
499
[519]500    frameListener_ = new OrxListener(keyboard_, mouse_, auMan_, steering_);
[462]501    ogre_->getRoot()->addFrameListener(frameListener_);
[137]502  }
[462]503
504  void Orxonox::startRenderLoop()
[137]505  {
[511]506    // this is a hack!!!
507    // the call to reset the mouse clipping size should probably be somewhere
508    // else, however this works for the moment.
[523]509    unsigned int width, height, depth;
510    int left, top;
511    ogre_->getRoot()->getAutoCreatedWindow()->getMetrics(width, height, depth, left, top);
[511]512
[523]513    const OIS::MouseState &ms = mouse_->getMouseState();
514    ms.width = width;
515    ms.height = height;
[511]516
[462]517    ogre_->getRoot()->startRendering();
[74]518  }
519}
Note: See TracBrowser for help on using the repository browser.