diff --git a/config/hyperion.config.json b/config/hyperion.config.json index 61fb7865..8e361ed0 100644 --- a/config/hyperion.config.json +++ b/config/hyperion.config.json @@ -81,7 +81,7 @@ "type" : "none", "time_ms" : 200, "updateFrequency" : 20.0000, - "framesDelay" : 0 + "updateDelay" : 0 } }, diff --git a/libsrc/hyperion/Hyperion.cpp b/libsrc/hyperion/Hyperion.cpp index 9b5eb9b9..5e76d8e8 100644 --- a/libsrc/hyperion/Hyperion.cpp +++ b/libsrc/hyperion/Hyperion.cpp @@ -243,9 +243,13 @@ LedDevice * Hyperion::createColorSmoothing(const Json::Value & smoothingConfig, } else { -// const unsigned framesDelay = smoothingConfig.get("framesDelay", Json::Value(0u)).asUInt(); + const unsigned updateDelay = smoothingConfig.get("updateDelay", Json::Value(0u)).asUInt(); std::cout << "Creating linear smoothing" << std::endl; - return new LinearColorSmoothing(ledDevice, smoothingConfig["updateFrequency"].asDouble(), smoothingConfig["time_ms"].asInt()); + return new LinearColorSmoothing( + ledDevice, + smoothingConfig["updateFrequency"].asDouble(), + smoothingConfig["time_ms"].asInt(), + updateDelay); } } else diff --git a/libsrc/hyperion/LinearColorSmoothing.cpp b/libsrc/hyperion/LinearColorSmoothing.cpp index 0fe3e208..47974c90 100644 --- a/libsrc/hyperion/LinearColorSmoothing.cpp +++ b/libsrc/hyperion/LinearColorSmoothing.cpp @@ -3,13 +3,18 @@ #include "LinearColorSmoothing.h" -LinearColorSmoothing::LinearColorSmoothing(LedDevice *ledDevice, double ledUpdateFrequency_hz, int settlingTime_ms) : +LinearColorSmoothing::LinearColorSmoothing( + LedDevice *ledDevice, + double ledUpdateFrequency_hz, + int settlingTime_ms, + unsigned updateDelay) : QObject(), LedDevice(), _ledDevice(ledDevice), _updateInterval(1000 / ledUpdateFrequency_hz), _settlingTime(settlingTime_ms), - _timer() + _timer(), + _outputDelay(updateDelay) { _timer.setSingleShot(false); _timer.setInterval(_updateInterval); @@ -25,7 +30,7 @@ LinearColorSmoothing::~LinearColorSmoothing() int LinearColorSmoothing::write(const std::vector &ledValues) { // received a new target color - if (_previousValues.size() == 0) + if (_previousValues.empty()) { // not initialized yet _targetTime = QDateTime::currentMSecsSinceEpoch() + _settlingTime; @@ -46,17 +51,19 @@ int LinearColorSmoothing::write(const std::vector &ledValues) int LinearColorSmoothing::switchOff() { - // stop smoothing filter - _timer.stop(); - - // return to uninitialized state - _previousValues.clear(); - _previousTime = 0; - _targetValues.clear(); + // Clear the smoothing parameters + std::fill(_targetValues.begin(), _targetValues.end(), ColorRgb::BLACK); _targetTime = 0; - // finally switch off all leds - return _ledDevice->switchOff(); + // Erase the output-queue + for (unsigned i=0; i<_outputQueue.size(); ++i) + { + _outputQueue.push_back(_targetValues); + _outputQueue.pop_front(); + } + + + return 0; } void LinearColorSmoothing::updateLeds() @@ -69,7 +76,7 @@ void LinearColorSmoothing::updateLeds() memcpy(_previousValues.data(), _targetValues.data(), _targetValues.size() * sizeof(ColorRgb)); _previousTime = now; - _ledDevice->write(_previousValues); + queueColors(_previousValues); } else { @@ -86,6 +93,23 @@ void LinearColorSmoothing::updateLeds() } _previousTime = now; - _ledDevice->write(_previousValues); + queueColors(_previousValues); + } +} + +void LinearColorSmoothing::queueColors(const std::vector & ledColors) +{ + if (_outputDelay == 0) + { + _ledDevice->write(ledColors); + } + else + { + _outputQueue.push_back(ledColors); + if (_outputQueue.size() > _outputDelay) + { + _ledDevice->write(_outputQueue.front()); + _outputQueue.pop_front(); + } } } diff --git a/libsrc/hyperion/LinearColorSmoothing.h b/libsrc/hyperion/LinearColorSmoothing.h index 5c27862d..2b75059e 100644 --- a/libsrc/hyperion/LinearColorSmoothing.h +++ b/libsrc/hyperion/LinearColorSmoothing.h @@ -23,7 +23,8 @@ public: /// @param LedDevice the led device /// @param LedUpdatFrequency The frequency at which the leds will be updated (Hz) /// @param settingTime The time after which the updated led values have been fully applied (sec) - LinearColorSmoothing(LedDevice *ledDevice, double ledUpdateFrequency, int settlingTime); + /// @param updateDelay The number of frames to delay outgoing led updates + LinearColorSmoothing(LedDevice *ledDevice, double ledUpdateFrequency, int settlingTime, unsigned updateDelay); /// Destructor virtual ~LinearColorSmoothing(); @@ -43,6 +44,13 @@ private slots: void updateLeds(); private: + /** + * Pushes the colors into the output queue and popping the head to the led-device + * + * @param ledColors The colors to queue + */ + void queueColors(const std::vector & ledColors); + /// The led device LedDevice * _ledDevice; @@ -66,4 +74,10 @@ private: /// The previously written led data std::vector _previousValues; + + /** The number of updates to keep in the output queue (delayed) before being output */ + const unsigned _outputDelay; + /** The output queue */ + std::list > _outputQueue; + };