<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html401/loose.dtd"> <html> <!-- Created by texi2html 1.76 --> <!-- Written by: Lionel Cons <Lionel.Cons@cern.ch> (original author) Karl Berry <karl@freefriends.org> Olaf Bachmann <obachman@mathematik.uni-kl.de> and many others. Maintained by: Many creative people <dev@texi2html.cvshome.org> Send bugs and suggestions to <users@texi2html.cvshome.org> --> <head> <title>Crystal Space 1.2.1: 4.2.4.11 AppMazing Main Class</title> <meta name="description" content="Crystal Space 1.2.1: 4.2.4.11 AppMazing Main Class"> <meta name="keywords" content="Crystal Space 1.2.1: 4.2.4.11 AppMazing Main Class"> <meta name="resource-type" content="document"> <meta name="distribution" content="global"> <meta name="Generator" content="texi2html 1.76"> <meta http-equiv="Content-Type" content="text/html; charset=us-ascii"> <style type="text/css"> <!-- a.summary-letter {text-decoration: none} pre.display {font-family: serif} pre.format {font-family: serif} pre.menu-comment {font-family: serif} pre.menu-preformatted {font-family: serif} pre.smalldisplay {font-family: serif; font-size: smaller} pre.smallexample {font-size: smaller} pre.smallformat {font-family: serif; font-size: smaller} pre.smalllisp {font-size: smaller} span.sansserif {font-family:sans-serif; font-weight:normal;} ul.toc {list-style: none} --> </style> </head> <body lang="en" bgcolor="#FFFFFF" text="#000000" link="#0000FF" vlink="#800080" alink="#FF0000"> <a name="Mazing-AppMazing-Class"></a> <a name="0"></a> <table cellpadding="1" cellspacing="1" border="0"> <tr><td valign="middle" align="left">[<a href="Mazing-Game-Class.html#0" title="Previous section in reading order"> < </a>]</td> <td valign="middle" align="left">[<a href="SCF-Chapter.html#0" title="Next section in reading order"> > </a>]</td> <td valign="middle" align="left"> </td> <td valign="middle" align="left">[<a href="Using-Crystal-Space.html#0" title="Beginning of this chapter or previous chapter"> << </a>]</td> <td valign="middle" align="left">[<a href="Tutorial-Mazing.html#0" title="Up section"> Up </a>]</td> <td valign="middle" align="left">[<a href="Working-with-Engine-Content.html#0" title="Next chapter"> >> </a>]</td> <td valign="middle" align="left"> </td> <td valign="middle" align="left"> </td> <td valign="middle" align="left"> </td> <td valign="middle" align="left"> </td> <td valign="middle" align="left">[<a href="index.html#SEC_Top" title="Cover (top) of document">Top</a>]</td> <td valign="middle" align="left">[<a href="cs_toc.html#SEC_Contents" title="Table of contents">Contents</a>]</td> <td valign="middle" align="left">[<a href="cs_Index.html#0" title="Index">Index</a>]</td> <td valign="middle" align="left">[<a href="cs_abt.html#SEC_About" title="About (help)"> ? </a>]</td> </tr></table> <hr size="1"> <h4 class="subsubsection"> 4.2.4.11 AppMazing Main Class </h4> <p><code>AppMazing</code> is the main application class. Besides the usual Crystal Space setup code it also contains the event handling code. </p> <table><tr><td> </td><td><pre class="example">class AppMazing : public csApplicationFramework, public csBaseEventHandler { private: /** * A reference to the 3D renderer plugin. */ csRef<iGraphics3D> g3d; /** * A reference to the 3D engine plugin. */ csRef<iEngine> engine; /** * The main loader. */ csRef<iLoader> loader; /** * The view. */ csRef<iView> view; /** * The collision detection system. */ csRef<iCollideSystem> cdsys; /** * The virtual clock. */ csRef<iVirtualClock> vc; /** * The string registry. This is used for common constants in * Crystal Space. */ csRef<iStringSet> strings; /** * Set up everything that needs to be rendered on screen. This routine is * called from the event handler in response to a cscmdProcess broadcast * message. */ virtual void ProcessFrame(); /** * Finally, render the screen. This routine is called from the event handler * in response to a cscmdFinalProcess broadcast message. */ virtual void FinishFrame(); /** * Handle keyboard events, such as key presses and releases. This routine is * called from the event handler in response to a csevKeyboard event. */ virtual bool OnKeyboard(iEvent&); /// The Game. Game game; public: /** * Constructor. */ AppMazing(); /** * Destructor. */ virtual ~AppMazing(); iCamera* GetCamera () const { return view->GetCamera (); } iEngine* GetEngine () const { return engine; } iLoader* GetLoader () const { return loader; } iStringSet* GetStrings () const { return strings; } iCollideSystem* GetCollisionDetectionSystem () const { return cdsys; } Game& GetGame () { return game; } /** * Final cleanup. */ virtual void OnExit(); /** * Main initialization routine. This routine should set up basic facilities * (such as loading startup-time plugins, etc.). In case of failure this * routine will return false. You can assume that the error message has been * reported to the user. */ virtual bool OnInitialize(int argc, char* argv[]); /** * Run the application. Performs additional initialization (if needed), and * then fires up the main run/event loop. The loop will fire events which * actually causes Crystal Space to "run". Only when the program exits does * this function return. */ virtual bool Application(); // Declare the name of this event handler. CS_EVENTHANDLER_NAMES("application.mazing") /* Declare that we're not terribly interested in having events delivered to us before or after other modules, plugins, etc. */ CS_EVENTHANDLER_NIL_CONSTRAINTS }; </pre></td></tr></table> <p>This is the basic Crystal Space setup code. All game logic is handled in the <code>Game</code> class of which we have one instance here (<samp>‘game’</samp>). </p> <table><tr><td> </td><td><pre class="example">CS_IMPLEMENT_APPLICATION AppMazing::AppMazing() : csApplicationFramework(), game (this) { SetApplicationName("mazing"); } AppMazing::~AppMazing() { } </pre></td></tr></table> <p>Just the constructor and the destructor. </p> <table><tr><td> </td><td><pre class="example">void AppMazing::ProcessFrame() { csTicks elapsed_time = vc->GetElapsedTicks (); game.Handle (elapsed_time); // Tell 3D driver we're going to display 3D things. if (!g3d->BeginDraw (engine->GetBeginDrawFlags () | CSDRAW_3DGRAPHICS)) return; view->Draw (); } void AppMazing::FinishFrame() { g3d->FinishDraw(); g3d->Print(0); } </pre></td></tr></table> <p><code>ProcessFrame()</code> and <code>FinishDraw()</code> are automatically called every frame. In <code>ProcessFrame()</code> we will let the <code>Game</code> class handle all game logic and finally we will render the 3D view. We use the virtual clock to get the elapsed time since previous frame. </p> <table><tr><td> </td><td><pre class="example">bool AppMazing::OnKeyboard(iEvent& ev) { // We got a keyboard event. if (csKeyEventHelper::GetEventType(&ev) == csKeyEventTypeDown) { // The user pressed a key (as opposed to releasing it). utf32_char code = csKeyEventHelper::GetCookedCode(&ev); if (code == CSKEY_ESC) { // The user pressed escape, so terminate the application. The proper // way to terminate a Crystal Space application is by broadcasting a // csevQuit event. That will cause the main run loop to stop. To do // so we retrieve the event queue from the object registry and then // post the event. csRef<iEventQueue> q = csQueryRegistry<iEventQueue> (GetObjectRegistry()); if (q.IsValid()) q->GetEventOutlet()->Broadcast(csevQuit(GetObjectRegistry())); } else { return game.OnKeyboard (ev); } } return false; } </pre></td></tr></table> <p>In this function we handle all keyboard events. The escape key is handled here because that's not related to game logic. All other keys are passed to the <code>Game</code> instance. </p> <table><tr><td> </td><td><pre class="example">bool AppMazing::OnInitialize(int argc, char* argv[]) { iObjectRegistry* r = GetObjectRegistry(); // Load application-specific configuration file. if (!csInitializer::SetupConfigManager(r, 0, GetApplicationName())) return ReportError("Failed to initialize configuration manager!"); // RequestPlugins() will load all plugins we specify. In addition it will // also check if there are plugins that need to be loaded from the // configuration system (both the application configuration and CS or global // configurations). It also supports specifying plugins on the command line // via the --plugin= option. if (!csInitializer::RequestPlugins(r, CS_REQUEST_VFS, CS_REQUEST_OPENGL3D, CS_REQUEST_ENGINE, CS_REQUEST_FONTSERVER, CS_REQUEST_IMAGELOADER, CS_REQUEST_LEVELLOADER, CS_REQUEST_PLUGIN ("crystalspace.collisiondetection.opcode", iCollideSystem), CS_REQUEST_REPORTER, CS_REQUEST_REPORTERLISTENER, CS_REQUEST_END)) return ReportError("Failed to initialize plugins!"); // "Warm up" the event handler so it can interact with the world csBaseEventHandler::Initialize(r); // Set up an event handler for the application. Crystal Space is fully // event-driven. Everything (except for this initialization) happens in // response to an event. if (!RegisterQueue (r, csevAllEvents(GetObjectRegistry()))) return ReportError("Failed to set up event handler!"); return true; } void AppMazing::OnExit() { } bool AppMazing::Application() { iObjectRegistry* r = GetObjectRegistry(); // Open the main system. This will open all the previously loaded plugins // (i.e. all windows will be opened). if (!OpenApplication(r)) return ReportError("Error opening system!"); // Now get the pointer to various modules we need. We fetch them from the // object registry. The RequestPlugins() call we did earlier registered all // loaded plugins with the object registry. It is also possible to load // plugins manually on-demand. g3d = csQueryRegistry<iGraphics3D> (r); if (!g3d) return ReportError("Failed to locate 3D renderer!"); engine = csQueryRegistry<iEngine> (r); if (!engine) return ReportError("Failed to locate 3D engine!"); loader = csQueryRegistry<iLoader> (r); if (!loader) return ReportError("Failed to locate the map loader!"); cdsys = csQueryRegistry<iCollideSystem> (r); if (!cdsys) return ReportError("Failed to locate the collision detection system!"); vc = csQueryRegistry<iVirtualClock> (r); if (!vc) return ReportError("Failed to locate the virtual clock!"); strings = csQueryRegistryTagInterface<iStringSet> (r, "crystalspace.shared.stringset"); if (!strings) return ReportError("Failed to locate the standard stringset!"); // Setup game. if (!game.SetupGame ()) return false; // Create a view. view = csPtr<iView> (new csView (engine, g3d)); view->GetCamera ()->SetSector (engine->FindSector ("room_0_0_0")); view->GetCamera ()->GetTransform ().SetOrigin (csVector3 (0, 0, 0)); iGraphics2D* g2d = g3d->GetDriver2D (); view->SetRectangle (0, 0, g2d->GetWidth (), g2d->GetHeight ()); // Start the default run/event loop. This will return only when some code, // such as OnKeyboard(), has asked the run loop to terminate. Run(); return true; } </pre></td></tr></table> <p>These are the main initialization functions. We also create our view here. </p> <table><tr><td> </td><td><pre class="example">int main(int argc, char** argv) { csPrintf ("mazing version 1.0 by Jorrit Tyberghein.\n"); /* Runs the application. * * csApplicationRunner<> cares about creating an application instance * which will perform initialization and event handling for the entire game. * * The underlying csApplicationFramework also performs some core * initialization. It will set up the configuration manager, event queue, * object registry, and much more. The object registry is very important, * and it is stored in your main application class (again, by * csApplicationFramework). */ return csApplicationRunner<AppMazing>::Run (argc, argv); } </pre></td></tr></table> <p>Finally the main program. </p> <hr size="1"> <table cellpadding="1" cellspacing="1" border="0"> <tr><td valign="middle" align="left">[<a href="Mazing-Game-Class.html#0" title="Previous section in reading order"> < </a>]</td> <td valign="middle" align="left">[<a href="SCF-Chapter.html#0" title="Next section in reading order"> > </a>]</td> <td valign="middle" align="left"> </td> <td valign="middle" align="left">[<a href="Using-Crystal-Space.html#0" title="Beginning of this chapter or previous chapter"> << </a>]</td> <td valign="middle" align="left">[<a href="Tutorial-Mazing.html#0" title="Up section"> Up </a>]</td> <td valign="middle" align="left">[<a href="Working-with-Engine-Content.html#0" title="Next chapter"> >> </a>]</td> <td valign="middle" align="left"> </td> <td valign="middle" align="left"> </td> <td valign="middle" align="left"> </td> <td valign="middle" align="left"> </td> <td valign="middle" align="left">[<a href="index.html#SEC_Top" title="Cover (top) of document">Top</a>]</td> <td valign="middle" align="left">[<a href="cs_toc.html#SEC_Contents" title="Table of contents">Contents</a>]</td> <td valign="middle" align="left">[<a href="cs_Index.html#0" title="Index">Index</a>]</td> <td valign="middle" align="left">[<a href="cs_abt.html#SEC_About" title="About (help)"> ? </a>]</td> </tr></table> <p> <font size="-1"> This document was generated using <a href="http://texi2html.cvshome.org/"><em>texi2html 1.76</em></a>. </font> <br> </p> </body> </html>