12
12
#ifndef EMBER_APPLICATION_H
13
13
#define EMBER_APPLICATION_H
15
#include "services/EmberServices.h"
16
#include "framework/ConsoleObject.h"
17
#include "framework/ConsoleBackend.h"
18
#include "framework/MainLoopController.h"
20
#include <sigc++/signal.h>
21
#include <boost/date_time/posix_time/posix_time.hpp>
20
#include "services/EmberServices.h"
21
#include "framework/ConsoleObject.h"
22
#include "framework/ConsoleBackend.h"
25
#include <sigc++/signal.h>
27
#include <unordered_map>
31
33
* Ember is a client for the Worldforge virtual world system. It uses the 3d library <a href="http://www.ogre3d.org">OGRE</a> to show the world to the user, and the <a href="http://www.cegui.org.uk">CEGUI</a> library to present a user interface.
32
* Two of the design tenants of Ember is to both be as modular as possible, and to reuse existing FOSS components as much as possible. The list of dependencies for the client is therefore quite hefty, but the advantage is the wealth of capabilities.
34
* Two of the design tenets of Ember is to both be as modular as possible, and to reuse existing FOSS components as much as possible. The list of dependencies for the client is therefore quite hefty, but the advantage is the wealth of capabilities.
34
36
* @section SystemDesign System design
42
44
* Sometimes we need to extend the libraries used by Ember, such as Atlas or Eris. Any extension added should then be moved to the real library, but while it's either being developed it can be put in this layer.
44
* Commonly used services are to be placed here. It might not always be clear what constitutes a service, but the most common characteristic of a service is an adapted API over an external component. A service should be light weight and not keep to much state.
46
* Commonly used services are to be placed here. It might not always be clear what constitutes a service, but the most common characteristic of a service is an adapted API over an external component. A service should be light weight and not keep to much state. The services should never depend on anything which is handled by the components (for example Ogre, CEGUI, Lua etc.).
46
48
* The meat of the application is placed here. These are highly complex components which provide the main functionality of what is shown to the user.
110
class Application : public ConsoleObject, public Singleton<Application>, public virtual sigc::trackable
112
class Application: public ConsoleObject, public Singleton<Application>, public virtual sigc::trackable
113
typedef std::map<std::string, std::map<std::string, std::string> > ConfigMap;
115
typedef std::unordered_map<std::string, std::map<std::string, std::string>> ConfigMap;
121
123
Application(const std::string prefix, const std::string homeDir, const ConfigMap& configSettings);
124
* @brief At destruction pretty much all game objects will be destroyed.
126
* @brief At destruction pretty much all game objects will be destroyed.
126
128
virtual ~Application();
129
* @brief Performs one step of the main loop.
130
* You only need to call this each "frame" if you're not using mainLoop().
131
* @param minMillisecondsPerFrame If the fps is capped, this is the minimum milliseconds needed to spend on each frame.
133
void mainLoopStep(long minMillisecondsPerFrame);
131
* @brief Performs one step of the main loop.
132
* You only need to call this each "frame" if you're not using mainLoop().
133
* @param minMicrosecondsPerFrame If the fps is capped, this is the minimum microseconds needed to spend on each frame.
135
void mainLoopStep(long minMicrosecondsPerFrame);
136
* @brief Enters the main loop.
137
* Will loop through the application until it exits. In most cases you want to call this for the main loop. However, if you want to handle all looping yourself you can call mainLoopStep() manually.
138
* @brief Enters the main loop.
139
* Will loop through the application until it exits. In most cases you want to call this for the main loop. However, if you want to handle all looping yourself you can call mainLoopStep() manually.
142
* @brief Return true if application has received an "exit" command else false.
144
* @return true if "shouldquit" else false
149
144
* @brief Registers all components with the system.
150
145
* Make sure to call this before calling prepareComponents(). This will allow all components to register themselves with the system, but won't do anything more.
174
@brief Emitted when all services have been initialized.
169
@brief Emitted when all services have been initialized.
176
171
sigc::signal<void> EventServicesInitialized;
179
* @brief Causes the application to quit.
180
* This will instantly shut down the application, in contrast to requestQuit which will try to show a confirmation dialog to the user.
185
174
* @brief Callback for running Console Commands
187
void runCommand(const std::string& command,const std::string& args);
190
* @brief Sets whether eris should be polled each frame. Defaults to true.
191
* Normally Eris is polled each frame. A "poll" means that Eris is asked to send and receive any data from the server and act on it.
192
* @param doPoll True if polling should occur each frame.
194
void setErisPolling(bool doPoll);
197
* @brief Gets whether eris should be polled each frame.
198
* @return True if polling occurs each frame.
200
bool getErisPolling() const;
203
* @brief Emitted when the use wants to quit the game. Preferrebly the GUI should show some kind of confirmation window.
205
sigc::signal<void, bool&> EventRequestQuit;
208
* @brief Emitted before the eris polling is started.
209
* The parameter sent is the time slice since this event last was emitted.
211
sigc::signal<void, float> EventStartErisPoll;
214
* @brief Emitted after the eris polling has finished.
215
* The parameter sent is the time slice since this event last was emitted.
217
sigc::signal<void, float> EventEndErisPoll;
220
* @brief Emitted before processing input. This event is emitted continously.
221
* The parameter sent is the time slice since this event last was emitted.
223
sigc::signal<void, float> EventBeforeInputProcessing;
226
* @brief Emitted after processing input. This event is emitted continously.
227
* The parameter sent is the time slice since this event last was emitted.
229
sigc::signal<void, float> EventAfterInputProcessing;
232
* @brief Call this to "soft quit" the app. This means that an signal will be emitted, which hopefully will be taken care of by some widget, which will show a confirmation window, asking the user if he/she wants to quit.
233
* However, if there is no widget etc. handling the request, the application will instantly quit.
176
void runCommand(const std::string& command, const std::string& args);
238
179
* @brief Accessor for the main eris world view, if any.
254
194
bool mShouldQuit;
197
* @brief Controls whether eris should be polled at each frame update.
202
* @brief The main loop controller instance, which mainly controls whether the application should quit or not.
204
MainLoopController mMainLoopController;
257
207
* @brief The file system prefix to where Ember has been installed.
259
209
const std::string mPrefix;
281
231
Eris::View* mWorldView;
284
* @brief Controls whether eris should be polled at each frame update.
289
* @brief Keeps track of the last time an Eris poll started.
290
* Value is in milliseconds.
292
long long mLastTimeErisPollStart;
295
* @brief Keeps track of the last time an Eris poll ended.
296
* Value is in milliseconds.
298
long long mLastTimeErisPollEnd;
301
234
* @brief Keeps track of the last time input processing started.
302
* Value is in milliseconds.
304
long long mLastTimeInputProcessingStart;
236
boost::posix_time::ptime mLastTimeInputProcessingStart;
307
239
* @brief Keeps track of the last time input processing ended.
308
* Value is in milliseconds.
310
long long mLastTimeInputProcessingEnd;
241
boost::posix_time::ptime mLastTimeInputProcessingEnd;
313
244
* @brief Keeps track of the last time the main loop step completed.
314
* Value is in milliseconds.
316
long long mLastTimeMainLoopStepEnded;
319
* @brief We listen to the GotView event to be able to store a reference to the View instance.
321
* @param view The world view.
323
void Server_GotView(Eris::View* view);
326
* @brief We listen to the DestroyedView event so that we can remove our View reference.
328
void Server_DestroyedView();
246
boost::posix_time::ptime mLastTimeMainLoopStepEnded;
331
249
* @brief We hold a pointer to the stream to which all logging messages are written.
333
std::auto_ptr<std::ofstream> mLogOutStream;
251
std::unique_ptr<std::ofstream> mLogOutStream;
336
254
* @brief A transient copy of command line set config settings. The settings here will be injected into the ConfigService when the services are started.
352
270
* @brief Toggles the polling of data from eris. Normally Eris is polled each frame, but this can be turned off (mainly for debug reasons).
354
272
const ConsoleCommandWrapper ToggleErisPolling;
275
* @brief Provides resources to the scripting system.
277
IResourceProvider* mScriptingResourceProvider;
280
* @brief We listen to the GotView event to be able to store a reference to the View instance.
282
* @param view The world view.
284
void Server_GotView(Eris::View* view);
287
* @brief We listen to the DestroyedView event so that we can remove our View reference.
289
void Server_DestroyedView();
292
* @brief Starts the scripting system.
294
void startScripting();