105 QNapi::Object windowStageOrWindowObject,
108 auto subWindowOptionsObject =
110 windowStageOrWindowObject.Env(),
112 {
"title", subWindowOptions.windowTitle},
113 {
"decorEnabled", subWindowOptions.decorEnabled},
114 {
"isModal", subWindowOptions.isModal},
116 "windowRect", makeRectObject(windowStageOrWindowObject.Env(), subWindowOptions.windowRect)
120 return windowStageOrWindowObject.evalToPromiseOrRejectOnThrow(
121 "createSubWindowWithOptions(*)",
122 {windowName, subWindowOptionsObject});
137 auto sharedContext = QtOhos::moveToSharedPtr(std::move(subWindowOnAppearCbCtx));
142 auto xComponent = takeNodeXComponentFromRegistryOrFail(sharedContext->xComponentId);
144 sharedContext->resultConsumer(
146 QOhosWindowProxyData {
147 .qAbilityPeer = sharedContext->qAbilityPeer,
148 .jsWindow = std::move(sharedContext->windowObject),
149 .windowProxyType = sharedContext->windowProxyType,
150 .nodeXComponent = std::make_shared<QXComponentNode>(xComponent),
151 .jsKeepAliveData = QtOhos::moveToSharedPtr(std::move(sharedContext->localStorageObj)),
152 .owningQWindowRef = sharedContext->owningQWindowRef,
155 sharedContext.reset();
167 auto *env = jsState.env();
169 auto localStorage = makeLocalStorage(jsState);
170 auto subWindowNativeNodeCreateInfo = QNapi::makeObject(
173 {
"xComponentId", createInfo.xComponentId.toNapiValue(env)},
176 [xComponentId = createInfo.xComponentId.stringId()]() {
178 "WindowNativeNodeCreateInfo.onDisAppear() called from JS for xComponentId='%s'",
179 xComponentId.c_str());
184 makeSubWindowOnAppearCallbackHandler(SubWindowOnAppearContext {
185 .xComponentId = createInfo.xComponentId,
186 .localStorageObj = Napi::Persistent(localStorage),
187 .windowObject = Napi::Persistent(createInfo.windowObject),
188 .resultConsumer = std::move(createInfo.resultConsumer),
189 .qAbilityPeer = std::move(createInfo.qAbilityPeer),
190 .windowProxyType = createInfo.windowProxyType,
191 .owningQWindowRef = createInfo.owningQWindowRef,
196 localStorage.eval(
"setOrCreate(*)", {
"createInfo", subWindowNativeNodeCreateInfo});
204 struct LoadWindowContentsArgs
206 QNapi::Reference<QNapi::Object> window;
207 QNapi::Reference<QNapi::Object> localStorage;
208 std::string contentPagePath;
211 return !context.disableWindowFocusableBeforeLoadContentHack
212 ? loadWindowContents(windowObject, context.localStorage, context.contentPagePath)
213 : windowObject.evalToPromiseOrRejectOnThrow(
"setWindowFocusable(*)", {
false})
214 .withContext(LoadWindowContentsArgs {
215 .window = Napi::Persistent(windowObject),
216 .localStorage = Napi::Persistent(context.localStorage),
217 .contentPagePath = context.contentPagePath,
219 .onThenWithContext([](LoadWindowContentsArgs &windowLocalStoragePair) {
220 return loadWindowContents(
221 windowLocalStoragePair.window.Value(),
222 windowLocalStoragePair.localStorage.Value(),
223 windowLocalStoragePair.contentPagePath);
232 QOhosConsumer<QtOhos::JsState &, QOhosWindowProxyData> resultConsumer)
234 auto abilityStartupOptions =
238 {
"windowLeft", createInfo.frameGeometry.x()},
239 {
"windowTop", createInfo.frameGeometry.y()},
240 {
"windowWidth", createInfo.frameGeometry.width()},
241 {
"windowHeight", createInfo.frameGeometry.height()},
245 auto fullscreenWindowMode = jsState.eval<QNapi::Number>(
246 "@ohos.app.ability.AbilityConstant.WindowMode.WINDOW_MODE_FULLSCREEN");
247 abilityStartupOptions.set(
"windowMode", fullscreenWindowMode);
250 jsState.startNewQAbilityInstance(
252 abilityStartupOptions,
253 [qWindowRef = createInfo.qWindowRef,
254 windowId = createInfo.windowId,
256 auto createInfo = QOhosWindowProxyExistingMainWindowCreateInfo {
257 .qWindowRef = qWindowRef,
258 .qAbilityInstanceId = qAbilityPeer->instanceId(),
259 .windowId = windowId,
262 makeWindowProxyDataForExistingMainWindowInJsThread(
263 jsState, createInfo,
std::move(resultConsumer));
270 QOhosConsumer<QtOhos::JsState &, QOhosWindowProxyData> resultConsumer)
273 getQAbilityPeerByInstanceIdOrFail(jsState, createInfo.qAbilityInstanceId));
274 if (!optQUiAbilityPeer) {
275 qOhosReportFatalErrorAndAbort(
276 "%s Attempting to make window proxy for main window for ability without windowStage. This is most likely a programming error. Aborting...",
279 optQUiAbilityPeer->setQWindow(jsState.env(), createInfo.qWindowRef);
281 auto window = optQUiAbilityPeer->windowStage().eval<QNapi::Object>(
"getMainWindowSync()");
283 auto nodeXComponent = takeNodeXComponentFromRegistryOrFail(nativeNodeXComponentId);
287 QOhosWindowProxyData {
288 .qAbilityPeer = optQUiAbilityPeer,
289 .jsWindow = Napi::Persistent(window),
290 .windowProxyType = WindowProxyType::MainWindow,
291 .nodeXComponent = std::make_shared<QXComponentNode>(nodeXComponent),
292 .jsKeepAliveData =
nullptr,
293 .owningQWindowRef = createInfo.qWindowRef,
315 QNapi::Object windowStageOrWindowObject,
317 QOhosConsumer<QtOhos::JsState &, QOhosWindowProxyData> resultConsumer)
319 auto xComponentId = QXComponentId::createForNativeNodeSubWindow(createInfo.windowId);
322 bool disableWindowFocusableBeforeLoadContentHack;
325 QtOhos::QObjectThreadSafeRef owningQWindowRef;
328 auto qAbilityPeer = getQAbilityPeerByInstanceIdOrFail(jsState, createInfo.qAbilityInstanceId);
336 auto subWindowCreationPromise = [&]() -> QNapi::Promise {
337 if (!QOhosDeviceInfo::isPhone()) {
338 return createSubWindowWithOptions(
339 windowStageOrWindowObject,
342 .windowTitle = createInfo.windowTitle,
343 .decorEnabled = createInfo.decorEnabled,
344 .isModal = createInfo.modal,
345 .windowRect = createInfo.windowRect,
350 auto optQUiAbilityPeer = QtOhos::QUiAbilityPeer::tryCastFromQAbilityPeerOrNull(qAbilityPeer);
351 if (!optQUiAbilityPeer) {
352 qOhosReportFatalErrorAndAbort(
353 "%s sub window creation requires an ability with a windowStage. Aborting...",
356 return createSubWindow(optQUiAbilityPeer->windowStage(), windowName);
359 subWindowCreationPromise
360 .withContext(Context {
362 .xComponentId = xComponentId,
363 .qAbilityPeer = qAbilityPeer,
364 .owningQWindowRef = createInfo.window,
366 .onThenWithContext([resultConsumer = std::move(resultConsumer)](
const QtOhos::
CallbackInfo &cbInfo, Context &context)
mutable {
367 auto windowObject = cbInfo.getFirstArg<QNapi::Object>(Q_FUNC_INFO);
369 auto localStorage = makeLocalStorageForWindow(
371 LocalStorageForWindowCreateInfo {
372 .xComponentId = context.xComponentId,
373 .windowObject = windowObject,
374 .resultConsumer = std::move(resultConsumer),
375 .qAbilityPeer = context.qAbilityPeer,
376 .windowProxyType = WindowProxyType::SubWindow,
377 .owningQWindowRef = context.owningQWindowRef,
380 return onWindowCreatedLoadWindowContents(
381 cbInfo.jsState(), windowObject,
382 OnWindowCreatedLoadWindowContentsContext {
383 .disableWindowFocusableBeforeLoadContentHack = context.disableWindowFocusableBeforeLoadContentHack,
384 .contentPagePath =
"pages/SubWindowNativeNode",
385 .localStorage = localStorage,
389 QtOhos::logJsCallbackError(cbInfo,
"sub window creation failed");
390 qOhosReportFatalErrorAndAbort(
391 "Failed to create subwindow for windowId='%s'",
392 windowId.toStdString().c_str());
398 QOhosConsumer<QtOhos::JsState &, QOhosWindowProxyData> resultConsumer)
400 auto xComponentId = QXComponentId::createForNativeNodeFloatWindow(createInfo.internalWindowId);
403 auto configurationObject = QNapi::makeObject(
407 {
"name", makeOhosUniqueSystemWindowName(createInfo.internalWindowId)},
408 {
"windowType", jsState.eval<QNapi::Number>(
"@ohos.window.WindowType.TYPE_FLOAT")},
409 {
"ctx", qAbilityPeer->qAbility().get<QNapi::Object>(
"context")},
416 QtOhos::QObjectThreadSafeRef owningQWindowRef;
420 .evalToPromiseOrRejectOnThrow(
"@ohos.window.createWindow(*)", {configurationObject})
421 .withContext(Context {
422 .xComponentId = xComponentId,
423 .qAbilityPeer = qAbilityPeer,
424 .owningQWindowRef = createInfo.qWindowRef,
426 .onThenWithContext([resultConsumer = std::move(resultConsumer)](
const QtOhos::
CallbackInfo &cbInfo, Context &context)
mutable {
427 auto windowObject = cbInfo.getFirstArg<QNapi::Object>(Q_FUNC_INFO);
429 auto localStorage = makeLocalStorageForWindow(
431 LocalStorageForWindowCreateInfo {
432 .xComponentId = context.xComponentId,
433 .windowObject = windowObject,
434 .resultConsumer = std::move(resultConsumer),
435 .qAbilityPeer = context.qAbilityPeer,
436 .windowProxyType = WindowProxyType::FloatWindow,
437 .owningQWindowRef = context.owningQWindowRef,
440 return onWindowCreatedLoadWindowContents(
441 cbInfo.jsState(), windowObject,
442 OnWindowCreatedLoadWindowContentsContext {
443 .disableWindowFocusableBeforeLoadContentHack =
false,
444 .contentPagePath =
"pages/FloatWindowNativeNode",
445 .localStorage = localStorage,
448 .onCatch([internalWindowId = createInfo.internalWindowId](
const QtOhos::
CallbackInfo &cbInfo) {
449 QtOhos::logJsCallbackError(cbInfo,
"Failed to create TYPE_FLOAT window");
450 qOhosReportFatalErrorAndAbort(
451 "Failed to create TYPE_FLOAT window for windowId='%s'",
452 internalWindowId.toStdString().c_str());
QNapi::Reference< QNapi::Object > windowObject
QOhosConsumer< QtOhos::JsState &, QOhosWindowProxyData > resultConsumer
std::shared_ptr< QtOhos::QAbilityPeer > qAbilityPeer
QNapi::Reference< QNapi::Object > localStorageObj