QtScript:如何重新加载当前脚本?

时间:2010-01-11 09:37:17

标签: qt qtscript

QScriptEngine有evaluate()方法,可用于加载脚本,执行它并从已加载的脚本运行指定的函数。但是如何清除当前脚本并加载新脚本呢?例如,我使用evaluate()从文件加载脚本,然后使用evaluate()来获取脚本函数并调用它们。但是,如何清除当前脚本并从另一个文件加载新脚本呢?删除和创建QScriptEngine似乎是一个解决方案,但它喜欢在GUI线程中创建(由于QScriptEngineDebugger),而所有脚本操作都在单独的线程中执行。那么在不重新创建QScriptEngine对象的情况下清除当前脚本是否有任何方法?

3 个答案:

答案 0 :(得分:7)

engine.pushContext();
engine.evaluate("...");
engine.popContext();
engine.pushContext();
engine.evaluate("...");
engine.popContext();

在评估脚本之前调用pushContext()并在评估新脚本之前调用popContext()将有效地清除所有脚本数据。

答案 1 :(得分:2)

我遇到了这个问题,想要改善地狱之眼的答案(顺便说一下,谢谢!),因为它遗漏了一个重要的细节。

我会使用我的问题的缩减版本,我正在重用QScriptEngine对象,并希望确保评估之间不会遗漏任何内容。特别是,我想确保没有为onEquipped实体调用"RC Helicopter Controller"函数,因为它在配备时不会更改其精灵,因此不会定义onEquipped函数在其脚本文件中。只需使用pushContext()popContext()即可完全调用任何内容:

#include <QtCore>
#include <QtScript>

int main(int argc, char *argv[])
{
    QCoreApplication app(argc, argv);

    QScriptEngine scriptEngine;

    scriptEngine.pushContext();
    scriptEngine.evaluate("function onEquipped(entity) { print('changing pixmap to equipped sprite for ' + entity); }").toString();
    QScriptValueList args;
    args << QScriptValue("Pistol");
    scriptEngine.globalObject().property("onEquipped").call(QScriptValue(), args);
    scriptEngine.popContext();

    scriptEngine.pushContext();
    args.clear();
    args << QScriptValue("RC Helicopter Controller");
    scriptEngine.globalObject().property("onEquipped").call(QScriptValue(), args);
    scriptEngine.popContext();

    return 0;
}

函数调用似乎发生在原始上下文中,而不是当前上下文中。在查看QScriptEngine::pushContext()文档后,我发现您需要明确使用从其返回的上下文,并且最重要的是,您必须使用QScriptEngine::activationContext()来访问任何变量:

#include <QtCore>
#include <QtScript>

int main(int argc, char *argv[])
{
    QCoreApplication app(argc, argv);

    QScriptEngine scriptEngine;

    scriptEngine.pushContext();
    scriptEngine.evaluate("function onEquipped(entity) { print('changing pixmap to equipped sprite for ' + entity); }").toString();
    QScriptValueList args;
    args << QScriptValue("Pistol");
    scriptEngine.currentContext()->activationObject().property("onEquipped").call(QScriptValue(), args);
    scriptEngine.popContext();

    scriptEngine.pushContext();
    args.clear();
    args << QScriptValue("RC Helicopter Controller");
    scriptEngine.currentContext()->activationObject().property("onEquipped").call(QScriptValue(), args);
    scriptEngine.popContext();

    return 0;
}
  

将pixmap更改为Pistol的装备精灵

答案 2 :(得分:0)

您可以尝试将空对象设置为http://qt.nokia.com/doc/4.6/qscriptengine.html#setGlobalObject

也许这样有用。