X-Git-Url: https://git.dogcows.com/gitweb?p=chaz%2Fyoink;a=blobdiff_plain;f=src%2FMoof%2FEngine.cc;h=f4bc712b27887d0b5397c579fc861d196ffc3bc6;hp=9ff5e1a8f1158188a4e58832a8a36a02c78ebcfb;hb=e495074443d9fd7bc16137084cf9de3d031b75c4;hpb=c9e20ac06383b20ceb5404c9237e319c2e90d157 diff --git a/src/Moof/Engine.cc b/src/Moof/Engine.cc index 9ff5e1a..f4bc712 100644 --- a/src/Moof/Engine.cc +++ b/src/Moof/Engine.cc @@ -35,15 +35,14 @@ #include "fastevents.h" #include -#include "Dispatcher.hh" #include "Engine.hh" #include "Event.hh" #include "Exception.hh" #include "Log.hh" +#include "Math.hh" #include "Random.hh" #include "Settings.hh" #include "Timer.hh" -#include "Video.hh" namespace Mf { @@ -53,36 +52,36 @@ class Engine::Impl { public: - Impl(int argc, char* argv[], const std::string& name, - const std::string& iconFile, const std::string& configFile, - Engine& engine) : + Impl(Engine& engine) : mInterface(engine), mTimestep(0.01), mPrintFps(false) { -#if defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) || defined(__WINDOWS__) + // first, initialize the libraries + +#if defined(_WIN32) || defined(__WIN32__) if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER) != 0) #else if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_EVENTTHREAD) != 0) #endif { const char* error = SDL_GetError(); - logError("sdl is complaining: %s", error); throw Exception(ErrorCode::SDL_INIT, error); } if (FE_Init() != 0) { const char* error = FE_GetError(); - logError("fast events error: %s", error); throw Exception(ErrorCode::FASTEVENTS_INIT, error); } - alutInit(&argc, argv); + int argc = 1; + char name[] = "hello"; + alutInit(&argc, (char**)&name); + + // now load the settings the engine needs Settings& settings = Settings::getInstance(); - settings.loadFromFile(configFile); - settings.parseArgs(argc, argv); - long randomSeed; + unsigned randomSeed; if (settings.get("rngseed", randomSeed)) setSeed(randomSeed); else setSeed(); @@ -92,12 +91,10 @@ public: Scalar maxFps = 40.0; settings.get("maxfps", maxFps); - mDrawRate = 1.0 / maxFps; + mMaxFps = 1.0 / maxFps; + capFps(); settings.get("printfps", mPrintFps); - - mVideo = Video::alloc(name, iconFile); - mVideo->makeActive(); } ~Impl() @@ -139,14 +136,15 @@ public: deltaTime = newTicks - ticksNow; ticksNow = newTicks; + // don't slow the animation until 4Hz, which is unplayable anyway if (deltaTime >= 0.25) deltaTime = 0.25; accumulator += deltaTime; Timer::fireIfExpired(ticksNow); + dispatchEvents(); while (accumulator >= mTimestep) { - dispatchEvents(); update(totalTime, mTimestep); totalTime += mTimestep; @@ -183,17 +181,17 @@ public: draw(accumulator / mTimestep); mVideo->swap(); - nextDraw += mDrawRate; + nextDraw += mMaxFps; if (ticksNow >= nextDraw) { // we missed some scheduled draws, so reset the schedule - nextDraw = ticksNow + mDrawRate; + nextDraw = ticksNow + mMaxFps; } } // be a good citizen and give back what you don't need Timer::sleep(std::min(std::min(nextStep, nextDraw), - Timer::getNextFire()), true); + Timer::getNextFire()), Timer::ACTUAL); } while (!mStack.empty()); } @@ -211,7 +209,8 @@ public: (SDL_GetModState() & KMOD_CTRL) ) { // emergency escape - exit(0); + logWarning("escape forced"); + exit(1); } break; @@ -229,7 +228,7 @@ public: { for (mStackIt = mStack.begin(); mStackIt != mStack.end(); ++mStackIt) { - (*mStackIt)->update(t, dt); + (*mStackIt)->update(mInterface, t, dt); } } @@ -239,7 +238,7 @@ public: std::list::reverse_iterator it; for (it = mStack.rbegin(); it != mStack.rend(); ++it) { - (*it)->draw(alpha); + (*it)->draw(mInterface, alpha); } } @@ -247,7 +246,7 @@ public: { for (mStackIt = mStack.begin(); mStackIt != mStack.end(); ++mStackIt) { - if ((*mStackIt)->handleEvent(event)) break; + if ((*mStackIt)->handleEvent(mInterface, event)) break; } } @@ -256,7 +255,7 @@ public: { ASSERT(layer && "cannot push null layer"); mStack.push_front(layer); - logInfo(" push: %d", mStack.size()); + logDebug("stack: %d [pushed %X]", mStack.size(), layer.get()); layer->pushed(mInterface); } @@ -265,26 +264,26 @@ public: bool fixIt = false; if (mStack.begin() == mStackIt) fixIt = true; - LayerP popped = mStack.front(); + LayerP layer = mStack.front(); mStack.pop_front(); - logInfo(" pop: %d", mStack.size()); - popped->popped(mInterface); + logDebug("stack: %d [popped %X]", mStack.size(), layer.get()); + layer->popped(mInterface); if (fixIt) mStackIt = --mStack.begin(); - return popped; + return layer; } LayerP pop(Layer* layer) { bool fixIt = false; - std::list popped; + std::list layers; std::list::iterator it; for (it = mStack.begin(); it != mStack.end(); ++it) { - popped.push_back(*it); + layers.push_back(*it); if (it == mStackIt) fixIt = true; @@ -293,14 +292,15 @@ public: ++it; mStack.erase(mStack.begin(), it); - for (it = popped.begin(); it != popped.end(); ++it) + for (it = layers.begin(); it != layers.end(); ++it) { (*it)->popped(mInterface); + logDebug("stack: %d [popped %X]", mStack.size(), (*it).get()); } if (fixIt) mStackIt = --mStack.begin(); - return popped.back(); + return layers.back(); } } @@ -311,77 +311,83 @@ public: { mStack.clear(); mStackIt = mStack.begin(); - logInfo("clear: %d", mStack.size()); + logDebug("stack: 0 [cleared]"); } - Engine& mInterface; + void capFps() + { + if (mMaxFps < mTimestep) + { + logWarning("capping maximum fps to timestep (%f)", mTimestep); + mMaxFps = mTimestep; + } + } + - VideoP mVideo; + Engine& mInterface; + VideoP mVideo; + Dispatch mDispatch; std::list mStack; std::list::iterator mStackIt; - Scalar mTimestep; - Scalar mDrawRate; + Scalar mTimestep; + Scalar mMaxFps; - long mFps; - bool mPrintFps; + int mFps; + bool mPrintFps; }; -static Engine* instance = 0; - -Engine::Engine(int argc, char* argv[], const std::string& name, - const std::string& iconFile, const std::string& configFile) : - mImpl(new Engine::Impl(argc, argv, name, iconFile, configFile, *this)) -{ - instance = this; -} - +Engine::Engine() : + // pass through + mImpl(new Engine::Impl(*this)) {} Engine& Engine::getInstance() { - ASSERT(instance && "dereferencing null pointer"); - return *instance; - // TODO this has not been completely thought out - //static Engine engine; - //return engine; + static Engine engine; + return engine; } -void Engine::run() +void Engine::setVideo(VideoP video) { - return mImpl->run(); + // pass through + mImpl->mVideo = video; } -void Engine::setTimestep(Scalar ts) +VideoP Engine::getVideo() const { - mImpl->mTimestep = ts; + return mImpl->mVideo; } -Scalar Engine::getTimestep() const + +void Engine::setTimestep(int ts) { - return mImpl->mTimestep; + mImpl->mTimestep = 1.0 / Scalar(ts); + mImpl->capFps(); } -void Engine::setMaxFrameRate(long maxFps) +int Engine::getTimestep() const { - mImpl->mDrawRate = 1.0 / Scalar(maxFps); + return int(1.0 / mImpl->mTimestep); } -long Engine::getMaxFrameRate() const + +void Engine::setMaxFps(int maxFps) { - return long(1.0 / mImpl->mDrawRate); + mImpl->mMaxFps = 1.0 / Scalar(maxFps); + mImpl->capFps(); } - -Video& Engine::getVideo() const +int Engine::getMaxFps() const { - return *mImpl->mVideo; + return int(1.0 / mImpl->mMaxFps); } -long Engine::getFrameRate() const + +int Engine::getFps() const { return mImpl->mFps; } @@ -411,6 +417,37 @@ void Engine::clear() mImpl->clear(); } +int Engine::getSize() const +{ + return mImpl->mStack.size(); +} + + +void Engine::run() +{ + // pass through + return mImpl->run(); +} + + +Dispatch::Handler Engine::addHandler(const std::string& event, + const Dispatch::Function& callback) +{ + return mImpl->mDispatch.addHandler(event, callback); +} + +Dispatch::Handler Engine::addHandler(const std::string& event, + const Dispatch::Function& callback, Dispatch::Handler handler) +{ + return mImpl->mDispatch.addHandler(event, callback, handler); +} + +void Engine::dispatch(const std::string& event, + const Dispatch::Message* message) +{ + mImpl->mDispatch.dispatch(event, message); +} + } // namespace Mf