diff --git a/engine/src/rgbalgorithm.cpp b/engine/src/rgbalgorithm.cpp index 7daae49dcb..86cabdce4d 100644 --- a/engine/src/rgbalgorithm.cpp +++ b/engine/src/rgbalgorithm.cpp @@ -39,15 +39,27 @@ RGBAlgorithm::RGBAlgorithm(Doc * doc) : m_doc(doc) - , m_startColor(QColor()) - , m_endColor(QColor()) { } -void RGBAlgorithm::setColors(QColor start, QColor end) +void RGBAlgorithm::setColors(QVector colors) { - m_startColor = start; - m_endColor = end; + int nCols = acceptColors(); + m_colors.clear(); + + for (int i = 0; i < nCols; i++) + { + if (i < colors.count()) + m_colors.append(colors.at(i)); + } +} + +QColor RGBAlgorithm::getColor(uint i) const +{ + if (i >= (uint)m_colors.count()) + return QColor(); + + return m_colors[i]; } /**************************************************************************** diff --git a/engine/src/rgbalgorithm.h b/engine/src/rgbalgorithm.h index 69ce660e05..47214bdcfa 100644 --- a/engine/src/rgbalgorithm.h +++ b/engine/src/rgbalgorithm.h @@ -40,6 +40,8 @@ typedef QVector > RGBMap; #define KXMLQLCRGBAlgorithm QString("Algorithm") #define KXMLQLCRGBAlgorithmType QString("Type") +#define RGBAlgorithmColorDisplayCount 5 + class RGBAlgorithm { public: @@ -72,6 +74,12 @@ class RGBAlgorithm /** Maximum step count for rgbMap() function. */ virtual int rgbMapStepCount(const QSize& size) = 0; + /** Set the colors for the RGBmap */ + virtual void rgbMapSetColors(QVector &colors) = 0; + + /** Get the colors from the RGB script */ + virtual QVector rgbMapGetColors() = 0; + /** Load a RGBMap for the given step. */ virtual void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) = 0; @@ -101,15 +109,14 @@ class RGBAlgorithm * RGB Colors ************************************************************************/ public: - /** Set the start/end color the algorithm can use */ - virtual void setColors(QColor start, QColor end); - - QColor startColor() { return m_startColor; } + /** Set the colors the algorithm can use */ + virtual void setColors(QVector); - QColor endColor() { return m_endColor; } + /** Get the color which is set for the algorithm */ + virtual QColor getColor(uint i) const; private: - QColor m_startColor, m_endColor; + QVector m_colors; /************************************************************************ * Available algorithms diff --git a/engine/src/rgbaudio.cpp b/engine/src/rgbaudio.cpp index d41769938d..817b4be649 100644 --- a/engine/src/rgbaudio.cpp +++ b/engine/src/rgbaudio.cpp @@ -86,19 +86,21 @@ void RGBAudio::calculateColors(int barsHeight) { if (barsHeight > 0) { + QColor startColor = getColor(0); + QColor endColor = getColor(1); m_barColors.clear(); - if (endColor() == QColor() + if (endColor == QColor() || barsHeight == 1) // to avoid division by 0 below { for (int i = 0; i < barsHeight; i++) - m_barColors.append(startColor().rgb()); + m_barColors.append(startColor.rgb()); } else { - int crDelta = (endColor().red() - startColor().red()) / (barsHeight - 1); - int cgDelta = (endColor().green() - startColor().green()) / (barsHeight - 1); - int cbDelta = (endColor().blue() - startColor().blue()) / (barsHeight - 1); - QColor pixelColor = startColor(); + int crDelta = (endColor.red() - startColor.red()) / (barsHeight - 1); + int cgDelta = (endColor.green() - startColor.green()) / (barsHeight - 1); + int cbDelta = (endColor.blue() - startColor.blue()) / (barsHeight - 1); + QColor pixelColor = startColor; for (int i = 0; i < barsHeight; i++) { @@ -121,6 +123,16 @@ int RGBAudio::rgbMapStepCount(const QSize& size) return 1; } +void RGBAudio::rgbMapSetColors(QVector &colors) +{ + Q_UNUSED(colors); +} + +QVector RGBAudio::rgbMapGetColors() +{ + return QVector(); +} + void RGBAudio::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) { Q_UNUSED(step); @@ -203,9 +215,9 @@ int RGBAudio::apiVersion() const return 1; } -void RGBAudio::setColors(QColor start, QColor end) +void RGBAudio::setColors(QVector colors) { - RGBAlgorithm::setColors(start, end); + RGBAlgorithm::setColors(colors); // invalidate bars colors so the next time a rendering is // required, it will be filled with the right values diff --git a/engine/src/rgbaudio.h b/engine/src/rgbaudio.h index 42718389d3..a8ea5742ae 100644 --- a/engine/src/rgbaudio.h +++ b/engine/src/rgbaudio.h @@ -70,6 +70,12 @@ protected slots: /** @reimp */ int rgbMapStepCount(const QSize& size); + /** @reimp */ + void rgbMapSetColors(QVector &colors); + + /** @reimp */ + QVector rgbMapGetColors(); + /** @reimp */ void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map); @@ -86,7 +92,7 @@ protected slots: int apiVersion() const; /** @reimp */ - void setColors(QColor start, QColor end); + void setColors(QVector colors); /** @reimp */ RGBAlgorithm::Type type() const; diff --git a/engine/src/rgbimage.cpp b/engine/src/rgbimage.cpp index 78d53b3c39..114c0e62d5 100644 --- a/engine/src/rgbimage.cpp +++ b/engine/src/rgbimage.cpp @@ -235,6 +235,16 @@ int RGBImage::rgbMapStepCount(const QSize& size) } } +void RGBImage::rgbMapSetColors(QVector &colors) +{ + Q_UNUSED(colors); +} + +QVector RGBImage::rgbMapGetColors() +{ + return QVector(); +} + void RGBImage::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) { Q_UNUSED(rgb); diff --git a/engine/src/rgbimage.h b/engine/src/rgbimage.h index 6ed672bfe4..96042e6186 100644 --- a/engine/src/rgbimage.h +++ b/engine/src/rgbimage.h @@ -102,6 +102,12 @@ class RGBImage : public RGBAlgorithm /** @reimp */ int rgbMapStepCount(const QSize& size); + /** @reimp */ + void rgbMapSetColors(QVector &colors); + + /** @reimp */ + QVector rgbMapGetColors(); + /** @reimp */ void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map); diff --git a/engine/src/rgbmatrix.cpp b/engine/src/rgbmatrix.cpp index 8e1aa79a63..e9ae57318a 100644 --- a/engine/src/rgbmatrix.cpp +++ b/engine/src/rgbmatrix.cpp @@ -36,6 +36,9 @@ #define KXMLQLCRGBMatrixStartColor QString("MonoColor") #define KXMLQLCRGBMatrixEndColor QString("EndColor") +#define KXMLQLCRGBMatrixColor QString("Color") +#define KXMLQLCRGBMatrixColorIndex QString("Index") + #define KXMLQLCRGBMatrixFixtureGroup QString("FixtureGroup") #define KXMLQLCRGBMatrixDimmerControl QString("DimmerControl") @@ -64,8 +67,6 @@ RGBMatrix::RGBMatrix(Doc* doc) #if QT_VERSION < QT_VERSION_CHECK(5, 14, 0) , m_algorithmMutex(QMutex::Recursive) #endif - , m_startColor(Qt::red) - , m_endColor(QColor()) , m_stepHandler(new RGBMatrixStep()) , m_roundTime(new QElapsedTimer()) , m_stepsCount(0) @@ -75,6 +76,9 @@ RGBMatrix::RGBMatrix(Doc* doc) setName(tr("New RGB Matrix")); setDuration(500); + m_rgbColors.fill(QColor(), RGBAlgorithmColorDisplayCount); + setColor(0, Qt::red); + RGBScript scr = doc->rgbScriptsCache()->script("Stripes"); setAlgorithm(scr.clone()); } @@ -162,12 +166,16 @@ bool RGBMatrix::copyFrom(const Function* function) setDimmerControl(mtx->dimmerControl()); setFixtureGroup(mtx->fixtureGroup()); + + m_rgbColors.clear(); + foreach (QColor col, mtx->getColors()) + m_rgbColors.append(col); + if (mtx->algorithm() != NULL) setAlgorithm(mtx->algorithm()->clone()); else setAlgorithm(NULL); - setStartColor(mtx->startColor()); - setEndColor(mtx->endColor()); + setControlMode(mtx->controlMode()); return Function::copyFrom(function); @@ -277,54 +285,78 @@ void RGBMatrix::previewMap(int step, RGBMatrixStep *handler) m_group = doc()->fixtureGroup(fixtureGroup()); if (m_group != NULL) + { + setMapColors(); m_algorithm->rgbMap(m_group->size(), handler->stepColor().rgb(), step, handler->m_map); + } } /**************************************************************************** * Color ****************************************************************************/ -void RGBMatrix::setStartColor(const QColor& c) +void RGBMatrix::setColor(int i, QColor c) { - m_startColor = c; + if (i < 0) + return; + + if (i >= m_rgbColors.count()) + m_rgbColors.resize(i + 1); + + m_rgbColors.replace(i, c); { QMutexLocker algorithmLocker(&m_algorithmMutex); if (m_algorithm != NULL) { - m_algorithm->setColors(m_startColor, m_endColor); + m_algorithm->setColors(m_rgbColors); updateColorDelta(); } } + setMapColors(); emit changed(id()); } -QColor RGBMatrix::startColor() const +QColor RGBMatrix::getColor(int i) const { - return m_startColor; + if (i < 0 || i >= m_rgbColors.count()) + return QColor(); + + return m_rgbColors.at(i); } -void RGBMatrix::setEndColor(const QColor &c) +QVector RGBMatrix::getColors() const { - m_endColor = c; - { - QMutexLocker algorithmLocker(&m_algorithmMutex); - if (m_algorithm != NULL) - { - m_algorithm->setColors(m_startColor, m_endColor); - updateColorDelta(); - } - } - emit changed(id()); + return m_rgbColors; } -QColor RGBMatrix::endColor() const +void RGBMatrix::updateColorDelta() { - return m_endColor; + m_stepHandler->calculateColorDelta(m_rgbColors[0], m_rgbColors[1], m_algorithm); } -void RGBMatrix::updateColorDelta() +void RGBMatrix::setMapColors() { - m_stepHandler->calculateColorDelta(m_startColor, m_endColor); + QMutexLocker algorithmLocker(&m_algorithmMutex); + if (m_algorithm == NULL) + return; + + if (m_algorithm->apiVersion() < 3) + return; + + if (m_group == NULL) + m_group = doc()->fixtureGroup(fixtureGroup()); + + if (m_group != NULL) + { + QVector rawColors; + for (int i = 0; i < m_algorithm->acceptColors(); i++) + { + QColor col = m_rgbColors.at(i); + rawColors.append(col.isValid() ? col.rgb() : 0); + } + + m_algorithm->rgbMapSetColors(rawColors); + } } /************************************************************************ @@ -339,6 +371,10 @@ void RGBMatrix::setProperty(QString propName, QString value) { RGBScript *script = static_cast (m_algorithm); script->setProperty(propName, value); + + QVector colors = script->rgbMapGetColors(); + for (int i = 0; i < colors.count(); i++) + setColor(i, QColor::fromRgb(colors.at(i))); } m_stepsCount = stepsCount(); } @@ -402,13 +438,19 @@ bool RGBMatrix::loadXML(QXmlStreamReader &root) { loadXMLRunOrder(root); } + // Legacy support else if (root.name() == KXMLQLCRGBMatrixStartColor) { - setStartColor(QColor::fromRgb(QRgb(root.readElementText().toUInt()))); + setColor(0, QColor::fromRgb(QRgb(root.readElementText().toUInt()))); } else if (root.name() == KXMLQLCRGBMatrixEndColor) { - setEndColor(QColor::fromRgb(QRgb(root.readElementText().toUInt()))); + setColor(1, QColor::fromRgb(QRgb(root.readElementText().toUInt()))); + } + else if (root.name() == KXMLQLCRGBMatrixColor) + { + int colorIdx = root.attributes().value(KXMLQLCRGBMatrixColorIndex).toInt(); + setColor(colorIdx, QColor::fromRgb(QRgb(root.readElementText().toUInt()))); } else if (root.name() == KXMLQLCRGBMatrixControlMode) { @@ -462,12 +504,14 @@ bool RGBMatrix::saveXML(QXmlStreamWriter *doc) if (dimmerControl()) doc->writeTextElement(KXMLQLCRGBMatrixDimmerControl, QString::number(dimmerControl())); - /* Start Color */ - doc->writeTextElement(KXMLQLCRGBMatrixStartColor, QString::number(startColor().rgb())); - - /* End Color */ - if (endColor().isValid()) - doc->writeTextElement(KXMLQLCRGBMatrixEndColor, QString::number(endColor().rgb())); + /* Colors */ + for (int i = 0; i < m_rgbColors.count(); i++) + { + doc->writeStartElement(KXMLQLCRGBMatrixColor); + doc->writeAttribute(KXMLQLCRGBMatrixColorIndex, QString::number(i)); + doc->writeCharacters(QString::number(m_rgbColors.at(i).rgb())); + doc->writeEndElement(); + } /* Control Mode */ doc->writeTextElement(KXMLQLCRGBMatrixControlMode, RGBMatrix::controlModeToString(m_controlMode)); @@ -526,7 +570,7 @@ void RGBMatrix::preRun(MasterTimer *timer) if (m_algorithm != NULL) { // Copy direction from parent class direction - m_stepHandler->initializeDirection(direction(), m_startColor, m_endColor, m_stepsCount); + m_stepHandler->initializeDirection(direction(), m_rgbColors[0], m_rgbColors[1], m_stepsCount, m_algorithm); if (m_algorithm->type() == RGBAlgorithm::Script) { @@ -664,7 +708,7 @@ void RGBMatrix::roundCheck() if (m_algorithm == NULL) return; - if (m_stepHandler->checkNextStep(runOrder(), m_startColor, m_endColor, m_stepsCount) == false) + if (m_stepHandler->checkNextStep(runOrder(), m_rgbColors[0], m_rgbColors[1], m_stepsCount) == false) stop(FunctionParent::master()); m_roundTime->restart(); @@ -980,13 +1024,13 @@ int RGBMatrixStep::currentStepIndex() const return m_currentStepIndex; } -void RGBMatrixStep::calculateColorDelta(QColor startColor, QColor endColor) +void RGBMatrixStep::calculateColorDelta(QColor startColor, QColor endColor, RGBAlgorithm *algorithm) { m_crDelta = 0; m_cgDelta = 0; m_cbDelta = 0; - if (endColor.isValid()) + if (endColor.isValid() && algorithm != NULL && algorithm->acceptColors() > 1) { m_crDelta = endColor.red() - startColor.red(); m_cgDelta = endColor.green() - startColor.green(); @@ -1025,7 +1069,7 @@ void RGBMatrixStep::updateStepColor(int stepIndex, QColor startColor, int stepsC //qDebug() << "RGBMatrix step" << stepIndex << ", color:" << QString::number(m_stepColor.rgb(), 16); } -void RGBMatrixStep::initializeDirection(Function::Direction direction, QColor startColor, QColor endColor, int stepsCount) +void RGBMatrixStep::initializeDirection(Function::Direction direction, QColor startColor, QColor endColor, int stepsCount, RGBAlgorithm *algorithm) { m_direction = direction; @@ -1044,7 +1088,7 @@ void RGBMatrixStep::initializeDirection(Function::Direction direction, QColor st setStepColor(startColor); } - calculateColorDelta(startColor, endColor); + calculateColorDelta(startColor, endColor, algorithm); } bool RGBMatrixStep::checkNextStep(Function::RunOrder order, diff --git a/engine/src/rgbmatrix.h b/engine/src/rgbmatrix.h index 8f607d9ba0..52ebaafc28 100644 --- a/engine/src/rgbmatrix.h +++ b/engine/src/rgbmatrix.h @@ -59,7 +59,7 @@ class RGBMatrixStep int currentStepIndex() const; /** Calculate the RGB components delta between $startColor and $endColor */ - void calculateColorDelta(QColor startColor, QColor endColor); + void calculateColorDelta(QColor startColor, QColor endColor, RGBAlgorithm *algorithm); /** Set/Get the final color of the next step to be reproduced */ void setStepColor(QColor color); @@ -71,7 +71,7 @@ class RGBMatrixStep /** Initialize the playback direction and set the initial step index and * color based on $startColor and $endColor */ - void initializeDirection(Function::Direction direction, QColor startColor, QColor endColor, int stepsCount); + void initializeDirection(Function::Direction direction, QColor startColor, QColor endColor, int stepsCount, RGBAlgorithm *algorithm); /** Check the steps progression based on $order and the internal m_direction. * This method returns true if the RGBMatrix can continue to run, otherwise @@ -188,17 +188,17 @@ class RGBMatrix : public Function * Color ************************************************************************/ public: - void setStartColor(const QColor& c); - QColor startColor() const; - - void setEndColor(const QColor& c); - QColor endColor() const; + void setColor(int i, QColor c); + QColor getColor(int i) const; + QVector getColors() const; void updateColorDelta(); + /** Set the colors of the current algorithm */ + void setMapColors(); + private: - QColor m_startColor; - QColor m_endColor; + QVector m_rgbColors; RGBMatrixStep *m_stepHandler; /************************************************************************ diff --git a/engine/src/rgbplain.cpp b/engine/src/rgbplain.cpp index 83f4f97924..5a43f630a8 100644 --- a/engine/src/rgbplain.cpp +++ b/engine/src/rgbplain.cpp @@ -55,9 +55,19 @@ int RGBPlain::rgbMapStepCount(const QSize& size) return 1; } +void RGBPlain::rgbMapSetColors(QVector &colors) +{ + Q_UNUSED(colors); +} + +QVector RGBPlain::rgbMapGetColors() +{ + return QVector(); +} + void RGBPlain::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) { - Q_UNUSED(step) + Q_UNUSED(step); map.resize(size.height()); for (int y = 0; y < size.height(); y++) { @@ -81,9 +91,9 @@ int RGBPlain::apiVersion() const return 1; } -void RGBPlain::setColors(QColor start, QColor end) +void RGBPlain::setColors(QVector colors) { - RGBAlgorithm::setColors(start, end); + RGBAlgorithm::setColors(colors); } RGBAlgorithm::Type RGBPlain::type() const diff --git a/engine/src/rgbplain.h b/engine/src/rgbplain.h index 83691b70ae..1624b4193a 100644 --- a/engine/src/rgbplain.h +++ b/engine/src/rgbplain.h @@ -49,6 +49,12 @@ class RGBPlain : public QObject, public RGBAlgorithm /** @reimp */ int rgbMapStepCount(const QSize& size); + /** @reimp */ + void rgbMapSetColors(QVector &colors); + + /** @reimp */ + QVector rgbMapGetColors(); + /** @reimp */ void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map); @@ -62,7 +68,7 @@ class RGBPlain : public QObject, public RGBAlgorithm int apiVersion() const; /** @reimp */ - void setColors(QColor start, QColor end); + void setColors(QVector colors); /** @reimp */ RGBAlgorithm::Type type() const; diff --git a/engine/src/rgbscript.cpp b/engine/src/rgbscript.cpp index 7620fbd62f..755bd7a382 100644 --- a/engine/src/rgbscript.cpp +++ b/engine/src/rgbscript.cpp @@ -117,6 +117,7 @@ bool RGBScript::load(const QDir& dir, const QString& fileName) m_script = QScriptValue(); m_rgbMap = QScriptValue(); m_rgbMapStepCount = QScriptValue(); + m_rgbMapSetColors = QScriptValue(); m_apiVersion = 0; m_fileName = fileName; @@ -154,6 +155,7 @@ bool RGBScript::evaluate() m_rgbMap = QScriptValue(); m_rgbMapStepCount = QScriptValue(); + m_rgbMapSetColors = QScriptValue(); m_apiVersion = 0; m_script = s_engine->evaluate(m_contents, m_fileName); @@ -184,7 +186,21 @@ bool RGBScript::evaluate() m_apiVersion = m_script.property("apiVersion").toInteger(); if (m_apiVersion > 0) { - if (m_apiVersion == 2) + if (m_apiVersion >= 3) + { + m_rgbMapSetColors = m_script.property("rgbMapSetColors"); + if (m_rgbMapSetColors.isFunction() == false) + { + qWarning() << m_fileName << "is missing the rgbMapSetColors() function!"; + return false; + } + + // retrieve the non-mandatory get color function + m_rgbMapGetColors = m_script.property("rgbMapGetColors"); + if (m_rgbMapGetColors.isFunction() == false) + qWarning() << m_fileName << "is missing the rgbMapGetColors() function!"; + } + if (m_apiVersion >= 2) return loadProperties(); return true; } @@ -249,6 +265,51 @@ int RGBScript::rgbMapStepCount(const QSize& size) } } +void RGBScript::rgbMapSetColors(QVector &colors) +{ + QMutexLocker engineLocker(s_engineMutex); + if (m_apiVersion <= 2) + return; + + if (m_rgbMapSetColors.isValid() == false) + return; + + int accColors = acceptColors(); + int rawColorCount = colors.count(); + QScriptValue jsRawColors = s_engine->newArray(accColors); + for (int i = 0; i < rawColorCount && i < accColors; i++) + jsRawColors.setProperty(i, QScriptValue(colors.at(i))); + + QScriptValueList args; + args << jsRawColors; + + QScriptValue value = m_rgbMapSetColors.call(QScriptValue(), args); + if (value.isError()) + displayError(value, m_fileName); +} + +QVector RGBScript::rgbMapGetColors() +{ + QMutexLocker engineLocker(s_engineMutex); + QVector colArray; + + if (m_apiVersion <= 2) + return colArray; + + if (m_rgbMapGetColors.isValid() == false) + return colArray; + + QScriptValue colors = m_rgbMapGetColors.call(); + if (colors.isValid() && colors.isArray()) + { + QVariantList arr = colors.toVariant().toList(); + foreach (QVariant color, arr) + colArray.append(color.toUInt()); + } + + return colArray; +} + void RGBScript::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) { QMutexLocker engineLocker(s_engineMutex); @@ -258,6 +319,7 @@ void RGBScript::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) QScriptValueList args; args << size.width() << size.height() << rgb << step; + QScriptValue yarray = m_rgbMap.call(QScriptValue(), args); if (yarray.isError()) diff --git a/engine/src/rgbscript.h b/engine/src/rgbscript.h index 6ee168b43f..b05c6e93b5 100644 --- a/engine/src/rgbscript.h +++ b/engine/src/rgbscript.h @@ -90,6 +90,12 @@ class RGBScript : public RGBAlgorithm /** @reimp */ int rgbMapStepCount(const QSize& size); + /** @reimp */ + void rgbMapSetColors(QVector &colors); + + /** @reimp */ + QVector rgbMapGetColors(); + /** @reimp */ void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map); @@ -119,6 +125,8 @@ class RGBScript : public RGBAlgorithm QScriptValue m_script; //! The script itself QScriptValue m_rgbMap; //! rgbMap() function QScriptValue m_rgbMapStepCount; //! rgbMapStepCount() function + QScriptValue m_rgbMapSetColors; //! rgbMapSetColors() function + QScriptValue m_rgbMapGetColors; //! rgbMapSetColors() function /************************************************************************ * Properties diff --git a/engine/src/rgbscriptv4.cpp b/engine/src/rgbscriptv4.cpp index c703b36e8a..f2254e0681 100644 --- a/engine/src/rgbscriptv4.cpp +++ b/engine/src/rgbscriptv4.cpp @@ -109,6 +109,7 @@ bool RGBScript::load(const QDir& dir, const QString& fileName) m_script = QJSValue(); m_rgbMap = QJSValue(); m_rgbMapStepCount = QJSValue(); + m_rgbMapSetColors = QJSValue(); m_apiVersion = 0; m_fileName = fileName; @@ -137,6 +138,7 @@ bool RGBScript::evaluate() m_rgbMap = QJSValue(); m_rgbMapStepCount = QJSValue(); + m_rgbMapSetColors = QJSValue(); m_apiVersion = 0; if (m_fileName.isEmpty() || m_contents.isEmpty()) @@ -169,7 +171,16 @@ bool RGBScript::evaluate() m_apiVersion = m_script.property("apiVersion").toInt(); if (m_apiVersion > 0) { - if (m_apiVersion == 2) + if (m_apiVersion >= 3) + { + m_rgbMapSetColors = m_script.property("rgbMapSetColors"); + if (m_rgbMapSetColors.isCallable() == false) + { + qWarning() << m_fileName << "is missing the rgbMapSetColors() function!"; + return false; + } + } + if (m_apiVersion >= 2) return loadProperties(); return true; } @@ -233,6 +244,49 @@ int RGBScript::rgbMapStepCount(const QSize& size) } } +void RGBScript::rgbMapSetColors(QVector &colors) +{ + QMutexLocker engineLocker(s_engineMutex); + if (m_apiVersion <= 2) + return; + if (m_rgbMap.isUndefined() == true) + return; + if (m_rgbMapSetColors.isCallable() == false) + return; + + int accColors = acceptColors(); + int rawColorCount = colors.count(); + QJSValue jsRawColors = s_engine->newArray(accColors); + for (int i = 0; i < rawColorCount && i < accColors; i++) + jsRawColors.setProperty(i, QJSValue(colors.at(i))); + + QJSValueList args; + args << jsRawColors; + + QJSValue value = m_rgbMapSetColors.call(args); + if (value.isError()) + displayError(value, m_fileName); +} + +QVector RGBScript::rgbMapGetColors() +{ + QMutexLocker engineLocker(s_engineMutex); + QVector colArray; + + if (m_rgbMap.isUndefined() == true) + return colArray; + + QJSValue colors = m_rgbMapGetColors.call(); + if (!colors.isError() && colors.isArray()) + { + QVariantList arr = colors.toVariant().toList(); + foreach (QVariant color, arr) + colArray.append(color.toUInt()); + } + + return colArray; +} + void RGBScript::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) { QMutexLocker engineLocker(s_engineMutex); @@ -240,12 +294,15 @@ void RGBScript::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) if (m_rgbMap.isUndefined() == true) return; + // Call the rgbMap function QJSValueList args; args << size.width() << size.height() << rgb << step; + QJSValue yarray(m_rgbMap.call(args)); if (yarray.isError()) displayError(yarray, m_fileName); + // Check the matrix to be a valid matrix if (yarray.isArray()) { QVariantList yvArray = yarray.toVariant().toList(); diff --git a/engine/src/rgbscriptv4.h b/engine/src/rgbscriptv4.h index 3a89ce93b1..4e1fcee93a 100644 --- a/engine/src/rgbscriptv4.h +++ b/engine/src/rgbscriptv4.h @@ -91,6 +91,12 @@ class RGBScript : public RGBAlgorithm /** @reimp */ int rgbMapStepCount(const QSize& size); + /** @reimp */ + void rgbMapSetColors(QVector &colors); + + /** @reimp */ + QVector rgbMapGetColors(); + /** @reimp */ void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map); @@ -120,6 +126,8 @@ class RGBScript : public RGBAlgorithm QJSValue m_script; //! The script itself QJSValue m_rgbMap; //! rgbMap() function QJSValue m_rgbMapStepCount; //! rgbMapStepCount() function + QJSValue m_rgbMapSetColors; //! rgbMapSetColors() function + QJSValue m_rgbMapGetColors; //! rgbMapSetColors() function /************************************************************************ * Properties diff --git a/engine/src/rgbtext.cpp b/engine/src/rgbtext.cpp index 10b2af6d79..d4d13f0fad 100644 --- a/engine/src/rgbtext.cpp +++ b/engine/src/rgbtext.cpp @@ -266,6 +266,16 @@ int RGBText::rgbMapStepCount(const QSize& size) return scrollingTextStepCount(); } +void RGBText::rgbMapSetColors(QVector &colors) +{ + Q_UNUSED(colors); +} + +QVector RGBText::rgbMapGetColors() +{ + return QVector(); +} + void RGBText::rgbMap(const QSize& size, uint rgb, int step, RGBMap &map) { if (animationStyle() == StaticLetters) diff --git a/engine/src/rgbtext.h b/engine/src/rgbtext.h index 1f1879c27a..2e4d5cafcc 100644 --- a/engine/src/rgbtext.h +++ b/engine/src/rgbtext.h @@ -98,6 +98,12 @@ class RGBText : public RGBAlgorithm /** @reimp */ int rgbMapStepCount(const QSize& size); + /** @reimp */ + void rgbMapSetColors(QVector &colors); + + /** @reimp */ + QVector rgbMapGetColors(); + /** @reimp */ void rgbMap(const QSize& size, uint rgb, int step, RGBMap &map); diff --git a/engine/test/rgbalgorithm/rgbalgorithm_test.cpp b/engine/test/rgbalgorithm/rgbalgorithm_test.cpp index d73c505d45..89d6b558b9 100644 --- a/engine/test/rgbalgorithm/rgbalgorithm_test.cpp +++ b/engine/test/rgbalgorithm/rgbalgorithm_test.cpp @@ -85,12 +85,23 @@ void RGBAlgorithm_Test::algorithm() QVERIFY(algo != NULL); QCOMPARE(algo->type(), RGBAlgorithm::Script); QCOMPARE(algo->name(), QString("Stripes")); - printf("%s\n", algo->name().toStdString().c_str()); - printf("%s\n", algo->name().toStdString().c_str()); - printf("%s\n", algo->name().toStdString().c_str()); - printf("%s\n", algo->name().toStdString().c_str()); - printf("%s\n", algo->name().toStdString().c_str()); - printf("%s\n", algo->name().toStdString().c_str()); + delete algo; + + algo = RGBAlgorithm::algorithm(m_doc, "Balls"); + QVERIFY(algo != NULL); + QCOMPARE(algo->type(), RGBAlgorithm::Script); + QCOMPARE(algo->name(), QString("Balls")); + QCOMPARE(algo->apiVersion(), 3); + QCOMPARE(algo->acceptColors(), 5); + QVector colors; + colors << Qt::red; + colors << Qt::green; + colors << Qt::blue; + algo->setColors(colors); + + QCOMPARE(algo->getColor(0), Qt::red); + QCOMPARE(algo->getColor(1), Qt::green); + QCOMPARE(algo->getColor(2), Qt::blue); delete algo; } diff --git a/engine/test/rgbmatrix/rgbmatrix_test.cpp b/engine/test/rgbmatrix/rgbmatrix_test.cpp index 88b165a78a..e1c74362c9 100644 --- a/engine/test/rgbmatrix/rgbmatrix_test.cpp +++ b/engine/test/rgbmatrix/rgbmatrix_test.cpp @@ -82,8 +82,8 @@ void RGBMatrix_Test::initial() RGBMatrix mtx(m_doc); QCOMPARE(mtx.type(), Function::RGBMatrixType); QCOMPARE(mtx.fixtureGroup(), FixtureGroup::invalidId()); - QCOMPARE(mtx.startColor(), QColor(Qt::red)); - QCOMPARE(mtx.endColor(), QColor()); + QCOMPARE(mtx.getColor(0), QColor(Qt::red)); + QCOMPARE(mtx.getColor(1), QColor()); QCOMPARE(mtx.m_fadersMap.count(), 0); QCOMPARE(mtx.m_stepHandler->currentStepIndex(), 0); QCOMPARE(mtx.name(), tr("New RGB Matrix")); @@ -110,32 +110,32 @@ void RGBMatrix_Test::group() void RGBMatrix_Test::color() { RGBMatrix mtx(m_doc); - mtx.setStartColor(Qt::blue); - QCOMPARE(mtx.startColor(), QColor(Qt::blue)); + mtx.setColor(0, Qt::blue); + QCOMPARE(mtx.getColor(0), QColor(Qt::blue)); - mtx.setStartColor(QColor()); - QCOMPARE(mtx.startColor(), QColor()); + mtx.setColor(0, QColor()); + QCOMPARE(mtx.getColor(0), QColor()); - mtx.setEndColor(Qt::green); - QCOMPARE(mtx.endColor(), QColor(Qt::green)); + mtx.setColor(1, Qt::green); + QCOMPARE(mtx.getColor(1), QColor(Qt::green)); - mtx.setEndColor(QColor()); - QCOMPARE(mtx.endColor(), QColor()); + mtx.setColor(1, QColor()); + QCOMPARE(mtx.getColor(1), QColor()); } void RGBMatrix_Test::copy() { RGBMatrix mtx(m_doc); - mtx.setStartColor(Qt::magenta); - mtx.setEndColor(Qt::yellow); + mtx.setColor(0, Qt::magenta); + mtx.setColor(1, Qt::yellow); mtx.setFixtureGroup(0); mtx.setAlgorithm(RGBAlgorithm::algorithm(m_doc, "Stripes")); QVERIFY(mtx.algorithm() != NULL); RGBMatrix* copyMtx = qobject_cast (mtx.createCopy(m_doc)); QVERIFY(copyMtx != NULL); - QCOMPARE(copyMtx->startColor(), QColor(Qt::magenta)); - QCOMPARE(copyMtx->endColor(), QColor(Qt::yellow)); + QCOMPARE(copyMtx->getColor(0), QColor(Qt::magenta)); + QCOMPARE(copyMtx->getColor(1), QColor(Qt::yellow)); QCOMPARE(copyMtx->fixtureGroup(), uint(0)); QVERIFY(copyMtx->algorithm() != NULL); QVERIFY(copyMtx->algorithm() != mtx.algorithm()); // Different object pointer! @@ -203,8 +203,11 @@ void RGBMatrix_Test::property() void RGBMatrix_Test::loadSave() { RGBMatrix* mtx = new RGBMatrix(m_doc); - mtx->setStartColor(Qt::magenta); - mtx->setEndColor(Qt::blue); + mtx->setColor(0, Qt::magenta); + mtx->setColor(1, Qt::blue); + mtx->setColor(2, Qt::green); + mtx->setColor(3, Qt::red); + mtx->setColor(4, Qt::yellow); mtx->setControlMode(RGBMatrix::ControlModeRgb); mtx->setFixtureGroup(42); mtx->setAlgorithm(RGBAlgorithm::algorithm(m_doc, "Stripes")); @@ -237,7 +240,7 @@ void RGBMatrix_Test::loadSave() QCOMPARE(xmlReader.attributes().value("ID").toString(), QString::number(mtx->id())); QCOMPARE(xmlReader.attributes().value("Name").toString(), QString("Xyzzy")); - int speed = 0, dir = 0, run = 0, algo = 0, monocolor = 0, endcolor = 0, grp = 0, colormode = 0; + int speed = 0, dir = 0, run = 0, algo = 0, grp = 0, color1 = 0, color2 = 0, color3 = 0, color4 = 0, color5 = 0, colormode = 0; while (xmlReader.readNextStartElement()) { @@ -265,15 +268,39 @@ void RGBMatrix_Test::loadSave() algo++; xmlReader.skipCurrentElement(); } - else if (xmlReader.name().toString() == "MonoColor") + else if (xmlReader.name().toString() == "Color") { - QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::magenta).rgb()); - monocolor++; - } - else if (xmlReader.name().toString() == "EndColor") - { - QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::blue).rgb()); - endcolor++; + bool ok = false; + int colorNum = xmlReader.attributes().value("Index").toInt(&ok); + QVERIFY(ok); + + switch (colorNum) + { + case 0: + QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::magenta).rgb()); + color1++; + break; + case 1: + QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::blue).rgb()); + color2++; + break; + case 2: + QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::green).rgb()); + color3++; + break; + case 3: + QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::red).rgb()); + color4++; + break; + case 4: + QCOMPARE(xmlReader.readElementText().toUInt(), QColor(Qt::yellow).rgb()); + color5++; + break; + default: + // The color number can be between 1 and MAXINT, but here we expect only 5. + QVERIFY(colorNum > 0 && colorNum <= 5); + break; + } } else if (xmlReader.name().toString() == "FixtureGroup") { @@ -295,8 +322,11 @@ void RGBMatrix_Test::loadSave() QCOMPARE(dir, 1); QCOMPARE(run, 1); QCOMPARE(algo, 1); - QCOMPARE(monocolor, 1); - QCOMPARE(endcolor, 1); + QCOMPARE(color1, 1); + QCOMPARE(color2, 1); + QCOMPARE(color3, 1); + QCOMPARE(color4, 1); + QCOMPARE(color5, 1); QCOMPARE(grp, 1); QCOMPARE(colormode, 1); @@ -309,8 +339,8 @@ void RGBMatrix_Test::loadSave() QVERIFY(mtx2.loadXML(xmlReader) == true); QCOMPARE(mtx2.direction(), Function::Backward); QCOMPARE(mtx2.runOrder(), Function::PingPong); - QCOMPARE(mtx2.startColor(), QColor(Qt::magenta)); - QCOMPARE(mtx2.endColor(), QColor(Qt::blue)); + QCOMPARE(mtx2.getColor(0), QColor(Qt::magenta)); + QCOMPARE(mtx2.getColor(1), QColor(Qt::blue)); QCOMPARE(mtx2.controlMode(), RGBMatrix::ControlModeRgb); QCOMPARE(mtx2.fixtureGroup(), uint(42)); QVERIFY(mtx2.algorithm() != NULL); diff --git a/engine/test/rgbscript/rgbscript_test.cpp b/engine/test/rgbscript/rgbscript_test.cpp index 65ea72283c..d3770e6354 100644 --- a/engine/test/rgbscript/rgbscript_test.cpp +++ b/engine/test/rgbscript/rgbscript_test.cpp @@ -204,11 +204,45 @@ void RGBScript_Test::rgbMapStepCount() QCOMPARE(s.rgbMapStepCount(QSize(10, 15)), 10); } +void RGBScript_Test::rgbMapColorArray() +{ + RGBMap map; + RGBScript s = m_doc->rgbScriptsCache()->script("Alternate"); + QCOMPARE(s.evaluate(), true); + QVector rawRgbColors = { + QColor(Qt::red).rgb() & 0x00ffffff, + QColor(Qt::green).rgb() & 0x00ffffff + }; + QSize mapSize = QSize(5, 5); + qDebug() << "C1: " << Qt::hex << rawRgbColors[0] << " C2: " << Qt::hex << rawRgbColors[1]; + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, 0, 0, map); + QVERIFY(map.isEmpty() == false); + + // check that both initial colors are used in the same step + for (int y = 0; y < mapSize.height(); y++) + { + for (int x = 0; x < mapSize.width(); x++) + { + // qDebug() << "y: " << y << " x: " << x << " C: " << Qt::hex << map[y][x]; + if (x % 2 == 0) + QCOMPARE(map[y][x], rawRgbColors[1]); + else + QCOMPARE(map[y][x], rawRgbColors[0]); + } + } +} + void RGBScript_Test::rgbMap() { RGBMap map; RGBScript s = m_doc->rgbScriptsCache()->script("Stripes"); + QVector rawRgbColors = { + QColor(Qt::red).rgb(), + uint(0) + }; s.rgbMap(QSize(3, 4), 0, 0, map); + // verify that an array within an array has been returned QVERIFY(map.isEmpty() == false); s.setProperty("orientation", "Vertical"); @@ -217,16 +251,15 @@ void RGBScript_Test::rgbMap() for (int step = 0; step < 5; step++) { RGBMap map; - s.rgbMap(QSize(5, 5), QColor(Qt::red).rgb(), step, map); - + s.rgbMap(QSize(5, 5), rawRgbColors[0], step, map); for (int y = 0; y < 5; y++) { for (int x = 0; x < 5; x++) { if (y == step) - QCOMPARE(map[y][x], QColor(Qt::red).rgb()); + QCOMPARE(map[y][x], rawRgbColors[0]); else - QCOMPARE(map[y][x], uint(0)); + QCOMPARE(map[y][x], rawRgbColors[1]); } } } @@ -236,9 +269,12 @@ void RGBScript_Test::runScripts() { QSize mapSize = QSize(7, 11); // Use different numbers for x and y for the test QSize mapSizePlus = QSize(12, 22); // Prepare a larger matrix to check behaviour on matrix change - // QColor(Qt::red).rgb() is 0xffff0000 due to the alpha channel - // This test also wants to test that there is no color space overrun. - int red = 0xff0000; + QVector rawRgbColors = { + // QColor(Qt::red).rgb() is 0xffff0000 due to the alpha channel + // This test also wants to test that there is no color space overrun. + QColor(Qt::red).rgb() & 0xffffff, + uint(0) + }; // Iterate the list of scripts QStringList names = m_doc->rgbScriptsCache()->names(); @@ -273,15 +309,19 @@ void RGBScript_Test::runScripts() { // limit the scope of this map to keep it clean for future executions RGBMap map; + s.rgbMapSetColors(rawRgbColors); s.rgbMap(mapSize, 0, 0, map); QVERIFY(map.isEmpty() == false); } - QVERIFY(s.apiVersion() >= 1 && s.apiVersion() <= 2); + QVERIFY(s.apiVersion() >= 1 && s.apiVersion() <= 3); QVERIFY(!s.author().isEmpty()); QVERIFY(!s.name().isEmpty()); QVERIFY(s.type() == RGBAlgorithm::Script); - QVERIFY(s.acceptColors() >= 0 && s.acceptColors() <= 2); + if (s.apiVersion() <= 2) + QVERIFY(s.acceptColors() >= 0 && s.acceptColors() <= 2); + else + QVERIFY(s.acceptColors() >= 0 && s.acceptColors() <= 5); int steps = s.rgbMapStepCount(mapSize); //qDebug() << "steps: " << steps; @@ -292,19 +332,20 @@ void RGBScript_Test::runScripts() RGBMap rgbMap; for (int step = 0; step < realsteps; step++) { - s.rgbMap(mapSize, red, step, rgbMap); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, rawRgbColors[0], step, rgbMap); QVERIFY(rgbMap.isEmpty() == false); // Check that the color values are limited to a valid range for (int y = 0; y < mapSize.height(); y++) { for (int x = 0; x < mapSize.width(); x++) { - //if (map[y][x] > 0x00ffffff) { - // uint pxr = (map[y][x] >> 16 & 0x000000ff); - // uint pxg = (map[y][x] >> 8 & 0x000000ff); - // uint pxb = (map[y][x] & 0x000000ff); - // qDebug() << "C:" << Qt::hex << pxr << ":" << Qt::hex << pxg << ":" << Qt::hex << pxb << " (" << Qt::hex << map[y][x]<< ")"; - //} + if (rgbMap[y][x] > 0x00ffffff) { + uint pxr = (rgbMap[y][x] >> 16 & 0x000000ff); + uint pxg = (rgbMap[y][x] >> 8 & 0x000000ff); + uint pxb = (rgbMap[y][x] & 0x000000ff); + qDebug() << "height:" << mapSize.height() << "width:" << mapSize.width() << "step:" << step << "y:" << y << "x:" << x << "C:" << Qt::hex << pxr << ":" << Qt::hex << pxg << ":" << Qt::hex << pxb << " (" << Qt::hex << rgbMap[y][x]<< ")"; + } QVERIFY(rgbMap[y][x] <= 0xffffff); } } @@ -314,12 +355,14 @@ void RGBScript_Test::runScripts() RGBMap rgbRefMap; if (1 < s.acceptColors() && 2 < steps && ! randomScript) { // When more than 2 colors are accepted, the steps shall be reproducible to allow back and forth color fade. - s.rgbMap(mapSizePlus, red, 0, rgbRefMap); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSizePlus, rawRgbColors[0], 0, rgbRefMap); } // Switch to the larger map and step a few times. for (int step = 0; step < realsteps; step++) { - s.rgbMap(mapSizePlus, red, step, rgbMap); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSizePlus, rawRgbColors[0], step, rgbMap); // Check that the color values are limited to a valid range for (int y = 0; y < mapSizePlus.height(); y++) { @@ -327,8 +370,15 @@ void RGBScript_Test::runScripts() { if (s.acceptColors() > 0) { - // If colors are accepted, verify that the requested color is applied - QVERIFY((rgbMap[y][x] & 0xff00ffff) == 0); + // verify that the alpha channel is zero + if (rgbMap[y][x] > 0x00ffffff) + { + uint pxr = (rgbMap[y][x] >> 16 & 0x000000ff); + uint pxg = (rgbMap[y][x] >> 8 & 0x000000ff); + uint pxb = (rgbMap[y][x] & 0x000000ff); + qDebug() << "step:" << step << "x:" << x << "y:" << y << "C:" << Qt::hex << pxr << ":" << Qt::hex << pxg << ":" << Qt::hex << pxb << " (" << Qt::hex << rgbMap[y][x]<< ")"; + } + QVERIFY((rgbMap[y][x] & 0xff000000) == 0); QVERIFY((rgbMap[y][x] >> 16) <= 0x0000ff); if (!randomScript && 0 == step && 1 < s.acceptColors() && 2 < steps) { @@ -386,7 +436,8 @@ void RGBScript_Test::runScripts() for (int step = 0; step < realsteps; step++) { RGBMap map; - s.rgbMap(mapSize, red, step, map); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, rawRgbColors[0], step, map); QVERIFY(map.isEmpty() == false); // Check that the color values are limited to a valid range for (int y = 0; y < mapSize.height(); y++) @@ -415,7 +466,8 @@ void RGBScript_Test::runScripts() for (int step = 0; step < realsteps; step++) { RGBMap map; - s.rgbMap(mapSize, red, step, map); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, rawRgbColors[0], step, map); QVERIFY(map.isEmpty() == false); // Check that the color values are limited to a valid range for (int y = 0; y < mapSize.height(); y++) @@ -433,7 +485,8 @@ void RGBScript_Test::runScripts() for (int step = 0; step < realsteps; step++) { RGBMap map; - s.rgbMap(mapSize, red, step, map); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, rawRgbColors[0], step, map); QVERIFY(map.isEmpty() == false); // Check that the color values are limited to a valid range for (int y = 0; y < mapSize.height(); y++) @@ -453,7 +506,8 @@ void RGBScript_Test::runScripts() for (int step = 0; step < realsteps; step++) { RGBMap map; - s.rgbMap(mapSize, red, step, map); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, rawRgbColors[0], step, map); QVERIFY(map.isEmpty() == false); // Check that the color values are limited to a valid range for (int y = 0; y < mapSize.height(); y++) @@ -473,7 +527,8 @@ void RGBScript_Test::runScripts() for (int step = 0; step < realsteps; step++) { RGBMap map; - s.rgbMap(mapSize, red, step, map); + s.rgbMapSetColors(rawRgbColors); + s.rgbMap(mapSize, rawRgbColors[0], step, map); QVERIFY(map.isEmpty() == false); // Check that the color values are limited to a valid range for (int y = 0; y < mapSize.height(); y++) diff --git a/engine/test/rgbscript/rgbscript_test.h b/engine/test/rgbscript/rgbscript_test.h index 60eb90b16a..c426a56469 100644 --- a/engine/test/rgbscript/rgbscript_test.h +++ b/engine/test/rgbscript/rgbscript_test.h @@ -40,6 +40,7 @@ private slots: void evaluateNoRgbMapStepCountFunction(); void evaluateInvalidApiVersion(); void rgbMapStepCount(); + void rgbMapColorArray(); void rgbMap(); void runScripts(); diff --git a/engine/test/rgbtext/rgbtext_test.cpp b/engine/test/rgbtext/rgbtext_test.cpp index 1c2a4cad90..afc1a6ae01 100644 --- a/engine/test/rgbtext/rgbtext_test.cpp +++ b/engine/test/rgbtext/rgbtext_test.cpp @@ -390,7 +390,7 @@ void RGBText_Test::horizontalScroll() RGBMap map; // Invalid step #if (QT_VERSION < QT_VERSION_CHECK(5, 13, 0)) - text.rgbMap(QSize(10, 10), QRgb(0xFFFFFFFF), fm.width("QLC"), map); + text.rgbMap(QSize(10, 10), QRgb(0xFFFFFFFF), fm.width("QLC"), map, rawRgbColors); #else text.rgbMap(QSize(10, 10), QRgb(0xFFFFFFFF), fm.horizontalAdvance("QLC"), map); #endif @@ -441,4 +441,12 @@ void RGBText_Test::verticalScroll() } } +void RGBText_Test::unused() +{ + RGBText text(m_doc); + QVector colors; + text.rgbMapSetColors(colors); + QCOMPARE(text.rgbMapGetColors().isEmpty(), true); +} + QTEST_MAIN(RGBText_Test) diff --git a/engine/test/rgbtext/rgbtext_test.h b/engine/test/rgbtext/rgbtext_test.h index c6656854e1..df66141499 100644 --- a/engine/test/rgbtext/rgbtext_test.h +++ b/engine/test/rgbtext/rgbtext_test.h @@ -42,6 +42,7 @@ private slots: void staticLetters(); void horizontalScroll(); void verticalScroll(); + void unused(); private: Doc * m_doc; diff --git a/qmlui/qml/fixturesfunctions/RGBMatrixEditor.qml b/qmlui/qml/fixturesfunctions/RGBMatrixEditor.qml index 90494132cd..a668023f44 100644 --- a/qmlui/qml/fixturesfunctions/RGBMatrixEditor.qml +++ b/qmlui/qml/fixturesfunctions/RGBMatrixEditor.qml @@ -58,6 +58,40 @@ Rectangle } } + ColorTool + { + id: colorTool + x: -width - (UISettings.iconSizeDefault * 1.25) + y: UISettings.bigItemHeight + visible: false + closeOnSelect: true + + property int colorIndex: -1 + property Item previewBtn + + function showTool(index, button) + { + colorIndex = index + previewBtn = button + currentRGB = rgbMatrixEditor.colorAtIndex(colorIndex) + visible = true + } + + function hide() + { + visible = false + colorIndex = -1 + previewBtn = null + } + + onColorChanged: + { + previewBtn.color = Qt.rgba(r, g, b, 1.0) + rgbMatrixEditor.setColorAtIndex(colorIndex, previewBtn.color) + } + onClose: visible = false + } + EditorTopBar { id: topBar @@ -267,72 +301,224 @@ Rectangle Rectangle { - id: startColButton + id: color1Button width: UISettings.iconSizeDefault * 2 height: editorColumn.itemsHeight radius: 5 - border.color: scMouseArea.containsMouse ? "white" : UISettings.bgLight + border.color: color1MouseArea.containsMouse ? "white" : UISettings.bgLight border.width: 2 - color: rgbMatrixEditor.startColor + color: rgbMatrixEditor.colorAtIndex(0) visible: rgbMatrixEditor.algoColors > 0 ? true : false MouseArea { - id: scMouseArea + id: color1MouseArea anchors.fill: parent hoverEnabled: true - onClicked: startColTool.visible = !startColTool.visible + onClicked: + { + if (colorTool.visible) + colorTool.hide() + else + colorTool.showTool(0, color1Button) + } } + } + Rectangle + { + width: UISettings.listItemHeight + height: width + color: "transparent" + visible: rgbMatrixEditor.algoColors > 2 ? true : false + } + + Rectangle + { + id: color2Button + width: UISettings.iconSizeDefault * 2 + height: editorColumn.itemsHeight + radius: 5 + border.color: color2MouseArea.containsMouse ? "white" : UISettings.bgLight + border.width: 2 + color: rgbMatrixEditor.colorAtIndex(1) + visible: rgbMatrixEditor.algoColors > 1 ? true : false - ColorTool + MouseArea { - id: startColTool - parent: rgbmeContainer - x: -width - (UISettings.iconSizeDefault * 1.25) - y: UISettings.bigItemHeight - visible: false - closeOnSelect: true - currentRGB: rgbMatrixEditor.startColor + id: color2MouseArea + anchors.fill: parent + hoverEnabled: true + onClicked: + { + if (colorTool.visible) + colorTool.hide() + else + colorTool.showTool(1, color2Button) + } + } + } + IconButton + { + width: UISettings.listItemHeight + height: width + imgSource: "qrc:/cancel.svg" + tooltip: qsTr("Reset color 2") + visible: rgbMatrixEditor.algoColors > 1 ? true : false + onClicked: + { + color2Button.color = "transparent" + rgbMatrixEditor.resetColorAtIndex(1) + } + } + } + + // row 7 + Row + { + width: editorColumn.colWidth + height: editorColumn.itemsHeight + spacing: 4 + visible: rgbMatrixEditor.algoColors > 4 ? true : false + + Rectangle + { + id: colorRow1 + height: editorColumn.itemsHeight + width: editorColumn.firstColumnWidth + color: "transparent" + visible: rgbMatrixEditor.algoColors > 4 ? true : false + + onWidthChanged: + { + editorColumn.checkLabelWidth(width) + width = Qt.binding(function() { return editorColumn.firstColumnWidth }) + } + } - onColorChanged: + Rectangle + { + id: color3Button + width: UISettings.iconSizeDefault * 2 + height: editorColumn.itemsHeight + radius: 5 + border.color: color3MouseArea.containsMouse ? "white" : UISettings.bgLight + border.width: 2 + color: rgbMatrixEditor.hasColorAtIndex(2) ? rgbMatrixEditor.colorAtIndex(2) : "transparent" + visible: rgbMatrixEditor.algoColors > 2 ? true : false + + MouseArea + { + id: color3MouseArea + anchors.fill: parent + hoverEnabled: true + onClicked: { - startColButton.color = Qt.rgba(r, g, b, 1.0) - rgbMatrixEditor.startColor = startColButton.color + if (colorTool.visible) + colorTool.hide() + else + colorTool.showTool(2, color3Button) } - onClose: visible = false } } + IconButton + { + width: UISettings.listItemHeight + height: width + imgSource: "qrc:/cancel.svg" + tooltip: qsTr("Reset color 3") + visible: rgbMatrixEditor.algoColors > 2 ? true : false + onClicked: + { + color3Button.color = "transparent" + rgbMatrixEditor.resetColorAtIndex(2) + } + } + Rectangle { - id: endColButton + id: color4Button width: UISettings.iconSizeDefault * 2 height: editorColumn.itemsHeight radius: 5 - border.color: ecMouseArea.containsMouse ? "white" : UISettings.bgLight + border.color: color4MouseArea.containsMouse ? "white" : UISettings.bgLight border.width: 2 - color: rgbMatrixEditor.hasEndColor ? rgbMatrixEditor.endColor : "transparent" - visible: rgbMatrixEditor.algoColors > 1 ? true : false + color: rgbMatrixEditor.hasColorAtIndex(3) ? rgbMatrixEditor.colorAtIndex(3) : "transparent" + visible: rgbMatrixEditor.algoColors > 3 ? true : false MouseArea { - id: ecMouseArea + id: color4MouseArea anchors.fill: parent hoverEnabled: true - onClicked: endColTool.visible = !endColTool.visible + onClicked: + { + if (colorTool.visible) + colorTool.hide() + else + colorTool.showTool(3, color4Button) + } + } + } + IconButton + { + width: UISettings.listItemHeight + height: width + imgSource: "qrc:/cancel.svg" + tooltip: qsTr("Reset color 4") + visible: rgbMatrixEditor.algoColors > 3 ? true : false + onClicked: + { + color4Button.color = "transparent" + rgbMatrixEditor.resetColorAtIndex(3) } + } + } + + // row 8 + Row + { + width: editorColumn.colWidth + height: editorColumn.itemsHeight + spacing: 4 + visible: rgbMatrixEditor.algoColors > 4 ? true : false - ColorTool + Rectangle + { + id: colorRow2 + height: editorColumn.itemsHeight + width: editorColumn.firstColumnWidth + color: "transparent" + visible: rgbMatrixEditor.algoColors > 4 ? true : false + onWidthChanged: { - id: endColTool - parent: rgbmeContainer - x: -width - (UISettings.iconSizeDefault * 1.25) - y: UISettings.bigItemHeight - visible: false - closeOnSelect: true - currentRGB: rgbMatrixEditor.endColor + editorColumn.checkLabelWidth(width) + width = Qt.binding(function() { return editorColumn.firstColumnWidth }) + } + } - onColorChanged: rgbMatrixEditor.endColor = Qt.rgba(r, g, b, 1.0) - onClose: visible = false + Rectangle + { + id: color5Button + width: UISettings.iconSizeDefault * 2 + height: editorColumn.itemsHeight + radius: 5 + border.color: color5MouseArea.containsMouse ? "white" : UISettings.bgLight + border.width: 2 + color: rgbMatrixEditor.hasColorAtIndex(4) ? rgbMatrixEditor.colorAtIndex(4) : "transparent" + visible: rgbMatrixEditor.algoColors > 4 ? true : false + + MouseArea + { + id: color5MouseArea + anchors.fill: parent + hoverEnabled: true + onClicked: + { + if (colorTool.visible) + colorTool.hide() + else + colorTool.showTool(4, color5Button) + } } } IconButton @@ -340,11 +526,14 @@ Rectangle width: UISettings.listItemHeight height: width imgSource: "qrc:/cancel.svg" - visible: rgbMatrixEditor.algoColors > 1 ? true : false - onClicked: rgbMatrixEditor.hasEndColor = false + tooltip: qsTr("Reset color 5") + visible: rgbMatrixEditor.algoColors > 4 ? true : false + onClicked: + { + color5Button.color = "transparent" + rgbMatrixEditor.resetColorAtIndex(4) + } } - // filler - //Rectangle { Layout.fillWidth: true; height: parent.height; color: "transparent" } } SectionBox diff --git a/qmlui/qml/virtualconsole/VCAnimationItem.qml b/qmlui/qml/virtualconsole/VCAnimationItem.qml index aa16f07934..9aa423e9b3 100644 --- a/qmlui/qml/virtualconsole/VCAnimationItem.qml +++ b/qmlui/qml/virtualconsole/VCAnimationItem.qml @@ -71,71 +71,170 @@ VCWidgetItem Rectangle { - id: startColButton + id: col1Button width: UISettings.iconSizeDefault * 1.5 height: width radius: 5 border.color: scMouseArea.containsMouse ? "white" : UISettings.bgLight border.width: 2 - color: animationObj ? animationObj.startColor : "transparent" - visible: animationObj ? animationObj.visibilityMask & VCAnimation.StartColor : true + color: animationObj ? animationObj.color1 : "transparent" + visible: animationObj ? animationObj.visibilityMask & VCAnimation.Color1 : true MouseArea { id: scMouseArea anchors.fill: parent hoverEnabled: true - onClicked: startColTool.visible = !startColTool.visible + onClicked: col1Tool.visible = !col1Tool.visible } ColorTool { - id: startColTool + id: col1Tool parent: animationRoot.parent x: animationRoot.x // -width - (UISettings.iconSizeDefault * 1.25) y: animationRoot.y // UISettings.bigItemHeight visible: false closeOnSelect: true - currentRGB: animationObj ? animationObj.startColor : "black" + currentRGB: animationObj ? animationObj.color1 : "black" onColorChanged: { - startColButton.color = Qt.rgba(r, g, b, 1.0) - animationObj.startColor = startColButton.color + col1Button.color = Qt.rgba(r, g, b, 1.0) + animationObj.color1 = col1Button.color } onClose: visible = false } } Rectangle { - id: endColButton + id: col2Button width: UISettings.iconSizeDefault * 1.5 height: width radius: 5 border.color: ecMouseArea.containsMouse ? "white" : UISettings.bgLight border.width: 2 - color: animationObj ? animationObj.endColor : "transparent" - visible: animationObj ? animationObj.visibilityMask & VCAnimation.EndColor : true + color: animationObj ? animationObj.color2 : "transparent" + visible: animationObj ? animationObj.visibilityMask & VCAnimation.Color2 : true MouseArea { id: ecMouseArea anchors.fill: parent hoverEnabled: true - onClicked: endColTool.visible = !endColTool.visible + onClicked: col2Tool.visible = !col2Tool.visible } ColorTool { - id: endColTool + id: col2Tool parent: animationRoot.parent x: animationRoot.x // -width - (UISettings.iconSizeDefault * 1.25) y: animationRoot.y // UISettings.bigItemHeight visible: false closeOnSelect: true - currentRGB: animationObj ? animationObj.endColor : "black" + currentRGB: animationObj ? animationObj.color2 : "black" - onColorChanged: animationObj.endColor = Qt.rgba(r, g, b, 1.0) + onColorChanged: animationObj.color2 = Qt.rgba(r, g, b, 1.0) + onClose: visible = false + } + } + Rectangle + { + id: col3Button + width: UISettings.iconSizeDefault * 1.5 + height: width + radius: 5 + border.color: ecMouseArea.containsMouse ? "white" : UISettings.bgLight + border.width: 2 + color: animationObj ? animationObj.color3 : "transparent" + visible: animationObj ? animationObj.visibilityMask & VCAnimation.Color3 : true + + MouseArea + { + id: ecMouseArea + anchors.fill: parent + hoverEnabled: true + onClicked: col3Tool.visible = !col3Tool.visible + } + + ColorTool + { + id: col3Tool + parent: animationRoot.parent + x: animationRoot.x // -width - (UISettings.iconSizeDefault * 1.25) + y: animationRoot.y // UISettings.bigItemHeight + visible: false + closeOnSelect: true + currentRGB: animationObj ? animationObj.color3 : "black" + + onColorChanged: animationObj.color3 = Qt.rgba(r, g, b, 1.0) + onClose: visible = false + } + } + Rectangle + { + id: col4Button + width: UISettings.iconSizeDefault * 1.5 + height: width + radius: 5 + border.color: ecMouseArea.containsMouse ? "white" : UISettings.bgLight + border.width: 2 + color: animationObj ? animationObj.color4 : "transparent" + visible: animationObj ? animationObj.visibilityMask & VCAnimation.Color4 : true + + MouseArea + { + id: ecMouseArea + anchors.fill: parent + hoverEnabled: true + onClicked: col4Tool.visible = !col4Tool.visible + } + + ColorTool + { + id: col4Tool + parent: animationRoot.parent + x: animationRoot.x // -width - (UISettings.iconSizeDefault * 1.25) + y: animationRoot.y // UISettings.bigItemHeight + visible: false + closeOnSelect: true + currentRGB: animationObj ? animationObj.color4 : "black" + + onColorChanged: animationObj.color4 = Qt.rgba(r, g, b, 1.0) + onClose: visible = false + } + } + Rectangle + { + id: col5Button + width: UISettings.iconSizeDefault * 1.5 + height: width + radius: 5 + border.color: ecMouseArea.containsMouse ? "white" : UISettings.bgLight + border.width: 2 + color: animationObj ? animationObj.color5 : "transparent" + visible: animationObj ? animationObj.visibilityMask & VCAnimation.Color5 : true + + MouseArea + { + id: ecMouseArea + anchors.fill: parent + hoverEnabled: true + onClicked: col5Tool.visible = !col5Tool.visible + } + + ColorTool + { + id: col5Tool + parent: animationRoot.parent + x: animationRoot.x // -width - (UISettings.iconSizeDefault * 1.25) + y: animationRoot.y // UISettings.bigItemHeight + visible: false + closeOnSelect: true + currentRGB: animationObj ? animationObj.color5 : "black" + + onColorChanged: animationObj.color5 = Qt.rgba(r, g, b, 1.0) onClose: visible = false } } diff --git a/qmlui/qml/virtualconsole/VCAnimationProperties.qml b/qmlui/qml/virtualconsole/VCAnimationProperties.qml index 16c07d79ef..3c8e14a63c 100644 --- a/qmlui/qml/virtualconsole/VCAnimationProperties.qml +++ b/qmlui/qml/virtualconsole/VCAnimationProperties.qml @@ -169,16 +169,16 @@ Rectangle { implicitWidth: UISettings.iconSizeMedium implicitHeight: implicitWidth - checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.StartColor : false + checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.Color1 : false onClicked: { if (!widgetRef) return if (checked) - widgetRef.visibilityMask |= VCAnimation.StartColor + widgetRef.visibilityMask |= VCAnimation.Color1 else - widgetRef.visibilityMask &= ~VCAnimation.StartColor + widgetRef.visibilityMask &= ~VCAnimation.Color1 } } @@ -186,23 +186,23 @@ Rectangle { height: UISettings.listItemHeight Layout.fillWidth: true - label: qsTr("Start Color Button") + label: qsTr("Color 1 Button") } CustomCheckBox { implicitWidth: UISettings.iconSizeMedium implicitHeight: implicitWidth - checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.EndColor : false + checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.Color2 : false onClicked: { if (!widgetRef) return if (checked) - widgetRef.visibilityMask |= VCAnimation.EndColor + widgetRef.visibilityMask |= VCAnimation.Color2 else - widgetRef.visibilityMask &= ~VCAnimation.EndColor + widgetRef.visibilityMask &= ~VCAnimation.Color2 } } @@ -210,7 +210,82 @@ Rectangle { height: UISettings.listItemHeight Layout.fillWidth: true - label: qsTr("End Color Button") + label: qsTr("Color 2 Button") + } + + + CustomCheckBox + { + implicitWidth: UISettings.iconSizeMedium + implicitHeight: implicitWidth + checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.Color3 : false + onClicked: + { + if (!widgetRef) + return + + if (checked) + widgetRef.visibilityMask |= VCAnimation.Color3 + else + widgetRef.visibilityMask &= ~VCAnimation.Color3 + } + } + + RobotoText + { + height: UISettings.listItemHeight + Layout.fillWidth: true + label: qsTr("Color 3 Button") + } + + + CustomCheckBox + { + implicitWidth: UISettings.iconSizeMedium + implicitHeight: implicitWidth + checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.Color4 : false + onClicked: + { + if (!widgetRef) + return + + if (checked) + widgetRef.visibilityMask |= VCAnimation.Color4 + else + widgetRef.visibilityMask &= ~VCAnimation.Color4 + } + } + + RobotoText + { + height: UISettings.listItemHeight + Layout.fillWidth: true + label: qsTr("Color 4 Button") + } + + + CustomCheckBox + { + implicitWidth: UISettings.iconSizeMedium + implicitHeight: implicitWidth + checked: widgetRef ? widgetRef.visibilityMask & VCAnimation.Color5 : false + onClicked: + { + if (!widgetRef) + return + + if (checked) + widgetRef.visibilityMask |= VCAnimation.Color5 + else + widgetRef.visibilityMask &= ~VCAnimation.Color5 + } + } + + RobotoText + { + height: UISettings.listItemHeight + Layout.fillWidth: true + label: qsTr("Color 5 Button") } // row 3 diff --git a/qmlui/rgbmatrixeditor.cpp b/qmlui/rgbmatrixeditor.cpp index c2d6cd012a..a1e789cb0e 100644 --- a/qmlui/rgbmatrixeditor.cpp +++ b/qmlui/rgbmatrixeditor.cpp @@ -134,7 +134,16 @@ void RGBMatrixEditor::setAlgorithmIndex(int algoIndex) /** if we're setting the same algorithm, then there's nothing to do */ if (m_matrix->algorithm() != nullptr && m_matrix->algorithm()->name() == algo->name()) return; - algo->setColors(m_matrix->startColor(), m_matrix->endColor()); + + Q_ASSERT(5 == RGBAlgorithmColorDisplayCount); + QVector colors = { + m_matrix->getColor(0), + m_matrix->getColor(1), + m_matrix->getColor(2), + m_matrix->getColor(3), + m_matrix->getColor(4) + }; + algo->setColors(colors); } Tardis::instance()->enqueueAction(Tardis::RGBMatrixSetAlgorithmIndex, m_matrix->id(), algorithmIndex(), algoIndex); @@ -154,66 +163,43 @@ int RGBMatrixEditor::algoColors() return m_matrix->algorithm()->acceptColors(); } -QColor RGBMatrixEditor::startColor() const +QColor RGBMatrixEditor::colorAtIndex(int index) { - if (m_matrix == nullptr) - return Qt::red; + if (m_matrix == nullptr || m_matrix->algorithm() == nullptr) + return QColor(); - return m_matrix->startColor(); + return m_matrix->getColor(index); } -void RGBMatrixEditor::setStartColor(QColor algoStartColor) +void RGBMatrixEditor::setColorAtIndex(int index, QColor color) { - if (m_matrix == nullptr || m_matrix->startColor() == algoStartColor) + if (m_matrix == nullptr || m_matrix->getColor(index) == color) return; - Tardis::instance()->enqueueAction(Tardis::RGBMatrixSetStartColor, m_matrix->id(), m_matrix->startColor(), algoStartColor); - m_matrix->setStartColor(algoStartColor); - m_previewStepHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); - - emit startColorChanged(algoStartColor); + Tardis::instance()->enqueueAction(Tardis::RGBMatrixSetColor1, m_matrix->id(), m_matrix->getColor(index), color); + m_matrix->setColor(index, color); + if (index < 2) + m_previewStepHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), m_matrix->algorithm()); } -QColor RGBMatrixEditor::endColor() const +void RGBMatrixEditor::resetColorAtIndex(int index) { - if (m_matrix == nullptr) - return QColor(); - - return m_matrix->endColor(); -} - -void RGBMatrixEditor::setEndColor(QColor algoEndColor) -{ - if (m_matrix == nullptr || m_matrix->endColor() == algoEndColor) + if (m_matrix == nullptr || m_matrix->getColor(index).isValid() == false) return; - Tardis::instance()->enqueueAction(Tardis::RGBMatrixSetEndColor, m_matrix->id(), m_matrix->endColor(), algoEndColor); - m_matrix->setEndColor(algoEndColor); - m_previewStepHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); - - emit endColorChanged(algoEndColor); - if (algoEndColor.isValid()) - emit hasEndColorChanged(true); + m_matrix->setColor(index, QColor()); + if (index < 2) + m_previewStepHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), m_matrix->algorithm()); } -bool RGBMatrixEditor::hasEndColor() const +bool RGBMatrixEditor::hasColorAtIndex(int index) { - if (m_matrix == nullptr || m_matrix->endColor().isValid() == false) + if (m_matrix == nullptr || m_matrix->getColor(index).isValid() == false) return false; return true; } -void RGBMatrixEditor::setHasEndColor(bool hasEndCol) -{ - if (m_matrix && hasEndCol == false) - { - m_matrix->setEndColor(QColor()); - m_previewStepHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); - } - emit hasEndColorChanged(hasEndCol); -} - QString RGBMatrixEditor::algoText() const { if (m_matrix != nullptr && m_matrix->algorithm() != nullptr && @@ -482,7 +468,9 @@ void RGBMatrixEditor::setScriptStringProperty(QString paramName, QString value) StringStringPair oldValue(paramName, m_matrix->property(paramName)); Tardis::instance()->enqueueAction(Tardis::RGBMatrixSetScriptStringValue, m_matrix->id(), QVariant::fromValue(oldValue), QVariant::fromValue(StringStringPair(paramName, value))); + m_matrix->setProperty(paramName, value); + emit algoColorsChanged(); } void RGBMatrixEditor::setScriptIntProperty(QString paramName, int value) @@ -593,8 +581,8 @@ void RGBMatrixEditor::slotPreviewTimeout() { QMutexLocker locker(&m_previewMutex); - m_previewStepHandler->checkNextStep(m_matrix->runOrder(), m_matrix->startColor(), - m_matrix->endColor(), m_matrix->stepsCount()); + m_previewStepHandler->checkNextStep(m_matrix->runOrder(), m_matrix->getColor(0), + m_matrix->getColor(1), m_matrix->stepsCount()); m_matrix->previewMap(m_previewStepHandler->currentStepIndex(), m_previewStepHandler); @@ -658,9 +646,9 @@ void RGBMatrixEditor::initPreviewData() if (m_matrix == nullptr) return; - m_previewStepHandler->initializeDirection(m_matrix->direction(), m_matrix->startColor(), - m_matrix->endColor(), m_matrix->stepsCount()); - m_previewStepHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewStepHandler->initializeDirection(m_matrix->direction(), m_matrix->getColor(0), + m_matrix->getColor(1), m_matrix->stepsCount(), m_matrix->algorithm()); + m_previewStepHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), m_matrix->algorithm()); m_previewTimer->start(MasterTimer::tick()); } diff --git a/qmlui/rgbmatrixeditor.h b/qmlui/rgbmatrixeditor.h index e78e60731a..ea44f5cb06 100644 --- a/qmlui/rgbmatrixeditor.h +++ b/qmlui/rgbmatrixeditor.h @@ -39,9 +39,6 @@ class RGBMatrixEditor : public FunctionEditor Q_PROPERTY(QStringList algorithms READ algorithms CONSTANT) Q_PROPERTY(int algorithmIndex READ algorithmIndex WRITE setAlgorithmIndex NOTIFY algorithmIndexChanged) Q_PROPERTY(int algoColors READ algoColors NOTIFY algoColorsChanged) - Q_PROPERTY(QColor startColor READ startColor WRITE setStartColor NOTIFY startColorChanged) - Q_PROPERTY(QColor endColor READ endColor WRITE setEndColor NOTIFY endColorChanged) - Q_PROPERTY(bool hasEndColor READ hasEndColor WRITE setHasEndColor NOTIFY hasEndColorChanged) Q_PROPERTY(int blendMode READ blendMode WRITE setBlendMode NOTIFY blendModeChanged) Q_PROPERTY(int controlMode READ controlMode WRITE setControlMode NOTIFY controlModeChanged) @@ -87,16 +84,10 @@ class RGBMatrixEditor : public FunctionEditor /** Return the accepted colors of the current algorithm */ int algoColors(); - /** Get/set the start color of the current algorithm */ - QColor startColor() const; - void setStartColor(QColor startColor); - - /** Get/set the end color of the current algorithm */ - QColor endColor() const; - void setEndColor(QColor algoEndColor); - - bool hasEndColor() const; - void setHasEndColor(bool hasEndCol); + Q_INVOKABLE QColor colorAtIndex(int index); + Q_INVOKABLE void setColorAtIndex(int index, QColor color); + Q_INVOKABLE void resetColorAtIndex(int index); + Q_INVOKABLE bool hasColorAtIndex(int index); QString algoText() const; void setAlgoText(QString text); @@ -130,9 +121,6 @@ class RGBMatrixEditor : public FunctionEditor signals: void algorithmIndexChanged(); void algoColorsChanged(); - void startColorChanged(QColor startColor); - void endColorChanged(QColor endColor); - void hasEndColorChanged(bool hasEndColor); void algoTextChanged(QString text); void algoTextFontChanged(QFont algoTextFont); diff --git a/qmlui/tardis/tardis.cpp b/qmlui/tardis/tardis.cpp index 1e5c2ae56e..834c046b10 100644 --- a/qmlui/tardis/tardis.cpp +++ b/qmlui/tardis/tardis.cpp @@ -1001,16 +1001,34 @@ int Tardis::processAction(TardisAction &action, bool undo) matrix->setAlgorithm(algo); } break; - case RGBMatrixSetStartColor: + case RGBMatrixSetColor1: { - auto member = std::mem_fn(&RGBMatrix::setStartColor); - member(qobject_cast(m_doc->function(action.m_objID)), value->value()); + auto member = std::mem_fn(&RGBMatrix::setColor); + member(qobject_cast(m_doc->function(action.m_objID)), 0, value->value()); } break; - case RGBMatrixSetEndColor: + case RGBMatrixSetColor2: { - auto member = std::mem_fn(&RGBMatrix::setEndColor); - member(qobject_cast(m_doc->function(action.m_objID)), value->value()); + auto member = std::mem_fn(&RGBMatrix::setColor); + member(qobject_cast(m_doc->function(action.m_objID)), 1, value->value()); + } + break; + case RGBMatrixSetColor3: + { + auto member = std::mem_fn(&RGBMatrix::setColor); + member(qobject_cast(m_doc->function(action.m_objID)), 2, value->value()); + } + break; + case RGBMatrixSetColor4: + { + auto member = std::mem_fn(&RGBMatrix::setColor); + member(qobject_cast(m_doc->function(action.m_objID)), 3, value->value()); + } + break; + case RGBMatrixSetColor5: + { + auto member = std::mem_fn(&RGBMatrix::setColor); + member(qobject_cast(m_doc->function(action.m_objID)), 4, value->value()); } break; case RGBMatrixSetScriptIntValue: diff --git a/qmlui/tardis/tardis.h b/qmlui/tardis/tardis.h index 24be82ffb5..3b39f40226 100644 --- a/qmlui/tardis/tardis.h +++ b/qmlui/tardis/tardis.h @@ -139,8 +139,11 @@ class Tardis : public QThread RGBMatrixSetFixtureGroup, RGBMatrixSetAlgorithmIndex, - RGBMatrixSetStartColor, - RGBMatrixSetEndColor, + RGBMatrixSetColor1, + RGBMatrixSetColor2, + RGBMatrixSetColor3, + RGBMatrixSetColor4, + RGBMatrixSetColor5, RGBMatrixSetScriptIntValue, RGBMatrixSetScriptDoubleValue, RGBMatrixSetScriptStringValue, diff --git a/qmlui/virtualconsole/vcanimation.cpp b/qmlui/virtualconsole/vcanimation.cpp index dbeab0edc7..b279f3b7a9 100644 --- a/qmlui/virtualconsole/vcanimation.cpp +++ b/qmlui/virtualconsole/vcanimation.cpp @@ -170,8 +170,8 @@ void VCAnimation::setFunctionID(quint32 newFunctionID) m_functionID = newFunctionID; emit functionIDChanged(); - emit startColorChanged(); - emit endColorChanged(); + emit color1Changed(); + emit color2Changed(); emit algorithmIndexChanged(); } @@ -230,47 +230,107 @@ void VCAnimation::setInstantChanges(bool newInstantChanges) * Colors and presets *********************************************************************/ -QColor VCAnimation::startColor() const +QColor VCAnimation::getColor1() const { if (m_matrix == NULL) return QColor(); - return m_matrix->startColor(); + return m_matrix->getColor(0); } -void VCAnimation::setStartColor(QColor color) +void VCAnimation::setColor1(QColor color) { if (m_matrix == NULL) return; - if (m_matrix->startColor() != color) + if (m_matrix->getColor(0) != color) { - m_matrix->setStartColor(color); + m_matrix->setColor(0, color); if (instantChanges()) m_matrix->updateColorDelta(); - emit startColorChanged(); + emit color1Changed(); } } -QColor VCAnimation::endColor() const +QColor VCAnimation::getColor2() const { if (m_matrix == NULL) return QColor(); - return m_matrix->endColor(); + return m_matrix->getColor(1); } -void VCAnimation::setEndColor(QColor color) +void VCAnimation::setColor2(QColor color) { if (m_matrix == NULL) return; - if (m_matrix->endColor() != color) + if (m_matrix->getColor(1) != color) { - m_matrix->setEndColor(color); + m_matrix->setColor(1, color); if (instantChanges()) m_matrix->updateColorDelta(); - emit endColorChanged(); + emit color2Changed(); + } +} + +QColor VCAnimation::getColor3() const +{ + if (m_matrix == NULL) + return QColor(); + + return m_matrix->getColor(2); +} + +void VCAnimation::setColor3(QColor color) +{ + if (m_matrix == NULL) + return; + + if (m_matrix->getColor(2) != color) + { + m_matrix->setColor(2, color); + emit color3Changed(); + } +} + +QColor VCAnimation::getColor4() const +{ + if (m_matrix == NULL) + return QColor(); + + return m_matrix->getColor(3); +} + +void VCAnimation::setColor4(QColor color) +{ + if (m_matrix == NULL) + return; + + if (m_matrix->getColor(3) != color) + { + m_matrix->setColor(3, color); + emit color4Changed(); + } +} + +QColor VCAnimation::getColor5() const +{ + if (m_matrix == NULL) + return QColor(); + + return m_matrix->getColor(4); +} + +void VCAnimation::setColor5(QColor color) +{ + if (m_matrix == NULL) + return; + + if (m_matrix->getColor(4) != color) + { + m_matrix->setColor(4, color); + emit color5Changed(); } } @@ -303,7 +363,7 @@ void VCAnimation::setAlgorithmIndex(int index) /** if we're setting the same algorithm, then there's nothing to do */ if (m_matrix->algorithm() != nullptr && m_matrix->algorithm()->name() == algo->name()) return; - algo->setColors(m_matrix->startColor(), m_matrix->endColor()); + algo->setColors(m_matrix->getColors()); } m_matrix->setAlgorithm(algo); diff --git a/qmlui/virtualconsole/vcanimation.h b/qmlui/virtualconsole/vcanimation.h index 7b5c2e7e63..9c4107b671 100644 --- a/qmlui/virtualconsole/vcanimation.h +++ b/qmlui/virtualconsole/vcanimation.h @@ -41,8 +41,11 @@ class VCAnimation : public VCWidget Q_PROPERTY(int faderLevel READ faderLevel WRITE setFaderLevel NOTIFY faderLevelChanged FINAL) Q_PROPERTY(bool instantChanges READ instantChanges WRITE setInstantChanges NOTIFY instantChangesChanged FINAL) - Q_PROPERTY(QColor startColor READ startColor WRITE setStartColor NOTIFY startColorChanged) - Q_PROPERTY(QColor endColor READ endColor WRITE setEndColor NOTIFY endColorChanged) + Q_PROPERTY(QColor color1 READ getColor1 WRITE setColor1 NOTIFY color1Changed) + Q_PROPERTY(QColor color2 READ getColor2 WRITE setColor2 NOTIFY color2Changed) + Q_PROPERTY(QColor color2 READ getColor3 WRITE setColor3 NOTIFY color3Changed) + Q_PROPERTY(QColor color2 READ getColor4 WRITE setColor4 NOTIFY color4Changed) + Q_PROPERTY(QColor color2 READ getColor5 WRITE setColor5 NOTIFY color5Changed) Q_PROPERTY(QStringList algorithms READ algorithms CONSTANT) Q_PROPERTY(int algorithmIndex READ algorithmIndex WRITE setAlgorithmIndex NOTIFY algorithmIndexChanged FINAL) @@ -133,13 +136,25 @@ class VCAnimation : public VCWidget * Colors and presets *********************************************************************/ public: - /** Get/set the start color of the current algorithm */ - QColor startColor() const; - void setStartColor(QColor color); + /** Get/set color 1 of the current algorithm */ + QColor getColor1() const; + void setColor1(QColor color); - /** Get/set the end color of the current algorithm */ - QColor endColor() const; - void setEndColor(QColor color); + /** Get/set color 2 of the current algorithm */ + QColor getColor2() const; + void setColor2(QColor color); + + /** Get/set color 1 of the current algorithm */ + QColor getColor3() const; + void setColor3(QColor color); + + /** Get/set color 2 of the current algorithm */ + QColor getColor4() const; + void setColor4(QColor color); + + /** Get/set color 2 of the current algorithm */ + QColor getColor5() const; + void setColor5(QColor color); /** Returns the list of available algorithms */ QStringList algorithms() const; @@ -149,8 +164,11 @@ class VCAnimation : public VCWidget void setAlgorithmIndex(int index); signals: - void startColorChanged(); - void endColorChanged(); + void color1Changed(); + void color2Changed(); + void color3Changed(); + void color4Changed(); + void color5Changed(); void algorithmIndexChanged(); /********************************************************************* diff --git a/resources/rgbscripts/CMakeLists.txt b/resources/rgbscripts/CMakeLists.txt index 7526c3d5c9..21a8b28607 100644 --- a/resources/rgbscripts/CMakeLists.txt +++ b/resources/rgbscripts/CMakeLists.txt @@ -3,7 +3,6 @@ project(scripts) set(SCRIPT_FILES alternate.js balls.js - ballscolors.js blinder.js circles.js circular.js @@ -22,7 +21,6 @@ set(SCRIPT_FILES onebyone.js opposite.js plasma.js - plasmacolors.js randomcolumn.js randomfillcolumn.js randomfillrow.js diff --git a/resources/rgbscripts/alternate.js b/resources/rgbscripts/alternate.js index 7381e06852..be9aa487f8 100644 --- a/resources/rgbscripts/alternate.js +++ b/resources/rgbscripts/alternate.js @@ -21,117 +21,18 @@ var testAlgo; (function() { - var colorPalette = new Object; - colorPalette.collection = new Array( - ["White", 0xFFFFFF], // 0 - ["Cream", 0xFFFF7F], // 1 - ["Pink", 0xFF7F7F], // 2 - ["Rose", 0x7F3F3F], // 3 - ["Coral", 0x7F3F1F], // 4 - ["Dim Red", 0x7F0000], // 5 - ["Red", 0xFF0000], // 6 - ["Orange", 0xFF3F00], // 7 - ["Dim Orange", 0x7F1F00], // 8 - ["Goldenrod", 0x7F3F00], // 9 - ["Gold", 0xFF7F00], // 10 - ["Yellow", 0xFFFF00], // 11 - ["Dim Yellow", 0x7F7F00], // 12 - ["Lime", 0x7FFF00], // 13 - ["Pale Green", 0x3F7F00], // 14 - ["Dim Green", 0x007F00], // 15 - ["Green", 0x00FF00], // 16 - ["Seafoam", 0x00FF3F], // 17 - ["Turquoise", 0x007F3F], // 18 - ["Teal", 0x007F7F], // 19 - ["Cyan", 0x00FFFF], // 20 - ["Electric Blue", 0x007FFF], // 21 - ["Blue", 0x0000FF], // 22 - ["Dim Blue", 0x00007F], // 23 - ["Pale Blue", 0x1F1F7F], // 24 - ["Indigo", 0x1F00BF], // 25 - ["Purple", 0x3F00BF], // 26 - ["Violet", 0x7F007F], // 27 - ["Magenta", 0xFF00FF], // 28 - ["Hot Pink", 0xFF003F], // 29 - ["Deep Pink", 0x7F001F], // 30 - ["OFF", 0x000000]); // 31 - - colorPalette.makeSubArray = function(_index) { - var _array = new Array(); - for (var i = 0; i < colorPalette.collection.length; i++) { - _array.push(colorPalette.collection[parseInt(i, 10)][parseInt(_index, 10)]); - } - return _array; - }; - colorPalette.names = colorPalette.makeSubArray(0); var algo = new Object; - algo.apiVersion = 2; + algo.apiVersion = 3; algo.name = "Alternate"; algo.author = "Hans-Jürgen Tappe"; var x = 0; var y = 0; - algo.acceptColors = 0; + algo.acceptColors = 2; algo.properties = new Array(); - algo.getColorIndex = function(_name) { - var idx = colorPalette.names.indexOf(_name); - if (idx === -1) { - idx = (colorPalette.collection.length - 1); - } - return idx; - }; - - algo.color1Index = algo.getColorIndex("Red"); - algo.properties.push("name:color1Index|type:list|display:Color 1|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor1Index|read:getColor1Name"); - algo.color2Index = algo.getColorIndex("Green"); - algo.properties.push("name:color2Index|type:list|display:Color 2|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor2Index|read:getColor2Name"); - - algo.getColorName = function(_index) { - if (_index < 0) { - _index = 0; - } - if (_index >= colorPalette.collection.length) { - _index = (colorPalette.collection.length - 1); - } - return colorPalette.collection[parseInt(_index, 10)][0]; - }; - algo.getColorValue = function(_index) { - if (_index < 0) { - _index = 0; - } - else if (_index >= colorPalette.collection.length) { - _index = (colorPalette.collection.length - 1); - } - return colorPalette.collection[parseInt(_index, 10)][1]; - }; - - algo.setColor1Index = function(_name) { - algo.color1Index = algo.getColorIndex(_name); - }; - algo.getColor1Name = function() { - return algo.getColorName(algo.color1Index); - }; - algo.getColor1Value = function() { - return algo.getColorValue(algo.color1Index); - }; - - algo.setColor2Index = function(_name) { - algo.color2Index = algo.getColorIndex(_name); - }; - algo.getColor2Name = function() { - return algo.getColorName(algo.color2Index); - }; - algo.getColor2Value = function() { - return algo.getColorValue(algo.color2Index); - }; - algo.align = 0; algo.properties.push("name:align|type:list|" + "display:Align (for even width)|values:Left,Centered,Split|" + @@ -203,17 +104,40 @@ var testAlgo; return algo.offset; }; + var util = new Object; + util.colorArray = new Array(algo.acceptColors); + + util.getRawColor = function (idx) { + var color = 0; + if (Array.isArray(util.colorArray) && util.colorArray.length > idx && util.colorArray[idx]) { + color = util.colorArray[idx]; + } + return color; + } + + algo.rgbMapSetColors = function(rawColors) + { + if (! Array.isArray(rawColors)) + return; + for (var i = 0; i < algo.acceptColors; i++) { + if (i < rawColors.length) + { + util.colorArray[i] = rawColors[i]; + } else { + util.colorArray[i] = 0; + } + } + } + algo.rgbMap = function(width, height, rgb, step) { var map = new Array(height); var colorSelectOne = (step === 1) ? false : true; var rowColorOne = colorSelectOne; var realBlockSize = algo.blockSize; + // Setup the rgb map for (y = 0; y < height; y++) { - map[parseInt(y, 10)] = new Array(width); - for (x = 0; x < width; x++) { - map[parseInt(y, 10)][parseInt(x, 10)] = 0; - } + map[y] = new Array(width); } var xMax = width; @@ -287,7 +211,7 @@ var testAlgo; lowRest = effectiveStep - realBlockCount * realBlockSize; highRest = (realBlockCount + 1) * realBlockSize - effectiveStep; rest = Math.min(lowRest, highRest); - if (rest < 0.5 || lowRest == 0.5) { + if (rest < 0.5 || lowRest === 0.5) { colorSelectOne = !colorSelectOne; } } else if (algo.orientation === 2) { @@ -303,9 +227,9 @@ var testAlgo; } } if (colorSelectOne) { - map[parseInt(y, 10)][parseInt(x, 10)] = algo.getColor1Value(); + map[y][x] = util.getRawColor(0); } else { - map[parseInt(y, 10)][parseInt(x, 10)] = algo.getColor2Value(); + map[y][x] = util.getRawColor(1); } } } @@ -314,21 +238,21 @@ var testAlgo; if (algo.orientation === 0) { for (y = 0; y < yMax; y++) { for (x = 0; x < xMax; x++) { - map[parseInt(y, 10)][parseInt(width - x - 1, 10)] = map[parseInt(y, 10)][parseInt(x, 10)]; + map[y][width - x - 1] = map[y][x]; } } } else if (algo.orientation === 1) { for (y = 0; y < yMax; y++) { for (x = 0; x < xMax; x++) { - map[parseInt(height - y - 1, 10)][parseInt(x, 10)] = map[parseInt(y, 10)][parseInt(x, 10)]; + map[height - y - 1][x] = map[y][x]; } } } else if (algo.orientation === 2) { for (y = 0; y < yMax; y++) { for (x = 0; x < xMax; x++) { - map[parseInt(height - y - 1, 10)][parseInt(x, 10)] = map[parseInt(y, 10)][parseInt(x, 10)]; - map[parseInt(y, 10)][parseInt(width - x - 1, 10)] = map[parseInt(y, 10)][parseInt(x, 10)]; - map[parseInt(height - y - 1, 10)][parseInt(width - x - 1, 10)] = map[parseInt(y, 10)][parseInt(x, 10)]; + map[height - y - 1][x] = map[y][x]; + map[y][width - x - 1] = map[y][x]; + map[height - y - 1][width - x - 1] = map[y][x]; } } } diff --git a/resources/rgbscripts/balls.js b/resources/rgbscripts/balls.js index f957953ce3..fdfdc1e91b 100644 --- a/resources/rgbscripts/balls.js +++ b/resources/rgbscripts/balls.js @@ -2,16 +2,16 @@ Q Light Controller Plus balls.js - Copyright (c) Tim Cullingworth + Copyright (c) Rob Nieuwenhuizen, Tim Cullingworth - Licensed under the Apache License, Version 2.0 (the "License"); + Licensed under the Apache License, Version 2.0 (the 'License'); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0.txt Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, + distributed under the License is distributed on an 'AS IS' BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License. @@ -21,122 +21,149 @@ var testAlgo; ( - function() - { + function () { var algo = new Object; - algo.apiVersion = 2; + algo.apiVersion = 3; algo.name = "Balls"; - algo.author = "Tim Cullingworth"; - algo.acceptColors = 1; + algo.author = "Rob Nieuwenhuizen, Tim Cullingworth"; + algo.acceptColors = 5; algo.properties = new Array(); - algo.rstepcount = 0; - algo.gstepcount = 50; - algo.bstepcount = 100; - algo.presetSize = 1; - algo.properties.push("name:presetSize|type:range|display:Size|values:1,20|write:setSize|read:getSize"); + algo.properties.push( + "name:presetSize|type:range|display:Size|" + + "values:1,20|write:setSize|read:getSize"); algo.presetNumber = 5; - algo.properties.push("name:presetNumber|type:range|display:Number|values:1,50|write:setNumber|read:getNumber"); - algo.presetRandom = 1; - algo.properties.push("name:presetRandom|type:list|display:Random Colour|values:No,Yes|write:setRandom|read:getRandom"); - algo.presetCollision = 1; - algo.properties.push("name:presetCollision|type:list|display:Self Collision|values:No,Yes|write:setCollision|read:getCollision"); - var util = new Object; + algo.properties.push( + "name:presetNumber|type:range|display:Number|" + + "values:1,15|write:setNumber|read:getNumber"); + algo.presetCollision = 0; + algo.properties.push( + "name:presetCollision|type:list|display:Self Collision|" + + "values:No,Yes|write:setCollision|read:getCollision"); + algo.presetSize = 5; + algo.properties.push( + "name:presetIndex|type:list|display:Preset|" + + "values:User Defined,Random|" + + "write:setPreset|read:getPreset"); + algo.presetIndex = 0; + algo.initialized = false; + + var util = new Object; + util.colorArray = new Array(algo.acceptColors); - algo.setSize = function(_size) - { + algo.setSize = function (_size) { algo.presetSize = _size; }; - - algo.getSize = function() - { + algo.getSize = function () { return algo.presetSize; }; - algo.setNumber = function(_step) - { + algo.setNumber = function (_step) { algo.presetNumber = _step; algo.initialized = false; }; - - algo.getNumber = function() - { + algo.getNumber = function () { return algo.presetNumber; }; - - algo.setRandom = function(_random) - { - if (_random === "Yes") { algo.presetRandom = 0; } - else if (_random === "No") { algo.presetRandom = 1; } + algo.setCollision = function (_colision) { + if (_colision === "Yes") { algo.presetCollision = 0; } + else if (_colision === "No") { algo.presetCollision = 1; } }; - - algo.getRandom = function() - { - if (algo.presetRandom === 0) { return "Yes"; } - else if (algo.presetRandom === 1) { return "No"; } + algo.getCollision = function () { + if (algo.presetCollision === 0) { return "Yes"; } + else if (algo.presetCollision === 1) { return "No"; } }; - algo.setCollision = function(_colision) + util.getRawColor = function (idx) { + idx = idx % util.colorArray.length; + var color = util.colorArray[idx]; + return color; + } + + algo.setPreset = function(_preset) { - if (_colision === "Yes") { algo.presetCollision = 0; } - else if (_colision === "No") { algo.presetCollision = 1; } + algo.acceptColors = 0; + if (_preset === "User Defined") + { + algo.presetIndex = 0; + algo.acceptColors = 5; + util.colorArray = [ 0x00FF00, 0xFFAA00, 0x0000FF, 0xFFFF00, 0x00AAFF ]; + } + else if (_preset === "Random") + { + algo.presetIndex = 1; + util.colorArray = new Array(); + for (var i = 0; i < algo.presetNumber; i++) + { + do + { + var ballR = Math.round(Math.random() * 255); // Chose random + var ballG = Math.round(Math.random() * 255); // colour for + var ballB = Math.round(Math.random() * 255); // each Ball + } while ((ballR + ballG + ballB) < 356); // if it it to dim try again + util.colorArray[i] = (ballR << 16) + (ballG << 8) + ballB; + } + } + else { algo.presetIndex = 0; } + util.initialized = false; }; - algo.getCollision = function() + algo.getPreset = function() { - if (algo.presetCollision === 0) { return "Yes"; } - else if (algo.presetCollision === 1) { return "No"; } + if (algo.presetIndex === 0) { return "User Defined"; } + else if (algo.presetIndex === 1) { return "Random"; } + else { return "Rainbow"; } }; - - util.initialize = function(width, height) + + algo.rgbMapSetColors = function(rawColors) { + if (! Array.isArray(rawColors)) + return; + if (algo.acceptColors > 0) + util.colorArray = Array(); + for (var i = 0; i < algo.acceptColors; i++) { + var isNumber = (rawColors[i] === rawColors[i]); + var color = rawColors[i]; + if (i < rawColors.length && isNumber) + { + util.colorArray.push(color); + } + } + } + + util.initialize = function (width, height) { algo.ball = new Array(algo.presetNumber); algo.direction = new Array(algo.presetNumber); - algo.colour = new Array(algo.presetNumber); - for (var i = 0; i < algo.presetNumber; i++) - { + for (var i = 0; i < algo.presetNumber; i++) { var x = Math.random() * (width - 1); // set random start var y = Math.random() * (height - 1); // locations for balls algo.ball[i] = [y, x]; var yDirection = (Math.random() * 2) - 1; // and random directions var xDirection = (Math.random() * 2) - 1; algo.direction[i] = [yDirection, xDirection]; - do - { - var ballR = Math.round(Math.random() * 255); // Chose random - var ballG = Math.round(Math.random() * 255); // colour for - var ballB = Math.round(Math.random() * 255); // each Ball - } while ((ballR + ballG + ballB) < 356); // if it it to dim try again - algo.colour[i] = (ballR << 16) + (ballG << 8) + ballB; } - - algo.initialized = true; - return; + algo.initialized = true; + return; }; - algo.rgbMap = function(width, height, rgb, progstep) - { - if (algo.initialized === false) - { + algo.rgbMap = function (width, height, rgb, progstep) { + if (algo.initialized === false) { util.initialize(width, height); } - var map = new Array(height); // Clear map data - for (var y = 0; y < height; y++) - { - map[y] = new Array(); + var map = new Array(height); // Clear map data + for (var y = 0; y < height; y++) { + map[y] = new Array(); - for (var x = 0; x < width; x++) - { - map[y][x] = 0; - } + for (var x = 0; x < width; x++) { + map[y][x] = 0; + } } - for (var i = 0; i < algo.presetNumber; i++) // for each ball displayed - { - if (algo.presetRandom === 0) { rgb = algo.colour[i]; } // use RGB or ball random colour + for (var i = 0; i < algo.presetNumber; i++) { // for each ball displayed + rgb = util.getRawColor(i); // use RGB for ball random colour var r = (rgb >> 16) & 0x00FF; // split colour in to var g = (rgb >> 8) & 0x00FF; // separate parts var b = rgb & 0x00FF; @@ -146,13 +173,12 @@ var testAlgo; var mx = Math.floor(yx[1]); var boxSize = Math.round(algo.presetSize / 2); // area size to draw ball - for (var ry = my-boxSize; ry < my+boxSize+2; ry++) // area for faded edges - { - for (var rx = mx-boxSize; rx < mx+boxSize+2; rx++) // to display ball - { - if (rx < width && rx > -1 && ry < height && ry > -1) // if edges are off the map - { // dont draw - var pointRGB = map[ry][rx]; // get curent colour on the map + for (var ry = my - boxSize; ry < my + boxSize + 2; ry++) { // area for faded edges + + for (var rx = mx - boxSize; rx < mx + boxSize + 2; rx++) { // to display ball + + if (rx < width && rx > -1 && ry < height && ry > -1) { // if edges are off the map dont draw + var pointRGB = map[ry][rx]; // get curent colour on the map var pointr = (pointRGB >> 16) & 0x00FF;// so that colours mix and don't over var pointg = (pointRGB >> 8) & 0x00FF; // write. var pointb = pointRGB & 0x00FF; // splt rgb in to components @@ -161,7 +187,8 @@ var testAlgo; var ballb = b; var offx = rx - yx[1]; // calculate the off set differance of map location var offy = ry - yx[0]; // to the float location of the ball, using the hypotenuse - var hyp = 1 - (Math.sqrt( (offx * offx) + (offy * offy))/((algo.presetSize/2)+1)); + var hyp = 1 - (Math.sqrt((offx * offx) + (offy * offy)) / ((algo.presetSize / 2) + 1)); + if (hyp < 0) { hyp = 0; } // if the distance multiplyed by ball size is negative = 0 pointr += Math.round(ballr * hyp); // dim mapped ball colours by the distance from pointg += Math.round(ballg * hyp); // the ball center ( hyp = 1, full colour / 0, off) @@ -176,18 +203,16 @@ var testAlgo; } } } - if (algo.presetCollision === 0) // if colision detection is on - { + + if (algo.presetCollision === 0) { // if colision detection is on // Ball collision detection - for (var ti = 0; ti < algo.presetNumber; ti++) // check all balls - { - if (ti !== i) // but not the current one - { + for (var ti = 0; ti < algo.presetNumber; ti++) { // check all balls + + if (ti !== i) { // but not the current one var disy = (yx[0] + step[0]) - algo.ball[ti][0]; // calculate distance var disx = (yx[1] + step[1]) - algo.ball[ti][1]; // to current ball var dish = Math.sqrt((disx * disx) + (disy * disy)); - if (dish < (1.414) * (algo.presetSize/2)) // if to close - { + if (dish < (1.414) * (algo.presetSize / 2)) { // if to close var stepy = step[0]; // swap speed / direction of current ball var stepx = step[1]; // with ball that is to close algo.direction[i][0] = algo.direction[ti][0]; @@ -201,10 +226,10 @@ var testAlgo; // edge collision detection if (yx[0] <= 0 && step[0] < 0) { step[0] *= -1; } // top edge and moving up - else if (yx[0] >= height-1 && step[0] > 0) { step[0] *= -1; } // bottom edge and moving down + else if (yx[0] >= height - 1 && step[0] > 0) { step[0] *= -1; } // bottom edge and moving down if (yx[1] <= 0 && step[1] < 0) { step[1] *= -1; } // left edge and moving left - else if (yx[1] >= width-1 && step[1] > 0) { step[1] *= -1; } // right edge and moving right + else if (yx[1] >= width - 1 && step[1] > 0) { step[1] *= -1; } // right edge and moving right yx[0] += step[0]; // set ball's next location yx[1] += step[1]; @@ -212,12 +237,10 @@ var testAlgo; algo.ball[i] = yx; // update location algo.direction[i] = step; // and direction / speed } - return map; }; - algo.rgbMapStepCount = function(width, height) - { + algo.rgbMapStepCount = function (width, height) { // This make no difference to the script ;-) return 2; }; diff --git a/resources/rgbscripts/ballscolors.js b/resources/rgbscripts/ballscolors.js deleted file mode 100644 index a000828dec..0000000000 --- a/resources/rgbscripts/ballscolors.js +++ /dev/null @@ -1,317 +0,0 @@ -/* - Q Light Controller Plus - ballscolors.js - - Copyright (c) Rob Nieuwenhuizen - - Licensed under the Apache License, Version 2.0 (the 'License'); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0.txt - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an 'AS IS' BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. -*/ - -// Development tool access -var testAlgo; - -( - function () { - var colorPalette = new Object; - colorPalette.collection = new Array( - ["White" , 0xFFFFFF], // 0 - ["Cream" , 0xFFFF7F], // 1 - ["Pink" , 0xFF7F7F], // 2 - ["Rose" , 0x7F3F3F], // 3 - ["Coral" , 0x7F3F1F], // 4 - ["Dim Red" , 0x7F0000], // 5 - ["Red" , 0xFF0000], // 6 - ["Orange" , 0xFF3F00], // 7 - ["Dim Orange" , 0x7F1F00], // 8 - ["Goldenrod" , 0x7F3F00], // 9 - ["Gold" , 0xFF7F00], // 10 - ["Yellow" , 0xFFFF00], // 11 - ["Dim Yellow" , 0x7F7F00], // 12 - ["Lime" , 0x7FFF00], // 13 - ["Pale Green" , 0x3F7F00], // 14 - ["Dim Green" , 0x007F00], // 15 - ["Green" , 0x00FF00], // 16 - ["Seafoam" , 0x00FF3F], // 17 - ["Turquoise" , 0x007F3F], // 18 - ["Teal" , 0x007F7F], // 19 - ["Cyan" , 0x00FFFF], // 20 - ["Electric Blue", 0x007FFF], // 21 - ["Blue" , 0x0000FF], // 22 - ["Dim Blue" , 0x00007F], // 23 - ["Pale Blue" , 0x1F1F7F], // 24 - ["Indigo" , 0x1F00BF], // 25 - ["Purple" , 0x3F00BF], // 26 - ["Violet" , 0x7F007F], // 27 - ["Magenta" , 0xFF00FF], // 28 - ["Hot Pink" , 0xFF003F], // 29 - ["Deep Pink" , 0x7F001F], // 30 - ["Black" , 0x000000]); // 31 - - colorPalette.makeSubArray = function (_index) { - var _array = new Array(); - for (var i = 0; i < colorPalette.collection.length; i++) { - _array.push(colorPalette.collection[i][_index]); - } - return _array; - }; - colorPalette.names = colorPalette.makeSubArray(0); - - var algo = new Object; - algo.apiVersion = 2; - algo.name = "Balls (Colors)"; - algo.author = "Rob Nieuwenhuizen"; - algo.acceptColors = 0; - algo.properties = new Array(); - algo.presetSize = 1; - algo.properties.push("name:presetSize|type:range|display:Size|values:1,20|write:setSize|read:getSize"); - algo.presetNumber = 5; - algo.properties.push("name:presetNumber|type:range|display:Number|values:1,5|write:setNumber|read:getNumber"); - algo.presetCollision = 0; - algo.properties.push("name:presetCollision|type:list|display:Self Collision|values:No,Yes|write:setCollision|read:getCollision"); - algo.color1Index = 0; - algo.properties.push( - "name:color1Index|type:list|display:Color 1|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor1|read:getColor1"); - algo.color2Index = 6; - algo.properties.push( - "name:color2Index|type:list|display:Color 2|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor2|read:getColor2"); - algo.color3Index = 16; - algo.properties.push( - "name:color3Index|type:list|display:Color 3|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor3|read:getColor3"); - algo.color4Index = 22; - algo.properties.push( - "name:color4Index|type:list|display:Color 4|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor4|read:getColor4"); - algo.color5Index = 7; - algo.properties.push( - "name:color5Index|type:list|display:Color 5|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor5|read:getColor5"); - algo.presetSize = 5; - - algo.colorIndex = new Array( - algo.color1Index, - algo.color2Index, - algo.color3Index, - algo.color4Index, - algo.color5Index); - - var util = new Object; - algo.initialized = false; - - algo.setSize = function (_size) { - algo.presetSize = _size; - }; - algo.getSize = function () { - return algo.presetSize; - }; - - algo.setNumber = function (_step) { - algo.presetNumber = _step; - algo.initialized = false; - }; - algo.getNumber = function () { - return algo.presetNumber; - }; - algo.setCollision = function (_colision) { - if (_colision === "Yes") { algo.presetCollision = 0; } - else if (_colision === "No") { algo.presetCollision = 1; } - }; - algo.getCollision = function () { - if (algo.presetCollision === 0) { return "Yes"; } - else if (algo.presetCollision === 1) { return "No"; } - }; - - algo.setColor = function (_index, _preset) { - var i = colorPalette.names.indexOf(_preset); - if (i === -1) { - i = (colorPalette.collection.length - 1); - } - algo.colorIndex[_index] = i; - return algo.colorIndex[_index]; - }; - algo.getColor = function (_index) { - var i = algo.colorIndex[_index]; - if (i < 0) { i = 0; } - if (i >= colorPalette.collection.length) { - i = (colorPalette.collection.length - 1); - } - return colorPalette.collection[i][0]; - }; - - algo.setColor1 = function (_preset) { - algo.color1Index = algo.setColor(0, _preset); - algo.initialized = false; - }; - algo.getColor1 = function () { - return algo.getColor(0); - }; - - algo.setColor2 = function (_preset) { - algo.color2Index = algo.setColor(1, _preset); - algo.initialized = false; - }; - algo.getColor2 = function () { - return algo.getColor(1); - }; - - algo.setColor3 = function (_preset) { - algo.color3Index = algo.setColor(2, _preset); - algo.initialized = false; - }; - algo.getColor3 = function () { - return algo.getColor(2); - }; - - algo.setColor4 = function (_preset) { - algo.color4Index = algo.setColor(3, _preset); - algo.initialized = false; - }; - algo.getColor4 = function () { - return algo.getColor(3); - }; - - algo.setColor5 = function (_preset) { - algo.color5Index = algo.setColor(4, _preset); - algo.initialized = false; - }; - algo.getColor5 = function () { - return algo.getColor(4); - }; - - util.initialize = function (width, height) { - algo.ball = new Array(algo.presetNumber); - algo.direction = new Array(algo.presetNumber); - algo.colour = new Array(algo.presetNumber); - - for (var i = 0; i < algo.presetNumber; i++) { - var x = Math.random() * (width - 1); // set random start - var y = Math.random() * (height - 1); // locations for balls - algo.ball[i] = [y, x]; - var yDirection = (Math.random() * 2) - 1; // and random directions - var xDirection = (Math.random() * 2) - 1; - algo.direction[i] = [yDirection, xDirection]; - algo.colour[i] = colorPalette.collection[algo.colorIndex[i % algo.colorIndex.length]][1]; - } - algo.initialized = true; - return; - }; - - algo.rgbMap = function (width, height, rgb, progstep) { - if (algo.initialized === false) { - util.initialize(width, height); - } - var map = new Array(height); // Clear map data - for (var y = 0; y < height; y++) { - map[y] = new Array(); - - for (var x = 0; x < width; x++) { - map[y][x] = 0; - } - } - - for (var i = 0; i < algo.presetNumber; i++) { // for each ball displayed - rgb = algo.colour[i]; // use RGB for ball random colour - var r = (rgb >> 16) & 0x00FF; // split colour in to - var g = (rgb >> 8) & 0x00FF; // separate parts - var b = rgb & 0x00FF; - var yx = algo.ball[i]; // ball's location, as float - var step = algo.direction[i]; // ball's direction / speed, as float - var my = Math.floor(yx[0]); // workout closest map location for ball - var mx = Math.floor(yx[1]); - var boxSize = Math.round(algo.presetSize / 2); // area size to draw ball - - for (var ry = my - boxSize; ry < my + boxSize + 2; ry++) { // area for faded edges - - for (var rx = mx - boxSize; rx < mx + boxSize + 2; rx++) { // to display ball - - if (rx < width && rx > -1 && ry < height && ry > -1) { // if edges are off the map dont draw - var pointRGB = map[ry][rx]; // get curent colour on the map - var pointr = (pointRGB >> 16) & 0x00FF;// so that colours mix and don't over - var pointg = (pointRGB >> 8) & 0x00FF; // write. - var pointb = pointRGB & 0x00FF; // splt rgb in to components - var ballr = r; - var ballg = g; - var ballb = b; - var offx = rx - yx[1]; // calculate the off set differance of map location - var offy = ry - yx[0]; // to the float location of the ball, using the hypotenuse - var hyp = 1 - (Math.sqrt((offx * offx) + (offy * offy)) / ((algo.presetSize / 2) + 1)); - - if (hyp < 0) { hyp = 0; } // if the distance multiplyed by ball size is negative = 0 - pointr += Math.round(ballr * hyp); // dim mapped ball colours by the distance from - pointg += Math.round(ballg * hyp); // the ball center ( hyp = 1, full colour / 0, off) - pointb += Math.round(ballb * hyp); // add the ball colour to the mapped location - if (pointr > 255) { pointr = 255; } // if addind the colours over saturates - if (pointg > 255) { pointg = 255; } // reduce it to the maximum - if (pointb > 255) { pointb = 255; } - - pointRGB = (pointr << 16) + (pointg << 8) + pointb; // combine colours - - map[ry][rx] = pointRGB; // set mapped point - } - } - } - - if (algo.presetCollision === 0) { // if colision detection is on - // Ball collision detection - for (var ti = 0; ti < algo.presetNumber; ti++) { // check all balls - - if (ti !== i) { // but not the current one - var disy = (yx[0] + step[0]) - algo.ball[ti][0]; // calculate distance - var disx = (yx[1] + step[1]) - algo.ball[ti][1]; // to current ball - var dish = Math.sqrt((disx * disx) + (disy * disy)); - if (dish < (1.414) * (algo.presetSize / 2)) { // if to close - var stepy = step[0]; // swap speed / direction of current ball - var stepx = step[1]; // with ball that is to close - algo.direction[i][0] = algo.direction[ti][0]; - algo.direction[i][1] = algo.direction[ti][1]; - algo.direction[ti][0] = stepy; - algo.direction[ti][1] = stepx; - } - } - } - } - - // edge collision detection - if (yx[0] <= 0 && step[0] < 0) { step[0] *= -1; } // top edge and moving up - else if (yx[0] >= height - 1 && step[0] > 0) { step[0] *= -1; } // bottom edge and moving down - - if (yx[1] <= 0 && step[1] < 0) { step[1] *= -1; } // left edge and moving left - else if (yx[1] >= width - 1 && step[1] > 0) { step[1] *= -1; } // right edge and moving right - - yx[0] += step[0]; // set ball's next location - yx[1] += step[1]; - - algo.ball[i] = yx; // update location - algo.direction[i] = step; // and direction / speed - } - return map; - }; - - algo.rgbMapStepCount = function (width, height) { - // This make no difference to the script ;-) - return 2; - }; - - // Development tool access - testAlgo = algo; - - return algo; - } -)(); diff --git a/resources/rgbscripts/devtool.html b/resources/rgbscripts/devtool.html index b7a7859f95..3fac197f39 100644 --- a/resources/rgbscripts/devtool.html +++ b/resources/rgbscripts/devtool.html @@ -127,17 +127,7 @@

Grid Size

Pixel colors

- - - - - - - - - - - +
Primary color (rrggbb)
Secondary color (rrggbb, leave empty to disable)
@@ -199,7 +189,7 @@

Preview


-This file is licensed under the Apache 2.0 license. Copyright © Heikki Junnila, Massimo Callegari, APIv2 integration: Hans-Jürgen Tappe. +This file is licensed under the Apache 2.0 license. Copyright © Heikki Junnila, Massimo Callegari, APIv2 & APIv3 integration: Hans-Jürgen Tappe. diff --git a/resources/rgbscripts/devtool/devtool.js b/resources/rgbscripts/devtool/devtool.js index 894790d507..f71515cd70 100644 --- a/resources/rgbscripts/devtool/devtool.js +++ b/resources/rgbscripts/devtool/devtool.js @@ -179,13 +179,59 @@ devtool.initProperties = function() properties.forEach(devtool.addPropertyTableEntry); } +devtool.getAcceptColors = function() +{ + var acceptColors = 2 // Default + if (typeof testAlgo.acceptColors !== "undefined") { + acceptColors = parseInt(testAlgo.acceptColors, 10); + } + + return acceptColors; +} + devtool.initPixelColors = function() { - var pixelColorChooser = document.getElementById("pixelColorChooser"); - pixelColorChooser.hidden = testAlgo.acceptColors === 0; + var acceptColors = devtool.getAcceptColors(); - var secondaryColorChooser = document.getElementById("secondaryColorChooser"); - secondaryColorChooser.hidden = testAlgo.acceptColors === 1; + var colorTable = document.getElementById("colorChooserTable"); + if (colorTable === null) + return; + while (colorTable.rows.length > acceptColors) + colorTable.deleteRow(-1); + while (colorTable.rows.length < acceptColors) { + var colorId = colorTable.rows.length + 1; + var row = colorTable.insertRow(); + row.id = "color" + colorId + "Chooser"; + var titleCell = row.insertCell(); + if (colorId === 1) + titleCell.textContent = "Color " + colorId + " (rrggbb)"; + else + titleCell.textContent = "Color " + colorId + " (rrggbb, leave empty to disable)"; + var colorInput = document.createElement("input"); + colorInput.setAttribute("type", "text"); + colorInput.setAttribute("id", "color" + colorId + "Text"); + if (colorId === 1) + colorInput.value = "FF0000"; + else + colorInput.value = ""; + colorInput.setAttribute("pattern", "[0-9A-Fa-f]{6}"); + colorInput.setAttribute("size", "6"); + colorInput.setAttribute("onInput", "devtool.onColorTextChange()"); + colorInput.required = true; + var colorCell = row.insertCell(); + colorCell.appendChild(colorInput); + var colorPicker = document.createElement("input"); + colorPicker.setAttribute("type", "color"); + colorPicker.setAttribute("id", "color" + colorId + "Picker"); + if (colorId === 1) + colorPicker.value = "#FF0000"; + else + colorPicker.value = "#000000"; + colorPicker.setAttribute("onInput", "devtool.onColorPickerChange(" + colorId + ")"); + colorPicker.required = true; + var pickerCell = row.insertCell(); + pickerCell.appendChild(colorPicker); + } } devtool.initSpeedValue = function() @@ -210,21 +256,24 @@ devtool.initAlternateValue = function() devtool.initColorValues = function() { - var primary = localStorage.getItem("devtool.primaryColor"); - if (primary === null || Number.isNaN(parseInt("0x" + primary, 16))) { - primary = "ff0000"; - } - primary = primary.padStart(6,"0"); - document.getElementById("primaryColorText").value = primary; - document.getElementById("primaryColorPicker").value = "#" + primary; - var secondary = localStorage.getItem("devtool.secondaryColor"); - if (secondary === null || secondary === "" || Number.isNaN(parseInt("0x" + secondary, 16))) { - document.getElementById("secondaryColorText").value = ""; - document.getElementById("secondaryColorPicker").value = "#000000"; - } else { - secondary = secondary.padStart(6,"0"); - document.getElementById("secondaryColorText").value = secondary; - document.getElementById("secondaryColorPicker").value = "#" + secondary; + var rawColors = []; + var acceptColors = devtool.getAcceptColors(); + for (var i = 0; i < acceptColors; i++) { + var idx = i + 1; + var color = localStorage.getItem("devtool.color" + idx); + if (color === null || Number.isNaN(parseInt("0x" + color, 16))) { + if (idx === 1) + color = "ff0000"; + else + color = "000000"; + } + color = color.padStart(6,"0"); + rawColors.push(parseInt("0x" + color, 16)); + document.getElementById("color" + idx + "Text").value = color; + document.getElementById("color" + idx + "Picker").value = "#" + color; + } + if (testAlgo.apiVersion >= 3) { + testAlgo.rgbMapSetColors(rawColors); } } @@ -255,18 +304,25 @@ devtool.getRgbFromColorInt = function(color) return [red, green, blue]; } +devtool.getColorInt = function(index) +{ + var colorInput = document.getElementById("color" + index + "Text"); + if (colorInput === null) + return 0; + return parseInt("0x" + colorInput.value, 16); +} + devtool.getCurrentColorInt = function() { - var primaryColorInput = document.getElementById("primaryColorText"); - var primaryColor = parseInt(primaryColorInput.value, 16); - var secondaryColorInput = document.getElementById("secondaryColorText"); - var secondaryColor = parseInt(secondaryColorInput.value, 16); + var primaryColor = devtool.getColorInt(1); + var secondaryColor = devtool.getColorInt(2); + var acceptColors = devtool.getAcceptColors(); - if (testAlgo.acceptColors === 0 || Number.isNaN(primaryColor)) { + if (acceptColors === 0 || Number.isNaN(primaryColor)) { return null; } - if (testAlgo.acceptColors === 1 || Number.isNaN(secondaryColor) || devtool.stepCount() <= 1) { + if (acceptColors === 1 || Number.isNaN(secondaryColor) || devtool.stepCount() <= 1) { return primaryColor; } @@ -285,12 +341,14 @@ devtool.getCurrentColorInt = function() devtool.writeCurrentStep = function() { - devtool.currentStep = parseInt(document.getElementById("currentStep").value); // currentStep may have been changed manually + // currentStep may have been changed manually + devtool.currentStep = parseInt(document.getElementById("currentStep").value, 10); var map = document.getElementById("map"); for (var i = map.rows.length - 1; i >= 0; i--) { map.deleteRow(i); } + var rgb = testAlgo.rgbMap(devtool.gridwidth, devtool.gridheight, devtool.getCurrentColorInt(), devtool.currentStep); for (var y = 0; y < devtool.gridheight; y++) @@ -300,11 +358,7 @@ devtool.writeCurrentStep = function() for (var x = 0; x < devtool.gridwidth; x++) { var cell = row.insertCell(x); - var rgbStr = rgb[y][x].toString(16); - while (rgbStr.length !== 6) { - rgbStr = "0" + rgbStr; - } - rgbStr = "#" + rgbStr; + var rgbStr = "#" + rgb[y][x].toString(16).padStart(6,"0"); cell.style.backgroundColor = rgbStr; cell.style.height = devtool.gridsize + "px"; cell.style.width = devtool.gridsize + "px"; @@ -335,13 +389,13 @@ devtool.updateStepCount = function() devtool.onGridSizeUpdated = function() { - devtool.gridwidth = parseInt(document.getElementById("gridwidth").value); + devtool.gridwidth = parseInt(document.getElementById("gridwidth").value, 10); localStorage.setItem("devtool.gridwidth", devtool.gridwidth); - devtool.gridheight = parseInt(document.getElementById("gridheight").value); + devtool.gridheight = parseInt(document.getElementById("gridheight").value, 10); localStorage.setItem("devtool.gridheight", devtool.gridheight); - devtool.gridsize = parseInt(document.getElementById("gridsize").value); + devtool.gridsize = parseInt(document.getElementById("gridsize").value, 10); localStorage.setItem("devtool.gridsize", devtool.gridsize); devtool.updateStepCount(); @@ -351,35 +405,40 @@ devtool.onGridSizeUpdated = function() devtool.onColorTextChange = function() { - var primary = parseInt("0x" + document.getElementById("primaryColorText").value).toString(16); - localStorage.setItem("devtool.primaryColor", primary); - var secondary = parseInt("0x" + document.getElementById("secondaryColorText").value).toString(16); - if(primary === "NaN"){ - document.getElementById("primaryColorPicker").value = "#000000"; - } else { - document.getElementById("primaryColorPicker").value = "#" + primary.padStart(6,"0");; + var rawColors = []; + var acceptColors = devtool.getAcceptColors(); + for (var i = 0; i < acceptColors; i++) { + var idx = i + 1; + var color = parseInt("0x" + document.getElementById("color" + idx + "Text").value, 16).toString(16); + if (color === "NaN" && + document.getElementById("color" + idx + "Picker").value != "#000000"){ + document.getElementById("color" + idx + "Picker").value = "#000000"; + } else { + var pickerValue = "#" + color.padStart(6,"0"); + if (document.getElementById("color" + idx + "Picker").value != pickerValue) { + document.getElementById("color" + idx + "Picker").value = pickerValue; + } + } + localStorage.setItem("devtool.color" + idx, color); + rawColors.push(devtool.getColorInt(idx)); } - if (secondary === "NaN") { // Evaluation of the string. - document.getElementById("secondaryColorPicker").value = "#000000"; - localStorage.setItem("devtool.secondaryColor", ""); - } else { - document.getElementById("secondaryColorPicker").value = "#" + secondary.padStart(6,"0");; - localStorage.setItem("devtool.secondaryColor", secondary); + if (testAlgo.apiVersion >= 3) { + testAlgo.rgbMapSetColors(rawColors); } - - devtool.writeCurrentStep(); -} -devtool.onPrimaryColorPickerChange = function() -{ - document.getElementById("primaryColorText").value = document.getElementById("primaryColorPicker").value.substring(1); - devtool.onColorTextChange(); + devtool.writeCurrentStep(); } -devtool.onSecondaryColorPickerChange = function() +devtool.onColorPickerChange = function(i) { - document.getElementById("secondaryColorText").value = document.getElementById("secondaryColorPicker").value.substring(1); - devtool.onColorTextChange(); + var textId = "color" + i + "Text"; + var pickerId = "color" + i + "Picker"; + var oldTextValue = document.getElementById(textId).value; + var newTextValue = document.getElementById(pickerId).value.substring(1); + if (oldTextValue != newTextValue) { + document.getElementById(textId).value = newTextValue; + devtool.onColorTextChange(); + } } devtool.startTest = function(inc) @@ -403,8 +462,8 @@ devtool.stopTest = function() devtool.initTestStatus = function() { let timerStatus = localStorage.getItem("devtool.timerRunning"); - if (timerStatus === null || parseInt(timerStatus) !== 0) { - devtool.startTest(parseInt(timerStatus)); + if (timerStatus === null || parseInt(timerStatus, 10) !== 0) { + devtool.startTest(parseInt(timerStatus, 10)); } } @@ -415,11 +474,11 @@ devtool.init = function() } devtool.initDefinitions(); devtool.initGridSize(); - devtool.setStep(0); - devtool.initSpeedValue(); - devtool.initColorValues(); devtool.initProperties(); devtool.initPixelColors(); + devtool.initColorValues(); + devtool.setStep(0); + devtool.initSpeedValue(); devtool.onGridSizeUpdated(); devtool.writeCurrentStep(); devtool.initTestStatus(); @@ -467,6 +526,8 @@ devtool.writeFunction = function(functionName, propertyName, value) { window.testAlgo[functionName](value); localStorage.setItem(propertyName, value); + devtool.initPixelColors(); + devtool.initColorValues(); devtool.updateStepCount(); } diff --git a/resources/rgbscripts/empty.js b/resources/rgbscripts/empty.js index 25589b639e..4d7f8f0e57 100644 --- a/resources/rgbscripts/empty.js +++ b/resources/rgbscripts/empty.js @@ -24,18 +24,57 @@ var testAlgo; function() { var algo = new Object; - algo.apiVersion = 2; + algo.apiVersion = 3; algo.name = "Script name"; algo.author = "Your Name"; + algo.acceptColors = 2; algo.properties = new Array(); + var util = new Object; + util.colorArray = new Array(algo.acceptColors); + + /** + * Evaluates the rawColors parameter and returns the idx value + * + * @param idx The index of the color in the array + * @return The requested array color or zero in case of invalid input + */ + util.getRawColor = function (idx) { + var color = 0; + if (Array.isArray(util.colorArray) && util.colorArray.length > idx && util.colorArray[idx]) { + color = util.colorArray[idx]; + } + return color; + } + + /** + * Ingests the colors as received through the parameter + * + * @param rawColors The array of colors + */ + algo.rgbMapSetColors = function(rawColors) + { + if (! Array.isArray(rawColors)) + return; + for (var i = 0; i < algo.acceptColors; i++) { + if (i < rawColors.length) + { + util.colorArray[i] = rawColors[i]; + } else { + util.colorArray[i] = 0; + } + } + } + /** * The actual "algorithm" for this RGB script. Produces a map of * size($width, $height) each time it is called. * + * @param width The width of the matrix in pixels + * @param height The height of the matrix in pixels + * @param rgb Tells the color requested by user in the UI, interpolated between stepCount. * @param step The step number that is requested (0 to (algo.rgbMapStepCount - 1)) - * @param rgb Tells the color requested by user in the UI. - * @return A two-dimensional array[height][width]. + * @return A two-dimensional matrix array[height][width]. */ algo.rgbMap = function(width, height, rgb, step) { @@ -44,7 +83,7 @@ var testAlgo; { map[y] = new Array(); for (var x = 0; x < width; x++) { - map[y][x] = 0; // <-- elapsed color goes here + map[y][x] = rgb; // <-- step color goes here } } diff --git a/resources/rgbscripts/marquee.js b/resources/rgbscripts/marquee.js index 3cab6d038a..0b7d5068b2 100644 --- a/resources/rgbscripts/marquee.js +++ b/resources/rgbscripts/marquee.js @@ -21,59 +21,11 @@ var testAlgo; (function () { - var colorPalette = new Object(); - colorPalette.collection = new Array( - ["White" , 0xFFFFFF], - ["LightGrey" , 0xAAAAAA], - ["MediumGrey" , 0x999999], - ["DarkGrey" , 0x666666], - ["Cream" , 0xFFFF7F], - ["Pink" , 0xFF7F7F], - ["Rose" , 0x7F3F3F], - ["Coral" , 0x7F3F1F], - ["Dim Red" , 0x7F0000], - ["Red" , 0xFF0000], - ["Orange" , 0xFF3F00], - ["Dim Orange" , 0x7F1F00], - ["Goldenrod" , 0x7F3F00], - ["Gold" , 0xFF7F00], - ["Yellow" , 0xFFFF00], - ["Dim Yellow" , 0x7F7F00], - ["Lime" , 0x7FFF00], - ["Pale Green" , 0x3F7F00], - ["Dim Green" , 0x007F00], - ["Green" , 0x00FF00], - ["Seafoam" , 0x00FF3F], - ["Turquoise" , 0x007F3F], - ["Teal" , 0x007F7F], - ["Cyan" , 0x00FFFF], - ["Electric Blue", 0x007FFF], - ["Blue" , 0x0000FF], - ["Dim Blue" , 0x00007F], - ["Pale Blue" , 0x1F1F7F], - ["Indigo" , 0x1F00BF], - ["Purple" , 0x3F00BF], - ["Violet" , 0x7F007F], - ["Magenta" , 0xFF00FF], - ["Hot Pink" , 0xFF003F], - ["Deep Pink" , 0x7F001F], - ["Black" , 0x000000] - ); - - colorPalette.makeSubArray = function (_index) { - var _array = new Array(); - for (var i = 0; i < colorPalette.collection.length; i++) { - _array.push(colorPalette.collection[i][_index]); - } - return _array; - }; - colorPalette.names = colorPalette.makeSubArray(0); - var algo = new Object(); - algo.apiVersion = 2; + algo.apiVersion = 3; algo.name = "Marquee"; algo.author = "Branson Matheson"; - algo.acceptColors = 1; + algo.acceptColors = 2; algo.properties = new Array(); algo.edgeDepth = 2; algo.properties.push( @@ -87,14 +39,6 @@ var testAlgo; algo.properties.push( "name:marqueeCount|type:range|display:Marquee Spaces|values:1,100|write:setMarqueeCount|read:getMarqueeCount" ); - algo.marqueeColorIndex = 0; - algo.properties.push( - "name:marqueColor|type:list|display:Marquee Light Color|" + - "values:" + - colorPalette.names.toString() + - "|" + - "write:setMarqueeColorIndex|read:getMarqueeColorIndex" - ); var util = new Object(); util.initialized = false; @@ -102,6 +46,7 @@ var testAlgo; util.height = 0; util.featureColor = 0; util.step = algo.marqueeCount; + util.colorArray = new Array(algo.acceptColors); util.lights = new Array(); util.feature = new Array(); @@ -149,18 +94,32 @@ var testAlgo; return algo.marqueeCount; }; - algo.setMarqueeColorIndex = function (_preset) { - algo.marqueeColorIndex = colorPalette.names.indexOf(_preset); - util.initialized = false; - }; + util.getRawColor = function (idx) { + var color = 0; + if (Array.isArray(util.colorArray) && util.colorArray.length > idx && util.colorArray[idx]) { + color = util.colorArray[idx]; + } + return color; + } + + algo.rgbMapSetColors = function(rawColors) + { + if (! Array.isArray(rawColors)) + return; + for (var i = 0; i < algo.acceptColors; i++) { + if (i < rawColors.length) + { + util.colorArray[i] = rawColors[i]; + } else { + util.colorArray[i] = 0; + } + } + } - algo.getMarqueeColorIndex = function () { - return colorPalette.collection[algo.marqueeColorIndex][0]; - }; - util.initialize = function (width, height, rgb) { + util.initialize = function (width, height) { // initialize feature - util.featureColor = rgb; + util.featureColor = util.getRawColor(0); util.feature = new Array(); var maxDistance = Math.min(width, height) / 2; for (var y = 0; y < height; y++) { @@ -184,6 +143,8 @@ var testAlgo; if (distance <= algo.edgeDepth && distance <= maxDistance) { var percent = ((algo.edgeDepth - distance) / algo.edgeDepth) * 100; util.feature[y][x] = util.fadeColor(util.featureColor, percent); + } else { + util.feature[y][x] = 0; } } } @@ -221,10 +182,12 @@ var testAlgo; }; util.getNextStep = function (width, height) { + var x = 0; + var y = 0; var map = new Array(height); - for (var y = 0; y <= height - 1; y++) { + for (y = 0; y <= height - 1; y++) { map[y] = new Array(width); - for (var x = 0; x <= width - 1; x++) { + for (x = 0; x <= width - 1; x++) { map[y][x] = util.feature[y][x]; } } @@ -240,35 +203,35 @@ var testAlgo; } // create light map add lights, go around the outside - var marqueeColor = colorPalette.collection[algo.marqueeColorIndex][1]; + var marqueeColor = util.getRawColor(1); var p = 0; // left - for (var y = 0; y < height; y++) { - var x = 0; + for (y = 0; y < height; y++) { + x = 0; if (util.lights[p] === 1) { map[y][x] = marqueeColor; } p += 1; } // bottom - for (var x = 1; x < width; x++) { - var y = height - 1; + for (x = 1; x < width; x++) { + y = height - 1; if (util.lights[p] === 1) { map[y][x] = marqueeColor; } p += 1; } // right - for (var y = height - 2; y >= 0; y--) { - var x = width - 1; + for (y = height - 2; y >= 0; y--) { + x = width - 1; if (util.lights[p] === 1) { map[y][x] = marqueeColor; } p += 1; } // top - for (var x = width - 2; x >= 0; x--) { - var y = 0; + for (x = width - 2; x >= 0; x--) { + y = 0; if (util.lights[p] === 1) { map[y][x] = marqueeColor; } @@ -277,14 +240,14 @@ var testAlgo; return map; }; - algo.rgbMap = function (width, height, rgb, step) { + algo.rgbMap = function(width, height, rgb, step) { if ( util.initialized === false || - util.featureColor != rgb || + util.featureColor != util.getRawColor(0) || util.width !== width || util.height !== height ) { - util.initialize(width, height, rgb); + util.initialize(width, height); } var map = util.getNextStep(width, height); diff --git a/resources/rgbscripts/plasma.js b/resources/rgbscripts/plasma.js index 6caf7f7f8e..7ef8cbccdf 100644 --- a/resources/rgbscripts/plasma.js +++ b/resources/rgbscripts/plasma.js @@ -24,40 +24,68 @@ var testAlgo; function() { var algo = new Object; - algo.apiVersion = 2; + algo.apiVersion = 3; algo.name = "Plasma"; - algo.author = "Tim Cullingworth"; + algo.author = "Tim Cullingworth, Massimo Callegari"; algo.acceptColors = 0; algo.properties = new Array(); algo.rstepcount = 0; algo.gstepcount = 50; algo.bstepcount = 100; algo.presetIndex = 0; - algo.properties.push("name:presetIndex|type:list|display:Preset|values:Rainbow,Fire,Abstract,Ocean|write:setPreset|read:getPreset"); + algo.properties.push( + "name:presetIndex|type:list|display:Preset|" + + "values:Rainbow,Fire,Abstract,Ocean,User Defined|" + + "write:setPreset|read:getPreset"); algo.presetSize = 5; - algo.properties.push("name:presetSize|type:range|display:Size|values:1,20|write:setSize|read:getSize"); + algo.properties.push( + "name:presetSize|type:range|display:Size|" + + "values:1,20|write:setSize|read:getSize"); algo.ramp = 20; - algo.properties.push("name:ramp|type:range|display:Ramp|values:10,30|write:setRamp|read:getRamp"); + algo.properties.push( + "name:ramp|type:range|display:Ramp|" + + "values:10,30|write:setRamp|read:getRamp"); algo.stepsize = 25; - algo.properties.push("name:stepsize|type:range|display:Speed|values:1,50|write:setStep|read:getStep"); + algo.properties.push( + "name:stepsize|type:range|display:Speed|" + + "values:1,50|write:setStep|read:getStep"); var util = new Object; util.initialized = false; util.gradientData = new Array(); - util.presets = new Array(); - util.presets.push(new Array(0xFF0000, 0x00FF00, 0x0000FF)); - util.presets.push(new Array(0xFFFF00, 0xFF0000, 0x000040, 0xFF0000)); - util.presets.push(new Array(0x5571FF, 0x00FFFF, 0xFF00FF, 0xFFFF00)); - util.presets.push(new Array(0x003AB9, 0x02EAFF)); + util.colorArray = new Array(); algo.setPreset = function(_preset) { - if (_preset === "Rainbow") { algo.presetIndex = 0; } - else if (_preset === "Fire") { algo.presetIndex = 1; } - else if (_preset === "Abstract") { algo.presetIndex = 2; } - else if (_preset === "Ocean") { algo.presetIndex = 3; } + algo.acceptColors = 0; + if (_preset === "Rainbow") + { + algo.presetIndex = 0; + util.colorArray = [ 0xFF0000, 0x00FF00, 0x0000FF ]; + } + else if (_preset === "Fire") + { + algo.presetIndex = 1; + util.colorArray = [ 0xFFFF00, 0xFF0000, 0x000040, 0xFF0000 ]; + } + else if (_preset === "Abstract") + { + algo.presetIndex = 2; + util.colorArray = [ 0x5571FF, 0x00FFFF, 0xFF00FF, 0xFFFF00 ]; + } + else if (_preset === "Ocean") + { + algo.presetIndex = 3; + util.colorArray = [ 0x003AB9, 0x02EAFF ]; + } + else if (_preset === "User Defined") + { + algo.presetIndex = 4; + algo.acceptColors = 5; + util.colorArray = [ 0x00FF00, 0xFFAA00, 0x0000FF, 0xFFFF00, 0xFFFFFF ]; + } else { algo.presetIndex = 0; } - util.initialize(); + util.initialized = false; }; algo.getPreset = function() @@ -66,13 +94,14 @@ var testAlgo; else if (algo.presetIndex === 1) { return "Fire"; } else if (algo.presetIndex === 2) { return "Abstract"; } else if (algo.presetIndex === 3) { return "Ocean"; } + else if (algo.presetIndex === 4) { return "User Defined"; } else { return "Rainbow"; } }; algo.setSize = function(_size) { algo.presetSize = _size; - util.initialize(); + util.initialized = false; }; algo.getSize = function() @@ -83,7 +112,7 @@ var testAlgo; algo.setRamp = function(_ramp) { algo.ramp = _ramp; - util.initialize(); + util.initialized = false; }; algo.getRamp = function() @@ -94,7 +123,7 @@ var testAlgo; algo.setStep = function(_step) { algo.stepsize = _step; - util.initialize(); + util.initialized = false; }; algo.getStep = function() @@ -108,13 +137,15 @@ var testAlgo; // with the given width var gradIdx = 0; util.gradientData = new Array(); - for (var i = 0; i < util.presets[algo.presetIndex].length; i++) + for (var i = 0; i < util.colorArray.length; i++) { - var sColor = util.presets[algo.presetIndex][i]; - var eColor = util.presets[algo.presetIndex][i + 1]; - if (eColor == undefined) { - eColor = util.presets[algo.presetIndex][0]; - } + var sColor = util.colorArray[i]; + var eColor = util.colorArray[(i + 1) % util.colorArray.length]; + if (! sColor) + sColor = 0; + if (! eColor) + eColor = 0; + util.gradientData[gradIdx++] = sColor; var sr = (sColor >> 16) & 0x00FF; var sg = (sColor >> 8) & 0x00FF; @@ -145,42 +176,115 @@ var testAlgo; util.noise = function(x, y, z) { var p = new Array(512); - var permutation = [ 151,160,137,91,90,15,131,13,201,95,96,53,194,233, 7,225,140,36,103,30,69,142,8,99,37,240,21,10,23,190, 6,148,247,120,234,75, 0,26,197,62,94,252,219,203,117,35,11,32,57,177,33,88,237,149,56,87,174,20, 125,136,171,168,68,175,74,165,71,134,139,48,27,166,77,146,158,231,83,111,229, 122,60,211,133,230,220,105,92,41,55,46,245,40,244,102,143,54, 65,25,63,161,1, 216,80,73,209,76,132,187,208,89,18,169,200,196,135,130,116,188,159,86,164,100, 109,198,173,186,3,64,52,217,226,250,124,123,5,202,38,147,118,126,255,82,85,212, 207,206,59,227,47,16,58,17,182,189,28,42,223,183,170,213,119,248,152, 2,44,154, 163,70,221,153,101,155,167,43,172,9,129,22,39,253,19,98,108,110,79,113,224,232, 178,185,112,104,218,246,97,228,251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107,49,192,214, 31,181,199,106,157,184, 84,204,176,115, 121,50,45,127,4,150,254,138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180]; + var permutation = [ // 256 members + 151, 160, 137, 91, 90, 15, 131, 13, 201, 95, 96, 53, 194, 233, 7, 225, + 140, 36, 103, 30, 69, 142, 8, 99, 37, 240, 21, 10, 23, 190, 6, 148, 247, + 120, 234, 75, 0, 26, 197, 62, 94, 252, 219, 203, 117, 35, 11, 32, 57, + 177, 33, 88, 237, 149, 56, 87, 174, 20, 125, 136, 171, 168, 68, 175, 74, + 165, 71, 134, 139, 48, 27, 166, 77, 146, 158, 231, 83, 111, 229, 122, + 60, 211, 133, 230, 220, 105, 92, 41, 55, 46, 245, 40, 244, 102, 143, 54, + 65, 25, 63, 161, 1, 216, 80, 73, 209, 76, 132, 187, 208, 89, 18, 169, + 200, 196, 135, 130, 116, 188, 159, 86, 164, 100, 109, 198, 173, 186, 3, + 64, 52, 217, 226, 250, 124, 123, 5, 202, 38, 147, 118, 126, 255, 82, 85, + 212, 207, 206, 59, 227, 47, 16, 58, 17, 182, 189, 28, 42, 223, 183, 170, + 213, 119, 248, 152, 2, 44, 154, 163, 70, 221, 153, 101, 155, 167, 43, + 172, 9, 129, 22, 39, 253, 19, 98, 108, 110, 79, 113, 224, 232, 178, 185, + 112, 104, 218, 246, 97, 228, 251, 34, 242, 193, 238, 210, 144, 12, 191, + 179, 162, 241, 81, 51, 145, 235, 249, 14, 239, 107, 49, 192, 214, 31, + 181, 199, 106, 157, 184, 84, 204, 176, 115, 121, 50, 45, 127, 4, 150, + 254, 138, 236, 205, 93, 222, 114, 67, 29, 24, 72, 243, 141, 128, 195, + 78, 66, 215, 61, 156, 180 + ]; - for (var i=0; i < 256 ; i++) { - p[256+i] = p[i] = permutation[i]; + // initialize symmetrical permutation array(512) + for (var i = 0; i < 256; i++) { + p[i] = permutation[i]; + p[256 + i] = permutation[i]; } - var X = Math.floor(x) & 255, // FIND UNIT CUBE THAT - Y = Math.floor(y) & 255, // CONTAINS POINT. - Z = Math.floor(z) & 255; - x -= Math.floor(x); // FIND RELATIVE X,Y,Z - y -= Math.floor(y); // OF POINT IN CUBE. - z -= Math.floor(z); - var u = fade(x), // COMPUTE FADE CURVES - v = fade(y), // FOR EACH OF X,Y,Z. - w = fade(z); - var A = p[X ]+Y, AA = p[A]+Z, AB = p[A+1]+Z, // HASH COORDINATES OF - B = p[X+1]+Y, BA = p[B]+Z, BB = p[B+1]+Z; // THE 8 CUBE CORNERS, - - return scale(lerp(w, lerp(v, lerp(u, grad(p[AA ], x , y , z ), // AND ADD - grad(p[BA ], x-1, y , z )), // BLENDED - lerp(u, grad(p[AB ], x , y-1, z ), // RESULTS - grad(p[BB ], x-1, y-1, z ))), // FROM 8 - lerp(v, lerp(u, grad(p[AA+1], x , y , z-1 ), // CORNERS - grad(p[BA+1], x-1, y , z-1 )), // OF CUBE - lerp(u, grad(p[AB+1], x , y-1, z-1 ), - grad(p[BB+1], x-1, y-1, z-1 ))))); + // Find unit cube that contains point. + var X = Math.floor(x) & 255; + var Y = Math.floor(y) & 255; + var Z = Math.floor(z) & 255; + // Find relative x,y,z of point in cube. + x -= Math.floor(x); + y -= Math.floor(y); + z -= Math.floor(z); + // Compute fade curves for each of y, y, z + var u = fade(x); + var v = fade(y); + var w = fade(z); + // Hash coordinates of the 8 cube corners, + var A = p[X] + Y; + var AA = p[A] + Z; + var AB = p[A + 1] + Z; + var B = p[X + 1] + Y; + var BA = p[B] + Z; + var BB = p[B + 1] + Z; + + // And add blended results from8 corners of cube + var rawNoise = lerp(w, + lerp(v, lerp(u, grad(p[AA ], x , y , z ), + grad(p[BA ], x-1, y , z )), + lerp(u, grad(p[AB ], x , y - 1, z ), + grad(p[BB ], x-1, y - 1, z ))), + lerp(v, lerp(u, grad(p[AA + 1], x , y , z - 1), + grad(p[BA + 1], x-1, y , z - 1)), + lerp(u, grad(p[AB + 1], x , y - 1, z - 1), + grad(p[BB + 1], x-1, y - 1, z - 1))) + ); + // Scale to range between 0 and 1 + var noise = scale(rawNoise); + return noise; }; - function fade(t) { return t * t * t * (t * (t * 6 - 15) + 10); } - function lerp( t, a, b) { return a + t * (b - a); } + // Fade function for values between 0 and 1 + function fade(t) + { + // https://www.geogebra.org/calculator + // f(t)=t^(3) (t (t*6-15)+10) + var fade = t * t * t * (t * (t * 6 - 15) + 10); + return fade; + } + // https://en.wikipedia.org/wiki/Linear_interpolation + function lerp(t, a, b) + { + return a + t * (b - a); + } + + // https://en.wikipedia.org/wiki/Gradient function grad(hash, x, y, z) { - var h = hash & 15; // CONVERT LO 4 BITS OF HASH CODE - var u = h<8 ? x : y, // INTO 12 GRADIENT DIRECTIONS. - v = h<4 ? y : h===12||h===14 ? x : z; - return ((h&1) === 0 ? u : -u) + ((h&2) === 0 ? v : -v); + // CONVERT TO 4 BITS OF HASH CODE + var h = hash & 0x0000000f; + // INTO 12 GRADIENT DIRECTIONS. + var u = (h < 8) ? x : y; + var v = (h < 4) ? y : (h === 12 || h === 14) ? x : z; + return (((h & 1) === 0) ? u : -1 * u) + (((h & 2) === 0) ? v : -1 * v); + } + function scale(n) + { + var scaled = (1 + n) / 2; + return scaled; + } + + algo.rgbMapSetColors = function(rawColors) + { + if (! Array.isArray(rawColors)) + return; + for (var i = 0; i < algo.acceptColors; i++) { + if (i < rawColors.length) + { + util.colorArray[i] = rawColors[i]; + } else { + util.colorArray[i] = 0; + } + } + util.initialized = false; + } + + algo.rgbMapGetColors = function() + { + return util.colorArray; } - function scale(n) { return (1 + n)/2; } algo.rgbMap = function(width, height, rgb, step) { @@ -189,11 +293,15 @@ var testAlgo; util.initialize(); } - var size = algo.presetSize/2; // set a scaling value - var speed = Math.pow(100 , (algo.stepsize / 50)); // create a more uniform speed control + // set a scaling value + var size = algo.presetSize / 2; + // create a more uniform speed control + var speed = Math.pow(100, (algo.stepsize / 50)); algo.bstepcount += (speed / 500); - algo.bstepcount = (algo.bstepcount % 256); // A rolling step count for the noise function - var square = width>height ? width : height; // keep the patten square + // A rolling step count for the noise function + algo.bstepcount = (algo.bstepcount % 256); + // keep the patten square + var square = (width > height) ? width : height; var map = new Array(height); for (var y = 0; y < height; y++) @@ -202,10 +310,10 @@ var testAlgo; for (var x = 0; x < width; x++) { - var nx = x / square; // Normalise nx & ny to 0 - 1 + var nx = x / square; // Normalize nx & ny to 0 - 1 var ny = y / square; - var n = util.noise( size*nx, size*ny, algo.bstepcount ); - var gradStep = Math.round( Math.pow(n , (algo.ramp/10)) * util.gradientData.length); + var n = util.noise(size * nx, size * ny, algo.bstepcount); + var gradStep = Math.round(Math.pow(n, (algo.ramp / 10)) * util.gradientData.length); map[y][x] = util.gradientData[gradStep]; } } @@ -215,10 +323,7 @@ var testAlgo; algo.rgbMapStepCount = function(width, height) { - if (util.initialized === false) { - util.initialize(); - } - return width * height; // This make no diferance to the script ;-) + return 2; // This make no difference to the script ;-) }; // Development tool access diff --git a/resources/rgbscripts/plasmacolors.js b/resources/rgbscripts/plasmacolors.js deleted file mode 100644 index 168d7d4c5e..0000000000 --- a/resources/rgbscripts/plasmacolors.js +++ /dev/null @@ -1,357 +0,0 @@ -/* - Q Light Controller Plus - plasmacolors.js - - Copyright (c) Nathan Durnan - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0.txt - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. -*/ - -// Development tool access -var testAlgo; - -( -function() -{ - var colorPalette = new Object; - colorPalette.collection = new Array( - ["White" , 0xFFFFFF], // 0 - ["Cream" , 0xFFFF7F], // 1 - ["Pink" , 0xFF7F7F], // 2 - ["Rose" , 0x7F3F3F], // 3 - ["Coral" , 0x7F3F1F], // 4 - ["Dim Red" , 0x7F0000], // 5 - ["Red" , 0xFF0000], // 6 - ["Orange" , 0xFF3F00], // 7 - ["Dim Orange" , 0x7F1F00], // 8 - ["Goldenrod" , 0x7F3F00], // 9 - ["Gold" , 0xFF7F00], // 10 - ["Yellow" , 0xFFFF00], // 11 - ["Dim Yellow" , 0x7F7F00], // 12 - ["Lime" , 0x7FFF00], // 13 - ["Pale Green" , 0x3F7F00], // 14 - ["Dim Green" , 0x007F00], // 15 - ["Green" , 0x00FF00], // 16 - ["Seafoam" , 0x00FF3F], // 17 - ["Turquoise" , 0x007F3F], // 18 - ["Teal" , 0x007F7F], // 19 - ["Cyan" , 0x00FFFF], // 20 - ["Electric Blue", 0x007FFF], // 21 - ["Blue" , 0x0000FF], // 22 - ["Dim Blue" , 0x00007F], // 23 - ["Pale Blue" , 0x1F1F7F], // 24 - ["Indigo" , 0x1F00BF], // 25 - ["Purple" , 0x3F00BF], // 26 - ["Violet" , 0x7F007F], // 27 - ["Magenta" , 0xFF00FF], // 28 - ["Hot Pink" , 0xFF003F], // 29 - ["Deep Pink" , 0x7F001F], // 30 - ["OFF" , 0x000000]); // 31 - - colorPalette.makeSubArray = function(_index) - { - var _array = new Array(); - for (var i = 0; i < colorPalette.collection.length; i++) - { - _array.push(colorPalette.collection[i][_index]); - } - return _array; - }; - colorPalette.names = colorPalette.makeSubArray(0); - - var algo = new Object; - algo.apiVersion = 2; - algo.name = "Plasma (Colors)"; - algo.author = "Nathan Durnan"; - algo.acceptColors = 0; - algo.properties = new Array(); - algo.rstepcount = 0; - algo.gstepcount = 50; - algo.bstepcount = 100; - algo.color1Index = 0; - algo.properties.push( - "name:color1Index|type:list|display:Color 1|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor1|read:getColor1"); - algo.color2Index = 6; - algo.properties.push( - "name:color2Index|type:list|display:Color 2|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor2|read:getColor2"); - algo.color3Index = 16; - algo.properties.push( - "name:color3Index|type:list|display:Color 3|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor3|read:getColor3"); - algo.color4Index = 22; - algo.properties.push( - "name:color4Index|type:list|display:Color 4|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor4|read:getColor4"); - algo.color5Index = 31; - algo.properties.push( - "name:color5Index|type:list|display:Color 5|" + - "values:" + colorPalette.names.toString() + "|" + - "write:setColor5|read:getColor5"); - algo.presetSize = 5; - algo.properties.push( - "name:presetSize|type:range|display:Size|" + - "values:1,20|write:setSize|read:getSize"); - algo.ramp = 15; - algo.properties.push( - "name:ramp|type:range|display:Ramp|" + - "values:10,30|write:setRamp|read:getRamp"); - algo.stepsize = 25; - algo.properties.push( - "name:stepsize|type:range|display:Speed|" + - "values:1,50|write:setStep|read:getStep"); - algo.colorIndex = new Array( - algo.color1Index, - algo.color2Index, - algo.color3Index, - algo.color4Index, - algo.color5Index); - - var util = new Object; - util.initialized = false; - util.gradientData = new Array(); - util.colorArray = new Array(); - - algo.setColor = function(_index, _preset) - { - var i = colorPalette.names.indexOf(_preset); - if (i === -1) { - i = (colorPalette.collection.length - 1); - } - algo.colorIndex[_index] = i; - return algo.colorIndex[_index]; - }; - - algo.getColor = function(_index) - { - var i = algo.colorIndex[_index]; - if (i < 0) { i = 0; } - if (i >= colorPalette.collection.length) { - i = (colorPalette.collection.length - 1); - } - return colorPalette.collection[i][0]; - }; - - algo.setColor1 = function(_preset) - { - algo.color1Index = algo.setColor(0, _preset); - util.initialize(); - }; - algo.getColor1 = function() - { - return algo.getColor(0); - }; - - algo.setColor2 = function(_preset) - { - algo.color2Index = algo.setColor(1, _preset); - util.initialize(); - }; - algo.getColor2 = function() - { - return algo.getColor(1); - }; - - algo.setColor3 = function(_preset) - { - algo.color3Index = algo.setColor(2, _preset); - util.initialize(); - }; - algo.getColor3 = function() - { - return algo.getColor(2); - }; - - algo.setColor4 = function(_preset) - { - algo.color4Index = algo.setColor(3, _preset); - util.initialize(); - }; - algo.getColor4 = function() - { - return algo.getColor(3); - }; - - algo.setColor5 = function(_preset) - { - algo.color5Index = algo.setColor(4, _preset); - util.initialize(); - }; - algo.getColor5 = function() - { - return algo.getColor(4); - }; - - algo.setSize = function(_size) - { - algo.presetSize = _size; - util.initialize(); - }; - algo.getSize = function() - { - return algo.presetSize; - }; - - algo.setRamp = function(_ramp) - { - algo.ramp = _ramp; - util.initialize(); - }; - algo.getRamp = function() - { - return algo.ramp; - }; - - algo.setStep = function(_step) - { - algo.stepsize = _step; - util.initialize(); - }; - algo.getStep = function() - { - return algo.stepsize; - }; - - util.initialize = function() - { - // calculate the gradient for the selected preset - // with the given width - var gradIdx = 0; - util.gradientData = new Array(); - util.colorArray = new Array(); - for (var j = 0; j < algo.colorIndex.length; j++) - { - util.colorArray[j] = colorPalette.collection[algo.colorIndex[j]][1]; - } - for (var i = 0; i < util.colorArray.length; i++) - { - var sColor = util.colorArray[i]; - var eColor = util.colorArray[i + 1]; - if (eColor == undefined) { - eColor = util.colorArray[0]; - } - util.gradientData[gradIdx++] = sColor; - var sr = (sColor >> 16) & 0x00FF; - var sg = (sColor >> 8) & 0x00FF; - var sb = sColor & 0x00FF; - var er = (eColor >> 16) & 0x00FF; - var eg = (eColor >> 8) & 0x00FF; - var eb = eColor & 0x00FF; - - var stepR = ((er - sr) / 300); - var stepG = ((eg - sg) / 300); - var stepB = ((eb - sb) / 300); - - for (var s = 1; s < 300; s++) - { - var gradR = Math.floor(sr + (stepR * s)) & 0x00FF; - var gradG = Math.floor(sg + (stepG * s)) & 0x00FF; - var gradB = Math.floor(sb + (stepB * s)) & 0x00FF; - var gradRGB = (gradR << 16) + (gradG << 8) + gradB; - util.gradientData[gradIdx++] = gradRGB; - } - } - util.initialized = true; - }; - - function fade(t) { return t * t * t * (t * (t * 6 - 15) + 10); } - function lerp( t, a, b) { return a + t * (b - a); } - function grad(hash, x, y, z) { - var h = hash & 15; // CONVERT LO 4 BITS OF HASH CODE - var u = h<8 ? x : y, // INTO 12 GRADIENT DIRECTIONS. - v = h<4 ? y : h===12||h===14 ? x : z; - return ((h&1) === 0 ? u : -u) + ((h&2) === 0 ? v : -v); - } - function scale(n) { return (1 + n)/2; } - - // This is a port of Ken Perlin's Java code. The - // original Java code is at http://cs.nyu.edu/%7Eperlin/noise/. - // Note that in this version, a number from 0 to 1 is returned. - util.noise = function(x, y, z) - { - var p = new Array(512); - var permutation = [ 151,160,137,91,90,15,131,13,201,95,96,53,194,233, 7,225,140,36,103,30,69,142,8,99,37,240,21,10,23,190, 6,148,247,120,234,75, 0,26,197,62,94,252,219,203,117,35,11,32,57,177,33,88,237,149,56,87,174,20, 125,136,171,168,68,175,74,165,71,134,139,48,27,166,77,146,158,231,83,111,229, 122,60,211,133,230,220,105,92,41,55,46,245,40,244,102,143,54, 65,25,63,161,1, 216,80,73,209,76,132,187,208,89,18,169,200,196,135,130,116,188,159,86,164,100, 109,198,173,186,3,64,52,217,226,250,124,123,5,202,38,147,118,126,255,82,85,212, 207,206,59,227,47,16,58,17,182,189,28,42,223,183,170,213,119,248,152, 2,44,154, 163,70,221,153,101,155,167,43,172,9,129,22,39,253,19,98,108,110,79,113,224,232, 178,185,112,104,218,246,97,228,251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107,49,192,214, 31,181,199,106,157,184, 84,204,176,115, 121,50,45,127,4,150,254,138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180]; - - for (var i=0; i < 256 ; i++) { - p[256+i] = p[i] = permutation[i]; - } - var X = Math.floor(x) & 255, // FIND UNIT CUBE THAT - Y = Math.floor(y) & 255, // CONTAINS POINT. - Z = Math.floor(z) & 255; - x -= Math.floor(x); // FIND RELATIVE X,Y,Z - y -= Math.floor(y); // OF POINT IN CUBE. - z -= Math.floor(z); - var u = fade(x), // COMPUTE FADE CURVES - v = fade(y), // FOR EACH OF X,Y,Z. - w = fade(z); - var A = p[X ]+Y, AA = p[A]+Z, AB = p[A+1]+Z, // HASH COORDINATES OF - B = p[X+1]+Y, BA = p[B]+Z, BB = p[B+1]+Z; // THE 8 CUBE CORNERS, - - return scale(lerp(w, lerp(v, lerp(u, grad(p[AA ], x , y , z ), // AND ADD - grad(p[BA ], x-1, y , z )), // BLENDED - lerp(u, grad(p[AB ], x , y-1, z ), // RESULTS - grad(p[BB ], x-1, y-1, z ))), // FROM 8 - lerp(v, lerp(u, grad(p[AA+1], x , y , z-1 ), // CORNERS - grad(p[BA+1], x-1, y , z-1 )), // OF CUBE - lerp(u, grad(p[AB+1], x , y-1, z-1 ), - grad(p[BB+1], x-1, y-1, z-1 ))))); - }; - - algo.rgbMap = function(width, height, rgb, step) - { - if (util.initialized === false) { - util.initialize(); - } - var size = algo.presetSize/2; // set a scaling value - var speed = Math.pow(100 , (algo.stepsize / 50)); // create a more uniform speed control - algo.bstepcount += (speed / 500); - algo.bstepcount = (algo.bstepcount % 256); // A rolling step count for the noise function - var square = width>height ? width : height; // keep the patten square - - var map = new Array(height); - for (var y = 0; y < height; y++) - { - map[y] = new Array(); - - for (var x = 0; x < width; x++) - { - var nx = x / square; // Normalize nx & ny to 0 - 1 - var ny = y / square; - var n = util.noise( size*nx, size*ny, algo.bstepcount); - var gradStep = Math.round( Math.pow(n , (algo.ramp/10)) * util.gradientData.length); - map[y][x] = util.gradientData[gradStep]; - } - } - - return map; - }; - - algo.rgbMapStepCount = function(width, height) - { - if (util.initialized === false) { - util.initialize(); - } - return width * height; // This make no difference to the script ;-) - }; - - // Development tool access - testAlgo = algo; - - return algo; -} -)(); diff --git a/resources/rgbscripts/rgbscripts.pro b/resources/rgbscripts/rgbscripts.pro index 2b4b28dc3c..a50c513885 100644 --- a/resources/rgbscripts/rgbscripts.pro +++ b/resources/rgbscripts/rgbscripts.pro @@ -5,7 +5,6 @@ TARGET = scripts scripts.files += alternate.js scripts.files += balls.js -scripts.files += ballscolors.js scripts.files += blinder.js scripts.files += circles.js scripts.files += circular.js @@ -24,7 +23,6 @@ scripts.files += noise.js scripts.files += onebyone.js scripts.files += opposite.js scripts.files += plasma.js -scripts.files += plasmacolors.js scripts.files += randomcolumn.js scripts.files += randomfillcolumn.js scripts.files += randomfillrow.js diff --git a/ui/src/rgbmatrixeditor.cpp b/ui/src/rgbmatrixeditor.cpp index 13382c4385..a151eeed65 100644 --- a/ui/src/rgbmatrixeditor.cpp +++ b/ui/src/rgbmatrixeditor.cpp @@ -174,14 +174,32 @@ void RGBMatrixEditor::init() fillImageAnimationCombo(); QPixmap pm(50, 26); - pm.fill(m_matrix->startColor()); - m_startColorButton->setIcon(QIcon(pm)); + pm.fill(m_matrix->getColor(0)); + m_mtxColor1Button->setIcon(QIcon(pm)); - if (m_matrix->endColor().isValid()) - pm.fill(m_matrix->endColor()); + if (m_matrix->getColor(1).isValid()) + pm.fill(m_matrix->getColor(1)); else pm.fill(Qt::transparent); - m_endColorButton->setIcon(QIcon(pm)); + m_mtxColor2Button->setIcon(QIcon(pm)); + + if (m_matrix->getColor(2).isValid()) + pm.fill(m_matrix->getColor(2)); + else + pm.fill(Qt::transparent); + m_mtxColor3Button->setIcon(QIcon(pm)); + + if (m_matrix->getColor(3).isValid()) + pm.fill(m_matrix->getColor(3)); + else + pm.fill(Qt::transparent); + m_mtxColor4Button->setIcon(QIcon(pm)); + + if (m_matrix->getColor(4).isValid()) + pm.fill(m_matrix->getColor(4)); + else + pm.fill(Qt::transparent); + m_mtxColor5Button->setIcon(QIcon(pm)); updateExtraOptions(); updateSpeedDials(); @@ -202,12 +220,24 @@ void RGBMatrixEditor::init() this, SLOT(slotBlendModeChanged(int))); connect(m_controlModeCombo, SIGNAL(activated(int)), this, SLOT(slotControlModeChanged(int))); - connect(m_startColorButton, SIGNAL(clicked()), - this, SLOT(slotStartColorButtonClicked())); - connect(m_endColorButton, SIGNAL(clicked()), - this, SLOT(slotEndColorButtonClicked())); - connect(m_resetEndColorButton, SIGNAL(clicked()), - this, SLOT(slotResetEndColorButtonClicked())); + connect(m_mtxColor1Button, SIGNAL(clicked()), + this, SLOT(slotMtxColor1ButtonClicked())); + connect(m_mtxColor2Button, SIGNAL(clicked()), + this, SLOT(slotMtxColor2ButtonClicked())); + connect(m_resetMtxColor2Button, SIGNAL(clicked()), + this, SLOT(slotResetMtxColor2ButtonClicked())); + connect(m_mtxColor3Button, SIGNAL(clicked()), + this, SLOT(slotMtxColor3ButtonClicked())); + connect(m_resetMtxColor3Button, SIGNAL(clicked()), + this, SLOT(slotResetMtxColor3ButtonClicked())); + connect(m_mtxColor4Button, SIGNAL(clicked()), + this, SLOT(slotMtxColor4ButtonClicked())); + connect(m_resetMtxColor4Button, SIGNAL(clicked()), + this, SLOT(slotResetMtxColor4ButtonClicked())); + connect(m_mtxColor5Button, SIGNAL(clicked()), + this, SLOT(slotMtxColor5ButtonClicked())); + connect(m_resetMtxColor5Button, SIGNAL(clicked()), + this, SLOT(slotResetMtxColor5ButtonClicked())); connect(m_textEdit, SIGNAL(textEdited(const QString&)), this, SLOT(slotTextEdited(const QString&))); connect(m_fontButton, SIGNAL(clicked()), @@ -364,34 +394,27 @@ void RGBMatrixEditor::updateExtraOptions() m_yOffsetSpin->setValue(text->yOffset()); } + updateColorOptions(); +} + +void RGBMatrixEditor::updateColorOptions() +{ if (m_matrix->algorithm() != NULL) { int accColors = m_matrix->algorithm()->acceptColors(); - if (accColors == 0) - { - m_startColorButton->hide(); - m_endColorButton->hide(); - m_resetEndColorButton->hide(); - m_blendModeLabel->hide(); - m_blendModeCombo->hide(); - } - else - { - m_startColorButton->show(); - if (accColors == 1 || m_blendModeCombo->currentIndex() == Universe::MaskBlend) - { - m_endColorButton->hide(); - m_resetEndColorButton->hide(); - } - else // accColors > 1 - { - m_endColorButton->show(); - m_resetEndColorButton->show(); - } - m_blendModeLabel->show(); - m_blendModeCombo->show(); - } + m_mtxColor1Button->setVisible(accColors == 0 ? false : true); + m_mtxColor2Button->setVisible(accColors > 1 ? true : false); + m_resetMtxColor2Button->setVisible(accColors > 1 ? true : false); + m_mtxColor3Button->setVisible(accColors > 2 ? true : false); + m_resetMtxColor3Button->setVisible(accColors > 2 ? true : false); + m_mtxColor4Button->setVisible(accColors > 3 ? true : false); + m_resetMtxColor4Button->setVisible(accColors > 3 ? true : false); + m_mtxColor5Button->setVisible(accColors > 4 ? true : false); + m_resetMtxColor5Button->setVisible(accColors > 4 ? true : false); + + m_blendModeLabel->setVisible(accColors == 0 ? false : true); + m_blendModeCombo->setVisible(accColors == 0 ? false : true); } } @@ -404,56 +427,133 @@ void RGBMatrixEditor::updateColors() { if (m_matrix->blendMode() == Universe::MaskBlend) { - m_matrix->setStartColor(Qt::white); - m_matrix->setEndColor(QColor()); - - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_matrix->setColor(0, Qt::white); + // Overwrite more colors only if applied. + if (accColors <= 2) + m_matrix->setColor(1, QColor()); + if (accColors <= 3) + m_matrix->setColor(2, QColor()); + if (accColors <= 4) + m_matrix->setColor(3, QColor()); + if (accColors <= 5) + m_matrix->setColor(4, QColor()); + + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); QPixmap pm(50, 26); pm.fill(Qt::white); - m_startColorButton->setIcon(QIcon(pm)); + m_mtxColor1Button->setIcon(QIcon(pm)); + + pm.fill(Qt::transparent); + m_mtxColor2Button->setIcon(QIcon(pm)); + m_mtxColor3Button->setIcon(QIcon(pm)); + m_mtxColor4Button->setIcon(QIcon(pm)); + m_mtxColor5Button->setIcon(QIcon(pm)); } else if (m_controlModeCombo->currentIndex() != RGBMatrix::ControlModeRgb) { - // Convert startColor to grayscale for single color modes - uchar gray = qGray(m_matrix->startColor().rgb()); + // Convert color 1 to grayscale for single color modes + uchar gray = qGray(m_matrix->getColor(0).rgb()); + m_matrix->setColor(0, QColor(gray, gray, gray)); QPixmap pm(50, 26); pm.fill(QColor(gray, gray, gray)); - m_startColorButton->setIcon(QIcon(pm)); - m_matrix->setStartColor(QColor(gray, gray, gray)); + m_mtxColor1Button->setIcon(QIcon(pm)); + + // Convert color 2 and following to grayscale for single color modes + if (accColors < 2) + m_matrix->setColor(1, QColor()); + if (m_matrix->getColor(1) == QColor()) + { + pm.fill(Qt::transparent); + } + else + { + gray = qGray(m_matrix->getColor(1).rgb()); + m_matrix->setColor(1, QColor(gray, gray, gray)); + pm.fill(QColor(gray, gray, gray)); + } + m_mtxColor2Button->setIcon(QIcon(pm)); - if (accColors > 1) + if (accColors < 3) + m_matrix->setColor(2, QColor()); + if (m_matrix->getColor(2) == QColor()) + { + pm.fill(Qt::transparent); + } + else { - // Convert endColor to grayscale for single color modes - gray = qGray(m_matrix->endColor().rgb()); - m_matrix->setEndColor(QColor(gray, gray, gray)); + gray = qGray(m_matrix->getColor(2).rgb()); + m_matrix->setColor(2, QColor(gray, gray, gray)); + pm.fill(QColor(gray, gray, gray)); + } + m_mtxColor3Button->setIcon(QIcon(pm)); - if (m_matrix->endColor() == QColor()) - pm.fill(Qt::transparent); - else - pm.fill(QColor(gray, gray, gray)); + if (accColors < 4) + m_matrix->setColor(3, QColor()); + if (m_matrix->getColor(3) == QColor()) + { + pm.fill(Qt::transparent); + } + else + { + gray = qGray(m_matrix->getColor(3).rgb()); + m_matrix->setColor(3, QColor(gray, gray, gray)); + pm.fill(QColor(gray, gray, gray)); + } + m_mtxColor4Button->setIcon(QIcon(pm)); - m_endColorButton->setIcon(QIcon(pm)); + if (accColors < 5) + m_matrix->setColor(4, QColor()); + if (m_matrix->getColor(4) == QColor()) + { + pm.fill(Qt::transparent); + } + else + { + gray = qGray(m_matrix->getColor(4).rgb()); + m_matrix->setColor(4, QColor(gray, gray, gray)); + pm.fill(QColor(gray, gray, gray)); } - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_mtxColor5Button->setIcon(QIcon(pm)); + + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); } else { QPixmap pm(50, 26); - pm.fill(m_matrix->startColor()); - m_startColorButton->setIcon(QIcon(pm)); + pm.fill(m_matrix->getColor(0)); + m_mtxColor1Button->setIcon(QIcon(pm)); - if (accColors > 1) - { - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + // Preserve the colors (do not set them to QColor(). + // RGBMatrixStep::calculateColorDelta will ensure correct color application + if (m_matrix->getColor(1) == QColor()) + pm.fill(Qt::transparent); + else + pm.fill(m_matrix->getColor(1)); + m_mtxColor2Button->setIcon(QIcon(pm)); - if (m_matrix->endColor() == QColor()) - pm.fill(Qt::transparent); - else - pm.fill(m_matrix->endColor()); + if (m_matrix->getColor(2) == QColor()) + pm.fill(Qt::transparent); + else + pm.fill(m_matrix->getColor(2)); + m_mtxColor3Button->setIcon(QIcon(pm)); - m_endColorButton->setIcon(QIcon(pm)); - } + if (m_matrix->getColor(3) == QColor()) + pm.fill(Qt::transparent); + else + pm.fill(m_matrix->getColor(3)); + m_mtxColor4Button->setIcon(QIcon(pm)); + + if (m_matrix->getColor(4) == QColor()) + pm.fill(Qt::transparent); + else + pm.fill(m_matrix->getColor(4)); + m_mtxColor5Button->setIcon(QIcon(pm)); + + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); } } } @@ -612,8 +712,9 @@ bool RGBMatrixEditor::createPreviewItems() return false; } - m_previewHandler->initializeDirection(m_matrix->direction(), m_matrix->startColor(), - m_matrix->endColor(), m_matrix->stepsCount()); + m_previewHandler->initializeDirection(m_matrix->direction(), m_matrix->getColor(0), + m_matrix->getColor(1), m_matrix->stepsCount(), + m_matrix->algorithm()); m_matrix->previewMap(m_previewHandler->currentStepIndex(), m_previewHandler); @@ -669,8 +770,8 @@ void RGBMatrixEditor::slotPreviewTimeout() uint elapsed = 0; while (m_previewIterator >= MAX(m_matrix->duration(), MasterTimer::tick())) { - m_previewHandler->checkNextStep(m_matrix->runOrder(), m_matrix->startColor(), - m_matrix->endColor(), m_matrix->stepsCount()); + m_previewHandler->checkNextStep(m_matrix->runOrder(), m_matrix->getColor(0), + m_matrix->getColor(1), m_matrix->stepsCount()); m_matrix->previewMap(m_previewHandler->currentStepIndex(), m_previewHandler); @@ -725,10 +826,23 @@ void RGBMatrixEditor::slotPatternActivated(int patternIndex) { QString algoName = m_patternCombo->itemText(patternIndex); RGBAlgorithm *algo = RGBAlgorithm::algorithm(m_doc, algoName); - if (algo != NULL) - algo->setColors(m_matrix->startColor(), m_matrix->endColor()); m_matrix->setAlgorithm(algo); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + if (algo != NULL) { + updateColors(); +#if (5 != RGBAlgorithmColorDisplayCount) +#error "Further colors need to be displayed." +#endif + QVector colors = { + m_matrix->getColor(0), + m_matrix->getColor(1), + m_matrix->getColor(2), + m_matrix->getColor(3), + m_matrix->getColor(4) + }; + algo->setColors(colors); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); + } updateExtraOptions(); slotRestartTest(); @@ -756,11 +870,11 @@ void RGBMatrixEditor::slotBlendModeChanged(int index) if (index == Universe::MaskBlend) { - m_startColorButton->setEnabled(false); + m_mtxColor1Button->setEnabled(false); } else { - m_startColorButton->setEnabled(true); + m_mtxColor1Button->setEnabled(true); } updateExtraOptions(); updateColors(); @@ -775,32 +889,85 @@ void RGBMatrixEditor::slotControlModeChanged(int index) slotRestartTest(); } -void RGBMatrixEditor::slotStartColorButtonClicked() +void RGBMatrixEditor::slotMtxColor1ButtonClicked() +{ + QColor col = QColorDialog::getColor(m_matrix->getColor(0)); + if (col.isValid() == true) + { + m_matrix->setColor(0, col); + updateColors(); + slotRestartTest(); + } +} + +void RGBMatrixEditor::slotMtxColor2ButtonClicked() +{ + QColor col = QColorDialog::getColor(m_matrix->getColor(1)); + if (col.isValid() == true) + { + m_matrix->setColor(1, col); + updateColors(); + slotRestartTest(); + } +} + +void RGBMatrixEditor::slotResetMtxColor2ButtonClicked() +{ + m_matrix->setColor(1, QColor()); + updateColors(); + slotRestartTest(); +} + +void RGBMatrixEditor::slotMtxColor3ButtonClicked() +{ + QColor col = QColorDialog::getColor(m_matrix->getColor(2)); + if (col.isValid() == true) + { + m_matrix->setColor(2, col); + updateColors(); + slotRestartTest(); + } +} + +void RGBMatrixEditor::slotResetMtxColor3ButtonClicked() +{ + m_matrix->setColor(2, QColor()); + updateColors(); + slotRestartTest(); +} + +void RGBMatrixEditor::slotMtxColor4ButtonClicked() { - QColor col = QColorDialog::getColor(m_matrix->startColor()); + QColor col = QColorDialog::getColor(m_matrix->getColor(3)); if (col.isValid() == true) { - m_matrix->setStartColor(col); + m_matrix->setColor(3, col); updateColors(); slotRestartTest(); } } -void RGBMatrixEditor::slotEndColorButtonClicked() +void RGBMatrixEditor::slotResetMtxColor4ButtonClicked() +{ + m_matrix->setColor(3, QColor()); + updateColors(); + slotRestartTest(); +} + +void RGBMatrixEditor::slotMtxColor5ButtonClicked() { - QColor col = QColorDialog::getColor(m_matrix->endColor()); + QColor col = QColorDialog::getColor(m_matrix->getColor(4)); if (col.isValid() == true) { - m_matrix->setEndColor(col); + m_matrix->setColor(4, col); updateColors(); slotRestartTest(); } } -void RGBMatrixEditor::slotResetEndColorButtonClicked() +void RGBMatrixEditor::slotResetMtxColor5ButtonClicked() { - m_matrix->setEndColor(QColor()); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_matrix->setColor(4, QColor()); updateColors(); slotRestartTest(); } @@ -937,35 +1104,40 @@ void RGBMatrixEditor::slotOffsetSpinChanged() void RGBMatrixEditor::slotLoopClicked() { m_matrix->setRunOrder(Function::Loop); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); slotRestartTest(); } void RGBMatrixEditor::slotPingPongClicked() { m_matrix->setRunOrder(Function::PingPong); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); slotRestartTest(); } void RGBMatrixEditor::slotSingleShotClicked() { m_matrix->setRunOrder(Function::SingleShot); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); slotRestartTest(); } void RGBMatrixEditor::slotForwardClicked() { m_matrix->setDirection(Function::Forward); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); slotRestartTest(); } void RGBMatrixEditor::slotBackwardClicked() { m_matrix->setDirection(Function::Backward); - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); slotRestartTest(); } @@ -1150,16 +1322,17 @@ void RGBMatrixEditor::slotSaveToSequenceClicked() int totalSteps = m_matrix->stepsCount(); int increment = 1; int currentStep = 0; - m_previewHandler->setStepColor(m_matrix->startColor()); + m_previewHandler->setStepColor(m_matrix->getColor(0)); if (m_matrix->direction() == Function::Backward) { currentStep = totalSteps - 1; increment = -1; - if (m_matrix->endColor().isValid()) - m_previewHandler->setStepColor(m_matrix->endColor()); + if (m_matrix->getColor(1).isValid()) + m_previewHandler->setStepColor(m_matrix->getColor(1)); } - m_previewHandler->calculateColorDelta(m_matrix->startColor(), m_matrix->endColor()); + m_previewHandler->calculateColorDelta(m_matrix->getColor(0), m_matrix->getColor(1), + m_matrix->algorithm()); if (m_matrix->runOrder() == RGBMatrix::PingPong) totalSteps = (totalSteps * 2) - 1; @@ -1266,7 +1439,7 @@ void RGBMatrixEditor::slotSaveToSequenceClicked() currentStep = totalSteps - 2; increment = -1; } - m_previewHandler->updateStepColor(currentStep, m_matrix->startColor(), m_matrix->stepsCount()); + m_previewHandler->updateStepColor(currentStep, m_matrix->getColor(0), m_matrix->stepsCount()); } m_doc->addFunction(sequence); @@ -1293,6 +1466,9 @@ void RGBMatrixEditor::slotPropertyComboChanged(int index) QString pValue = combo->itemText(index); qDebug() << "Property combo changed to" << pValue; m_matrix->setProperty(pName, pValue); + + updateColorOptions(); + updateColors(); } } diff --git a/ui/src/rgbmatrixeditor.h b/ui/src/rgbmatrixeditor.h index 83fd049835..22ccb63531 100644 --- a/ui/src/rgbmatrixeditor.h +++ b/ui/src/rgbmatrixeditor.h @@ -63,6 +63,7 @@ public slots: void fillAnimationCombo(); void fillImageAnimationCombo(); void updateExtraOptions(); + void updateColorOptions(); void updateColors(); void resetProperties(QLayoutItem *item); void displayProperties(RGBScript *script); @@ -77,9 +78,15 @@ private slots: void slotFixtureGroupActivated(int index); void slotBlendModeChanged(int index); void slotControlModeChanged(int index); - void slotStartColorButtonClicked(); - void slotEndColorButtonClicked(); - void slotResetEndColorButtonClicked(); + void slotMtxColor1ButtonClicked(); + void slotMtxColor2ButtonClicked(); + void slotResetMtxColor2ButtonClicked(); + void slotMtxColor3ButtonClicked(); + void slotResetMtxColor3ButtonClicked(); + void slotMtxColor4ButtonClicked(); + void slotResetMtxColor4ButtonClicked(); + void slotMtxColor5ButtonClicked(); + void slotResetMtxColor5ButtonClicked(); void slotTextEdited(const QString& text); void slotFontButtonClicked(); diff --git a/ui/src/rgbmatrixeditor.ui b/ui/src/rgbmatrixeditor.ui index 2f3209edd7..d966295e3d 100644 --- a/ui/src/rgbmatrixeditor.ui +++ b/ui/src/rgbmatrixeditor.ui @@ -26,7 +26,7 @@ 0 0 575 - 728 + 798 @@ -42,13 +42,184 @@ 5 - + - - + + + + + 0 + 0 + + + + Other Controls + + + + 4 + + + 4 + + + + + Set the dimmer channel of fixtures to 100% + + + Dimmer control + + + + + + + + - + + + + 0 + 0 + + + + RGB matrix name + + + + + + + + 0 + 0 + + + + The name of this RGB matrix function + + + + + + + + + + + Show/Hide speed dial window + + + + :/speed.png:/speed.png + + + + 28 + 28 + + + + true + + + + + + + Save this matrix to a sequence + + + + + + + :/sequence.png:/sequence.png + + + + 28 + 28 + + + + + + + + Toggle between circle and square preview + + + + :/square.png:/square.png + + + + 28 + 28 + + + + true + + + + + + + See what the RGB Matrix does when it is run + + + + :/player_play.png:/player_play.png + + + + 28 + 28 + + + + true + + + + + + + + 0 + 0 + + + + Fixture group + + + + + + + + 0 + 0 + + + + The fixture group to use as the pixel matrix + + + + + + + + + 0 @@ -56,70 +227,167 @@ - Pattern + Run Order - + 4 4 - - 4 - - - + + - Matrix start color + Run through over and over again - - - 50 - 26 - + + Loop + + + true - - + + - Matrix end color + Run through once and stop - + Single Shot - - - 50 - 26 - + + + + + + First run forwards, then backwards, again forwards, etc. + + + Ping Pong - - + + + + + + + + 0 + 0 + + + + Direction + + + + 4 + + + 4 + + + - The RGB matrix pattern + Start from the first step + + + Forward + + + true - - + + - Reset the end color + Start from the last step - - - :/fileclose.png:/fileclose.png + + Backward - - - - - Default (HTP) + + + + Qt::Vertical + + + QSizePolicy::Maximum + + + + 20 + 35 + + + + + + + + + + + + + + + + 0 + 0 + + + + Pattern + + + + 4 + + + 4 + + + 4 + + + + + Matrix color 3 + + + + 50 + 26 + + + + + + + + Matrix color 1 + + + + 50 + 26 + + + + + + + + + Default (HTP) @@ -139,21 +407,56 @@ - + + + + Control mode + + + + + + + Matrix color 5 + + + + 50 + 26 + + + + + + + + Reset color 2 + + + + :/fileclose.png:/fileclose.png + + + + Blend mode - - - - Control mode + + + + Reset color 3 + + + + :/fileclose.png:/fileclose.png - + @@ -187,448 +490,203 @@ - - - - - - - Properties - - - - 4 - - - 4 - - - 4 - - - - - - - - - - - Animated Text - - - - 4 - - - 4 - - - 4 - - - - - - 0 - 0 - - - - Text to display - - - - - + + - Choose the font - - - - - - - :/fonts.png:/fonts.png - - - - 32 - 32 - + The RGB matrix pattern - - + + - Animation style - - - - - - - - - - Image - - - - 4 - - - 4 - - - 4 - - - - - - 0 - 0 - + Matrix color 2 - - - - - - - - - :/image.png:/image.png + - 32 - 32 - - - - - - - - - - - - - - Offset - - - - 4 - - - 4 - - - - - X - - - - - - - Shift the pattern X pixels horizontally - - - -255 - - - 255 - - - - - - - Y - - - - - - - Shift the pattern Y pixels vertically - - - -255 - - - 255 - - - - - - - - - - Qt::Vertical - - - QSizePolicy::Expanding - - - - 20 - 40 - - - - - - - - - - - 0 - 0 - - - - Other Controls - - - - 4 - - - 4 - - - - - Set the dimmer channel of fixtures to 100% - - - Dimmer control - - - - - - - - - - - - - 0 - 0 - - - - RGB matrix name - - - - - - - - 0 - 0 - - - - The name of this RGB matrix function - - - - - - - - - - - Show/Hide speed dial window - - - - :/speed.png:/speed.png - - - - 28 - 28 - - - - true - - - - - - - Save this matrix to a sequence - - - - - - - :/sequence.png:/sequence.png - - - - 28 - 28 - - - - - - - - Toggle between circle and square preview - - - - :/square.png:/square.png - - - - 28 - 28 - - - - true - - - - - - - See what the RGB Matrix does when it is run - - - - :/player_play.png:/player_play.png - - - - 28 - 28 - - - - true - + 50 + 26 + + + + + + + + Matrix color 4 + + + + + + + 50 + 26 + + + + + + + + Reset color 4 + + + + :/fileclose.png:/fileclose.png + + + + + + + Reset color 5 + + + + :/fileclose.png:/fileclose.png + + + + - - - - 0 - 0 - - - - Fixture group + + + Properties + + + 4 + + + 4 + + + 4 + + + + + - - - - 0 - 0 - - - - The fixture group to use as the pixel matrix - - - - - - - - - - - - 0 - 0 - - + - Run Order + Animated Text - + 4 4 - - - - Run through over and over again - - - Loop + + 4 + + + + + + 0 + 0 + - - true + + Text to display - - + + - Run through once and stop + Choose the font - Single Shot + + + + + :/fonts.png:/fonts.png + + + + 32 + 32 + - - + + - First run forwards, then backwards, again forwards, etc. + Animation style + + + + + + + + + + Image + + + + 4 + + + 4 + + + 4 + + + + + + 0 + 0 + + + + + - Ping Pong + + + + + :/image.png:/image.png + + + + 32 + 32 + + + + - - - - - 0 - 0 - - + + - Direction + Offset - + 4 @@ -636,47 +694,64 @@ 4 - - - Start from the first step - + - Forward - - - true + X - + - Start from the last step + Shift the pattern X pixels horizontally + + + -255 + + 255 + + + + + - Backward + Y - - - Qt::Vertical + + + Shift the pattern Y pixels vertically - - QSizePolicy::Maximum + + -255 - - - 20 - 35 - + + 255 - + + + + + Qt::Vertical + + + QSizePolicy::Expanding + + + + 20 + 40 + + + + diff --git a/ui/src/virtualconsole/vcmatrix.cpp b/ui/src/virtualconsole/vcmatrix.cpp index 06841b5be5..d64748d754 100644 --- a/ui/src/virtualconsole/vcmatrix.cpp +++ b/ui/src/virtualconsole/vcmatrix.cpp @@ -79,37 +79,90 @@ VCMatrix::VCMatrix(QWidget *parent, Doc *doc) QVBoxLayout *vbox = new QVBoxLayout(); - m_startColorButton = new QToolButton(this); - m_startColorButton->setFixedSize(48, 48); - m_startColorButton->setIconSize(QSize(42, 42)); + /* Color 1 Button */ + m_mtxColor1Button = new QToolButton(this); + m_mtxColor1Button->setFixedSize(48, 48); + m_mtxColor1Button->setIconSize(QSize(42, 42)); QWidgetAction* scAction = new QWidgetAction(this); - m_scCnGWidget = new ClickAndGoWidget(); - m_scCnGWidget->setType(ClickAndGoWidget::RGB, NULL); - scAction->setDefaultWidget(m_scCnGWidget); - QMenu *startColorMenu = new QMenu(); - startColorMenu->addAction(scAction); - m_startColorButton->setMenu(startColorMenu); - m_startColorButton->setPopupMode(QToolButton::InstantPopup); - - connect(m_scCnGWidget, SIGNAL(colorChanged(QRgb)), - this, SLOT(slotStartColorChanged(QRgb))); - - m_endColorButton = new QToolButton(this); - m_endColorButton->setFixedSize(48, 48); - m_endColorButton->setIconSize(QSize(42, 42)); - - QWidgetAction* ecAction = new QWidgetAction(this); - m_ecCnGWidget = new ClickAndGoWidget(); - m_ecCnGWidget->setType(ClickAndGoWidget::RGB, NULL); - ecAction->setDefaultWidget(m_ecCnGWidget); - QMenu *endColorMenu = new QMenu(); - endColorMenu->addAction(ecAction); - m_endColorButton->setMenu(endColorMenu); - m_endColorButton->setPopupMode(QToolButton::InstantPopup); - - connect(m_ecCnGWidget, SIGNAL(colorChanged(QRgb)), - this, SLOT(slotEndColorChanged(QRgb))); + m_mtxColor1CnGWidget = new ClickAndGoWidget(); + m_mtxColor1CnGWidget->setType(ClickAndGoWidget::RGB, NULL); + scAction->setDefaultWidget(m_mtxColor1CnGWidget); + QMenu *color1Menu = new QMenu(); + color1Menu->addAction(scAction); + m_mtxColor1Button->setMenu(color1Menu); + m_mtxColor1Button->setPopupMode(QToolButton::InstantPopup); + + connect(m_mtxColor1CnGWidget, SIGNAL(colorChanged(QRgb)), + this, SLOT(slotColor1Changed(QRgb))); + + /* Color 2 Button */ + m_mtxColor2Button = new QToolButton(this); + m_mtxColor2Button->setFixedSize(48, 48); + m_mtxColor2Button->setIconSize(QSize(42, 42)); + + QWidgetAction* ecAction2 = new QWidgetAction(this); + m_mtxColor2CnGWidget = new ClickAndGoWidget(); + m_mtxColor2CnGWidget->setType(ClickAndGoWidget::RGB, NULL); + ecAction2->setDefaultWidget(m_mtxColor2CnGWidget); + QMenu *color2Menu = new QMenu(); + color2Menu->addAction(ecAction2); + m_mtxColor2Button->setMenu(color2Menu); + m_mtxColor2Button->setPopupMode(QToolButton::InstantPopup); + + connect(m_mtxColor2CnGWidget, SIGNAL(colorChanged(QRgb)), + this, SLOT(slotColor2Changed(QRgb))); + + /* 3rd Color Button */ + m_mtxColor3Button = new QToolButton(this); + m_mtxColor3Button->setFixedSize(48, 48); + m_mtxColor3Button->setIconSize(QSize(42, 42)); + + QWidgetAction* ecAction3 = new QWidgetAction(this); + m_mtxColor3CnGWidget = new ClickAndGoWidget(); + m_mtxColor3CnGWidget->setType(ClickAndGoWidget::RGB, NULL); + ecAction3->setDefaultWidget(m_mtxColor3CnGWidget); + QMenu *color3Menu = new QMenu(); + color3Menu->addAction(ecAction3); + m_mtxColor3Button->setMenu(color3Menu); + m_mtxColor3Button->setPopupMode(QToolButton::InstantPopup); + + connect(m_mtxColor3CnGWidget, SIGNAL(colorChanged(QRgb)), + this, SLOT(slotColor3Changed(QRgb))); + + /* 4th Color Button */ + m_mtxColor4Button = new QToolButton(this); + m_mtxColor4Button->setFixedSize(48, 48); + m_mtxColor4Button->setIconSize(QSize(42, 42)); + + QWidgetAction* ecAction4 = new QWidgetAction(this); + m_mtxColor4CnGWidget = new ClickAndGoWidget(); + m_mtxColor4CnGWidget->setType(ClickAndGoWidget::RGB, NULL); + ecAction4->setDefaultWidget(m_mtxColor4CnGWidget); + QMenu *color4Menu = new QMenu(); + color4Menu->addAction(ecAction4); + m_mtxColor4Button->setMenu(color4Menu); + m_mtxColor4Button->setPopupMode(QToolButton::InstantPopup); + + connect(m_mtxColor4CnGWidget, SIGNAL(colorChanged(QRgb)), + this, SLOT(slotColor4Changed(QRgb))); + + /* 5th Color Button */ + m_mtxColor5Button = new QToolButton(this); + m_mtxColor5Button->setFixedSize(48, 48); + m_mtxColor5Button->setIconSize(QSize(42, 42)); + + QWidgetAction* ecAction5 = new QWidgetAction(this); + m_mtxColor5CnGWidget = new ClickAndGoWidget(); + m_mtxColor5CnGWidget->setType(ClickAndGoWidget::RGB, NULL); + ecAction5->setDefaultWidget(m_mtxColor5CnGWidget); + QMenu *color5Menu = new QMenu(); + color5Menu->addAction(ecAction5); + m_mtxColor5Button->setMenu(color5Menu); + m_mtxColor5Button->setPopupMode(QToolButton::InstantPopup); + + connect(m_mtxColor5CnGWidget, SIGNAL(colorChanged(QRgb)), + this, SLOT(slotColor5Changed(QRgb))); m_label = new QLabel(this); m_label->setAlignment(Qt::AlignCenter); @@ -118,8 +171,11 @@ VCMatrix::VCMatrix(QWidget *parent, Doc *doc) QHBoxLayout *btnHbox = new QHBoxLayout(); - btnHbox->addWidget(m_startColorButton); - btnHbox->addWidget(m_endColorButton); + btnHbox->addWidget(m_mtxColor1Button); + btnHbox->addWidget(m_mtxColor2Button); + btnHbox->addWidget(m_mtxColor3Button); + btnHbox->addWidget(m_mtxColor4Button); + btnHbox->addWidget(m_mtxColor5Button); vbox->addLayout(btnHbox); @@ -224,8 +280,11 @@ void VCMatrix::setCaption(const QString &text) void VCMatrix::enableWidgetUI(bool enable) { m_slider->setEnabled(enable); - m_startColorButton->setEnabled(enable); - m_endColorButton->setEnabled(enable); + m_mtxColor1Button->setEnabled(enable); + m_mtxColor2Button->setEnabled(enable); + m_mtxColor3Button->setEnabled(enable); + m_mtxColor4Button->setEnabled(enable); + m_mtxColor5Button->setEnabled(enable); m_presetCombo->setEnabled(enable); foreach (QWidget *ctlBtn, m_controls.keys()) @@ -281,84 +340,159 @@ int VCMatrix::sliderValue() return m_slider->value(); } -void VCMatrix::slotSetStartColor(QColor color) +void VCMatrix::slotSetColor1(QColor color) { RGBMatrix *matrix = qobject_cast(m_doc->function(m_matrixID)); if (matrix == NULL) return; - if (matrix->startColor() != color) + if (matrix->getColor(0) != color) { - matrix->setStartColor(color); - emit startColorChanged(); + matrix->setColor(0, color); + emit mtxColor1Changed(); } } -QColor VCMatrix::startColor() +void VCMatrix::slotSetColor2(QColor color) { RGBMatrix *matrix = qobject_cast(m_doc->function(m_matrixID)); if (matrix == NULL) - return QColor(); + return; - return matrix->startColor(); + if (matrix->getColor(1) != color) + { + matrix->setColor(1, color); + emit mtxColor2Changed(); + } } -void VCMatrix::slotStartColorChanged(QRgb color) +void VCMatrix::slotSetColor3(QColor color) { - QColor col(color); - slotSetStartColor(col); - QPixmap px(42, 42); - px.fill(col); - m_startColorButton->setIcon(px); + RGBMatrix *matrix = qobject_cast(m_doc->function(m_matrixID)); + if (matrix == NULL) + return; - RGBMatrix* matrix = qobject_cast(m_doc->function(m_matrixID)); - if (matrix == NULL || mode() == Doc::Design) + if (matrix->getColor(2) != color) + { + matrix->setColor(2, color); + emit mtxColor3Changed(); + } +} + +void VCMatrix::slotSetColor4(QColor color) +{ + RGBMatrix *matrix = qobject_cast(m_doc->function(m_matrixID)); + if (matrix == NULL) return; - matrix->setStartColor(col); - if (instantChanges() == true) - matrix->updateColorDelta(); + if (matrix->getColor(3) != color) + { + matrix->setColor(3, color); + emit mtxColor4Changed(); + } } -void VCMatrix::slotSetEndColor(QColor color) +void VCMatrix::slotSetColor5(QColor color) { RGBMatrix *matrix = qobject_cast(m_doc->function(m_matrixID)); if (matrix == NULL) return; - if (matrix->endColor() != color) + if (matrix->getColor(4) != color) { - matrix->setEndColor(color); - emit endColorChanged(); + matrix->setColor(4, color); + emit mtxColor5Changed(); } } -QColor VCMatrix::endColor() +QColor VCMatrix::mtxColor(int id) { RGBMatrix *matrix = qobject_cast(m_doc->function(m_matrixID)); if (matrix == NULL) return QColor(); - return matrix->endColor(); + return matrix->getColor(id); } -void VCMatrix::slotEndColorChanged(QRgb color) +void VCMatrix::slotColor1Changed(QRgb color) { QColor col(color); - slotSetEndColor(col); + slotSetColor1(col); QPixmap px(42, 42); px.fill(col); - m_endColorButton->setIcon(px); + m_mtxColor1Button->setIcon(px); RGBMatrix* matrix = qobject_cast(m_doc->function(m_matrixID)); if (matrix == NULL || mode() == Doc::Design) return; - matrix->setEndColor(col); + matrix->setColor(0, col); if (instantChanges() == true) matrix->updateColorDelta(); } +void VCMatrix::slotColor2Changed(QRgb color) +{ + QColor col(color); + slotSetColor2(col); + QPixmap px(42, 42); + px.fill(col); + m_mtxColor2Button->setIcon(px); + + RGBMatrix* matrix = qobject_cast(m_doc->function(m_matrixID)); + if (matrix == NULL || mode() == Doc::Design) + return; + + matrix->setColor(1, col); + if (instantChanges() == true) + matrix->updateColorDelta(); +} + +void VCMatrix::slotColor3Changed(QRgb color) +{ + QColor col(color); + slotSetColor3(col); + QPixmap px(42, 42); + px.fill(col); + m_mtxColor3Button->setIcon(px); + + RGBMatrix* matrix = qobject_cast(m_doc->function(m_matrixID)); + if (matrix == NULL || mode() == Doc::Design) + return; + + matrix->setColor(2, col); +} + +void VCMatrix::slotColor4Changed(QRgb color) +{ + QColor col(color); + slotSetColor4(col); + QPixmap px(42, 42); + px.fill(col); + m_mtxColor4Button->setIcon(px); + + RGBMatrix* matrix = qobject_cast(m_doc->function(m_matrixID)); + if (matrix == NULL || mode() == Doc::Design) + return; + + matrix->setColor(3, col); +} + +void VCMatrix::slotColor5Changed(QRgb color) +{ + QColor col(color); + slotSetColor5(col); + QPixmap px(42, 42); + px.fill(col); + m_mtxColor5Button->setIcon(px); + + RGBMatrix* matrix = qobject_cast(m_doc->function(m_matrixID)); + if (matrix == NULL || mode() == Doc::Design) + return; + + matrix->setColor(4, col); +} + void VCMatrix::slotSetAnimationValue(QString name) { for (int i = 0; i < m_presetCombo->count(); i++) @@ -400,11 +534,20 @@ void VCMatrix::setVisibilityMask(quint32 mask) if (mask & ShowLabel) m_label->show(); else m_label->hide(); - if (mask & ShowStartColorButton) m_startColorButton->show(); - else m_startColorButton->hide(); + if (mask & ShowColor1Button) m_mtxColor1Button->show(); + else m_mtxColor1Button->hide(); + + if (mask & ShowColor2Button) m_mtxColor2Button->show(); + else m_mtxColor2Button->hide(); + + if (mask & ShowColor3Button) m_mtxColor3Button->show(); + else m_mtxColor3Button->hide(); - if (mask & ShowEndColorButton) m_endColorButton->show(); - else m_endColorButton->hide(); + if (mask & ShowColor4Button) m_mtxColor4Button->show(); + else m_mtxColor4Button->hide(); + + if (mask & ShowColor5Button) m_mtxColor5Button->show(); + else m_mtxColor5Button->hide(); if (mask & ShowPresetCombo) m_presetCombo->show(); else m_presetCombo->hide(); @@ -421,9 +564,12 @@ quint32 VCMatrix::defaultVisibilityMask() { return ShowSlider | ShowLabel - | ShowStartColorButton - | ShowEndColorButton | ShowPresetCombo + | ShowColor1Button + | ShowColor2Button + | ShowColor3Button + | ShowColor4Button + | ShowColor5Button ; } @@ -537,8 +683,6 @@ void VCMatrix::slotUpdate() if (matrix == NULL) return; - QColor startColor = matrix->startColor(); - QColor endColor = matrix->endColor(); QString algorithmName; RGBAlgorithm::Type algorithmType = RGBAlgorithm::Plain; QHash algorithmProperties; @@ -563,15 +707,34 @@ void VCMatrix::slotUpdate() } } - // Start / End color buttons + // Color buttons QPixmap px(42, 42); - px.fill(startColor); - m_startColorButton->setIcon(px); - slotSetStartColor(startColor); + px.fill(matrix->getColor(0)); + m_mtxColor1Button->setIcon(px); - px.fill(endColor == QColor() ? Qt::transparent : endColor); - m_endColorButton->setIcon(px); - slotSetEndColor(endColor); + if (matrix->getColor(1) == QColor()) + px.fill(Qt::transparent); + else + px.fill(matrix->getColor(1)); + m_mtxColor2Button->setIcon(px); + + if (matrix->getColor(2) == QColor()) + px.fill(Qt::transparent); + else + px.fill(matrix->getColor(2)); + m_mtxColor3Button->setIcon(px); + + if (matrix->getColor(3) == QColor()) + px.fill(Qt::transparent); + else + px.fill(matrix->getColor(3)); + m_mtxColor4Button->setIcon(px); + + if (matrix->getColor(4) == QColor()) + px.fill(Qt::transparent); + else + px.fill(matrix->getColor(4)); + m_mtxColor5Button->setIcon(px); // Algo combo box if (algorithmName != QString()) @@ -588,10 +751,10 @@ void VCMatrix::slotUpdate() QWidget *widget = it.key(); VCMatrixControl *control = it.value(); - if (control->m_type == VCMatrixControl::StartColorKnob) + if (control->m_type == VCMatrixControl::Color1Knob) { KnobWidget *knob = reinterpret_cast(widget); - int val = control->rgbToValue(startColor.rgb()); + int val = control->rgbToValue(matrix->getColor(0).rgb()); if (knob->value() != val) { knob->blockSignals(true); @@ -600,10 +763,10 @@ void VCMatrix::slotUpdate() knob->blockSignals(false); } } - else if (control->m_type == VCMatrixControl::EndColorKnob) + else if (control->m_type == VCMatrixControl::Color2Knob) { KnobWidget *knob = reinterpret_cast(widget); - int val = control->rgbToValue(endColor.rgb()); + int val = control->rgbToValue(matrix->getColor(1).rgb()); if (knob->value() != val) { knob->blockSignals(true); @@ -612,15 +775,66 @@ void VCMatrix::slotUpdate() knob->blockSignals(false); } } - else if (control->m_type == VCMatrixControl::StartColor) + else if (control->m_type == VCMatrixControl::Color3Knob) { - QPushButton *button = reinterpret_cast(it.key()); - button->setDown(startColor == control->m_color); + KnobWidget *knob = reinterpret_cast(widget); + int val = control->rgbToValue(matrix->getColor(2).rgb()); + if (knob->value() != val) + { + knob->blockSignals(true); + knob->setValue(val); + emit matrixControlKnobValueChanged(control->m_id, val); + knob->blockSignals(false); + } } - else if (control->m_type == VCMatrixControl::EndColor) + else if (control->m_type == VCMatrixControl::Color4Knob) { - QPushButton *button = reinterpret_cast(it.key()); - button->setDown(endColor == control->m_color); + KnobWidget *knob = reinterpret_cast(widget); + int val = control->rgbToValue(matrix->getColor(3).rgb()); + if (knob->value() != val) + { + knob->blockSignals(true); + knob->setValue(val); + emit matrixControlKnobValueChanged(control->m_id, val); + knob->blockSignals(false); + } + } + else if (control->m_type == VCMatrixControl::Color5Knob) + { + KnobWidget *knob = reinterpret_cast(widget); + int val = control->rgbToValue(matrix->getColor(4).rgb()); + if (knob->value() != val) + { + knob->blockSignals(true); + knob->setValue(val); + emit matrixControlKnobValueChanged(control->m_id, val); + knob->blockSignals(false); + } + } + else if (control->m_type == VCMatrixControl::Color1) + { + QPushButton* button = reinterpret_cast(it.key()); + button->setDown(matrix->getColor(0) == control->m_color); + } + else if (control->m_type == VCMatrixControl::Color2) + { + QPushButton* button = reinterpret_cast(it.key()); + button->setDown(matrix->getColor(1) == control->m_color); + } + else if (control->m_type == VCMatrixControl::Color3) + { + QPushButton* button = reinterpret_cast(it.key()); + button->setDown(matrix->getColor(2) == control->m_color); + } + else if (control->m_type == VCMatrixControl::Color4) + { + QPushButton* button = reinterpret_cast(it.key()); + button->setDown(matrix->getColor(3) == control->m_color); + } + else if (control->m_type == VCMatrixControl::Color5) + { + QPushButton* button = reinterpret_cast(it.key()); + button->setDown(matrix->getColor(4) == control->m_color); } else if (control->m_type == VCMatrixControl::Animation) { @@ -684,25 +898,52 @@ void VCMatrix::addCustomControl(VCMatrixControl const& control) { QWidget *controlWidget = NULL; - if (control.m_type == VCMatrixControl::StartColor) + if (control.m_type == VCMatrixControl::Color1) { QPushButton *controlButton = new QPushButton(this); controlWidget = controlButton; controlButton->setStyleSheet(controlBtnSS.arg(control.m_color.name())); controlButton->setFixedWidth(36); controlButton->setFocusPolicy(Qt::TabFocus); - controlButton->setText("S"); + controlButton->setText("1"); } - else if (control.m_type == VCMatrixControl::EndColor) + else if (control.m_type == VCMatrixControl::Color2) { QPushButton *controlButton = new QPushButton(this); controlWidget = controlButton; controlButton->setStyleSheet(controlBtnSS.arg(control.m_color.name())); controlButton->setFixedWidth(36); controlButton->setFocusPolicy(Qt::TabFocus); - controlButton->setText("E"); + controlButton->setText("2"); } - else if (control.m_type == VCMatrixControl::ResetEndColor) + else if (control.m_type == VCMatrixControl::Color3) + { + QPushButton *controlButton = new QPushButton(this); + controlWidget = controlButton; + controlButton->setStyleSheet(controlBtnSS.arg(control.m_color.name())); + controlButton->setFixedWidth(36); + controlButton->setFocusPolicy(Qt::TabFocus); + controlButton->setText("3"); + } + else if (control.m_type == VCMatrixControl::Color4) + { + QPushButton *controlButton = new QPushButton(this); + controlWidget = controlButton; + controlButton->setStyleSheet(controlBtnSS.arg(control.m_color.name())); + controlButton->setFixedWidth(36); + controlButton->setFocusPolicy(Qt::TabFocus); + controlButton->setText("4"); + } + else if (control.m_type == VCMatrixControl::Color5) + { + QPushButton *controlButton = new QPushButton(this); + controlWidget = controlButton; + controlButton->setStyleSheet(controlBtnSS.arg(control.m_color.name())); + controlButton->setFixedWidth(36); + controlButton->setFocusPolicy(Qt::TabFocus); + controlButton->setText("5"); + } + else if (control.m_type == VCMatrixControl::Color2Reset) { QPushButton *controlButton = new QPushButton(this); controlWidget = controlButton; @@ -710,7 +951,43 @@ void VCMatrix::addCustomControl(VCMatrixControl const& control) controlButton->setMinimumWidth(36); controlButton->setMaximumWidth(80); controlButton->setFocusPolicy(Qt::TabFocus); - QString btnLabel = tr("End Color Reset"); + QString btnLabel = tr("Color 2 Reset"); + controlButton->setToolTip(btnLabel); + controlButton->setText(fontMetrics().elidedText(btnLabel, Qt::ElideRight, 72)); + } + else if (control.m_type == VCMatrixControl::Color3Reset) + { + QPushButton *controlButton = new QPushButton(this); + controlWidget = controlButton; + controlButton->setStyleSheet(controlBtnSS.arg("#BBBBBB")); + controlButton->setMinimumWidth(36); + controlButton->setMaximumWidth(80); + controlButton->setFocusPolicy(Qt::TabFocus); + QString btnLabel = tr("Color 3 Reset"); + controlButton->setToolTip(btnLabel); + controlButton->setText(fontMetrics().elidedText(btnLabel, Qt::ElideRight, 72)); + } + else if (control.m_type == VCMatrixControl::Color4Reset) + { + QPushButton *controlButton = new QPushButton(this); + controlWidget = controlButton; + controlButton->setStyleSheet(controlBtnSS.arg("#BBBBBB")); + controlButton->setMinimumWidth(36); + controlButton->setMaximumWidth(80); + controlButton->setFocusPolicy(Qt::TabFocus); + QString btnLabel = tr("Color 4 Reset"); + controlButton->setToolTip(btnLabel); + controlButton->setText(fontMetrics().elidedText(btnLabel, Qt::ElideRight, 72)); + } + else if (control.m_type == VCMatrixControl::Color5Reset) + { + QPushButton *controlButton = new QPushButton(this); + controlWidget = controlButton; + controlButton->setStyleSheet(controlBtnSS.arg("#BBBBBB")); + controlButton->setMinimumWidth(36); + controlButton->setMaximumWidth(80); + controlButton->setFocusPolicy(Qt::TabFocus); + QString btnLabel = tr("Color 5 Reset"); controlButton->setToolTip(btnLabel); controlButton->setText(fontMetrics().elidedText(btnLabel, Qt::ElideRight, 72)); } @@ -740,7 +1017,7 @@ void VCMatrix::addCustomControl(VCMatrixControl const& control) controlButton->setToolTip(btnLabel); controlButton->setText(fontMetrics().elidedText(btnLabel, Qt::ElideRight, 72)); } - else if (control.m_type == VCMatrixControl::StartColorKnob) + else if (control.m_type == VCMatrixControl::Color1Knob) { KnobWidget *controlKnob = new KnobWidget(this); controlWidget = controlKnob; @@ -749,14 +1026,14 @@ void VCMatrix::addCustomControl(VCMatrixControl const& control) controlKnob->setFixedHeight(36); QString knobLabel; if (control.m_color == Qt::red) - knobLabel = tr("Start color Red component"); + knobLabel = tr("Color 1 Red component"); else if (control.m_color == Qt::green) - knobLabel = tr("Start color Green component"); + knobLabel = tr("Color 1 Green component"); else if (control.m_color == Qt::blue) - knobLabel = tr("Start color Blue component"); + knobLabel = tr("Color 1 Blue component"); controlKnob->setToolTip(knobLabel); } - else if (control.m_type == VCMatrixControl::EndColorKnob) + else if (control.m_type == VCMatrixControl::Color2Knob) { KnobWidget *controlKnob = new KnobWidget(this); controlWidget = controlKnob; @@ -765,11 +1042,59 @@ void VCMatrix::addCustomControl(VCMatrixControl const& control) controlKnob->setFixedHeight(36); QString knobLabel; if (control.m_color == Qt::red) - knobLabel = tr("End color Red component"); + knobLabel = tr("Color 2 Red component"); else if (control.m_color == Qt::green) - knobLabel = tr("End color Green component"); + knobLabel = tr("Color 2 Green component"); else if (control.m_color == Qt::blue) - knobLabel = tr("End color Blue component"); + knobLabel = tr("Color 2 Blue component"); + controlKnob->setToolTip(knobLabel); + } + else if (control.m_type == VCMatrixControl::Color3Knob) + { + KnobWidget *controlKnob = new KnobWidget(this); + controlWidget = controlKnob; + controlKnob->setColor(control.m_color.darker(250)); + controlKnob->setFixedWidth(36); + controlKnob->setFixedHeight(36); + QString knobLabel; + if (control.m_color == Qt::red) + knobLabel = tr("Color 3 Red component"); + else if (control.m_color == Qt::green) + knobLabel = tr("Color 3 Green component"); + else if (control.m_color == Qt::blue) + knobLabel = tr("Color 3 Blue component"); + controlKnob->setToolTip(knobLabel); + } + else if (control.m_type == VCMatrixControl::Color4Knob) + { + KnobWidget *controlKnob = new KnobWidget(this); + controlWidget = controlKnob; + controlKnob->setColor(control.m_color.darker(250)); + controlKnob->setFixedWidth(36); + controlKnob->setFixedHeight(36); + QString knobLabel; + if (control.m_color == Qt::red) + knobLabel = tr("Color 4 Red component"); + else if (control.m_color == Qt::green) + knobLabel = tr("Color 4 Green component"); + else if (control.m_color == Qt::blue) + knobLabel = tr("Color 4 Blue component"); + controlKnob->setToolTip(knobLabel); + } + else if (control.m_type == VCMatrixControl::Color5Knob) + { + KnobWidget *controlKnob = new KnobWidget(this); + controlWidget = controlKnob; + controlKnob->setColor(control.m_color.darker(250)); + controlKnob->setFixedWidth(36); + controlKnob->setFixedHeight(36); + QString knobLabel; + if (control.m_color == Qt::red) + knobLabel = tr("Color 5 Red component"); + else if (control.m_color == Qt::green) + knobLabel = tr("Color 5 Green component"); + else if (control.m_color == Qt::blue) + knobLabel = tr("Color 5 Blue component"); controlKnob->setToolTip(knobLabel); } @@ -854,28 +1179,61 @@ void VCMatrix::slotCustomControlClicked() if (matrix == NULL || mode() == Doc::Design) return; - if (control->m_type == VCMatrixControl::StartColor) + if (control->m_type == VCMatrixControl::Color1) { - matrix->setStartColor(control->m_color); + matrix->setColor(0, control->m_color); if (instantChanges() == true) matrix->updateColorDelta(); btn->setDown(true); - emit startColorChanged(); + emit mtxColor1Changed(); } - else if (control->m_type == VCMatrixControl::EndColor) + else if (control->m_type == VCMatrixControl::Color2) { - matrix->setEndColor(control->m_color); + matrix->setColor(1, control->m_color); if (instantChanges() == true) matrix->updateColorDelta(); btn->setDown(true); - emit endColorChanged(); + emit mtxColor2Changed(); + } + else if (control->m_type == VCMatrixControl::Color3) + { + matrix->setColor(2, control->m_color); + btn->setDown(true); + emit mtxColor3Changed(); + } + else if (control->m_type == VCMatrixControl::Color4) + { + matrix->setColor(3, control->m_color); + btn->setDown(true); + emit mtxColor4Changed(); + } + else if (control->m_type == VCMatrixControl::Color5) + { + matrix->setColor(4, control->m_color); + btn->setDown(true); + emit mtxColor5Changed(); } - else if (control->m_type == VCMatrixControl::ResetEndColor) + else if (control->m_type == VCMatrixControl::Color2Reset) { - matrix->setEndColor(QColor()); + matrix->setColor(1, QColor()); if (instantChanges() == true) matrix->updateColorDelta(); - emit endColorChanged(); + emit mtxColor2Changed(); + } + else if (control->m_type == VCMatrixControl::Color3Reset) + { + matrix->setColor(2, QColor()); + emit mtxColor3Changed(); + } + else if (control->m_type == VCMatrixControl::Color4Reset) + { + matrix->setColor(3, QColor()); + emit mtxColor4Changed(); + } + else if (control->m_type == VCMatrixControl::Color5Reset) + { + matrix->setColor(4, QColor()); + emit mtxColor5Changed(); } else if (control->m_type == VCMatrixControl::Animation) { @@ -919,27 +1277,54 @@ void VCMatrix::slotCustomControlValueChanged() if (matrix == NULL || mode() == Doc::Design) return; - if (control->m_type == VCMatrixControl::StartColorKnob) + if (control->m_type == VCMatrixControl::Color1Knob) { - QRgb color = matrix->startColor().rgb(); + QRgb color = matrix->getColor(0).rgb(); QRgb knobValueColor = control->valueToRgb(knob->value()); color = (color & ~control->m_color.rgb()) | (knobValueColor & control->m_color.rgb()); - matrix->setStartColor(color); + matrix->setColor(0, color); if (instantChanges() == true) matrix->updateColorDelta(); - emit startColorChanged(); + emit mtxColor1Changed(); } - else if (control->m_type == VCMatrixControl::EndColorKnob) + else if (control->m_type == VCMatrixControl::Color2Knob) { - QRgb color = matrix->endColor().rgb(); + QRgb color = matrix->getColor(1).rgb(); QRgb knobValueColor = control->valueToRgb(knob->value()); color = (color & ~control->m_color.rgb()) | (knobValueColor & control->m_color.rgb()); - matrix->setEndColor(color); + matrix->setColor(1, color); if (instantChanges() == true) matrix->updateColorDelta(); - emit endColorChanged(); + emit mtxColor2Changed(); + } + else if (control->m_type == VCMatrixControl::Color3Knob) + { + QRgb color = matrix->getColor(2).rgb(); + QRgb knobValueColor = control->valueToRgb(knob->value()); + color = (color & ~control->m_color.rgb()) | (knobValueColor & control->m_color.rgb()); + + matrix->setColor(2, color); + emit mtxColor3Changed(); + } + else if (control->m_type == VCMatrixControl::Color4Knob) + { + QRgb color = matrix->getColor(3).rgb(); + QRgb knobValueColor = control->valueToRgb(knob->value()); + color = (color & ~control->m_color.rgb()) | (knobValueColor & control->m_color.rgb()); + + matrix->setColor(3, color); + emit mtxColor4Changed(); + } + else if (control->m_type == VCMatrixControl::Color5Knob) + { + QRgb color = matrix->getColor(4).rgb(); + QRgb knobValueColor = control->valueToRgb(knob->value()); + color = (color & ~control->m_color.rgb()) | (knobValueColor & control->m_color.rgb()); + + matrix->setColor(4, color); + emit mtxColor5Changed(); } else { @@ -957,7 +1342,11 @@ void VCMatrix::slotMatrixControlKnobValueChanged(int controlID, int value) { if (customControls[i]->m_id == controlID) { - if (customControls[i]->m_type == VCMatrixControl::StartColorKnob || customControls[i]->m_type == VCMatrixControl::EndColorKnob) + if (customControls[i]->m_type == VCMatrixControl::Color1Knob + || customControls[i]->m_type == VCMatrixControl::Color2Knob + || customControls[i]->m_type == VCMatrixControl::Color3Knob + || customControls[i]->m_type == VCMatrixControl::Color4Knob + || customControls[i]->m_type == VCMatrixControl::Color5Knob) { KnobWidget *knob = qobject_cast(this->getWidget(customControls[i])); knob->setValue(value); diff --git a/ui/src/virtualconsole/vcmatrix.h b/ui/src/virtualconsole/vcmatrix.h index a961271454..58c8e72e31 100644 --- a/ui/src/virtualconsole/vcmatrix.h +++ b/ui/src/virtualconsole/vcmatrix.h @@ -47,8 +47,11 @@ class RGBMatrix; #define KXMLQLCVCMatrixInstantApply QString("InstantApply") -#define KXMLQLCVCMatrixStartColor QString("StartColor") -#define KXMLQLCVCMatrixEndColor QString("EndColor") +#define KXMLQLCVCMatrixColor1 QString("Color 1") +#define KXMLQLCVCMatrixColor2 QString("Color 2") +#define KXMLQLCVCMatrixColor3 QString("Color 3") +#define KXMLQLCVCMatrixColor4 QString("Color 4") +#define KXMLQLCVCMatrixColor5 QString("Color 5") #define KXMLQLCVCMatrixVisibilityMask QString("Visibility") @@ -63,9 +66,12 @@ class VCMatrix : public VCWidget None = 0, ShowSlider = 1 << 0, ShowLabel = 1 << 1, - ShowStartColorButton = 1 << 2, - ShowEndColorButton = 1 << 3, - ShowPresetCombo = 1 << 4, + ShowPresetCombo = 1 << 2, + ShowColor1Button = 1 << 3, + ShowColor2Button = 1 << 4, + ShowColor3Button = 1 << 5, + ShowColor4Button = 1 << 6, + ShowColor5Button = 1 << 7 }; public: @@ -86,10 +92,16 @@ class VCMatrix : public VCWidget ClickAndGoSlider *m_slider; bool m_sliderExternalMovement; QLabel *m_label; - QToolButton *m_startColorButton; - ClickAndGoWidget *m_scCnGWidget; - QToolButton *m_endColorButton; - ClickAndGoWidget *m_ecCnGWidget; + QToolButton *m_mtxColor1Button; + ClickAndGoWidget *m_mtxColor1CnGWidget; + QToolButton *m_mtxColor2Button; + ClickAndGoWidget *m_mtxColor2CnGWidget; + QToolButton *m_mtxColor3Button; + ClickAndGoWidget *m_mtxColor3CnGWidget; + QToolButton *m_mtxColor4Button; + ClickAndGoWidget *m_mtxColor4CnGWidget; + QToolButton *m_mtxColor5Button; + ClickAndGoWidget *m_mtxColor5CnGWidget; QComboBox *m_presetCombo; FlowLayout *m_controlsLayout; @@ -115,23 +127,31 @@ class VCMatrix : public VCWidget /** @reimp */ int sliderValue(); QString animationValue(); - QColor startColor(); - QColor endColor(); + QColor mtxColor(int id); signals: void sliderValueChanged(int value); - void startColorChanged(); - void endColorChanged(); + void mtxColor1Changed(); + void mtxColor2Changed(); + void mtxColor3Changed(); + void mtxColor4Changed(); + void mtxColor5Changed(); void animationValueChanged(QString name); void matrixControlKnobValueChanged(int controlID, int value); public slots: void slotSetSliderValue(int value); void slotSliderMoved(int value); - void slotSetStartColor(QColor color); - void slotStartColorChanged(QRgb color); - void slotSetEndColor(QColor color); - void slotEndColorChanged(QRgb color); + void slotSetColor1(QColor color); + void slotColor1Changed(QRgb color); + void slotSetColor2(QColor color); + void slotColor2Changed(QRgb color); + void slotSetColor3(QColor color); + void slotColor3Changed(QRgb color); + void slotSetColor4(QColor color); + void slotColor4Changed(QRgb color); + void slotSetColor5(QColor color); + void slotColor5Changed(QRgb color); void slotSetAnimationValue(QString name); void slotAnimationChanged(int index); void slotMatrixControlKnobValueChanged(int controlID, int value); diff --git a/ui/src/virtualconsole/vcmatrixcontrol.cpp b/ui/src/virtualconsole/vcmatrixcontrol.cpp index 12472c373f..09f118b904 100644 --- a/ui/src/virtualconsole/vcmatrixcontrol.cpp +++ b/ui/src/virtualconsole/vcmatrixcontrol.cpp @@ -96,15 +96,24 @@ VCMatrixControl::WidgetType VCMatrixControl::widgetType() const { switch(m_type) { - case StartColor: - case EndColor: + case Color1: + case Color2: + case Color3: + case Color4: + case Color5: case Animation: case Image: case Text: - case ResetEndColor: + case Color2Reset: + case Color3Reset: + case Color4Reset: + case Color5Reset: return Button; - case StartColorKnob: - case EndColorKnob: + case Color1Knob: + case Color2Knob: + case Color3Knob: + case Color4Knob: + case Color5Knob: return Knob; } @@ -117,30 +126,48 @@ QString VCMatrixControl::typeToString(VCMatrixControl::ControlType type) { switch(type) { - case StartColor: return "StartColor"; break; - case EndColor: return "EndColor"; break; - case ResetEndColor: return "ResetEndColor"; break; + case Color1: return "Color1"; break; + case Color2: return "Color2"; break; + case Color3: return "Color3"; break; + case Color4: return "Color4"; break; + case Color5: return "Color5"; break; + case Color2Reset: return "ResetColor2"; break; + case Color3Reset: return "ResetColor3"; break; + case Color4Reset: return "ResetColor4"; break; + case Color5Reset: return "ResetColor5"; break; case Animation: return "Animation"; break; case Image: return "Image"; break; case Text: return "Text"; break; - case StartColorKnob: return "StartColorKnob"; break; - case EndColorKnob: return "EndColorKnob"; break; + case Color1Knob: return "Color1Knob"; break; + case Color2Knob: return "Color2Knob"; break; + case Color3Knob: return "Color3Knob"; break; + case Color4Knob: return "Color4Knob"; break; + case Color5Knob: return "Color5Knob"; break; } return QString(); } VCMatrixControl::ControlType VCMatrixControl::stringToType(QString str) { - if (str == "StartColor") return StartColor; - else if (str == "EndColor") return EndColor; - else if (str == "ResetEndColor") return ResetEndColor; + if (str == "Color1") return Color1; + else if (str == "Color2") return Color2; + else if (str == "Color3") return Color3; + else if (str == "Color4") return Color4; + else if (str == "Color5") return Color5; + else if (str == "ResetColor2") return Color2Reset; + else if (str == "ResetColor3") return Color3Reset; + else if (str == "ResetColor4") return Color4Reset; + else if (str == "ResetColor5") return Color5Reset; else if (str == "Animation") return Animation; else if (str == "Image") return Image; else if (str == "Text") return Text; - else if (str == "StartColorKnob") return StartColorKnob; - else if (str == "EndColorKnob") return EndColorKnob; + else if (str == "Color1Knob") return Color1Knob; + else if (str == "Color2Knob") return Color2Knob; + else if (str == "Color3Knob") return Color3Knob; + else if (str == "Color4Knob") return Color4Knob; + else if (str == "Color5Knob") return Color5Knob; else - return StartColor; + return Color1; } bool VCMatrixControl::operator<(VCMatrixControl const& right) const @@ -221,7 +248,16 @@ bool VCMatrixControl::saveXML(QXmlStreamWriter *doc) doc->writeTextElement(KXMLQLCVCMatrixControlType, typeToString(m_type)); - if (m_type == StartColor || m_type == EndColor || m_type == StartColorKnob || m_type == EndColorKnob) + if (m_type == Color1 + || m_type == Color2 + || m_type == Color3 + || m_type == Color4 + || m_type == Color5 + || m_type == Color1Knob + || m_type == Color2Knob + || m_type == Color3Knob + || m_type == Color4Knob + || m_type == Color5Knob) { doc->writeTextElement(KXMLQLCVCMatrixControlColor, m_color.name()); } diff --git a/ui/src/virtualconsole/vcmatrixcontrol.h b/ui/src/virtualconsole/vcmatrixcontrol.h index b71854b730..9033bffab4 100644 --- a/ui/src/virtualconsole/vcmatrixcontrol.h +++ b/ui/src/virtualconsole/vcmatrixcontrol.h @@ -56,14 +56,23 @@ class VCMatrixControl enum ControlType { - StartColor = 0, - EndColor, + Color1 = 0, + Color1Knob, + Color2, + Color2Knob, + Color2Reset, + Color3, + Color3Knob, + Color3Reset, + Color4, + Color4Knob, + Color4Reset, + Color5, + Color5Knob, + Color5Reset, Animation, Image, - Text, - ResetEndColor, - StartColorKnob, - EndColorKnob + Text }; enum WidgetType diff --git a/ui/src/virtualconsole/vcmatrixproperties.cpp b/ui/src/virtualconsole/vcmatrixproperties.cpp index e954f03ad0..dadd1e308c 100644 --- a/ui/src/virtualconsole/vcmatrixproperties.cpp +++ b/ui/src/virtualconsole/vcmatrixproperties.cpp @@ -69,8 +69,11 @@ VCMatrixProperties::VCMatrixProperties(VCMatrix* matrix, Doc* doc) quint32 visibilityMask = m_matrix->visibilityMask(); if (visibilityMask & VCMatrix::ShowSlider) m_sliderCheck->setChecked(true); if (visibilityMask & VCMatrix::ShowLabel) m_labelCheck->setChecked(true); - if (visibilityMask & VCMatrix::ShowStartColorButton) m_startColorButtonCheck->setChecked(true); - if (visibilityMask & VCMatrix::ShowEndColorButton) m_endColorButtonCheck->setChecked(true); + if (visibilityMask & VCMatrix::ShowColor1Button) m_mtxColor1ButtonCheck->setChecked(true); + if (visibilityMask & VCMatrix::ShowColor2Button) m_mtxColor2ButtonCheck->setChecked(true); + if (visibilityMask & VCMatrix::ShowColor3Button) m_mtxColor3ButtonCheck->setChecked(true); + if (visibilityMask & VCMatrix::ShowColor4Button) m_mtxColor4ButtonCheck->setChecked(true); + if (visibilityMask & VCMatrix::ShowColor5Button) m_mtxColor5ButtonCheck->setChecked(true); if (visibilityMask & VCMatrix::ShowPresetCombo) m_presetComboCheck->setChecked(true); /* Custom controls */ @@ -88,16 +91,34 @@ VCMatrixProperties::VCMatrixProperties(VCMatrix* matrix, Doc* doc) connect(m_controlsTree, SIGNAL(itemClicked(QTreeWidgetItem*,int)), this, SLOT(slotTreeSelectionChanged())); - connect(m_addStartColorButton, SIGNAL(clicked()), - this, SLOT(slotAddStartColorClicked())); - connect(m_addStartColorKnobsButton, SIGNAL(clicked()), - this, SLOT(slotAddStartColorKnobsClicked())); - connect(m_addEndColorButton, SIGNAL(clicked()), - this, SLOT(slotAddEndColorClicked())); - connect(m_addEndColorKnobsButton, SIGNAL(clicked()), - this, SLOT(slotAddEndColorKnobsClicked())); - connect(m_addEndColorResetButton, SIGNAL(clicked()), - this, SLOT(slotAddEndColorResetClicked())); + connect(m_addMtxColor1Button, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor1Clicked())); + connect(m_addMtxColor1KnobsButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor1KnobsClicked())); + connect(m_addMtxColor2Button, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor2Clicked())); + connect(m_addMtxColor2KnobsButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor2KnobsClicked())); + connect(m_addMtxColor2ResetButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor2ResetClicked())); + connect(m_addMtxColor3Button, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor3Clicked())); + connect(m_addMtxColor3KnobsButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor3KnobsClicked())); + connect(m_addMtxColor3ResetButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor3ResetClicked())); + connect(m_addMtxColor4Button, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor4Clicked())); + connect(m_addMtxColor4KnobsButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor4KnobsClicked())); + connect(m_addMtxColor4ResetButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor4ResetClicked())); + connect(m_addMtxColor5Button, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor5Clicked())); + connect(m_addMtxColor5KnobsButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor5KnobsClicked())); + connect(m_addMtxColor5ResetButton, SIGNAL(clicked()), + this, SLOT(slotAddMtxColor5ResetClicked())); connect(m_addPresetButton, SIGNAL(clicked()), this, SLOT(slotAddAnimationClicked())); connect(m_addTextButton, SIGNAL(clicked()), @@ -224,33 +245,81 @@ void VCMatrixProperties::updateTree() switch(control->m_type) { - case VCMatrixControl::StartColor: + case VCMatrixControl::Color1: item->setIcon(0, QIcon(":/color.png")); - item->setText(0, tr("Start Color")); + item->setText(0, tr("Color 1")); item->setText(1, control->m_color.name()); item->setBackground(1, QBrush(control->m_color)); break; - case VCMatrixControl::StartColorKnob: + case VCMatrixControl::Color1Knob: item->setIcon(0, QIcon(":/knob.png")); - item->setText(0, tr("Start Color Knob")); + item->setText(0, tr("Color 1 Knob")); item->setText(1, control->m_color.name()); item->setBackground(1, QBrush(control->m_color)); break; - case VCMatrixControl::EndColor: + case VCMatrixControl::Color2: item->setIcon(0, QIcon(":/color.png")); - item->setText(0, tr("End Color")); + item->setText(0, tr("Color 2")); item->setText(1, control->m_color.name()); item->setBackground(1, QBrush(control->m_color)); break; - case VCMatrixControl::EndColorKnob: + case VCMatrixControl::Color2Knob: item->setIcon(0, QIcon(":/knob.png")); - item->setText(0, tr("End Color Knob")); + item->setText(0, tr("Color 2 Knob")); item->setText(1, control->m_color.name()); item->setBackground(1, QBrush(control->m_color)); break; - case VCMatrixControl::ResetEndColor: + case VCMatrixControl::Color2Reset: item->setIcon(0, QIcon(":/fileclose.png")); - item->setText(0, tr("End Color Reset")); + item->setText(0, tr("Color 2 Reset")); + break; + case VCMatrixControl::Color3: + item->setIcon(0, QIcon(":/color.png")); + item->setText(0, tr("Color 3")); + item->setText(1, control->m_color.name()); + item->setBackground(1, QBrush(control->m_color)); + break; + case VCMatrixControl::Color3Knob: + item->setIcon(0, QIcon(":/knob.png")); + item->setText(0, tr("Color 3 Knob")); + item->setText(1, control->m_color.name()); + item->setBackground(1, QBrush(control->m_color)); + break; + case VCMatrixControl::Color3Reset: + item->setIcon(0, QIcon(":/fileclose.png")); + item->setText(0, tr("Color 3 Reset")); + break; + case VCMatrixControl::Color4: + item->setIcon(0, QIcon(":/color.png")); + item->setText(0, tr("Color 4")); + item->setText(1, control->m_color.name()); + item->setBackground(1, QBrush(control->m_color)); + break; + case VCMatrixControl::Color4Knob: + item->setIcon(0, QIcon(":/knob.png")); + item->setText(0, tr("Color 4 Knob")); + item->setText(1, control->m_color.name()); + item->setBackground(1, QBrush(control->m_color)); + break; + case VCMatrixControl::Color4Reset: + item->setIcon(0, QIcon(":/fileclose.png")); + item->setText(0, tr("Color 4 Reset")); + break; + case VCMatrixControl::Color5: + item->setIcon(0, QIcon(":/color.png")); + item->setText(0, tr("Color 5")); + item->setText(1, control->m_color.name()); + item->setBackground(1, QBrush(control->m_color)); + break; + case VCMatrixControl::Color5Knob: + item->setIcon(0, QIcon(":/knob.png")); + item->setText(0, tr("Color 5 Knob")); + item->setText(1, control->m_color.name()); + item->setBackground(1, QBrush(control->m_color)); + break; + case VCMatrixControl::Color5Reset: + item->setIcon(0, QIcon(":/fileclose.png")); + item->setText(0, tr("Color 5 Reset")); break; case VCMatrixControl::Animation: { @@ -332,60 +401,159 @@ void VCMatrixProperties::removeControl(quint8 id) } } -void VCMatrixProperties::slotAddStartColorClicked() +void VCMatrixProperties::slotAddMtxColor1Clicked() +{ + QColor col = QColorDialog::getColor(); + if (col.isValid() == true) + { + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color1; + newControl->m_color = col; + addControl(newControl); + updateTree(); + } +} + +void VCMatrixProperties::slotAddMtxColor1KnobsClicked() +{ + foreach (QColor col, VCMatrixProperties::rgbColorList()) + { + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color1Knob; + newControl->m_color = col; + addControl(newControl); + } + updateTree(); +} + +void VCMatrixProperties::slotAddMtxColor2Clicked() { QColor col = QColorDialog::getColor(); if (col.isValid() == true) { VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); - newControl->m_type = VCMatrixControl::StartColor; + newControl->m_type = VCMatrixControl::Color2; newControl->m_color = col; addControl(newControl); updateTree(); } } -void VCMatrixProperties::slotAddStartColorKnobsClicked() +void VCMatrixProperties::slotAddMtxColor2KnobsClicked() { foreach (QColor col, VCMatrixProperties::rgbColorList()) { VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); - newControl->m_type = VCMatrixControl::StartColorKnob; + newControl->m_type = VCMatrixControl::Color2Knob; newControl->m_color = col; addControl(newControl); } updateTree(); } -void VCMatrixProperties::slotAddEndColorClicked() +void VCMatrixProperties::slotAddMtxColor2ResetClicked() +{ + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color2Reset; + addControl(newControl); + updateTree(); +} + +void VCMatrixProperties::slotAddMtxColor3Clicked() +{ + QColor col = QColorDialog::getColor(); + if (col.isValid() == true) + { + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color3; + newControl->m_color = col; + addControl(newControl); + updateTree(); + } +} + +void VCMatrixProperties::slotAddMtxColor3KnobsClicked() +{ + foreach (QColor col, VCMatrixProperties::rgbColorList()) + { + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color3Knob; + newControl->m_color = col; + addControl(newControl); + } + updateTree(); +} + +void VCMatrixProperties::slotAddMtxColor3ResetClicked() +{ + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color3Reset; + addControl(newControl); + updateTree(); +} + +void VCMatrixProperties::slotAddMtxColor4Clicked() +{ + QColor col = QColorDialog::getColor(); + if (col.isValid() == true) + { + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color4; + newControl->m_color = col; + addControl(newControl); + updateTree(); + } +} + +void VCMatrixProperties::slotAddMtxColor4KnobsClicked() +{ + foreach (QColor col, VCMatrixProperties::rgbColorList()) + { + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color4Knob; + newControl->m_color = col; + addControl(newControl); + } + updateTree(); +} + +void VCMatrixProperties::slotAddMtxColor4ResetClicked() +{ + VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); + newControl->m_type = VCMatrixControl::Color4Reset; + addControl(newControl); + updateTree(); +} + +void VCMatrixProperties::slotAddMtxColor5Clicked() { QColor col = QColorDialog::getColor(); if (col.isValid() == true) { VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); - newControl->m_type = VCMatrixControl::EndColor; + newControl->m_type = VCMatrixControl::Color5; newControl->m_color = col; addControl(newControl); updateTree(); } } -void VCMatrixProperties::slotAddEndColorKnobsClicked() +void VCMatrixProperties::slotAddMtxColor5KnobsClicked() { foreach (QColor col, VCMatrixProperties::rgbColorList()) { VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); - newControl->m_type = VCMatrixControl::EndColorKnob; + newControl->m_type = VCMatrixControl::Color5Knob; newControl->m_color = col; addControl(newControl); } updateTree(); } -void VCMatrixProperties::slotAddEndColorResetClicked() +void VCMatrixProperties::slotAddMtxColor5ResetClicked() { VCMatrixControl *newControl = new VCMatrixControl(++m_lastAssignedID); - newControl->m_type = VCMatrixControl::ResetEndColor; + newControl->m_type = VCMatrixControl::Color5Reset; addControl(newControl); updateTree(); } @@ -434,8 +602,11 @@ void VCMatrixProperties::slotRemoveClicked() VCMatrixControl *control = getSelectedControl(); if (control != NULL) { - if (control->m_type == VCMatrixControl::StartColorKnob - || control->m_type == VCMatrixControl::EndColorKnob) + if (control->m_type == VCMatrixControl::Color1Knob + || control->m_type == VCMatrixControl::Color2Knob + || control->m_type == VCMatrixControl::Color3Knob + || control->m_type == VCMatrixControl::Color4Knob + || control->m_type == VCMatrixControl::Color5Knob) { if (control->m_color == Qt::red) { @@ -522,8 +693,11 @@ void VCMatrixProperties::accept() quint32 visibilityMask = 0; if (m_sliderCheck->isChecked()) visibilityMask |= VCMatrix::ShowSlider; if (m_labelCheck->isChecked()) visibilityMask |= VCMatrix::ShowLabel; - if (m_startColorButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowStartColorButton; - if (m_endColorButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowEndColorButton; + if (m_mtxColor1ButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowColor1Button; + if (m_mtxColor2ButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowColor2Button; + if (m_mtxColor3ButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowColor3Button; + if (m_mtxColor4ButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowColor4Button; + if (m_mtxColor5ButtonCheck->isChecked()) visibilityMask |= VCMatrix::ShowColor5Button; if (m_presetComboCheck->isChecked()) visibilityMask |= VCMatrix::ShowPresetCombo; m_matrix->setVisibilityMask(visibilityMask); diff --git a/ui/src/virtualconsole/vcmatrixproperties.h b/ui/src/virtualconsole/vcmatrixproperties.h index 35f5a02639..6e4356ee8d 100644 --- a/ui/src/virtualconsole/vcmatrixproperties.h +++ b/ui/src/virtualconsole/vcmatrixproperties.h @@ -84,11 +84,20 @@ protected slots: protected slots: void slotTreeSelectionChanged(); - void slotAddStartColorClicked(); - void slotAddStartColorKnobsClicked(); - void slotAddEndColorClicked(); - void slotAddEndColorKnobsClicked(); - void slotAddEndColorResetClicked(); + void slotAddMtxColor1Clicked(); + void slotAddMtxColor1KnobsClicked(); + void slotAddMtxColor2Clicked(); + void slotAddMtxColor2KnobsClicked(); + void slotAddMtxColor2ResetClicked(); + void slotAddMtxColor3Clicked(); + void slotAddMtxColor3KnobsClicked(); + void slotAddMtxColor3ResetClicked(); + void slotAddMtxColor4Clicked(); + void slotAddMtxColor4KnobsClicked(); + void slotAddMtxColor4ResetClicked(); + void slotAddMtxColor5Clicked(); + void slotAddMtxColor5KnobsClicked(); + void slotAddMtxColor5ResetClicked(); void slotAddAnimationClicked(); void slotAddTextClicked(); void slotRemoveClicked(); diff --git a/ui/src/virtualconsole/vcmatrixproperties.ui b/ui/src/virtualconsole/vcmatrixproperties.ui index 10cb36f07f..627a2e2692 100644 --- a/ui/src/virtualconsole/vcmatrixproperties.ui +++ b/ui/src/virtualconsole/vcmatrixproperties.ui @@ -152,20 +152,41 @@ - + - Show Start Color Button + Show Color 1 Button - + - Show End Color Button + Show Color 2 Button + + + Show Color 3 Button + + + + + + + Show Color 4 Button + + + + + + + Show Color 5 Button + + + + Show Preset Combo @@ -275,18 +296,7 @@ - - - - Add end color knobs - - - - :/knob.png:/knob.png - - - - + false @@ -306,35 +316,54 @@ - - + + - Add preset + Add color 1 - :/script.png:/script.png + :/color.png:/color.png - - + + - Add text + Add color 1 knobs - :/fonts.png:/fonts.png + :/knob.png:/knob.png - - + + + + Add color 2 + + + + :/color.png:/color.png + + + + + + + Add color 2 knobs + + + + :/knob.png:/knob.png + + - + - Add end color reset + Add color 2 reset @@ -342,21 +371,43 @@ + + + + Add color 3 + + + + :/color.png:/color.png + + + + + + + Add color 3 knobs + + + + :/knob.png:/knob.png + + + - + - Remove + Add color 3 reset - :/edit_remove.png:/edit_remove.png + :/fileclose.png:/fileclose.png - - + + - Add start color + Add color 4 @@ -364,10 +415,10 @@ - - + + - Add start color knobs + Add color 4 knobs @@ -375,10 +426,21 @@ - - + + - Add end color + Add color 4 reset + + + + :/fileclose.png:/fileclose.png + + + + + + + Add color 5 @@ -386,6 +448,64 @@ + + + + Add color 5 knobs + + + + :/knob.png:/knob.png + + + + + + + Add color 5 reset + + + + :/fileclose.png:/fileclose.png + + + + + + + Add preset + + + + :/script.png:/script.png + + + + + + + Add text + + + + :/fonts.png:/fonts.png + + + + + + + Remove + + + + :/edit_remove.png:/edit_remove.png + + + + + + diff --git a/webaccess/res/virtualconsole.js b/webaccess/res/virtualconsole.js index 5641125ea4..ea4b916f8f 100644 --- a/webaccess/res/virtualconsole.js +++ b/webaccess/res/virtualconsole.js @@ -543,7 +543,6 @@ function updateTime() { } function controlWatch(id, op) { - var obj = document.getElementById(id); var msg = id + "|" + op; websocket.send(msg); } @@ -608,25 +607,58 @@ function setMatrixComboValue(id, comboValue) { combo.value = comboValue; } -function matrixStartColorChange(id) { - var colorObj = document.querySelector("#msc" + id); - var colorMsg = id + "|MATRIX_COLOR_CHANGE|START|" + hexToUint(colorObj.value); +function matrixColor1Change(id) { + var colorObj = document.querySelector("#mc1i" + id); + var colorMsg = id + "|MATRIX_COLOR_CHANGE|COLOR_1|" + hexToUint(colorObj.value); + websocket.send(colorMsg); +} + +function setMatrixColor1Value(id, color) { + var combo = document.querySelector("#mc1i" + id); + combo.value = color; +} + +function matrixColor2Change(id) { + var colorObj = document.querySelector("#mc2i" + id); + var colorMsg = id + "|MATRIX_COLOR_CHANGE|COLOR_2|" + hexToUint(colorObj.value); + websocket.send(colorMsg); +} + +function setMatrixColor2Value(id, color) { + var combo = document.querySelector("#mc2i" + id); + combo.value = color; +} + +function matrixColor3Change(id) { + var colorObj = document.querySelector("#mc3i" + id); + var colorMsg = id + "|MATRIX_COLOR_CHANGE|COLOR_3|" + hexToUint(colorObj.value); + websocket.send(colorMsg); +} + +function setMatrixColor3Value(id, color) { + var combo = document.querySelector("#mc3i" + id); + combo.value = color; +} + +function matrixColor4Change(id) { + var colorObj = document.querySelector("#mc4i" + id); + var colorMsg = id + "|MATRIX_COLOR_CHANGE|COLOR_4|" + hexToUint(colorObj.value); websocket.send(colorMsg); } -function setMatrixStartColorValue(id, color) { - var combo = document.querySelector("#msc" + id); +function setMatrixColor4Value(id, color) { + var combo = document.querySelector("#mc4i" + id); combo.value = color; } -function matrixEndColorChange(id) { - var colorObj = document.querySelector("#mec" + id); - var colorMsg = id + "|MATRIX_COLOR_CHANGE|END|" + hexToUint(colorObj.value); +function matrixColor5Change(id) { + var colorObj = document.querySelector("#mc5i" + id); + var colorMsg = id + "|MATRIX_COLOR_CHANGE|COLOR_5|" + hexToUint(colorObj.value); websocket.send(colorMsg); } -function setMatrixEndColorValue(id, color) { - var combo = document.querySelector("#mec" + id); +function setMatrixColor5Value(id, color) { + var combo = document.querySelector("#mc5i" + id); combo.value = color; } diff --git a/webaccess/res/websocket.js b/webaccess/res/websocket.js index 8b558babf4..130607b541 100644 --- a/webaccess/res/websocket.js +++ b/webaccess/res/websocket.js @@ -91,9 +91,15 @@ function connect() { setCueButtonStyle(msgParams[0], msgParams[2], msgParams[3], msgParams[4], msgParams[5]); } else if (msgParams[1] === "MATRIX_SLIDER") { setMatrixSliderValue(msgParams[0], msgParams[2]); - } else if (msgParams[1] === "MATRIX_START_COLOR") { + } else if (msgParams[1] === "MATRIX_COLOR_1") { setMatrixStartColorValue(msgParams[0], msgParams[2]); - } else if (msgParams[1] === "MATRIX_END_COLOR") { + } else if (msgParams[1] === "MATRIX_COLOR_2") { + setMatrixEndColorValue(msgParams[0], msgParams[2]); + } else if (msgParams[1] === "MATRIX_COLOR_3") { + setMatrixEndColorValue(msgParams[0], msgParams[2]); + } else if (msgParams[1] === "MATRIX_COLOR_4") { + setMatrixEndColorValue(msgParams[0], msgParams[2]); + } else if (msgParams[1] === "MATRIX_COLOR_5") { setMatrixEndColorValue(msgParams[0], msgParams[2]); } else if (msgParams[1] === "MATRIX_COMBO") { setMatrixComboValue(msgParams[0], msgParams[2]); diff --git a/webaccess/src/webaccess.cpp b/webaccess/src/webaccess.cpp index 45466014ca..03105b6095 100644 --- a/webaccess/src/webaccess.cpp +++ b/webaccess/src/webaccess.cpp @@ -889,10 +889,16 @@ void WebAccess::slotHandleWebSocketRequest(QHttpConnection *conn, QString data) matrix->slotSetSliderValue(cmdList[2].toInt()); if (cmdList[1] == "MATRIX_COMBO_CHANGE") matrix->slotSetAnimationValue(cmdList[2]); - if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "START") - matrix->slotStartColorChanged(cmdList[3].toInt()); - if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "END") - matrix->slotEndColorChanged(cmdList[3].toInt()); + if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "COLOR_1") + matrix->slotColor1Changed(cmdList[3].toInt()); + if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "COLOR_2") + matrix->slotColor2Changed(cmdList[3].toInt()); + if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "COLOR_3") + matrix->slotColor3Changed(cmdList[3].toInt()); + if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "COLOR_4") + matrix->slotColor4Changed(cmdList[3].toInt()); + if (cmdList[1] == "MATRIX_COLOR_CHANGE" && cmdList[2] == "COLOR_5") + matrix->slotColor5Changed(cmdList[3].toInt()); if (cmdList[1] == "MATRIX_KNOB") matrix->slotMatrixControlKnobValueChanged(cmdList[2].toInt(), cmdList[3].toInt()); if (cmdList[1] == "MATRIX_PUSHBUTTON") @@ -1922,24 +1928,54 @@ void WebAccess::slotMatrixSliderValueChanged(int value) sendWebSocketMessage(wsMessage); } -void WebAccess::slotMatrixStartColorChanged() +void WebAccess::slotMatrixColor1Changed() { VCMatrix *matrix = qobject_cast(sender()); if (matrix == NULL) return; - QString wsMessage = QString("%1|MATRIX_START_COLOR|%2").arg(matrix->id()).arg(matrix->startColor().name()); - sendWebSocketMessage(wsMessage); + QString wsMessage = QString("%1|MATRIX_COLOR_1|%2").arg(matrix->id()).arg(matrix->mtxColor(0).name()); + sendWebSocketMessage(wsMessage.toUtf8()); } -void WebAccess::slotMatrixEndColorChanged() +void WebAccess::slotMatrixColor2Changed() { VCMatrix *matrix = qobject_cast(sender()); if (matrix == NULL) return; - QString wsMessage = QString("%1|MATRIX_END_COLOR|%2").arg(matrix->id()).arg(matrix->endColor().name()); - sendWebSocketMessage(wsMessage); + QString wsMessage = QString("%1|MATRIX_COLOR_2|%2").arg(matrix->id()).arg(matrix->mtxColor(1).name()); + sendWebSocketMessage(wsMessage.toUtf8()); +} + +void WebAccess::slotMatrixColor3Changed() +{ + VCMatrix *matrix = qobject_cast(sender()); + if (matrix == NULL) + return; + + QString wsMessage = QString("%1|MATRIX_COLOR_3|%2").arg(matrix->id()).arg(matrix->mtxColor(2).name()); + sendWebSocketMessage(wsMessage.toUtf8()); +} + +void WebAccess::slotMatrixColor4Changed() +{ + VCMatrix *matrix = qobject_cast(sender()); + if (matrix == NULL) + return; + + QString wsMessage = QString("%1|MATRIX_COLOR_4|%2").arg(matrix->id()).arg(matrix->mtxColor(3).name()); + sendWebSocketMessage(wsMessage.toUtf8()); +} + +void WebAccess::slotMatrixColor5Changed() +{ + VCMatrix *matrix = qobject_cast(sender()); + if (matrix == NULL) + return; + + QString wsMessage = QString("%1|MATRIX_COLOR_5|%2").arg(matrix->id()).arg(matrix->mtxColor(4).name()); + sendWebSocketMessage(wsMessage.toUtf8()); } void WebAccess::slotMatrixAnimationValueChanged(QString name) @@ -1987,15 +2023,29 @@ QString WebAccess::getMatrixHTML(VCMatrix *matrix) str += "
"+matrix->caption()+"
"; } str += "
"; - if (matrix->visibilityMask() & VCMatrix::Visibility::ShowStartColorButton) { - - str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->startColor().name())+"\" " - "oninput=\"matrixStartColorChange(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixStartColorChange(" + QString::number(matrix->id()) + ");\" " + if (matrix->visibilityMask() & VCMatrix::Visibility::ShowColor1Button) { + str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->mtxColor(0).name())+"\" " + "oninput=\"matrixColor1Change(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixColor1Change(" + QString::number(matrix->id()) + ");\" " + " />"; + } + if (matrix->visibilityMask() & VCMatrix::Visibility::ShowColor2Button) { + str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->mtxColor(1).name())+"\" " + "oninput=\"matrixColor2Change(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixColor2Change(" + QString::number(matrix->id()) + ");\" " + " />"; + } + if (matrix->visibilityMask() & VCMatrix::Visibility::ShowColor3Button) { + str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->mtxColor(2).name())+"\" " + "oninput=\"matrixColor3Change(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixColor3Change(" + QString::number(matrix->id()) + ");\" " " />"; } - if (matrix->visibilityMask() & VCMatrix::Visibility::ShowEndColorButton) { - str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->endColor().name())+"\" " - "oninput=\"matrixEndColorChange(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixEndColorChange(" + QString::number(matrix->id()) + ");\" " + if (matrix->visibilityMask() & VCMatrix::Visibility::ShowColor4Button) { + str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->mtxColor(3).name())+"\" " + "oninput=\"matrixColor4Change(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixColor4Change(" + QString::number(matrix->id()) + ");\" " + " />"; + } + if (matrix->visibilityMask() & VCMatrix::Visibility::ShowColor5Button) { + str += "id())+"\" class=\"vMatrix\" value=\""+(matrix->mtxColor(4).name())+"\" " + "oninput=\"matrixColor5Change(" + QString::number(matrix->id()) + ");\" ontouchmove=\"matrixColor5Change(" + QString::number(matrix->id()) + ");\" " " />"; } str += "
"; @@ -2014,18 +2064,45 @@ QString WebAccess::getMatrixHTML(VCMatrix *matrix) str += "
"; for (int i = 0; i < customControls.length(); i++) { VCMatrixControl *control = customControls[i]; - if (control->m_type == VCMatrixControl::StartColor) { + if (control->m_type == VCMatrixControl::Color1) { str += "
m_color.name())+"; margin-right: 4px; margin-bottom: 4px; \" " - "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">S
"; - } else if (control->m_type == VCMatrixControl::EndColor) { + "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">1
"; + } else if (control->m_type == VCMatrixControl::Color2) { str += "
m_color.name())+"; margin-right: 4px; margin-bottom: 4px; \" " - "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">E
"; - } else if (control->m_type == VCMatrixControl::ResetEndColor) { - QString btnLabel = tr("End Color Reset"); + "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">2"; + } else if (control->m_type == VCMatrixControl::Color2Reset) { + QString btnLabel = tr("Color 2 Reset"); str += "
m_id))+")\">"+btnLabel+"
"; + } else if (control->m_type == VCMatrixControl::Color3) { + str += "
m_color.name())+"; margin-right: 4px; margin-bottom: 4px; \" " + "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">3
"; + } else if (control->m_type == VCMatrixControl::Color3Reset) { + QString btnLabel = tr("Color 3 Reset"); + str += "
m_id))+")\">"+btnLabel+"
"; + } else if (control->m_type == VCMatrixControl::Color4) { + str += "
m_color.name())+"; margin-right: 4px; margin-bottom: 4px; \" " + "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">4
"; + } else if (control->m_type == VCMatrixControl::Color4Reset) { + QString btnLabel = tr("Color 4 Reset"); + str += "
m_id))+")\">"+btnLabel+"
"; + } else if (control->m_type == VCMatrixControl::Color5) { + str += "
m_color.name())+"; margin-right: 4px; margin-bottom: 4px; \" " + "onclick=\"wcMatrixPushButtonClicked("+(QString::number(control->m_id))+")\">5
"; + } else if (control->m_type == VCMatrixControl::Color5Reset) { + QString btnLabel = tr("Color 5 Reset"); + str += "
m_id))+")\">"+btnLabel+"
"; } else if (control->m_type == VCMatrixControl::Animation || control->m_type == VCMatrixControl::Text) { QString btnLabel = control->m_resource; @@ -2045,10 +2122,14 @@ QString WebAccess::getMatrixHTML(VCMatrix *matrix) str += "
m_id))+")\">"+btnLabel+"
"; - } else if (control->m_type == VCMatrixControl::StartColorKnob || control->m_type == VCMatrixControl::EndColorKnob) { + } else if (control->m_type == VCMatrixControl::Color1Knob + || control->m_type == VCMatrixControl::Color2Knob + || control->m_type == VCMatrixControl::Color3Knob + || control->m_type == VCMatrixControl::Color4Knob + || control->m_type == VCMatrixControl::Color5Knob) { KnobWidget *knob = qobject_cast(matrix->getWidget(control)); QString slID = QString::number(control->m_id); - QColor color = control->m_type == VCMatrixControl::StartColorKnob ? control->m_color : control->m_color.darker(250); + QColor color = control->m_type == VCMatrixControl::Color1Knob ? control->m_color : control->m_color.darker(250); str += "
"; str += "
"; diff --git a/webaccess/src/webaccess.h b/webaccess/src/webaccess.h index 42f385fb08..495f4b11b9 100644 --- a/webaccess/src/webaccess.h +++ b/webaccess/src/webaccess.h @@ -106,8 +106,11 @@ protected slots: void slotFramePageChanged(int pageNum); void slotFrameDisableStateChanged(bool disable); void slotMatrixSliderValueChanged(int value); - void slotMatrixStartColorChanged(); - void slotMatrixEndColorChanged(); + void slotMatrixColor1Changed(); + void slotMatrixColor2Changed(); + void slotMatrixColor3Changed(); + void slotMatrixColor4Changed(); + void slotMatrixColor5Changed(); void slotMatrixAnimationValueChanged(QString name); void slotMatrixControlKnobValueChanged(int controlID, int value);