From beaafc4344c4b7e63921d711bf6f66a7f1634ca8 Mon Sep 17 00:00:00 2001 From: Till Theato Date: Thu, 8 Sep 2011 15:18:40 +0000 Subject: [PATCH] Add an easier way to handle simple parameter updates. (see frei0r.levels.js) svn path=/trunk/kdenlive/; revision=5864 --- effects/update/frei0r.levels.js | 31 ++++++----------- src/documentvalidator.cpp | 62 ++++++++++++++++++++++++++------- src/documentvalidator.h | 7 ++++ 3 files changed, 66 insertions(+), 34 deletions(-) diff --git a/effects/update/frei0r.levels.js b/effects/update/frei0r.levels.js index 279ae2fa..36d5d052 100644 --- a/effects/update/frei0r.levels.js +++ b/effects/update/frei0r.levels.js @@ -1,23 +1,12 @@ -function update(serviceVersion, effectVersion, effectString) { - var locale = new QLocale(); - var doc = new QDomDocument(); - doc.setContent(effectString); - for (var node = doc.documentElement().firstChild(); !node.isNull(); node = node.nextSibling()) { - var effectparam = node.toElement(); - if (effectparam.attribute("name") == "Channel" || effectparam.attribute("name") == "Histogram position") { - if (serviceVersion < effectVersion) { - // downgrade - if (effectVersion > 0.1) { - effectparam.firstChild().toText().setData(locale.toString(effectparam.text() * 10)); - } - } else { - // upgrade - if (effectVersion < 0.2) { - effectparam.firstChild().toText().setData(locale.toString(effectparam.text() / 10.)); - } - } - } - } - return doc.toString(); +var update = new Object(); + +update["Channel"] = new Array(new Array(0.2, function(v, d) { return this.upd1(v, d); })); +update["Histogram position"] = update["Channel"]; + +function upd1(value, isDowngrade) { + if (isDowngrade) + return value * 10; + else + return value / 10.; } diff --git a/src/documentvalidator.cpp b/src/documentvalidator.cpp index 52bb70ca..3722a0d9 100644 --- a/src/documentvalidator.cpp +++ b/src/documentvalidator.cpp @@ -1031,7 +1031,7 @@ bool DocumentValidator::isModified() const void DocumentValidator::updateEffects() { - // WARNING: order by findDirs will determine which js file to use (in case multiple for the same filter exist) + // WARNING: order by findDirs will determine which js file to use (in case multiple scripts for the same filter exist) QMap paths; #if QT_VERSION >= 0x040700 QMap scripts; @@ -1087,25 +1087,61 @@ void DocumentValidator::updateEffects() scripts.insert(effectId, scriptProgram); } - QDomDocument scriptDoc; - scriptDoc.appendChild(scriptDoc.importNode(effect, true)); - QScriptEngine scriptEngine; scriptEngine.importExtension("qt.core"); scriptEngine.importExtension("qt.xml"); scriptEngine.evaluate(scripts.value(effectId)); - QString effectString = scriptEngine.globalObject().property("update").call(QScriptValue(), QScriptValueList() << serviceVersion << effectVersion << scriptDoc.toString()).toString(); - - if (!effectString.isEmpty()) { - scriptDoc.setContent(effectString); - QDomNode updatedEffect = effect.ownerDocument().importNode(scriptDoc.documentElement(), true); - effect.parentNode().replaceChild(updatedEffect, effect); - // TODO: set version to avoid dependency on latest MLT - m_modified = true; + QScriptValue updateRules = scriptEngine.globalObject().property("update"); + if (!updateRules.isValid()) + continue; + if (updateRules.isFunction()) { + QDomDocument scriptDoc; + scriptDoc.appendChild(scriptDoc.importNode(effect, true)); + + QString effectString = updateRules.call(QScriptValue(), QScriptValueList() << serviceVersion << effectVersion << scriptDoc.toString()).toString(); + + if (!effectString.isEmpty()) { + scriptDoc.setContent(effectString); + QDomNode updatedEffect = effect.ownerDocument().importNode(scriptDoc.documentElement(), true); + effect.parentNode().replaceChild(updatedEffect, effect); + m_modified = true; + } + } else { + m_modified = updateEffectParameters(effect.childNodes(), &updateRules, serviceVersion, effectVersion); } } } } } - +bool DocumentValidator::updateEffectParameters(QDomNodeList parameters, const QScriptValue* updateRules, const double serviceVersion, const double effectVersion) +{ + bool updated = false; + bool isDowngrade = serviceVersion < effectVersion; + for (int i = 0; i < parameters.count(); ++i) { + QDomElement parameter = parameters.at(i).toElement(); + QScriptValue rules = updateRules->property(parameter.attribute("name")); + if (rules.isValid() && rules.isArray()) { + int rulesCount = rules.property("length").toInt32(); + if (isDowngrade) { + // start with the highest version and downgrade step by step + for (int j = rulesCount - 1; j >= 0; --j) { + double version = rules.property(j).property(0).toNumber(); + if (version <= effectVersion && version > serviceVersion) { + parameter.firstChild().setNodeValue(rules.property(j).property(1).call(QScriptValue(), QScriptValueList() << parameter.text() << isDowngrade).toString()); + updated = true; + } + } + } else { + for (int j = 0; j < rulesCount; ++j) { + double version = rules.property(j).property(0).toNumber(); + if (version > effectVersion && version <= serviceVersion) { + parameter.firstChild().setNodeValue(rules.property(j).property(1).call(QScriptValue(), QScriptValueList() << parameter.text() << isDowngrade).toString()); + updated = true; + } + } + } + } + } + return updated; +} diff --git a/src/documentvalidator.h b/src/documentvalidator.h index dd15c1e3..5708f5fc 100644 --- a/src/documentvalidator.h +++ b/src/documentvalidator.h @@ -24,6 +24,9 @@ #include #include +class QScriptValue; + + class DocumentValidator { @@ -39,7 +42,11 @@ private: bool upgrade(double version, const double currentVersion); QStringList getInfoFromEffectName(const QString oldName); QString colorToString(const QColor& c); + /** @brief Updates effects that were created using a different version of the underlaying filter than the one installed. */ void updateEffects(); + /** @brief Updates the parameters according to the updateRules. + * @see the related in README in effects/update */ + bool updateEffectParameters(QDomNodeList parameters, const QScriptValue *updateRules, const double serviceVersion, const double effectVersion); }; #endif -- 2.39.2