diff options
Diffstat (limited to 'mwe/events/src/eventManager.cpp')
-rw-r--r-- | mwe/events/src/eventManager.cpp | 108 |
1 files changed, 108 insertions, 0 deletions
diff --git a/mwe/events/src/eventManager.cpp b/mwe/events/src/eventManager.cpp index 8b13789..ce8e940 100644 --- a/mwe/events/src/eventManager.cpp +++ b/mwe/events/src/eventManager.cpp @@ -1 +1,109 @@ +#include "eventManager.h" +void EventManager::shutdown() +{ + m_subscribers.clear(); +} + +void EventManager::subscribe(int eventType, std::unique_ptr<IEventHandlerWrapper>&& handler, int eventId) +{ + if (eventId) { + std::unordered_map<int, std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>>::iterator subscribers = m_subscribersByEventId.find(eventType); + + if (subscribers != m_subscribersByEventId.end()) { + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>& handlersMap = subscribers->second; + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>::iterator handlers = handlersMap.find(eventId); + if (handlers != handlersMap.end()) { + handlers->second.emplace_back(std::move(handler)); + return; + } + } + m_subscribersByEventId[eventType][eventId].emplace_back(std::move(handler)); + + } else { + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>::iterator subscribers = m_subscribers.find(eventType); + if (subscribers != m_subscribers.end()) { + std::vector<std::unique_ptr<IEventHandlerWrapper>>& handlers = subscribers->second; + for (std::unique_ptr<IEventHandlerWrapper>& it : handlers) { + if (it->getType() == handler->getType()) { + // log for double register + return; + } + } + handlers.emplace_back(std::move(handler)); + } else { + m_subscribers[eventType].emplace_back(std::move(handler)); + } + } +} + +void EventManager::unsubscribe(int eventType, const std::string& handlerName, int eventId) +{ + if (eventId) { + std::unordered_map<int, std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>>::iterator subscribers = m_subscribersByEventId.find(eventType); + if (subscribers != m_subscribersByEventId.end()) { + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>& handlersMap = subscribers->second; + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>::iterator handlers = handlersMap.find(eventId); + if (handlers != handlersMap.end()) { + std::vector<std::unique_ptr<IEventHandlerWrapper>>& callbacks = handlers->second; + for (std::vector<std::unique_ptr<IEventHandlerWrapper>>::iterator it = callbacks.begin(); it != callbacks.end(); ++it) { + if (it->get()->getType() == handlerName) { + it = callbacks.erase(it); + return; + } + } + } + } + } else { + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>::iterator handlersIt = m_subscribers.find(eventType); + if (handlersIt != m_subscribers.end()) { + std::vector<std::unique_ptr<IEventHandlerWrapper>>& handlers = handlersIt->second; + for (std::vector<std::unique_ptr<IEventHandlerWrapper>>::iterator it = handlers.begin(); it != handlers.end(); ++it) { + if (it->get()->getType() == handlerName) { + it = handlers.erase(it); + return; + } + } + } + } +} + +void EventManager::triggerEvent(const Event& event_, int eventId) +{ + std::vector<std::unique_ptr<IEventHandlerWrapper>>& handlers = m_subscribers[event_.getEventType()]; + for (std::unique_ptr<IEventHandlerWrapper>& handler : handlers) { + handler->exec(event_); + } + + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>& handlersMap = m_subscribersByEventId[event_.getEventType()]; + std::unordered_map<int, std::vector<std::unique_ptr<IEventHandlerWrapper>>>::iterator handlersIt = handlersMap.find(eventId); + if (handlersIt != handlersMap.end()) { + std::vector<std::unique_ptr<IEventHandlerWrapper>>& callbacks = handlersIt->second; + for (std::vector<std::unique_ptr<IEventHandlerWrapper>>::iterator it = callbacks.begin(); it != callbacks.end();) { + std::unique_ptr<IEventHandlerWrapper>& handler = *it; + handler->exec(event_); + if (handler->isDestroyOnSuccess()) { + it = callbacks.erase(it); + } else { + ++it; + } + } + } +} + +void EventManager::queueEvent(std::unique_ptr<Event>&& event_, int eventId) +{ + m_eventsQueue.emplace_back(std::move(event_), eventId); +} + +void EventManager::dispatchEvents() +{ + for (std::vector<std::pair<std::unique_ptr<Event>, int>>::iterator eventIt = m_eventsQueue.begin(); eventIt != m_eventsQueue.end();) { + if (!eventIt->first.get()->getHandled()) { + triggerEvent(*eventIt->first.get(), eventIt->second); + eventIt = m_eventsQueue.erase(eventIt); + } else { + ++eventIt; + } + } +} |