本页内容

JavaScript 宿主环境

QML 提供了一个专为编写 QML 应用程序量身定制的 JavaScript 宿主环境。该环境与浏览器提供的宿主环境或 Node.js 等服务器端 JavaScript 环境有所不同。例如,QML 不提供浏览器环境中常见的 `window ` 对象或 `DOM API `。

共同基础

与浏览器或服务器端 JavaScript 环境类似,QML Runtime 实现了ECMAScript 语言规范标准。这使得可以访问该标准定义的所有内置类型和函数,例如 Object、Array 和 Math。QML Runtime 实现了该标准的第 7 版。

QML Runtime 还实现了空值合并(?? )(自 Qt 5.15 起)和可选链式调用(?. )(自 Qt 6.2 起)。

此外,自 Qt 6.8 起,还支持数值字面量分隔符(即1_000_000 中的下划线)。

QML 文档中并未明确记录标准的 ECMAScript 内置函数。有关其使用的更多信息,请参阅 ECMA-262 第 7 版标准,或众多在线 JavaScript 参考和教程网站之一,例如W3Schools JavaScript 参考(JavaScript 对象参考部分)。 许多网站侧重于浏览器中的 JavaScript,因此在某些情况下,您可能需要仔细核对规范,以确定某个函数或对象是标准 ECMAScript 的一部分,还是特定于浏览器环境。 以上述 W3Schools 链接为例,JavaScript Objects Reference 部分通常涵盖标准内容,而Browser Objects Reference 和HTML DOM Objects Reference 部分则属于浏览器特有的内容(因此不适用于 QML)。

类型注释与断言

QML 文档中的函数声明可以且应当包含类型注解。类型注解附加在参数声明和函数本身之后,用于标注返回类型。以下函数接受一个int 和一个string 参数,并返回一个QtObject :

function doThings(a: int, b: string) : QtObject { ... }

类型注释有助于 Qt Creator 和qmllint等工具理解代码并提供更准确的诊断。此外,它们还使函数在 C++ 中更易于使用。更多信息请参阅《从 C++ 与 QML 对象交互》。

此规则的例外是分配给信号处理程序的函数:在此处,为避免与信号类型的潜在不匹配,禁止使用类型注释。这不会给工具带来问题,因为信号本身已经提供了必要的信息。

注意:在 QML 中,枚举不是类型,因此不能用作类型注释。应改用其底层的数值类型(int 或 double)。

类型断言(有时称为as-cast)也可用于将对象强制转换为另一种对象类型。如果对象确实是给定类型,则类型断言返回该对象本身;否则,返回null 。在下面的代码片段中,我们在访问parent 对象的特定成员之前,先断言该对象是Rectangle 。

Item {
    property color parentColor: (parent as Rectangle)?.color || "red"
}

可选链式调用(?. )可避免在父对象实际上并非矩形时抛出异常。在这种情况下,“red”会被选定为parentColor 。

自 Qt 6.7 起,调用函数时始终强制执行类型注解。值会根据需要被强制转换为所需类型。 此前,解释器和 JIT 编译器会忽略类型注解,但在编译为 C++ 时,qmlcachegen和qmlsc会强制执行这些注解。这可能会导致某些特殊情况下的行为差异。若要显式请求解释器和 JIT 采用旧的行为,可在 QML 文档中添加以下内容:

pragma FunctionSignatureBehavior: Ignored

QML 全局对象

QML JavaScript 主机环境实现了多个主机对象和函数,详情请参阅QML 全局对象文档。

无论是否导入了任何模块,这些宿主对象和函数始终可用。

JavaScript 对象和函数

QML 引擎支持的 JavaScript 对象、函数和属性的列表,请参见《JavaScript 对象和函数列表》。

请注意,QML 对原生对象进行了以下修改:

  • 在 `String ` 原型中添加了 `arg() ` 函数。
  • 在 `Date` 和 `Number` 原型中添加了支持区域设置的转换函数。

另请参阅:

  • Number- JavaScript 中的 Number 对象
  • Date- JavaScript 中的 Date 对象
  • XMLHttpRequest- JavaScript 中的 XMLHttpRequest 对象

此外,QML 还扩展了 `instanceof` 函数的行为,使其能够对 QML 类型进行类型检查。这意味着您可以使用它来验证一个变量是否确实是您预期的类型,例如:

var v = something();
if (!v instanceof Item) {
    throw new TypeError("I need an Item type!");
}

...

JavaScript 环境限制

QML 对 JavaScript 代码实施了以下限制:

  • 在.qml 文件中编写的JavaScript代码无法修改全局对象。而.js文件中的JavaScript代码可以修改全局对象,且这些修改在导入时对.qml文件是可见的。

    在 QML 中,全局对象是常量——现有属性无法被修改或删除,也不允许创建新属性。

    大多数 JavaScript 程序不会有意修改全局对象。但是,JavaScript 自动创建未声明的变量属于对全局对象的隐式修改,在 QML 中是被禁止的。

    假设a 变量在作用域链中不存在,则以下代码在QML中是非法的:

    // Illegal modification of undeclared variable
    a = 1;
    for (var ii = 1; ii < 10; ++ii)
        a = a * ii;
    console.log("Result: " + a);

    只需稍作修改,即可将其转换为以下合法代码:

    var a = 1;
    for (var ii = 1; ii < 10; ++ii)
        a = a * ii;
    console.log("Result: " + a);

    任何尝试修改全局对象的行为——无论是隐式还是显式——都会引发异常。如果未被捕获,系统将输出警告信息,其中包含出错代码所在的文件和行号。

  • 全局代码在受限的作用域内运行。

    在启动过程中,如果某个 QML 文件包含了一个带有“全局”代码的外部 JavaScript 文件,则该代码将在一个仅包含该外部文件本身和全局对象的作用域中执行。也就是说,它将无法访问通常可以访问的 QML 对象和属性。

    仅访问脚本局部变量的全局代码是被允许的。以下是一个有效全局代码的示例。

    var colors = [ "red", "blue", "green", "orange", "purple" ];

    访问 QML 对象的全局代码将无法正常运行。

    // Invalid global code - the "rootObject" variable is undefined
    var initialPosition = { rootObject.x, rootObject.y }

    由于 QML 环境尚未完全建立,因此存在此限制。若要在环境设置完成后运行代码,请参阅《应用程序启动代码中的 JavaScript》。

  • 在大多数上下文中,this 的值在 QML 中未定义。

    在从 JavaScript 绑定属性时,支持 `this ` 关键字。在 QML 绑定表达式、QML 信号处理程序以及 QML 声明的函数中,`this ` 指代作用域对象。在所有其他情况下,`this ` 的值在 QML 中未定义。

    若要引用特定对象,请使用 `id`。例如:

    Item {
        width: 200; height: 100
        function mouseAreaClicked(area) {
            console.log("Clicked in area at: " + area.x + ", " + area.y);
        }
        // This will pass area to the function
        MouseArea {
            id: area
            y: 50; height: 50; width: 200
            onClicked: mouseAreaClicked(area)
        }
    }

另请参阅 “作用域与命名解析”。

© 2026 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.