#pragma once // Qt includes #include #include #include #include #include // Hyperion includes #include #include #include class Hyperion; class Logger; class Effect : public QThread { Q_OBJECT public: friend class EffectModule; Effect(Hyperion* hyperion , int priority , int timeout , const QString& script , const QString& name , const QJsonObject& args = QJsonObject() , const QString& imageData = "" ); ~Effect() override; void run() override; int getPriority() const { return _priority; } /// /// @brief Set manual interruption to true, /// Note: DO NOT USE QThread::interruption! /// void requestInterruption() { _interupt = true; } /// /// @brief Check an interruption was requested. /// This can come from requestInterruption() /// or the effect's timeout expiring. /// /// @return The flag state /// bool isInterruptionRequested(); /// /// @brief Get the remaining timeout, or indication it is endless /// /// @return The flag state /// int getRemaining() const; QString getScript() const { return _script; } QString getName() const { return _name; } int getTimeout() const { return _timeout; } bool isEndless() const { return _isEndless; } QJsonObject getArgs() const { return _args; } signals: void setInput(int priority, const std::vector& ledColors, int timeout_ms, bool clearEffect); void setInputImage(int priority, const Image& image, int timeout_ms, bool clearEffect); private: bool setModuleParameters(); void addImage(); Hyperion* _hyperion; const int _priority; const int _timeout; bool _isEndless; const QString _script; const QString _name; const QJsonObject _args; const QString _imageData; qint64 _endTime; /// Buffer for colorData QVector _colors; Logger* _log; // Reflects whenever this effects should interrupt (timeout or external request) std::atomic _interupt{}; QSize _imageSize; QImage _image; QPainter* _painter; QVector _imageStack; double _lowestUpdateIntervalInSeconds; };