Event Bus

November 9, 2025 - Sebastian Himmer
ProjectsC++
329 words 2 min read

EventBus

Over the span of my last three projects, I have found myself needing a system that connects two distinct parts of an application without coupling them tightly together.

I had a simple event-driven usecase in mind:

// player.cpp
int damage = 1;
Publish<PlayerDamaged>({damage});

// ui.cpp
Subscribe<PlayerDamaged>([](const PlayerDamaged& event) {
    // Do something with event.damage
});

I achieved this by creating the open-source EventBus library, which implements the aforementioned approach and creates a simple API for Subscribing, Unsubscribing, and Publishing.

The implementation heavily relies on typeids and lambdas, but is battle-tested in my last two game engine projects, where I used this system for the following:

  • Viewport Resize Events
  • Editor Entity and Resource Selection
  • Entity Destruction

I have not used this library for gameplay scripting, however that is something I will look into in my next project. The same way I use it for the editor events, I could apply it for cross-script communication, collision notifications, and others.

Showcase

The library in action looks like this:

#include "event_bus.hpp"

// Define custom events (any type works)
struct PlayerDamaged {
    int playerId;
    float damage;
};

struct GameOver {
    int winnerId;
};

// Create event bus
EventBus bus;

// Subscribe to events, with the pointer to this class as a handle for later unsubscription.
bus.Subscribe<PlayerDamaged>([](const PlayerDamaged& e) {
    std::cout << "Player " << e.playerId << " took " << e.damage << " damage\n";
}, this);

bus.Subscribe<GameOver>([](const GameOver& e) {
    std::cout << "Player " << e.winnerId << " wins!\n";
}, this);

// Publish events
bus.Publish(PlayerDamaged{1, 25.0f});
bus.Publish(GameOver{1});

// Unsubscribe
bus.Unsubscribe<PlayerDamaged>(this);
bus.Unsubscribe<GameOver>(this);

Future

There are quite some limitations right now, primarily regarding thread safety and a lacking subscription handle implementation. I am going to keep using this library in my future projects and improve it whenever I find it applicable.