Skip to content

Instantly share code, notes, and snippets.

@sukinull
Created March 3, 2014 15:36
Show Gist options
  • Save sukinull/9327512 to your computer and use it in GitHub Desktop.
Save sukinull/9327512 to your computer and use it in GitHub Desktop.
#include <boost/bind.hpp>
#include "EventBus.h"
std::hash<std::string> Event::key;
void EventBus::Init()
{
is_io_running = true;
m_work.reset(new boost::asio::io_service::work(io_service));
io_service.run(); // blocking
}
void EventBus::stop()
{
if (is_io_running) {
io_service.stop();
m_work.reset();
is_io_running = false;
}
if (m_thread.joinable())
m_thread.join();
}
EventBus::EventBus() : is_io_running(false)
{
m_thread = std::thread(&EventBus::Init, this);
}
EventBus::~EventBus()
{
stop();
}
EventBus& EventBus::Instance()
{
static EventBus eventBus;
return eventBus;
}
void EventBus::PostEvent(std::shared_ptr<Event>& evt)
{
uint16_t cateory = uint16_t(evt->type >> 16);
on& f = m_on[cateory];
io_service.post(boost::bind(f, evt));
}
void EventBus::Register(uint16_t category, on& receiver)
{
m_on[category] = receiver;
}
void EventBus::Unregister(uint16_t category)
{
std::map<uint16_t, on >::iterator it = m_on.find(category);
m_on.erase(it);
}
//
// EventBus.h
// OxAuth
//
// Created by sukinull on 11/15/13.
// Copyright (c) 2013 sukinull. All rights reserved.
//
#ifndef __OxAuth__EventBus__
#define __OxAuth__EventBus__
#include <stdint.h>
#include <memory>
#include <string>
#include <thread>
#include <boost/asio.hpp>
#include <boost/function.hpp>
#pragma once
/**
* struct B { virtual ~B() { } };
* struct D : B { };
*
* std::shared_ptr<B> bp(new D);
* std::shared_ptr<D> dp(static_pointer_cast<D>(b));
*/
struct Event;
struct Event
{
static std::hash<std::string> key;
virtual ~Event() {}
uint32_t type;
std::size_t source;
std::size_t target;
std::size_t modifier;
};
class EventBus : public boost::noncopyable
{
public:
typedef boost::function < void(std::shared_ptr<Event>)> on;
static EventBus& Instance();
void stop();
void PostEvent(std::shared_ptr<Event>& evt);
void Register(uint16_t category, on& receiver);
void Unregister(uint16_t category);
protected:
void Init();
EventBus();
~EventBus();
std::map<uint16_t, on > m_on;
std::thread m_thread;
bool is_io_running;
boost::asio::io_service io_service;
std::unique_ptr<boost::asio::io_service::work> m_work;
};
#endif /* defined(__OxAuth__EventBus__) */
#include <iostream>
#include <boost/bind.hpp>
#include <boost/function.hpp>
#include "EventBus.h"
class Handler {
public:
void Doit(std::shared_ptr<Event> evt) {
std::cout << "Evt: " << evt->source << " => " << evt->target << std::endl;
}
};
struct MyEvent : public Event
{
virtual ~MyEvent() {}
};
int main(int argc, char* argv[]) {
Handler h;
EventBus& eventBus = EventBus::Instance();
EventBus::on f = boost::bind(&Handler::Doit, &h, _1);
eventBus.Register(1, f);
std::string line;
while (1) {
std::getline(std::cin, line);
if ("q" == line)
break;
std::shared_ptr<Event> e(new MyEvent());
e->source = Event::key(line);
e->source = 0^Event::key(line);
e->type = 1L << 16;
eventBus.PostEvent(e);
}
eventBus.stop();
return EXIT_SUCCESS;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment