55static bool beginDeferred(QQmlEnginePrivate *enginePriv,
const QQmlProperty &property, QQmlComponentPrivate::DeferredState *deferredState)
57 QObject *object = property.object();
58 QQmlData *ddata = QQmlData::get(object);
59 Q_ASSERT(!ddata->deferredData.isEmpty());
61 if (!ddata->propertyCache)
62 ddata->propertyCache = QQmlMetaType::propertyCache(object->metaObject());
64 int propertyIndex = property.index();
65 int wasInProgress = enginePriv->inProgressCreations;
68
69
70
71 auto bindingStatus = QtPrivate::suspendCurrentBindingStatus();
72 auto cleanup = qScopeGuard([&](){
73 QtPrivate::restoreBindingStatus(bindingStatus);
76 for (
auto dit = ddata->deferredData.rbegin(); dit != ddata->deferredData.rend(); ++dit) {
77 QQmlData::DeferredData *deferData = *dit;
79 auto bindings = deferData->bindings;
80 auto range = bindings.equal_range(propertyIndex);
81 if (range.first == bindings.end())
84 QQmlComponentPrivate::ConstructionState state;
85 state.setCompletePending(
true);
87 QQmlContextData *creationContext =
nullptr;
89 state.initCreator(deferData->context->parent(), deferData->compilationUnit, creationContext, deferData->inlineComponentName);
91 enginePriv->inProgressCreations++;
93 std::deque<
const QV4::CompiledData::Binding *> reversedBindings;
94 std::copy(range.first, range.second,
std::front_inserter(reversedBindings));
95 state.creator()->beginPopulateDeferred(deferData->context);
96 for (
const QV4::CompiledData::Binding *binding : reversedBindings)
97 state.creator()->populateDeferredBinding(property, deferData->deferredIdx, binding);
98 state.creator()->finalizePopulateDeferred();
99 state.appendCreatorErrors();
101 deferredState->push_back(
std::move(state));
105 cancelDeferred(ddata, propertyIndex);
109 return enginePriv->inProgressCreations > wasInProgress;
113 QQuickUntypedDeferredPointer *delegate,
bool isOwnState, QQmlEngine *engine)
115 QQmlData *data = QQmlData::get(object);
118 if (data && !data->deferredData.isEmpty() && !data->wasDeleted(object) && (data->context || engine)) {
119 QQmlEnginePrivate *ep = QQmlEnginePrivate::get(
120 data->context && data->context->engine() ? data->context->engine() : engine);
122 QQmlComponentPrivate::DeferredState state;
123 if (beginDeferred(ep, QQmlProperty(object, property), &state)) {
124 if (QQmlComponentPrivate::DeferredState *delegateState = delegate->deferredState())
125 delegateState->swap(state);
126 }
else if (isOwnState) {
127 delegate->clearDeferredState();
131 data->releaseDeferredData();
132 }
else if (isOwnState) {
133 delegate->clearDeferredState();
144void completeDeferred(QObject *object,
const QString &property, QQuickUntypedDeferredPointer *delegate,
148 QQmlComponentPrivate::DeferredState *state = delegate->deferredState();
152 QQmlData *data = QQmlData::get(object);
153 if (data && !data->wasDeleted(object)) {
155
156
157
158 auto bindingStatus = QtPrivate::suspendCurrentBindingStatus();
159 auto cleanup = qScopeGuard([&](){
160 QtPrivate::restoreBindingStatus(bindingStatus);
163 QQmlComponentPrivate::DeferredState localState =
std::move(*state);
164 delegate->clearDeferredState();
165 QQmlEnginePrivate *ep = QQmlEnginePrivate::get(
166 data->context && data->context->engine() ? data->context->engine() : engine);
167 QQmlComponentPrivate::completeDeferred(ep, &localState);
169 delegate->clearDeferredState();