QQmlIncubator Class

QQmlIncubator 类允许异步创建 QML 对象。更多

头文件: #include <QQmlIncubator>
CMake: find_package(Qt6 REQUIRED COMPONENTS Qml)
target_link_libraries(mytarget PRIVATE Qt6::Qml)
qmake: QT += qml

公共类型

enum IncubationMode { Asynchronous, AsynchronousIfNested, Synchronous }
enum Status { Null, Ready, Loading, Error }

公共函数

QQmlIncubator(QQmlIncubator::IncubationMode mode = Asynchronous)
void clear()
QList<QQmlError> errors() const
void forceCompletion()
QQmlIncubator::IncubationMode incubationMode() const
bool isError() const
bool isLoading() const
bool isNull() const
bool isReady() const
QObject *object() const
void setInitialProperties(const QVariantMap &initialProperties)
QQmlIncubator::Status status() const

受保护函数

virtual void setInitialState(QObject *object)
virtual void statusChanged(QQmlIncubator::Status status)

详细说明

创建 QML 对象(如视图中的委托或应用程序中的新页面)需要花费大量时间,尤其是在资源有限的移动设备上。当应用程序直接使用QQmlComponent::create() 时,QML 对象实例是同步创建的,这取决于对象的复杂程度,可能会导致应用程序出现明显的停顿或卡顿。

使用 QQmlIncubator 可对 QML 对象的创建进行更多控制,包括允许利用应用程序空闲时间异步创建。下面的例子展示了 QQmlIncubator 的一个简单用法。

// Initialize the incubator
QQmlIncubator incubator;
component->create(incubator);

让孵化器运行一段时间(通常是把控制权返回给事件循环),然后轮询它。稍后有多种方法返回孵化器。您可能想连接到QQuickWindow 发送的信号之一,或者专门为此运行一个QTimer 。您可能还需要该对象用于某些特定目的,并在出现该目的时轮询培养器。

// Poll the incubator
if (incubator.isReady()) {
    QObject *object = incubator.object();
    // Use created object
}

异步孵化器由QQmlEngine 上设置的QQmlIncubationController 控制,它可让引擎知道应用程序何时空闲,何时应处理孵化对象。如果未在QQmlEngine 上设置孵化控制器,则QQmlIncubator 会同步创建对象,与指定的IncubationMode 无关。默认情况下,不设置孵化控制器。不过,QQuickViewQQuickWindowQQuickWidget 都在各自的QQmlEngine上设置了孵化控制器。这些孵化控制器会在视图渲染时,在多个帧中间隔孵化。

QQmlIncubator 支持三种孵化模式:

  • 同步 创建是同步进行的。也就是说,一旦QQmlComponent::create() 调用返回,孵化器就会处于错误或就绪状态。与直接使用QQmlComponent 上的同步创建方法相比,同步孵化器并无实际优势,但同步和异步创建使用相同的 API 可以简化应用程序的实现。
  • 异步(默认) 假设在QQmlEngine 上设置了 QQmlIncubatorController,创建将以异步方式进行。

    孵化器将保持加载状态,直到创建完成或出现错误。statusChanged() 回调可用于通知状态变化。

    应用程序应使用异步孵化模式创建不需要立即使用的对象。例如,ListView 类型使用异步孵化来创建在滚动列表时略微偏离屏幕的对象。如果在异步创建过程中需要立即创建对象,可以调用QQmlIncubator::forceCompletion() 方法同步完成创建过程。

  • AsynchronousIfNested 如果是嵌套异步创建的一部分,创建将以异步方式进行;如果不是嵌套异步创建的一部分,创建将以同步方式进行。

    在大多数情况下,如果 QML 组件希望获得同步实例化的外观,就应该使用这种模式。

    最好用一个例子来解释这种模式。当ListView 类型首次创建时,它需要用一组初始委托来填充自己。如果ListView 的高度为 400 像素,而每个委托的高度为 100 像素,则需要创建四个初始委托实例。如果ListView 使用的是异步孵化模式,那么ListView 将始终为空,然后,在某个时候,四个初始项目就会出现。

    相反,如果ListView 使用同步孵化模式,虽然行为正确,但可能会给应用程序带来卡顿。由于 QML 必须停止并同步实例化ListView 的委托,如果ListView 是异步实例化的 QML 组件的一部分,异步实例化的好处就会大打折扣。

    AsynchronousIfNested 模式解决了这个问题。通过使用AsynchronousIfNested ,如果ListView 本身已经是异步实例化的一部分,那么ListView 委托就会被异步实例化,否则就会被同步实例化。在嵌套异步实例化的情况下,外层异步实例化要等到所有嵌套实例化完成后才能完成。这样可以确保在外部异步实例化完成时,内部项目(如ListView )已经完成了初始委托的加载。

    使用同步实例化模式几乎总是不正确的--如果元素或组件希望获得同步实例化的外观,但又不想在应用程序中引入冻结或停顿的缺点,则应使用AsynchronousIfNested 实例化模式。

成员类型文档

enum QQmlIncubator::IncubationMode

指定孵化器的运行模式。无论孵化模式如何,如果QQmlEngine 没有设置QQmlIncubationController ,则QQmlIncubator 将同步运行。

常数说明
QQmlIncubator::Asynchronous0对象将以异步方式创建。
QQmlIncubator::AsynchronousIfNested1如果对象是在已经属于异步创建的上下文中创建的,则该孵化器将加入现有孵化并异步执行。在现有的孵化和此孵化都完成之前,现有的孵化不会成为就绪状态。否则,孵化将同步执行。
QQmlIncubator::Synchronous2对象将同步创建。

enum QQmlIncubator::Status

指定QQmlIncubator 的状态。

常数说明
QQmlIncubator::Null0孵化未开始。调用QQmlComponent::create() 开始孵化。
QQmlIncubator::Ready1对象已完全创建,可通过调用object() 访问。
QQmlIncubator::Loading2对象正在创建中。
QQmlIncubator::Error3出现错误。可通过调用errors() 访问错误信息。

成员函数文档

QQmlIncubator::QQmlIncubator(QQmlIncubator::IncubationMode mode = Asynchronous)

用指定的mode

void QQmlIncubator::clear()

清除培养箱。任何正在进行的孵化都会中止。如果孵化箱处于就绪状态,则不会删除已创建的对象。

QList<QQmlError> QQmlIncubator::errors() const

返回孵化对象时遇到的错误列表。

void QQmlIncubator::forceCompletion()

强制任何正在进行的孵化同步完成。该调用返回后,孵化器将不再处于加载状态。

QQmlIncubator::IncubationMode QQmlIncubator::incubationMode() const

返回传递给QQmlIncubator 构造函数的孵化模式。

bool QQmlIncubator::isError() const

如果孵化器的status() 为 Error,则返回 true。

bool QQmlIncubator::isLoading() const

如果孵化器的status() 正在加载,则返回 true。

bool QQmlIncubator::isNull() const

如果孵化器的status() 为空,则返回 true。

bool QQmlIncubator::isReady() const

如果孵化器的status() 已就绪,则返回 true。

QObject *QQmlIncubator::object() const

如果状态为就绪,则返回孵化对象,否则返回 0。

void QQmlIncubator::setInitialProperties(const QVariantMap &initialProperties)

存储从属性名称到初始值的映射(包含在initialProperties 中),孵化组件将使用该映射进行初始化。

另请参见 QQmlComponent::setInitialProperties

[virtual protected] void QQmlIncubator::setInitialState(QObject *object)

object 首次创建后,但在评估复杂属性绑定和调用QQmlParserStatus::componentComplete() 之前(如果适用)调用。这相当于QQmlComponent::beginCreate() 和QQmlComponent::completeCreate() 之间的一点,可用于为对象的属性分配初始值。

默认实现不做任何操作。

注意: 简单绑定(如数字字面)会在调用 setInitialState() 之前进行评估。绑定分为简单绑定和复杂绑定是故意未加说明的,在不同版本的 Qt 中可能会有所变化,这取决于您是否使用qmlcachegen 以及如何使用。在调用 setInitialState() 之前或之后,都不应依赖于对任何特定绑定进行评估。例如,MyType.EnumValue这样的常量表达式可能在编译时被识别为常量表达式,也可能作为绑定被延迟执行。对于-(5)"a" + " 常量字符串 "这样的常量表达式也是如此。

QQmlIncubator::Status QQmlIncubator::status() const

返回孵化器的当前状态。

[virtual protected] void QQmlIncubator::statusChanged(QQmlIncubator::Status status)

孵化器状态发生变化时调用。status 是新状态。

默认实现不做任何操作。

© 2025 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.