Skip to content

Usage Class Members

Andrew Gresyk edited this page Apr 2, 2022 · 4 revisions

FSMs as Class Members

  1. The main goal here is to avoid #include <hfsm2/machine.hpp> in the class header, thus reducing the build times.

.hpp

class Actor {
public:
    using FsmHost = char[32]; // the size is hand-adjusted

    struct Context { /* .. */ };

public:
    Actor();
    ~Actor();

private:
    Context _context;
    FsmHost _fsmHost;
};

.cpp

#include "actor.hpp"
#include <hfsm2/machine.hpp>

namespace actor_fsm {

    using Config = hfsm2::Config
                        ::ContextT<Actor::Context&>;

    using M = hfsm2::MachineT<Config>;

    #define S(s) struct s
    using FSM = M::PeerRoot<
                    S(Off),
                    S(On)
                >;
    #undef S

    struct Off : FSM::State { /* .. */ };
    struct On  : FSM::State { /* .. */ };

    FSM::Instance&
    fsm(Actor::FsmHost& fsmHost) {
        return *reinterpret_cast<FSM::Instance*>(&fsmHost);
    }

}

Actor::Actor() {
    //hfsm2::StaticPrintConstT<sizeof(actor_fsm::FSM::Instance)> dummy;
    static_assert(sizeof(actor_fsm::FSM::Instance) <= sizeof(FsmHost), "");

    new (&_fsmHost) actor_fsm::FSM::Instance{_context};
}

Actor::~Actor() {
    actor_fsm::fsm(_fsmHost).~RC_();
}
Clone this wiki locally