diff options
author | Thiago Marcos P. Santos <thiago@mapbox.com> | 2015-09-01 11:09:19 +0300 |
---|---|---|
committer | Thiago Marcos P. Santos <thiago@mapbox.com> | 2015-12-01 00:00:09 +0200 |
commit | d422c8cac4e436fb2fb1eeafbae5ed5d847e0b00 (patch) | |
tree | dd8efd2cd842820f3f13fddf40cc0039fb261363 /platform | |
parent | 1d623322044c4650bb39c9224f596341a23f490f (diff) | |
download | qtlocation-mapboxgl-d422c8cac4e436fb2fb1eeafbae5ed5d847e0b00.tar.gz |
[core] Abstract main loop inside RunLoop class
Diffstat (limited to 'platform')
-rw-r--r-- | platform/default/async_task.cpp | 2 | ||||
-rw-r--r-- | platform/default/run_loop.cpp | 83 | ||||
-rw-r--r-- | platform/node/src/node_mapbox_gl_native.cpp | 2 |
3 files changed, 85 insertions, 2 deletions
diff --git a/platform/default/async_task.cpp b/platform/default/async_task.cpp index 4b4372451c..1f2381f716 100644 --- a/platform/default/async_task.cpp +++ b/platform/default/async_task.cpp @@ -12,7 +12,7 @@ namespace util { class AsyncTask::Impl { public: Impl(std::function<void()>&& fn) - : async(RunLoop::getLoop(), [this] { runTask(); }) + : async(reinterpret_cast<uv_loop_t*>(RunLoop::getLoopHandle()), [this] { runTask(); }) , task(std::move(fn)) { } diff --git a/platform/default/run_loop.cpp b/platform/default/run_loop.cpp new file mode 100644 index 0000000000..7c3a74f2cb --- /dev/null +++ b/platform/default/run_loop.cpp @@ -0,0 +1,83 @@ +#include <mbgl/util/run_loop.hpp> + +#include <uv.h> + +namespace mbgl { +namespace util { + +uv::tls<RunLoop> RunLoop::current; + +class RunLoop::Impl { +public: + Impl() = default; + + uv_loop_t *loop; + RunLoop::Type type; +}; + +RunLoop::RunLoop(Type type) : impl(std::make_unique<Impl>()) { + switch (type) { + case Type::New: +#if UV_VERSION_MAJOR == 0 && UV_VERSION_MINOR <= 10 + impl->loop = uv_loop_new(); + if (impl->loop == nullptr) { +#else + impl->loop = new uv_loop_t; + if (uv_loop_init(impl->loop) != 0) { +#endif + throw std::runtime_error("Failed to initialize loop."); + } + break; + case Type::Default: + impl->loop = uv_default_loop(); + break; + } + + impl->type = type; + + current.set(this); + async = std::make_unique<AsyncTask>(std::bind(&RunLoop::process, this)); +} + +RunLoop::~RunLoop() { + current.set(nullptr); + + if (impl->type == Type::Default) { + return; + } + + // Run the loop again to ensure that async + // close callbacks have been called. Not needed + // for the default main loop because it is only + // closed when the application exits. + async.reset(); + runOnce(); + +#if UV_VERSION_MAJOR == 0 && UV_VERSION_MINOR <= 10 + uv_loop_delete(impl->loop); +#else + if (uv_loop_close(impl->loop) == UV_EBUSY) { + throw std::runtime_error("Failed to close loop."); + } + delete impl->loop; +#endif +} + +LOOP_HANDLE RunLoop::getLoopHandle() { + return current.get()->impl->loop; +} + +void RunLoop::run() { + uv_run(impl->loop, UV_RUN_DEFAULT); +} + +void RunLoop::runOnce() { + uv_run(impl->loop, UV_RUN_ONCE); +} + +void RunLoop::stop() { + invoke([&] { async->unref(); }); +} + +} +} diff --git a/platform/node/src/node_mapbox_gl_native.cpp b/platform/node/src/node_mapbox_gl_native.cpp index 4a86a8d855..e0b094d570 100644 --- a/platform/node/src/node_mapbox_gl_native.cpp +++ b/platform/node/src/node_mapbox_gl_native.cpp @@ -13,7 +13,7 @@ namespace node_mbgl { mbgl::util::RunLoop& NodeRunLoop() { - static mbgl::util::RunLoop nodeRunLoop(uv_default_loop()); + static mbgl::util::RunLoop nodeRunLoop; return nodeRunLoop; } |