// overall layout: // queue for each led stripe // enum class EffectID { OFF, STATIC, CIRCLE, CIRCLE_WAVE, COLOR_FADE, RAINBOW_FADE, }; struct EffectCircularConfig { float speed; // in degrees per second float width; // width in degrees float brightnessFalloffFactor; }; template class AbstractEffect { public: virtual int operator()(TLedStrip &s) = 0; }; template class EffectCircle : public AbstractEffect { public: EffectCircle(const EffectCircularConfig &cfg) : config_(cfg) {} int operator()(TLedStrip &s) override; private: EffectCircularConfig config_; float currentPosition_; // between 0 and 1 }; unsigned char effectStorage[128]; template AbstractEffect *makeEffect(const char *buffer) { const EffectID &effectId = *reinterpret_cast(buffer); if (effectId == EffectID::CIRCLE) { auto cfg = reinterpret_cast(buffer + sizeof(EffectID)); return new (effectStorage) EffectCircle(*cfg); } // read effect id code from buffer // read config from buffer }