• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022-2023 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "adapter/ohos/entrance/subwindow/subwindow_ohos.h"
17 
18 #include "dm/display_manager.h"
19 #include "interfaces/inner_api/ace/viewport_config.h"
20 #include "render_service_client/core/ui/rs_surface_node.h"
21 #include "window.h"
22 
23 #include "adapter/ohos/entrance/ace_application_info.h"
24 #include "base/geometry/rect.h"
25 #include "base/log/log_wrapper.h"
26 #include "core/components/root/root_element.h"
27 #include "core/components_ng/base/frame_node.h"
28 #include "core/components_ng/base/ui_node.h"
29 #include "core/components_ng/property/property.h"
30 #include "core/components_v2/inspector/inspector_constants.h"
31 #include "core/pipeline_ng/pipeline_context.h"
32 #if defined(ENABLE_ROSEN_BACKEND) and !defined(UPLOAD_GPU_DISABLED)
33 #include "adapter/ohos/entrance/ace_rosen_sync_task.h"
34 #endif
35 
36 #include "bundlemgr/bundle_mgr_interface.h"
37 #include "iservice_registry.h"
38 
39 #include "adapter/ohos/entrance/ace_container.h"
40 #include "adapter/ohos/entrance/ace_view_ohos.h"
41 #include "adapter/ohos/entrance/dialog_container.h"
42 #include "adapter/ohos/entrance/ui_content_impl.h"
43 #include "adapter/ohos/entrance/utils.h"
44 #include "base/log/frame_report.h"
45 #include "base/utils/system_properties.h"
46 #include "base/utils/utils.h"
47 #include "core/common/connect_server_manager.h"
48 #include "core/common/container_scope.h"
49 #include "core/common/frontend.h"
50 #include "core/common/hdc_register.h"
51 #include "core/common/text_field_manager.h"
52 #include "core/components/bubble/bubble_component.h"
53 #include "core/components/popup/popup_component.h"
54 #include "core/components_ng/pattern/menu/menu_view.h"
55 #include "core/components_ng/pattern/menu/wrapper/menu_wrapper_pattern.h"
56 #include "core/components_ng/pattern/overlay/overlay_manager.h"
57 #include "core/components_ng/render/adapter/rosen_render_context.h"
58 #include "core/components_ng/render/adapter/rosen_window.h"
59 #include "frameworks/bridge/common/utils/engine_helper.h"
60 #include "frameworks/bridge/declarative_frontend/declarative_frontend.h"
61 #ifdef OS_ACCOUNT_EXISTS
62 #include "os_account_manager.h"
63 #endif
64 #include "system_ability_definition.h"
65 
66 namespace OHOS::Ace {
67 namespace {
68 const Rect MIN_WINDOW_HOT_AREA = Rect(0.0f, 0.0f, 1.0f, 1.0f);
69 #ifndef NG_BUILD
70 constexpr int32_t PLATFORM_VERSION_TEN = 10;
71 #endif
72 } // namespace
73 
74 int32_t SubwindowOhos::id_ = 0;
75 static std::atomic<int32_t> gToastDialogId = 0;
76 
77 class SwitchFreeMultiWindowListener : public OHOS::Rosen::ISwitchFreeMultiWindowListener {
78 public:
SwitchFreeMultiWindowListener(int32_t instanceId)79     explicit SwitchFreeMultiWindowListener(int32_t instanceId) : instanceId_(instanceId) {}
80     ~SwitchFreeMultiWindowListener() = default;
81 
OnSwitchFreeMultiWindow(bool enable)82     void OnSwitchFreeMultiWindow(bool enable)
83     {
84         TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Window status changes, freeMultiWindow is %{public}d", enable);
85         auto container = Platform::AceContainer::GetContainer(instanceId_);
86         CHECK_NULL_VOID(container);
87         auto parentContainerId = SubwindowManager::GetInstance()->GetParentContainerId(instanceId_);
88         auto subWindow = SubwindowManager::GetInstance()->GetSubwindow(parentContainerId);
89         CHECK_NULL_VOID(subWindow);
90 
91         auto taskExecutor = container->GetTaskExecutor();
92         CHECK_NULL_VOID(taskExecutor);
93         ContainerScope scope(instanceId_);
94         taskExecutor->PostTask(
95             [subWindow, enable]() {
96                 CHECK_NULL_VOID(subWindow);
97                 subWindow->OnFreeMultiWindowSwitch(enable);
98             },
99             TaskExecutor::TaskType::UI, "ArkUIFreeMultiWindowSwitch");
100     }
101 
102 private:
103     int32_t instanceId_ = -1;
104 };
105 
CreateSubwindow(int32_t instanceId)106 RefPtr<Subwindow> Subwindow::CreateSubwindow(int32_t instanceId)
107 {
108     return AceType::MakeRefPtr<SubwindowOhos>(instanceId);
109 }
110 
SubwindowOhos(int32_t instanceId)111 SubwindowOhos::SubwindowOhos(int32_t instanceId) : windowId_(id_), parentContainerId_(instanceId)
112 {
113     SetSubwindowId(windowId_);
114     id_++;
115     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Create Subwindow, subwindow id %{public}d, container id %{public}d", windowId_,
116         instanceId);
117 }
118 
GetToastRosenType(bool IsSceneBoardEnabled)119 Rosen::WindowType SubwindowOhos::GetToastRosenType(bool IsSceneBoardEnabled)
120 {
121     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW,
122         "SubwindowOhos::GetToastRosenType, windowType: %{public}d, IsSceneBoardEnabled: %{public}d",
123         GetToastWindowType(), IsSceneBoardEnabled);
124     if (GetToastWindowType() == ToastWindowType::TOAST_IN_TYPE_APP_SUB_WINDOW) {
125         if (!IsSceneBoardEnabled) {
126             return Rosen::WindowType::WINDOW_TYPE_TOAST;
127         }
128         return Rosen::WindowType::WINDOW_TYPE_APP_SUB_WINDOW;
129     } else if (GetToastWindowType() ==  ToastWindowType::TOAST_IN_TYPE_SYSTEM_SUB_WINDOW) {
130         return Rosen::WindowType::WINDOW_TYPE_TOAST;
131     } else if (GetToastWindowType() == ToastWindowType::TOAST_IN_TYPE_SYSTEM_FLOAT) {
132         return Rosen::WindowType::WINDOW_TYPE_SYSTEM_FLOAT;
133     }
134     return Rosen::WindowType::WINDOW_TYPE_TOAST;
135 }
136 
SetToastWindowOption(RefPtr<Platform::AceContainer> & parentContainer,OHOS::sptr<OHOS::Rosen::WindowOption> & windowOption,const Rosen::WindowType & toastWindowType,uint32_t mainWindowId)137 void SetToastWindowOption(RefPtr<Platform::AceContainer>& parentContainer,
138     OHOS::sptr<OHOS::Rosen::WindowOption>& windowOption,
139     const Rosen::WindowType& toastWindowType, uint32_t mainWindowId)
140 {
141     if (toastWindowType == Rosen::WindowType::WINDOW_TYPE_APP_SUB_WINDOW) {
142         windowOption->SetWindowMode(Rosen::WindowMode::WINDOW_MODE_FLOATING);
143         windowOption->AddWindowFlag(Rosen::WindowFlag::WINDOW_FLAG_IS_TOAST);
144     }
145     windowOption->SetWindowType(toastWindowType);
146     if (parentContainer->IsUIExtensionWindow()) {
147         auto parentPipeline = parentContainer->GetPipelineContext();
148         CHECK_NULL_VOID(parentPipeline);
149         auto hostWindowId = parentPipeline->GetFocusWindowId();
150         windowOption->SetIsUIExtensionSubWindowFlag(true);
151         windowOption->SetParentId(hostWindowId);
152     } else {
153         windowOption->SetParentId(mainWindowId);
154     }
155 }
156 
SetUIExtensionSubwindowFlag(OHOS::sptr<OHOS::Rosen::WindowOption> & windowOption,bool isAppSubwindow,sptr<OHOS::Rosen::Window> & parentWindow)157 void SetUIExtensionSubwindowFlag(OHOS::sptr<OHOS::Rosen::WindowOption>& windowOption,
158     bool isAppSubwindow, sptr<OHOS::Rosen::Window>& parentWindow)
159 {
160     if (isAppSubwindow && (parentWindow->GetIsUIExtensionFlag() ||
161         parentWindow->GetIsUIExtensionSubWindowFlag())) {
162         windowOption->SetIsUIExtensionSubWindowFlag(true);
163     }
164 }
165 
InitContainer()166 void SubwindowOhos::InitContainer()
167 {
168     auto parentContainer = Platform::AceContainer::GetContainer(parentContainerId_);
169     CHECK_NULL_VOID(parentContainer);
170     auto parentPipeline = parentContainer->GetPipelineContext();
171     CHECK_NULL_VOID(parentPipeline);
172     if (!window_) {
173         OHOS::sptr<OHOS::Rosen::WindowOption> windowOption = new OHOS::Rosen::WindowOption();
174         auto parentWindowName = parentContainer->GetWindowName();
175         auto parentWindowId = parentContainer->GetWindowId();
176         sptr<OHOS::Rosen::Window> parentWindow = parentContainer->GetUIWindow(parentContainerId_);
177         CHECK_NULL_VOID(parentWindow);
178         parentWindow_ = parentWindow;
179         auto windowType = parentWindow->GetType();
180         std::string windowTag = "";
181         bool isAppSubwindow = false;
182         if (IsSystemTopMost()) {
183             windowOption->SetWindowType(Rosen::WindowType::WINDOW_TYPE_SYSTEM_TOAST);
184         } else if (GetAboveApps()) {
185             auto toastWindowType = GetToastRosenType(parentContainer->IsSceneBoardEnabled());
186             isAppSubwindow = toastWindowType == Rosen::WindowType::WINDOW_TYPE_APP_SUB_WINDOW;
187             auto mainWindowId = GetMainWindowId();
188             SetToastWindowOption(parentContainer, windowOption, toastWindowType, mainWindowId);
189             windowTag = "TOPMOST_TOAST_";
190         } else if (parentContainer->IsScenceBoardWindow() || windowType == Rosen::WindowType::WINDOW_TYPE_DESKTOP) {
191             windowOption->SetWindowType(Rosen::WindowType::WINDOW_TYPE_SYSTEM_FLOAT);
192         } else if (windowType == Rosen::WindowType::WINDOW_TYPE_UI_EXTENSION) {
193             auto hostWindowId = parentPipeline->GetFocusWindowId();
194             windowOption->SetExtensionTag(true);
195             windowOption->SetWindowType(Rosen::WindowType::WINDOW_TYPE_APP_SUB_WINDOW);
196             windowOption->SetParentId(hostWindowId);
197             SetUIExtensionHostWindowId(hostWindowId);
198             isAppSubwindow = true;
199         } else if (windowType >= Rosen::WindowType::SYSTEM_WINDOW_BASE) {
200             windowOption->SetWindowType(Rosen::WindowType::WINDOW_TYPE_SYSTEM_SUB_WINDOW);
201             windowOption->SetParentId(parentWindowId);
202         } else {
203             windowOption->SetWindowType(Rosen::WindowType::WINDOW_TYPE_APP_SUB_WINDOW);
204             windowOption->SetParentId(parentWindowId);
205             isAppSubwindow = true;
206         }
207         auto defaultDisplay = Rosen::DisplayManager::GetInstance().GetDefaultDisplay();
208         if (!defaultDisplay) {
209             TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "DisplayManager GetDefaultDisplay failed");
210         }
211         CHECK_NULL_VOID(defaultDisplay);
212         windowOption->SetWindowRect({ 0, 0, defaultDisplay->GetWidth(), defaultDisplay->GetHeight() });
213         windowOption->SetWindowMode(Rosen::WindowMode::WINDOW_MODE_FLOATING);
214         SetUIExtensionSubwindowFlag(windowOption, isAppSubwindow, parentWindow);
215         window_ = OHOS::Rosen::Window::Create("ARK_APP_SUBWINDOW_" + windowTag + parentWindowName +
216             std::to_string(windowId_), windowOption, parentWindow->GetContext());
217         if (!window_) {
218             SetIsRosenWindowCreate(false);
219             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Window create failed");
220         }
221         CHECK_NULL_VOID(window_);
222     }
223     std::string url = "";
224     auto subSurface = window_->GetSurfaceNode();
225     CHECK_NULL_VOID(subSurface);
226     subSurface->SetShadowElevation(0.0f);
227     window_->NapiSetUIContent(url, nullptr, nullptr, Rosen::BackupAndRestoreType::NONE);
228     childContainerId_ = SubwindowManager::GetInstance()->GetContainerId(window_->GetWindowId());
229     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "Window child containerId : %{public}d", childContainerId_);
230     SubwindowManager::GetInstance()->AddParentContainerId(childContainerId_, parentContainerId_);
231 
232     auto container = Platform::AceContainer::GetContainer(childContainerId_);
233     if (!container) {
234         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Window get ace container failed");
235     }
236     CHECK_NULL_VOID(container);
237 
238     auto parentToken = parentContainer->GetToken();
239     container->SetToken(parentToken);
240     container->SetWindowId(window_->GetWindowId());
241     container->SetParentId(parentContainerId_);
242     container->GetSettings().SetUsingSharedRuntime(true);
243     container->SetSharedRuntime(parentContainer->GetSharedRuntime());
244     container->Initialize();
245     container->SetAssetManager(parentContainer->GetAssetManager());
246     container->SetResourceConfiguration(parentContainer->GetResourceConfiguration());
247     container->SetPackagePathStr(parentContainer->GetPackagePathStr());
248     container->SetHapPath(parentContainer->GetHapPath());
249     container->SetIsSubContainer(true);
250     container->InitializeSubContainer(parentContainerId_);
251     SetIsRosenWindowCreate(true);
252     ViewportConfig config;
253     // create ace_view
254     auto aceView =
255         Platform::AceViewOhos::CreateView(childContainerId_, false, container->GetSettings().usePlatformAsUIThread);
256     Platform::AceViewOhos::SurfaceCreated(aceView, window_);
257 
258     int32_t width = static_cast<int32_t>(window_->GetRequestRect().width_);
259     int32_t height = static_cast<int32_t>(window_->GetRequestRect().height_);
260     auto density = parentPipeline->GetDensity();
261     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
262         "UIContent Initialize: width: %{public}d, height: %{public}d, density: %{public}lf", width, height, density);
263 
264     Ace::Platform::UIEnvCallback callback = nullptr;
265     // set view
266     Platform::AceContainer::SetView(aceView, density, width, height, window_, callback);
267     Platform::AceViewOhos::SurfaceChanged(aceView, width, height, config.Orientation());
268 
269     auto uiContentImpl = reinterpret_cast<UIContentImpl*>(window_->GetUIContent());
270     CHECK_NULL_VOID(uiContentImpl);
271     uiContentImpl->SetFontScaleAndWeightScale(container, childContainerId_);
272     freeMultiWindowListener_ = new SwitchFreeMultiWindowListener(childContainerId_);
273     window_->RegisterSwitchFreeMultiWindowListener(freeMultiWindowListener_);
274 
275 #ifndef NG_BUILD
276 #ifdef ENABLE_ROSEN_BACKEND
277     if (SystemProperties::GetRosenBackendEnabled()) {
278         rsUiDirector = OHOS::Rosen::RSUIDirector::Create();
279         if (rsUiDirector != nullptr) {
280             rsUiDirector->SetRSSurfaceNode(window_->GetSurfaceNode());
281             auto context = DynamicCast<PipelineContext>(container->GetPipelineContext());
282             if (context != nullptr) {
283                 context->SetRSUIDirector(rsUiDirector);
284             }
285             rsUiDirector->Init();
286             TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "UIContent Init Rosen Backend");
287         }
288     }
289 #endif
290 #endif
291 #ifdef NG_BUILD
292     auto subPipelineContextNG = AceType::DynamicCast<NG::PipelineContext>(
293         Platform::AceContainer::GetContainer(childContainerId_)->GetPipelineContext());
294     CHECK_NULL_VOID(subPipelineContextNG);
295     subPipelineContextNG->SetParentPipeline(parentContainer->GetPipelineContext());
296     subPipelineContextNG->SetupSubRootElement();
297     subPipelineContextNG->SetMinPlatformVersion(parentPipeline->GetMinPlatformVersion());
298     subPipelineContextNG->SetDragNodeGrayscale(parentPipeline->GetDragNodeGrayscale());
299     subPipelineContextNG->SetMaxAppFontScale(parentPipeline->GetMaxAppFontScale());
300     subPipelineContextNG->SetFollowSystem(parentPipeline->IsFollowSystem());
301     subPipelineContextNG->SetFontScale(parentPipeline->GetFontScale());
302 #else
303     if (container->IsCurrentUseNewPipeline()) {
304         auto subPipelineContextNG = AceType::DynamicCast<NG::PipelineContext>(
305             Platform::AceContainer::GetContainer(childContainerId_)->GetPipelineContext());
306         CHECK_NULL_VOID(subPipelineContextNG);
307         subPipelineContextNG->SetParentPipeline(parentContainer->GetPipelineContext());
308         subPipelineContextNG->SetupSubRootElement();
309         subPipelineContextNG->SetMinPlatformVersion(parentPipeline->GetMinPlatformVersion());
310         subPipelineContextNG->SetKeyboardAnimationConfig(parentPipeline->GetKeyboardAnimationConfig());
311         subPipelineContextNG->SetDragNodeGrayscale(parentPipeline->GetDragNodeGrayscale());
312         subPipelineContextNG->SetMaxAppFontScale(parentPipeline->GetMaxAppFontScale());
313         subPipelineContextNG->SetFollowSystem(parentPipeline->IsFollowSystem());
314         subPipelineContextNG->SetFontScale(parentPipeline->GetFontScale());
315         return;
316     }
317     auto subPipelineContext =
318         DynamicCast<PipelineContext>(Platform::AceContainer::GetContainer(childContainerId_)->GetPipelineContext());
319     CHECK_NULL_VOID(subPipelineContext);
320     subPipelineContext->SetParentPipeline(parentContainer->GetPipelineContext());
321     subPipelineContext->SetupSubRootElement();
322     subPipelineContext->SetMinPlatformVersion(parentPipeline->GetMinPlatformVersion());
323     subPipelineContext->SetKeyboardAnimationConfig(parentPipeline->GetKeyboardAnimationConfig());
324     subPipelineContext->SetDragNodeGrayscale(parentPipeline->GetDragNodeGrayscale());
325     subPipelineContext->SetMaxAppFontScale(parentPipeline->GetMaxAppFontScale());
326     subPipelineContext->SetFollowSystem(parentPipeline->IsFollowSystem());
327     subPipelineContext->SetFontScale(parentPipeline->GetFontScale());
328 #endif
329 }
330 
GetChildPipelineContext() const331 RefPtr<PipelineBase> SubwindowOhos::GetChildPipelineContext() const
332 {
333     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
334     CHECK_NULL_RETURN(aceContainer, nullptr);
335     return aceContainer->GetPipelineContext();
336 }
337 
GetInitToastDelayTask(const NG::ToastInfo & toastInfo)338 std::function<void()> SubwindowOhos::GetInitToastDelayTask(const NG::ToastInfo& toastInfo)
339 {
340     return [toastInfo]() {
341         int32_t posX = 0;
342         int32_t posY = 0;
343         int32_t width = 0;
344         int32_t height = 0;
345         float density = 1.0f;
346         auto subwindowOhos =
347             AceType::DynamicCast<SubwindowOhos>(SubwindowManager::GetInstance()->GetCurrentDialogWindow());
348         CHECK_NULL_VOID(subwindowOhos);
349         subwindowOhos->GetToastDialogWindowProperty(width, height, posX, posY, density);
350         auto childContainerId = subwindowOhos->GetChildContainerId();
351         auto window = Platform::DialogContainer::GetUIWindow(childContainerId);
352         auto dialogWindow = subwindowOhos->GetDialogWindow();
353         if (!dialogWindow || !window || !subwindowOhos->IsToastWindow()) {
354             bool ret = subwindowOhos->InitToastDialogWindow(width, height, posX, posY, true);
355             if (!ret) {
356                 TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog window failed");
357                 return;
358             }
359             ret = subwindowOhos->InitToastDialogView(width, height, density);
360             if (!ret) {
361                 TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog view failed");
362                 return;
363             }
364             subwindowOhos->SetIsToastWindow(true);
365         }
366         childContainerId = subwindowOhos->GetChildContainerId();
367         ContainerScope scope(childContainerId);
368         subwindowOhos->UpdateAceView(width, height, density, childContainerId);
369         TAG_LOGD(AceLogTag::ACE_SUB_WINDOW,
370             "update ace view width : %{public}d,  height : %{public}d, density : %{public}f,childContainerId : "
371             "%{public}d",
372             width, height, density, childContainerId);
373         auto container = Platform::DialogContainer::GetContainer(childContainerId);
374         CHECK_NULL_VOID(container);
375         container->SetFontScaleAndWeightScale(childContainerId);
376         auto ret = subwindowOhos->InitToastServiceConfig();
377         if (!ret) {
378             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast service conf failed");
379         }
380         Platform::DialogContainer::ShowToastDialogWindow(childContainerId, posX, posY, width, height, true);
381         Platform::DialogContainer::ShowToast(childContainerId, toastInfo.message, toastInfo.duration, toastInfo.bottom);
382     };
383 }
384 
ResizeWindow()385 void SubwindowOhos::ResizeWindow()
386 {
387     auto defaultDisplay = Rosen::DisplayManager::GetInstance().GetDefaultDisplay();
388     CHECK_NULL_VOID(defaultDisplay);
389     CHECK_NULL_VOID(window_);
390     auto ret = window_->Resize(defaultDisplay->GetWidth(), defaultDisplay->GetHeight());
391     if (ret != Rosen::WMError::WM_OK) {
392         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Resize window by default display failed with errCode: %{public}d",
393             static_cast<int32_t>(ret));
394         return;
395     }
396     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
397         "SubwindowOhos window rect is resized to x: %{public}d, y: %{public}d, width: %{public}u, height: %{public}u",
398         window_->GetRect().posX_, window_->GetRect().posY_, window_->GetRect().width_, window_->GetRect().height_);
399 }
400 
ResizeWindowForMenu()401 void SubwindowOhos::ResizeWindowForMenu()
402 {
403     CHECK_NULL_VOID(window_);
404     auto container = Container::Current();
405     CHECK_NULL_VOID(container);
406     auto containerId = Container::CurrentId();
407     if (container->IsSubContainer()) {
408         containerId = SubwindowManager::GetInstance()->GetParentContainerId(containerId);
409         container = Platform::AceContainer::GetContainer(containerId);
410         CHECK_NULL_VOID(container);
411     }
412     auto pipeline = DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
413     CHECK_NULL_VOID(pipeline);
414     auto theme = pipeline->GetTheme<SelectTheme>();
415     CHECK_NULL_VOID(theme);
416     Rosen::WMError ret;
417     if (!(theme->GetExpandDisplay() || container->IsFreeMultiWindow()) &&
418         SystemProperties::GetDeviceOrientation() == DeviceOrientation::LANDSCAPE) {
419         if (container->IsUIExtensionWindow()) {
420             auto subwindow = SubwindowManager::GetInstance()->GetSubwindow(containerId);
421             CHECK_NULL_VOID(subwindow);
422             auto rect = subwindow->GetUIExtensionHostWindowRect();
423             ret = window_->Resize(rect.Width(), rect.Height());
424         } else {
425             auto rect = pipeline->GetDisplayWindowRectInfo();
426             ret = window_->Resize(rect.Width(), rect.Height());
427         }
428     } else {
429         auto displayId = window_->GetDisplayId();
430         auto defaultDisplay = Rosen::DisplayManager::GetInstance().GetDisplayById(displayId);
431         CHECK_NULL_VOID(defaultDisplay);
432         ret = window_->Resize(defaultDisplay->GetWidth(), defaultDisplay->GetHeight());
433     }
434     if (ret != Rosen::WMError::WM_OK) {
435         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Resize window by default display failed with errCode: %{public}d",
436             static_cast<int32_t>(ret));
437         return;
438     }
439     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
440         "SubwindowOhos window rect is resized for menu to x: %{public}d, y: %{public}d, width: %{public}u, height: "
441         "%{public}u",
442         window_->GetRect().posX_, window_->GetRect().posY_, window_->GetRect().width_, window_->GetRect().height_);
443 }
444 
GetRect()445 NG::RectF SubwindowOhos::GetRect()
446 {
447     NG::RectF rect;
448     CHECK_NULL_RETURN(window_, rect);
449     rect.SetRect(
450         window_->GetRect().posX_, window_->GetRect().posY_, window_->GetRect().width_, window_->GetRect().height_);
451     return rect;
452 }
453 
ShowPopup(const RefPtr<Component> & newComponent,bool disableTouchEvent)454 void SubwindowOhos::ShowPopup(const RefPtr<Component>& newComponent, bool disableTouchEvent)
455 {
456     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show popup enter");
457 #ifndef NG_BUILD
458     ShowWindow();
459     auto stack = GetStack();
460     CHECK_NULL_VOID(stack);
461     auto popup = AceType::DynamicCast<TweenComponent>(newComponent);
462     CHECK_NULL_VOID(popup);
463     stack->PopPopup(popup->GetId());
464     stack->PushComponent(newComponent, disableTouchEvent);
465     auto bubble = AceType::DynamicCast<BubbleComponent>(popup->GetChild());
466     if (bubble) {
467         bubble->SetWeakStack(WeakClaim(RawPtr(stack)));
468     }
469 #endif
470 }
471 
CancelPopup(const std::string & id)472 bool SubwindowOhos::CancelPopup(const std::string& id)
473 {
474     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "cancel popup enter");
475 #ifndef NG_BUILD
476     auto stack = GetStack();
477     CHECK_NULL_RETURN(stack, false);
478     stack->PopPopup(id);
479     auto context = stack->GetContext().Upgrade();
480     CHECK_NULL_RETURN(context, false);
481     context->FlushPipelineImmediately();
482     HideWindow();
483 #endif
484     return true;
485 }
486 
ShowPopupNG(int32_t targetId,const NG::PopupInfo & popupInfo,const std::function<void (int32_t)> && onWillDismiss,bool interactiveDismiss)487 void SubwindowOhos::ShowPopupNG(int32_t targetId, const NG::PopupInfo& popupInfo,
488     const std::function<void(int32_t)>&& onWillDismiss, bool interactiveDismiss)
489 {
490     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show popup ng enter, subwindowId: %{public}d", window_->GetWindowId());
491     popupTargetId_ = targetId;
492     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
493     CHECK_NULL_VOID(aceContainer);
494     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
495     CHECK_NULL_VOID(context);
496     auto overlayManager = context->GetOverlayManager();
497     CHECK_NULL_VOID(overlayManager);
498     ResizeWindow();
499     ShowWindow(popupInfo.focusable);
500     CHECK_NULL_VOID(window_);
501     window_->SetTouchable(true);
502     ContainerScope scope(childContainerId_);
503     needAvoidKeyboard_ = popupInfo.isAvoidKeyboard;
504     overlayManager->ShowPopup(targetId, popupInfo, std::move(onWillDismiss), interactiveDismiss);
505     window_->SetFocusable(true);
506 }
507 
HidePopupNG(int32_t targetId)508 void SubwindowOhos::HidePopupNG(int32_t targetId)
509 {
510     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
511         "hide popup ng enter, subwindowId: %{public}d, subwindowName: %{public}s",
512         window_->GetWindowId(), window_->GetWindowName().c_str());
513     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
514     CHECK_NULL_VOID(aceContainer);
515     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
516     CHECK_NULL_VOID(context);
517     auto overlayManager = context->GetOverlayManager();
518     CHECK_NULL_VOID(overlayManager);
519     auto popupInfo = overlayManager->GetPopupInfo(targetId == -1 ? popupTargetId_ : targetId);
520     popupInfo.markNeedUpdate = true;
521     ContainerScope scope(childContainerId_);
522     overlayManager->HidePopup(targetId == -1 ? popupTargetId_ : targetId, popupInfo);
523     context->FlushPipelineImmediately();
524     HideEventColumn();
525     HidePixelMap();
526     HideFilter(false);
527 }
528 
GetPopupInfoNG(int32_t targetId,NG::PopupInfo & popupInfo)529 void SubwindowOhos::GetPopupInfoNG(int32_t targetId, NG::PopupInfo& popupInfo)
530 {
531     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "get popup info ng enter");
532     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
533     CHECK_NULL_VOID(aceContainer);
534     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
535     CHECK_NULL_VOID(context);
536     auto overlayManager = context->GetOverlayManager();
537     CHECK_NULL_VOID(overlayManager);
538     popupInfo = overlayManager->GetPopupInfo(targetId);
539 }
540 
GetOverlayManager()541 const RefPtr<NG::OverlayManager> SubwindowOhos::GetOverlayManager()
542 {
543     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
544     CHECK_NULL_RETURN(aceContainer, nullptr);
545     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
546     CHECK_NULL_RETURN(context, nullptr);
547     return context->GetOverlayManager();
548 }
549 
ShowWindow(bool needFocus)550 void SubwindowOhos::ShowWindow(bool needFocus)
551 {
552     CHECK_NULL_VOID(window_);
553     if (isShowed_) {
554         TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "subwindow id:%{public}u is on display", window_->GetWindowId());
555         if (needFocus) {
556             window_->SetFocusable(needFocus);
557             RequestFocus();
558         }
559         return;
560     }
561     // Set min window hot area so that sub window can transparent event.
562     std::vector<Rosen::Rect> hotAreas;
563     Rosen::Rect rosenRect {};
564     RectConverter(MIN_WINDOW_HOT_AREA, rosenRect);
565     hotAreas.emplace_back(rosenRect);
566     window_->SetTouchHotAreas(hotAreas);
567 
568     window_->SetNeedDefaultAnimation(false);
569     auto ret = window_->SetFocusable(needFocus);
570     if (ret != OHOS::Rosen::WMError::WM_OK) {
571         TAG_LOGE(AceLogTag::ACE_SUB_WINDOW,
572             "subwindow id:%{public}u set focusable %{public}d failed with WMError: %{public}d", window_->GetWindowId(),
573             needFocus, static_cast<int32_t>(ret));
574     }
575     ret = window_->Show(0, false, needFocus);
576     if (ret != OHOS::Rosen::WMError::WM_OK) {
577         TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "Show subwindow id:%{public}u failed with WMError: %{public}d",
578             window_->GetWindowId(), static_cast<int32_t>(ret));
579         return;
580     }
581     if (needFocus) {
582         RequestFocus();
583     }
584 
585     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
586     CHECK_NULL_VOID(aceContainer);
587     auto context = aceContainer->GetPipelineContext();
588     CHECK_NULL_VOID(context);
589     AccessibilityEvent event;
590     event.type = AccessibilityEventType::PAGE_CHANGE;
591     event.windowId = context->GetWindowId();
592     event.windowChangeTypes = WINDOW_UPDATE_ADDED;
593     context->SendEventToAccessibility(event);
594     isShowed_ = true;
595     SubwindowManager::GetInstance()->SetCurrentSubwindow(AceType::Claim(this));
596 }
597 
HideWindow()598 void SubwindowOhos::HideWindow()
599 {
600     CHECK_NULL_VOID(window_);
601     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Hide the subwindow %{public}s", window_->GetWindowName().c_str());
602 
603     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
604     CHECK_NULL_VOID(aceContainer);
605 
606 #ifdef NG_BUILD
607     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
608     CHECK_NULL_VOID(context);
609     auto rootNode = context->GetRootElement();
610     CHECK_NULL_VOID(rootNode);
611     if (!rootNode->GetChildren().empty() &&
612         !(rootNode->GetChildren().size() == 1 && rootNode->GetLastChild()->GetTag() == V2::KEYBOARD_ETS_TAG)) {
613         auto lastChildId = rootNode->GetLastChild()->GetId();
614         auto iter = hotAreasMap_.find(lastChildId);
615         if (iter != hotAreasMap_.end()) {
616             auto hotAreaRect = iter->second;
617             OHOS::Rosen::WMError ret = window_->SetTouchHotAreas(hotAreaRect);
618             if (ret != OHOS::Rosen::WMError::WM_OK) {
619                 TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Set hot areas failed with errCode: %{public}d",
620                     static_cast<int32_t>(ret));
621             }
622         }
623         return;
624     }
625     auto focusHub = rootNode->GetFocusHub();
626     CHECK_NULL_VOID(focusHub);
627     focusHub->SetIsDefaultHasFocused(false);
628     context->SetIsFocusActive(false);
629 #else
630     if (Container::IsCurrentUseNewPipeline()) {
631         auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
632         CHECK_NULL_VOID(context);
633         auto rootNode = context->GetRootElement();
634         CHECK_NULL_VOID(rootNode);
635         if (!rootNode->GetChildren().empty() &&
636             !(rootNode->GetChildren().size() == 1 && rootNode->GetLastChild()->GetTag() == V2::KEYBOARD_ETS_TAG)) {
637             TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Subwindow has other node, the last child is %{public}s",
638                 rootNode->GetLastChild()->GetTag().c_str());
639             return;
640         }
641         auto focusHub = rootNode->GetFocusHub();
642         CHECK_NULL_VOID(focusHub);
643         focusHub->SetIsDefaultHasFocused(false);
644         context->SetIsFocusActive(false);
645     } else {
646         auto context = DynamicCast<PipelineContext>(aceContainer->GetPipelineContext());
647         CHECK_NULL_VOID(context);
648         auto rootNode = context->GetRootElement();
649         CHECK_NULL_VOID(rootNode);
650         rootNode->SetIsDefaultHasFocused(false);
651     }
652 #endif
653 
654     if (!window_->IsFocused()) {
655         ContainerModalUnFocus();
656     }
657 
658     OHOS::Rosen::WMError ret = window_->Hide();
659     auto parentContainer = Platform::AceContainer::GetContainer(parentContainerId_);
660     CHECK_NULL_VOID(parentContainer);
661     if (parentContainer->IsScenceBoardWindow()) {
662         window_->SetTouchable(true);
663     }
664 
665     if (ret != OHOS::Rosen::WMError::WM_OK) {
666         TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "Hide window failed with errCode: %{public}d", static_cast<int32_t>(ret));
667         return;
668     }
669     isShowed_ = false;
670     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Hide the subwindow successfully.");
671 #ifndef NG_BUILD
672     auto context = aceContainer->GetPipelineContext();
673     CHECK_NULL_VOID(context);
674 #endif
675     AccessibilityEvent event;
676     event.type = AccessibilityEventType::PAGE_CHANGE;
677     event.windowId = context->GetWindowId();
678     event.windowChangeTypes = WINDOW_UPDATE_REMOVED;
679     context->SendEventToAccessibility(event);
680 }
681 
ContainerModalUnFocus()682 void SubwindowOhos::ContainerModalUnFocus()
683 {
684     auto parentContainer = Platform::AceContainer::GetContainer(parentContainerId_);
685     CHECK_NULL_VOID(parentContainer);
686     auto parentWindowName = parentContainer->GetWindowName();
687     sptr<OHOS::Rosen::Window> parentWindow = OHOS::Rosen::Window::Find(parentWindowName);
688     CHECK_NULL_VOID(parentWindow);
689     if (parentWindow->GetFocusable() && !parentWindow->IsFocused()) {
690         auto pipelineContext = parentContainer->GetPipelineContext();
691         CHECK_NULL_VOID(pipelineContext);
692         pipelineContext->ContainerModalUnFocus();
693     }
694 }
695 
AddMenu(const RefPtr<Component> & newComponent)696 void SubwindowOhos::AddMenu(const RefPtr<Component>& newComponent)
697 {
698     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "add menu enter");
699 #ifndef NG_BUILD
700     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Subwindow push new component start.");
701     auto stack = GetStack();
702     CHECK_NULL_VOID(stack);
703     // Push the component
704     stack->PopMenu();
705     stack->PushComponent(newComponent);
706     popup_ = AceType::DynamicCast<SelectPopupComponent>(newComponent);
707 #endif
708 }
709 
ClearMenu()710 void SubwindowOhos::ClearMenu()
711 {
712     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "clear menu enter");
713     if (haveDialog_) {
714         return;
715     }
716 #ifndef NG_BUILD
717     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Subwindow Clear menu start.");
718     auto stack = GetStack();
719     CHECK_NULL_VOID(stack);
720     // Pop the component
721     stack->PopMenu();
722     auto context = stack->GetContext().Upgrade();
723     CHECK_NULL_VOID(context);
724     context->FlushPipelineImmediately();
725     HideWindow();
726 #endif
727 }
728 
ShowPreviewNG(bool isStartDraggingFromSubWindow)729 bool SubwindowOhos::ShowPreviewNG(bool isStartDraggingFromSubWindow)
730 {
731     CHECK_NULL_RETURN(window_, false);
732     ShowWindow(false);
733     ResizeWindow();
734     if (!isStartDraggingFromSubWindow) {
735         window_->SetTouchable(false);
736     }
737     return true;
738 }
739 
HidePreviewNG()740 void SubwindowOhos::HidePreviewNG()
741 {
742     auto overlayManager = GetOverlayManager();
743     CHECK_NULL_VOID(overlayManager);
744     overlayManager->RemovePixelMap();
745     overlayManager->RemovePreviewBadgeNode();
746     overlayManager->RemoveGatherNode();
747     overlayManager->RemoveEventColumn();
748     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
749     CHECK_NULL_VOID(aceContainer);
750     auto pipeline = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
751     CHECK_NULL_VOID(pipeline);
752     pipeline->FlushPipelineImmediately();
753     HideSubWindowNG();
754 }
755 
ShowMenuNG(const RefPtr<NG::FrameNode> customNode,const NG::MenuParam & menuParam,const RefPtr<NG::FrameNode> & targetNode,const NG::OffsetF & offset)756 void SubwindowOhos::ShowMenuNG(const RefPtr<NG::FrameNode> customNode, const NG::MenuParam& menuParam,
757     const RefPtr<NG::FrameNode>& targetNode, const NG::OffsetF& offset)
758 {
759     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show menu ng enter");
760     CHECK_NULL_VOID(customNode);
761     CHECK_NULL_VOID(targetNode);
762     ContainerScope scope(childContainerId_);
763     auto container = Container::Current();
764     CHECK_NULL_VOID(container);
765     auto context = DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
766     CHECK_NULL_VOID(context);
767     auto overlay = context->GetOverlayManager();
768     CHECK_NULL_VOID(overlay);
769     auto menuNode = customNode;
770     if (customNode->GetTag() != V2::MENU_WRAPPER_ETS_TAG) {
771         menuNode = NG::MenuView::Create(customNode, targetNode->GetId(), targetNode->GetTag(), menuParam, true);
772         auto menuWrapperPattern = menuNode->GetPattern<NG::MenuWrapperPattern>();
773         CHECK_NULL_VOID(menuWrapperPattern);
774         menuWrapperPattern->RegisterMenuCallback(menuNode, menuParam);
775         menuWrapperPattern->SetMenuTransitionEffect(menuNode, menuParam);
776     }
777     ShowWindow();
778     ResizeWindowForMenu();
779     CHECK_NULL_VOID(window_);
780     window_->SetTouchable(true);
781     overlay->ShowMenuInSubWindow(targetNode->GetId(), offset, menuNode);
782 }
783 
ShowMenuNG(std::function<void ()> && buildFunc,std::function<void ()> && previewBuildFunc,const NG::MenuParam & menuParam,const RefPtr<NG::FrameNode> & targetNode,const NG::OffsetF & offset)784 void SubwindowOhos::ShowMenuNG(std::function<void()>&& buildFunc, std::function<void()>&& previewBuildFunc,
785     const NG::MenuParam& menuParam, const RefPtr<NG::FrameNode>& targetNode, const NG::OffsetF& offset)
786 {
787     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show menu ng enter");
788     ContainerScope scope(childContainerId_);
789     auto container = Container::Current();
790     CHECK_NULL_VOID(container);
791     auto context = DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
792     CHECK_NULL_VOID(context);
793     auto overlay = context->GetOverlayManager();
794     CHECK_NULL_VOID(overlay);
795     ShowWindow();
796     ResizeWindowForMenu();
797     CHECK_NULL_VOID(window_);
798     window_->SetTouchable(true);
799     NG::ScopedViewStackProcessor builderViewStackProcessor;
800     buildFunc();
801     auto customNode = NG::ViewStackProcessor::GetInstance()->Finish();
802     RefPtr<NG::UINode> previewCustomNode;
803     if (previewBuildFunc && menuParam.previewMode == MenuPreviewMode::CUSTOM) {
804         previewBuildFunc();
805         previewCustomNode = NG::ViewStackProcessor::GetInstance()->Finish();
806     }
807     auto menuNode =
808         NG::MenuView::Create(customNode, targetNode->GetId(), targetNode->GetTag(), menuParam, true, previewCustomNode);
809     auto menuWrapperPattern = menuNode->GetPattern<NG::MenuWrapperPattern>();
810     CHECK_NULL_VOID(menuWrapperPattern);
811     menuWrapperPattern->RegisterMenuCallback(menuNode, menuParam);
812     menuWrapperPattern->SetMenuTransitionEffect(menuNode, menuParam);
813     overlay->ShowMenuInSubWindow(targetNode->GetId(), offset, menuNode);
814 }
815 
HideMenuNG(bool showPreviewAnimation,bool startDrag)816 void SubwindowOhos::HideMenuNG(bool showPreviewAnimation, bool startDrag)
817 {
818     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "hide menu ng enter");
819     if (!isShowed_) {
820         return;
821     }
822     ContainerScope scope(childContainerId_);
823     auto container = Container::Current();
824     CHECK_NULL_VOID(container);
825     auto context = DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
826     CHECK_NULL_VOID(context);
827     auto overlay = context->GetOverlayManager();
828     CHECK_NULL_VOID(overlay);
829     overlay->HideMenuInSubWindow(showPreviewAnimation, startDrag);
830     HideEventColumn();
831     HidePixelMap(startDrag, 0, 0, false);
832     HideFilter(false);
833     HideFilter(true);
834 }
835 
HideMenuNG(const RefPtr<NG::FrameNode> & menu,int32_t targetId)836 void SubwindowOhos::HideMenuNG(const RefPtr<NG::FrameNode>& menu, int32_t targetId)
837 {
838     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "hide menu ng enter");
839     if (!isShowed_) {
840         return;
841     }
842     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "Subwindow hide menu for target id %{public}d", targetId);
843     targetId_ = targetId;
844     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
845     CHECK_NULL_VOID(aceContainer);
846     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
847     CHECK_NULL_VOID(context);
848     auto overlay = context->GetOverlayManager();
849     CHECK_NULL_VOID(overlay);
850     overlay->HideMenuInSubWindow(menu, targetId_);
851     HideEventColumn();
852     HidePixelMap(false, 0, 0, false);
853     HideFilter(false);
854     HideFilter(true);
855 }
856 
UpdatePreviewPosition()857 void SubwindowOhos::UpdatePreviewPosition()
858 {
859     ContainerScope scope(childContainerId_);
860     auto pipelineContext = NG::PipelineContext::GetCurrentContext();
861     CHECK_NULL_VOID(pipelineContext);
862     auto overlay = pipelineContext->GetOverlayManager();
863     CHECK_NULL_VOID(overlay);
864     if (overlay->GetHasPixelMap()) {
865         return;
866     }
867     overlay->UpdatePixelMapPosition(true);
868 }
869 
GetMenuPreviewCenter(NG::OffsetF & offset)870 bool SubwindowOhos::GetMenuPreviewCenter(NG::OffsetF& offset)
871 {
872     ContainerScope scope(childContainerId_);
873     auto pipelineContext = NG::PipelineContext::GetCurrentContext();
874     CHECK_NULL_RETURN(pipelineContext, false);
875     auto overlay = pipelineContext->GetOverlayManager();
876     CHECK_NULL_RETURN(overlay, false);
877     return overlay->GetMenuPreviewCenter(offset);
878 }
879 
UpdateHideMenuOffsetNG(const NG::OffsetF & offset,float menuScale,bool isRedragStart,int32_t menuWrapperId)880 void SubwindowOhos::UpdateHideMenuOffsetNG(
881     const NG::OffsetF& offset, float menuScale, bool isRedragStart, int32_t menuWrapperId)
882 {
883     ContainerScope scope(childContainerId_);
884     auto pipelineContext = NG::PipelineContext::GetCurrentContext();
885     CHECK_NULL_VOID(pipelineContext);
886     auto overlay = pipelineContext->GetOverlayManager();
887     CHECK_NULL_VOID(overlay);
888     if (overlay->IsContextMenuDragHideFinished()) {
889         return;
890     }
891     overlay->UpdateContextMenuDisappearPosition(offset, menuScale, isRedragStart, menuWrapperId);
892 }
893 
ContextMenuSwitchDragPreviewAnimationtNG(const RefPtr<NG::FrameNode> & dragPreviewNode,const NG::OffsetF & offset)894 void SubwindowOhos::ContextMenuSwitchDragPreviewAnimationtNG(const RefPtr<NG::FrameNode>& dragPreviewNode,
895     const NG::OffsetF& offset)
896 {
897     CHECK_NULL_VOID(dragPreviewNode);
898     ContainerScope scope(childContainerId_);
899     auto pipelineContext = NG::PipelineContext::GetCurrentContext();
900     CHECK_NULL_VOID(pipelineContext);
901     auto overlay = pipelineContext->GetOverlayManager();
902     CHECK_NULL_VOID(overlay);
903     overlay->ContextMenuSwitchDragPreviewAnimation(dragPreviewNode, offset);
904 }
905 
ClearMenuNG(int32_t targetId,bool inWindow,bool showAnimation)906 void SubwindowOhos::ClearMenuNG(int32_t targetId, bool inWindow, bool showAnimation)
907 {
908     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "clear menu ng enter");
909     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
910     CHECK_NULL_VOID(aceContainer);
911     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
912     CHECK_NULL_VOID(context);
913     auto overlay = context->GetOverlayManager();
914     CHECK_NULL_VOID(overlay);
915     if (showAnimation) {
916         overlay->CleanMenuInSubWindowWithAnimation();
917         HideFilter(true);
918     } else {
919         overlay->CleanMenuInSubWindow(targetId);
920         overlay->RemoveFilter();
921     }
922     overlay->EraseMenuInfo(targetId);
923     HideWindow();
924     context->FlushPipelineImmediately();
925     if (inWindow) {
926         HideEventColumn();
927     }
928     HidePixelMap(false, 0, 0, false);
929     HideFilter(false);
930 }
931 
ClearPopupNG()932 void SubwindowOhos::ClearPopupNG()
933 {
934     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "clear popup ng enter");
935     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
936     CHECK_NULL_VOID(aceContainer);
937     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
938     CHECK_NULL_VOID(context);
939     auto overlay = context->GetOverlayManager();
940     CHECK_NULL_VOID(overlay);
941     overlay->CleanPopupInSubWindow();
942     HideWindow();
943     context->FlushPipelineImmediately();
944 }
945 
ShowMenu(const RefPtr<Component> & newComponent)946 void SubwindowOhos::ShowMenu(const RefPtr<Component>& newComponent)
947 {
948     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show menu enter");
949     ShowWindow();
950     AddMenu(newComponent);
951 }
952 
CloseMenu()953 void SubwindowOhos::CloseMenu()
954 {
955     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "close menu enter");
956 #ifndef NG_BUILD
957     if (!isShowed_) {
958         return;
959     }
960     if (popup_) {
961         popup_->CloseContextMenu();
962     }
963 #endif
964 }
965 
GetStack()966 RefPtr<StackElement> SubwindowOhos::GetStack()
967 {
968 #ifndef NG_BUILD
969     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
970     CHECK_NULL_RETURN(aceContainer, nullptr);
971 
972     auto context = DynamicCast<PipelineContext>(aceContainer->GetPipelineContext());
973     CHECK_NULL_RETURN(context, nullptr);
974     return context->GetLastStack();
975 #else
976     return nullptr;
977 #endif
978 }
979 
DeleteHotAreas(int32_t nodeId)980 void SubwindowOhos::DeleteHotAreas(int32_t nodeId)
981 {
982     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "delete hot area %{public}d", nodeId);
983     hotAreasMap_.erase(nodeId);
984 
985     std::vector<Rosen::Rect> hotAreas;
986     for (auto it = hotAreasMap_.begin(); it != hotAreasMap_.end(); it++) {
987         hotAreas.insert(hotAreas.end(), it->second.begin(), it->second.end());
988     }
989     CHECK_NULL_VOID(window_);
990     window_->SetTouchHotAreas(hotAreas);
991 }
992 
SetHotAreas(const std::vector<Rect> & rects,int32_t nodeId)993 void SubwindowOhos::SetHotAreas(const std::vector<Rect>& rects, int32_t nodeId)
994 {
995     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "set hot areas enter");
996     CHECK_NULL_VOID(window_);
997 
998     std::vector<Rosen::Rect> hotAreas;
999     Rosen::Rect rosenRect {};
1000 
1001     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "set hot area %{public}d", nodeId);
1002     for (const auto& rect : rects) {
1003         TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "set hot area rect %{public}s", rect.ToString().c_str());
1004         RectConverter(rect, rosenRect);
1005         hotAreas.emplace_back(rosenRect);
1006     }
1007     if (nodeId >= 0) {
1008         hotAreasMap_[nodeId] = hotAreas;
1009     }
1010 
1011     std::vector<Rosen::Rect> hotAreasNow;
1012     for (auto it = hotAreasMap_.begin(); it != hotAreasMap_.end(); it++) {
1013         hotAreasNow.insert(hotAreasNow.end(), it->second.begin(), it->second.end());
1014     }
1015     window_->SetTouchHotAreas(hotAreasNow);
1016 }
1017 
RectConverter(const Rect & rect,Rosen::Rect & rosenRect)1018 void SubwindowOhos::RectConverter(const Rect& rect, Rosen::Rect& rosenRect)
1019 {
1020     rosenRect.posX_ = static_cast<int>(rect.GetOffset().GetX());
1021     rosenRect.posY_ = static_cast<int>(rect.GetOffset().GetY());
1022     rosenRect.width_ = static_cast<uint32_t>(rect.GetSize().Width());
1023     rosenRect.height_ = static_cast<uint32_t>(rect.GetSize().Height());
1024     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
1025         "Convert rect to rosenRect, x is %{public}d, y is %{public}d, width is %{public}d, height is %{public}d",
1026         rosenRect.posX_, rosenRect.posY_, rosenRect.width_, rosenRect.height_);
1027 }
1028 
ShowDialogNG(const DialogProperties & dialogProps,std::function<void ()> && buildFunc)1029 RefPtr<NG::FrameNode> SubwindowOhos::ShowDialogNG(
1030     const DialogProperties& dialogProps, std::function<void()>&& buildFunc)
1031 {
1032     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show dialog ng enter");
1033     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1034     CHECK_NULL_RETURN(aceContainer, nullptr);
1035     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1036     CHECK_NULL_RETURN(context, nullptr);
1037     auto overlay = context->GetOverlayManager();
1038     CHECK_NULL_RETURN(overlay, nullptr);
1039     std::map<int32_t, RefPtr<NG::FrameNode>> DialogMap(overlay->GetDialogMap().begin(), overlay->GetDialogMap().end());
1040     int dialogMapSize = static_cast<int>(DialogMap.size());
1041     if (dialogMapSize == 0) {
1042         auto parentAceContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1043         CHECK_NULL_RETURN(parentAceContainer, nullptr);
1044         auto parentcontext = DynamicCast<NG::PipelineContext>(parentAceContainer->GetPipelineContext());
1045         CHECK_NULL_RETURN(parentcontext, nullptr);
1046         auto parentOverlay = parentcontext->GetOverlayManager();
1047         CHECK_NULL_RETURN(parentOverlay, nullptr);
1048         parentOverlay->SetSubWindowId(SubwindowManager::GetInstance()->GetDialogSubwindowInstanceId(GetSubwindowId()));
1049     }
1050     SubwindowManager::GetInstance()->SetDialogSubWindowId(
1051         SubwindowManager::GetInstance()->GetDialogSubwindowInstanceId(GetSubwindowId()));
1052     ShowWindow();
1053     CHECK_NULL_RETURN(window_, nullptr);
1054     window_->SetFullScreen(true);
1055     window_->SetTouchable(true);
1056     ResizeWindow();
1057     ContainerScope scope(childContainerId_);
1058     auto dialog = overlay->ShowDialog(dialogProps, std::move(buildFunc));
1059     CHECK_NULL_RETURN(dialog, nullptr);
1060     haveDialog_ = true;
1061     return dialog;
1062 }
1063 
ShowDialogNGWithNode(const DialogProperties & dialogProps,const RefPtr<NG::UINode> & customNode)1064 RefPtr<NG::FrameNode> SubwindowOhos::ShowDialogNGWithNode(
1065     const DialogProperties& dialogProps, const RefPtr<NG::UINode>& customNode)
1066 {
1067     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show dialog ng enter");
1068     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1069     CHECK_NULL_RETURN(aceContainer, nullptr);
1070     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1071     CHECK_NULL_RETURN(context, nullptr);
1072     auto overlay = context->GetOverlayManager();
1073     CHECK_NULL_RETURN(overlay, nullptr);
1074     std::map<int32_t, RefPtr<NG::FrameNode>> DialogMap(overlay->GetDialogMap().begin(), overlay->GetDialogMap().end());
1075     int dialogMapSize = static_cast<int>(DialogMap.size());
1076     if (dialogMapSize == 0) {
1077         auto parentAceContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1078         CHECK_NULL_RETURN(parentAceContainer, nullptr);
1079         auto parentcontext = DynamicCast<NG::PipelineContext>(parentAceContainer->GetPipelineContext());
1080         CHECK_NULL_RETURN(parentcontext, nullptr);
1081         auto parentOverlay = parentcontext->GetOverlayManager();
1082         CHECK_NULL_RETURN(parentOverlay, nullptr);
1083         parentOverlay->SetSubWindowId(SubwindowManager::GetInstance()->GetDialogSubwindowInstanceId(GetSubwindowId()));
1084     }
1085     SubwindowManager::GetInstance()->SetDialogSubWindowId(
1086         SubwindowManager::GetInstance()->GetDialogSubwindowInstanceId(GetSubwindowId()));
1087     ShowWindow();
1088     CHECK_NULL_RETURN(window_, nullptr);
1089     window_->SetFullScreen(true);
1090     window_->SetTouchable(true);
1091     ResizeWindow();
1092     ContainerScope scope(childContainerId_);
1093     auto dialog = overlay->ShowDialogWithNode(dialogProps, customNode);
1094     CHECK_NULL_RETURN(dialog, nullptr);
1095     haveDialog_ = true;
1096     return dialog;
1097 }
1098 
CloseDialogNG(const RefPtr<NG::FrameNode> & dialogNode)1099 void SubwindowOhos::CloseDialogNG(const RefPtr<NG::FrameNode>& dialogNode)
1100 {
1101     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "close dialog ng enter");
1102     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1103     CHECK_NULL_VOID(aceContainer);
1104     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1105     CHECK_NULL_VOID(context);
1106     auto overlay = context->GetOverlayManager();
1107     CHECK_NULL_VOID(overlay);
1108     ContainerScope scope(childContainerId_);
1109     return overlay->CloseDialog(dialogNode);
1110 }
1111 
OpenCustomDialogNG(const DialogProperties & dialogProps,std::function<void (int32_t)> && callback)1112 void SubwindowOhos::OpenCustomDialogNG(const DialogProperties& dialogProps, std::function<void(int32_t)>&& callback)
1113 {
1114     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "open customDialog ng subwindow enter");
1115     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1116     CHECK_NULL_VOID(aceContainer);
1117     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1118     CHECK_NULL_VOID(context);
1119     auto overlay = context->GetOverlayManager();
1120     CHECK_NULL_VOID(overlay);
1121     std::map<int32_t, RefPtr<NG::FrameNode>> DialogMap(overlay->GetDialogMap().begin(), overlay->GetDialogMap().end());
1122     int dialogMapSize = static_cast<int>(DialogMap.size());
1123     if (dialogMapSize == 0) {
1124         auto parentAceContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1125         CHECK_NULL_VOID(parentAceContainer);
1126         auto parentcontext = DynamicCast<NG::PipelineContext>(parentAceContainer->GetPipelineContext());
1127         CHECK_NULL_VOID(parentcontext);
1128         auto parentOverlay = parentcontext->GetOverlayManager();
1129         CHECK_NULL_VOID(parentOverlay);
1130         parentOverlay->SetSubWindowId(SubwindowManager::GetInstance()->GetDialogSubwindowInstanceId(GetSubwindowId()));
1131         TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "overlay in parent container %{public}d, SetSubWindowId %{public}d",
1132             parentContainerId_, GetSubwindowId());
1133     }
1134     SubwindowManager::GetInstance()->SetDialogSubWindowId(
1135         SubwindowManager::GetInstance()->GetDialogSubwindowInstanceId(GetSubwindowId()));
1136     ShowWindow();
1137     CHECK_NULL_VOID(window_);
1138     window_->SetFullScreen(true);
1139     window_->SetTouchable(true);
1140     ResizeWindow();
1141     ContainerScope scope(childContainerId_);
1142     overlay->OpenCustomDialog(dialogProps, std::move(callback));
1143     haveDialog_ = true;
1144 }
1145 
CloseCustomDialogNG(int32_t dialogId)1146 void SubwindowOhos::CloseCustomDialogNG(int32_t dialogId)
1147 {
1148     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "close customDialog ng subwindow enter, child container id %{public}d",
1149         childContainerId_);
1150     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1151     CHECK_NULL_VOID(aceContainer);
1152     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1153     CHECK_NULL_VOID(context);
1154     auto overlay = context->GetOverlayManager();
1155     CHECK_NULL_VOID(overlay);
1156     ContainerScope scope(childContainerId_);
1157     return overlay->CloseCustomDialog(dialogId);
1158 }
1159 
CloseCustomDialogNG(const WeakPtr<NG::UINode> & node,std::function<void (int32_t)> && callback)1160 void SubwindowOhos::CloseCustomDialogNG(const WeakPtr<NG::UINode>& node, std::function<void(int32_t)>&& callback)
1161 {
1162     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "close customDialog ng subwindow enter, child container id %{public}d",
1163         childContainerId_);
1164     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1165     CHECK_NULL_VOID(aceContainer);
1166     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1167     CHECK_NULL_VOID(context);
1168     auto overlay = context->GetOverlayManager();
1169     CHECK_NULL_VOID(overlay);
1170     ContainerScope scope(childContainerId_);
1171     return overlay->CloseCustomDialog(node, std::move(callback));
1172 }
1173 
UpdateCustomDialogNG(const WeakPtr<NG::UINode> & node,const DialogProperties & dialogProps,std::function<void (int32_t)> && callback)1174 void SubwindowOhos::UpdateCustomDialogNG(
1175     const WeakPtr<NG::UINode>& node, const DialogProperties& dialogProps, std::function<void(int32_t)>&& callback)
1176 {
1177     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "update customDialog ng subwindow enter");
1178     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1179     CHECK_NULL_VOID(aceContainer);
1180     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1181     CHECK_NULL_VOID(context);
1182     auto overlay = context->GetOverlayManager();
1183     CHECK_NULL_VOID(overlay);
1184     ContainerScope scope(childContainerId_);
1185     return overlay->UpdateCustomDialog(node, dialogProps, std::move(callback));
1186 }
1187 
HideSubWindowNG()1188 void SubwindowOhos::HideSubWindowNG()
1189 {
1190     ContainerScope scope(childContainerId_);
1191     auto container = Container::Current();
1192     CHECK_NULL_VOID(container);
1193     if (container->IsDialogContainer()) {
1194         if (IsToastWindow()) {
1195             Platform::DialogContainer::HideWindow(Container::CurrentId());
1196         } else {
1197             Platform::DialogContainer::CloseWindow(Container::CurrentId());
1198             Platform::DialogContainer::DestroyContainer(Container::CurrentId());
1199         }
1200     } else {
1201         HideWindow();
1202     }
1203 }
1204 
GetToastDialogWindowProperty(int32_t & width,int32_t & height,int32_t & posX,int32_t & posY,float & density) const1205 void SubwindowOhos::GetToastDialogWindowProperty(
1206     int32_t& width, int32_t& height, int32_t& posX, int32_t& posY, float& density) const
1207 {
1208     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "get toast dialog window property enter");
1209     auto defaultDisplay = Rosen::DisplayManager::GetInstance().GetDefaultDisplay();
1210     if (defaultDisplay) {
1211         posX = 0;
1212         posY = 0;
1213         width = defaultDisplay->GetWidth();
1214         height = defaultDisplay->GetHeight();
1215         density = defaultDisplay->GetVirtualPixelRatio();
1216     }
1217     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
1218         "Toast posX: %{public}d, posY: %{public}d, width: %{public}d, height: %{public}d, density: %{public}f", posX,
1219         posY, width, height, density);
1220 }
1221 
InitToastDialogWindow(int32_t width,int32_t height,int32_t posX,int32_t posY,bool isToast)1222 bool SubwindowOhos::InitToastDialogWindow(int32_t width, int32_t height, int32_t posX, int32_t posY, bool isToast)
1223 {
1224     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "init toast dialog window enter");
1225     OHOS::sptr<OHOS::Rosen::WindowOption> windowOption = new OHOS::Rosen::WindowOption();
1226     if (isToast) {
1227         auto windowType =
1228             IsSystemTopMost() ? Rosen::WindowType::WINDOW_TYPE_SYSTEM_TOAST : Rosen::WindowType::WINDOW_TYPE_TOAST;
1229         windowOption->SetWindowType(windowType);
1230     } else {
1231         windowOption->SetWindowType(Rosen::WindowType::WINDOW_TYPE_APP_MAIN_WINDOW);
1232     }
1233     windowOption->SetWindowRect({ posX, posY, width, height });
1234     windowOption->SetWindowMode(Rosen::WindowMode::WINDOW_MODE_FULLSCREEN);
1235     windowOption->SetFocusable(!isToast);
1236     int32_t dialogId = gToastDialogId.fetch_add(1, std::memory_order_relaxed);
1237     std::string windowName = "ARK_APP_SUBWINDOW_TOAST_DIALOG_" + std::to_string(dialogId);
1238     if (isToast) {
1239         auto context = OHOS::AbilityRuntime::Context::GetApplicationContext();
1240         dialogWindow_ = OHOS::Rosen::Window::Create(windowName, windowOption, context);
1241     } else {
1242         dialogWindow_ = OHOS::Rosen::Window::Create(windowName, windowOption);
1243     }
1244     CHECK_NULL_RETURN(dialogWindow_, false);
1245     dialogWindow_->SetLayoutFullScreen(true);
1246     return true;
1247 }
1248 
InitToastDialogView(int32_t width,int32_t height,float density)1249 bool SubwindowOhos::InitToastDialogView(int32_t width, int32_t height, float density)
1250 {
1251     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "init toast dialog view enter");
1252 #ifndef NG_BUILD
1253     dialogWindow_->NapiSetUIContent("", nullptr, nullptr, Rosen::BackupAndRestoreType::NONE);
1254     childContainerId_ = SubwindowManager::GetInstance()->GetContainerId(dialogWindow_->GetWindowId());
1255     SubwindowManager::GetInstance()->AddParentContainerId(childContainerId_, parentContainerId_);
1256     ContainerScope scope(childContainerId_);
1257 
1258     auto container = Platform::DialogContainer::GetContainer(childContainerId_);
1259     CHECK_NULL_RETURN(container, false);
1260     // create ace_view
1261     auto aceView = Platform::AceViewOhos::CreateView(childContainerId_, true, true);
1262     Platform::AceViewOhos::SurfaceCreated(aceView, dialogWindow_);
1263     // set view
1264     Platform::DialogContainer::SetView(aceView, density, width, height, dialogWindow_);
1265     Ace::Platform::DialogContainer::SetUIWindow(childContainerId_, dialogWindow_);
1266     ViewportConfig config(width, height, density);
1267     Platform::AceViewOhos::SetViewportMetrics(aceView, config);
1268     Platform::AceViewOhos::SurfaceChanged(aceView, width, height, 0);
1269 
1270 #ifdef ENABLE_ROSEN_BACKEND
1271     if (SystemProperties::GetRosenBackendEnabled()) {
1272         rsUiDirector = OHOS::Rosen::RSUIDirector::Create();
1273         if (rsUiDirector != nullptr) {
1274             rsUiDirector->SetRSSurfaceNode(dialogWindow_->GetSurfaceNode());
1275             auto context = DynamicCast<PipelineContext>(container->GetPipelineContext());
1276             if (context != nullptr) {
1277                 context->SetRSUIDirector(rsUiDirector);
1278             }
1279             rsUiDirector->Init();
1280         }
1281     }
1282 #endif
1283 
1284     auto pipelineContext = container->GetPipelineContext();
1285     CHECK_NULL_RETURN(pipelineContext, false);
1286     pipelineContext->SetupRootElement();
1287     auto parentContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1288     if (parentContainer) {
1289         auto parentPipeline = parentContainer->GetPipelineContext();
1290         CHECK_NULL_RETURN(parentPipeline, false);
1291         pipelineContext->SetMinPlatformVersion(parentPipeline->GetMinPlatformVersion());
1292     } else {
1293         pipelineContext->SetMinPlatformVersion(PLATFORM_VERSION_TEN);
1294     }
1295     return true;
1296 #else
1297     return true;
1298 #endif
1299 }
1300 
InitToastServiceConfig()1301 bool SubwindowOhos::InitToastServiceConfig()
1302 {
1303     auto context = OHOS::AbilityRuntime::Context::GetApplicationContext();
1304     CHECK_NULL_RETURN(context, false);
1305     auto config = context->GetConfiguration();
1306     CHECK_NULL_RETURN(config, false);
1307     auto maxAppFontScale = config->GetItem(OHOS::AAFwk::GlobalConfigurationKey::APP_FONT_MAX_SCALE);
1308     auto followSystem = config->GetItem(OHOS::AAFwk::GlobalConfigurationKey::APP_FONT_SIZE_SCALE);
1309     auto container = Platform::DialogContainer::GetContainer(childContainerId_);
1310     CHECK_NULL_RETURN(container, false);
1311     auto pipelineContext = container->GetPipelineContext();
1312     CHECK_NULL_RETURN(pipelineContext, false);
1313     auto isFollowSystem = followSystem == "followSystem";
1314     if (!followSystem.empty()) {
1315         pipelineContext->SetFollowSystem(isFollowSystem);
1316     }
1317     if (!maxAppFontScale.empty()) {
1318         pipelineContext->SetMaxAppFontScale(StringUtils::StringToFloat(maxAppFontScale));
1319     }
1320     if (!isFollowSystem) {
1321         pipelineContext->SetFontScale(1.0f);
1322     }
1323     auto fontScale = config->GetItem(OHOS::AAFwk::GlobalConfigurationKey::SYSTEM_FONT_SIZE_SCALE);
1324     if (!fontScale.empty()) {
1325         pipelineContext->SetFontScale(StringUtils::StringToFloat(fontScale));
1326     }
1327 
1328     return true;
1329 }
1330 
CreateEventRunner()1331 bool SubwindowOhos::CreateEventRunner()
1332 {
1333     if (!eventLoop_) {
1334         eventLoop_ = AppExecFwk::EventRunner::Create("Subwindow_Toast_Dialog");
1335         CHECK_NULL_RETURN(eventLoop_, false);
1336         handler_ = std::make_shared<AppExecFwk::EventHandler>(eventLoop_);
1337         CHECK_NULL_RETURN(handler_, false);
1338     }
1339     return true;
1340 }
1341 
ClearToast()1342 void SubwindowOhos::ClearToast()
1343 {
1344     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "clear toast enter");
1345     if (!IsToastWindow()) {
1346         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "default toast needs not to be clear");
1347         return;
1348     }
1349     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1350     CHECK_NULL_VOID(aceContainer);
1351     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1352     CHECK_NULL_VOID(context);
1353     auto overlayManager = context->GetOverlayManager();
1354     CHECK_NULL_VOID(overlayManager);
1355     ContainerScope scope(childContainerId_);
1356     overlayManager->ClearToast();
1357     context->FlushPipelineImmediately();
1358     HideWindow();
1359 }
1360 
ShowToastForAbility(const NG::ToastInfo & toastInfo)1361 void SubwindowOhos::ShowToastForAbility(const NG::ToastInfo& toastInfo)
1362 {
1363     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show toast for ability enter, containerId : %{public}d", childContainerId_);
1364     SetIsToastWindow(
1365         toastInfo.showMode == NG::ToastShowMode::TOP_MOST || toastInfo.showMode == NG::ToastShowMode::SYSTEM_TOP_MOST);
1366     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1367     if (!aceContainer) {
1368         TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "get container failed, child containerId : %{public}d", childContainerId_);
1369         return;
1370     }
1371 
1372     auto engine = EngineHelper::GetEngine(aceContainer->GetInstanceId());
1373     RefPtr<Framework::FrontendDelegate> delegate;
1374     if (!engine) {
1375         auto frontend = AceType::DynamicCast<DeclarativeFrontend>(aceContainer->GetFrontend());
1376         CHECK_NULL_VOID(frontend);
1377         delegate = frontend->GetDelegate();
1378         if (!delegate) {
1379             TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "get engine failed, containerId : %{public}d",
1380                 aceContainer->GetInstanceId());
1381             return;
1382         }
1383     } else {
1384         delegate = engine->GetFrontend();
1385         if (!delegate) {
1386             TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "get frontend failed, child containerId : %{public}d",
1387                 childContainerId_);
1388             return;
1389         }
1390     }
1391     ContainerScope scope(childContainerId_);
1392     auto parentContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1393     CHECK_NULL_VOID(parentContainer);
1394     if (parentContainer->IsScenceBoardWindow() || toastInfo.showMode == NG::ToastShowMode::TOP_MOST ||
1395         toastInfo.showMode == NG::ToastShowMode::SYSTEM_TOP_MOST) {
1396         ResizeWindow();
1397         // Recover current subwindow in subwindow manager to ensure popup/menu can close the right subwindow
1398         auto currentWindow = SubwindowManager::GetInstance()->GetCurrentWindow();
1399         ShowWindow(false);
1400         SubwindowManager::GetInstance()->SetCurrentSubwindow(currentWindow);
1401         CHECK_NULL_VOID(window_);
1402         window_->SetTouchable(false);
1403     }
1404     delegate->ShowToast(toastInfo);
1405 }
1406 
ShowToastForService(const NG::ToastInfo & toastInfo)1407 void SubwindowOhos::ShowToastForService(const NG::ToastInfo& toastInfo)
1408 {
1409     bool ret = CreateEventRunner();
1410     if (!ret) {
1411         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create event runner failed");
1412         return;
1413     }
1414 
1415     SubwindowManager::GetInstance()->SetCurrentDialogSubwindow(AceType::Claim(this));
1416     if (!handler_->PostTask(GetInitToastDelayTask(toastInfo))) {
1417         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create show dialog callback failed");
1418         return;
1419     }
1420 }
1421 
ShowToast(const NG::ToastInfo & toastInfo)1422 void SubwindowOhos::ShowToast(const NG::ToastInfo& toastInfo)
1423 {
1424     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show toast, window parent id is %{public}d", parentContainerId_);
1425     bool isTopMost = toastInfo.showMode == NG::ToastShowMode::TOP_MOST;
1426     // for pa service
1427     if ((isTopMost && parentContainerId_ >= MIN_PA_SERVICE_ID && parentContainerId_ < MIN_SUBCONTAINER_ID) ||
1428         (!isTopMost && parentContainerId_ >= MIN_PA_SERVICE_ID) || parentContainerId_ < 0) {
1429         ShowToastForService(toastInfo);
1430     } else {
1431         ShowToastForAbility(toastInfo);
1432     }
1433 }
1434 
ShowDialogForAbility(const std::string & title,const std::string & message,const std::vector<ButtonInfo> & buttons,bool autoCancel,std::function<void (int32_t,int32_t)> && callback,const std::set<std::string> & callbacks)1435 void SubwindowOhos::ShowDialogForAbility(const std::string& title, const std::string& message,
1436     const std::vector<ButtonInfo>& buttons, bool autoCancel, std::function<void(int32_t, int32_t)>&& callback,
1437     const std::set<std::string>& callbacks)
1438 {
1439     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show dialog for ability enter");
1440     SubwindowManager::GetInstance()->SetCurrentSubwindow(AceType::Claim(this));
1441 
1442     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1443     if (!aceContainer) {
1444         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "get container failed, child containerId : %{public}d", childContainerId_);
1445         return;
1446     }
1447 
1448     auto engine = EngineHelper::GetEngine(aceContainer->GetInstanceId());
1449     auto delegate = engine->GetFrontend();
1450     if (!delegate) {
1451         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "get frontend failed, child containerId : %{public}d", childContainerId_);
1452         return;
1453     }
1454     delegate->ShowDialog(title, message, buttons, autoCancel, std::move(callback), callbacks);
1455 }
1456 
ShowDialogForService(const std::string & title,const std::string & message,const std::vector<ButtonInfo> & buttons,bool autoCancel,std::function<void (int32_t,int32_t)> && callback,const std::set<std::string> & callbacks)1457 void SubwindowOhos::ShowDialogForService(const std::string& title, const std::string& message,
1458     const std::vector<ButtonInfo>& buttons, bool autoCancel, std::function<void(int32_t, int32_t)>&& callback,
1459     const std::set<std::string>& callbacks)
1460 {
1461     bool ret = CreateEventRunner();
1462     if (!ret) {
1463         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create event runner failed");
1464         return;
1465     }
1466 
1467     SubwindowManager::GetInstance()->SetCurrentDialogSubwindow(AceType::Claim(this));
1468     auto showDialogCallback = [title, message, &buttons, autoCancel, callbackParam = std::move(callback),
1469                                   &callbacks]() {
1470         int32_t posX = 0;
1471         int32_t posY = 0;
1472         int32_t width = 0;
1473         int32_t height = 0;
1474         float density = 1.0f;
1475         auto subwindowOhos =
1476             AceType::DynamicCast<SubwindowOhos>(SubwindowManager::GetInstance()->GetCurrentDialogWindow());
1477         CHECK_NULL_VOID(subwindowOhos);
1478         subwindowOhos->GetToastDialogWindowProperty(width, height, posX, posY, density);
1479         bool ret = subwindowOhos->InitToastDialogWindow(width, height, posX, posY);
1480         if (!ret) {
1481             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog window failed");
1482             return;
1483         }
1484         ret = subwindowOhos->InitToastDialogView(width, height, density);
1485         if (!ret) {
1486             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog view failed");
1487             return;
1488         }
1489         auto childContainerId = subwindowOhos->GetChildContainerId();
1490         ContainerScope scope(childContainerId);
1491         auto container = Platform::DialogContainer::GetContainer(childContainerId);
1492         CHECK_NULL_VOID(container);
1493         container->SetFontScaleAndWeightScale(childContainerId);
1494         Platform::DialogContainer::ShowToastDialogWindow(childContainerId, posX, posY, width, height);
1495         Platform::DialogContainer::ShowDialog(childContainerId, title, message, buttons, autoCancel,
1496             std::move(const_cast<std::function<void(int32_t, int32_t)>&&>(callbackParam)), callbacks);
1497     };
1498     isToastWindow_ = false;
1499     if (!handler_->PostTask(showDialogCallback)) {
1500         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create show dialog callback failed");
1501         return;
1502     }
1503 }
1504 
ShowDialogForAbility(const PromptDialogAttr & dialogAttr,const std::vector<ButtonInfo> & buttons,std::function<void (int32_t,int32_t)> && callback,const std::set<std::string> & callbacks)1505 void SubwindowOhos::ShowDialogForAbility(const PromptDialogAttr& dialogAttr, const std::vector<ButtonInfo>& buttons,
1506     std::function<void(int32_t, int32_t)>&& callback, const std::set<std::string>& callbacks)
1507 {
1508     SubwindowManager::GetInstance()->SetCurrentSubwindow(AceType::Claim(this));
1509 
1510     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1511     if (!aceContainer) {
1512         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "get ace container failed");
1513         return;
1514     }
1515 
1516     auto engine = EngineHelper::GetEngine(aceContainer->GetInstanceId());
1517     auto delegate = engine->GetFrontend();
1518     if (!delegate) {
1519         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "get frontend failed");
1520         return;
1521     }
1522     delegate->ShowDialog(dialogAttr, buttons, std::move(callback), callbacks);
1523 }
1524 
ShowDialogForService(const PromptDialogAttr & dialogAttr,const std::vector<ButtonInfo> & buttons,std::function<void (int32_t,int32_t)> && callback,const std::set<std::string> & callbacks)1525 void SubwindowOhos::ShowDialogForService(const PromptDialogAttr& dialogAttr, const std::vector<ButtonInfo>& buttons,
1526     std::function<void(int32_t, int32_t)>&& callback, const std::set<std::string>& callbacks)
1527 {
1528     bool ret = CreateEventRunner();
1529     if (!ret) {
1530         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create event runner failed");
1531         return;
1532     }
1533 
1534     SubwindowManager::GetInstance()->SetCurrentDialogSubwindow(AceType::Claim(this));
1535     auto showDialogCallback = [dialogAttr, &buttons, callbackParam = std::move(callback), &callbacks]() {
1536         int32_t posX = 0;
1537         int32_t posY = 0;
1538         int32_t width = 0;
1539         int32_t height = 0;
1540         float density = 1.0f;
1541         auto subwindowOhos =
1542             AceType::DynamicCast<SubwindowOhos>(SubwindowManager::GetInstance()->GetCurrentDialogWindow());
1543         CHECK_NULL_VOID(subwindowOhos);
1544         subwindowOhos->GetToastDialogWindowProperty(width, height, posX, posY, density);
1545         bool ret = subwindowOhos->InitToastDialogWindow(width, height, posX, posY);
1546         if (!ret) {
1547             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog window failed");
1548             return;
1549         }
1550         ret = subwindowOhos->InitToastDialogView(width, height, density);
1551         if (!ret) {
1552             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog view failed");
1553             return;
1554         }
1555         auto childContainerId = subwindowOhos->GetChildContainerId();
1556         ContainerScope scope(childContainerId);
1557         Platform::DialogContainer::ShowToastDialogWindow(childContainerId, posX, posY, width, height);
1558         Platform::DialogContainer::ShowDialog(childContainerId, dialogAttr, buttons,
1559             std::move(const_cast<std::function<void(int32_t, int32_t)>&&>(callbackParam)), callbacks);
1560     };
1561     isToastWindow_ = false;
1562     if (!handler_->PostTask(showDialogCallback)) {
1563         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create show dialog callback failed");
1564         return;
1565     }
1566 }
1567 
ShowDialog(const std::string & title,const std::string & message,const std::vector<ButtonInfo> & buttons,bool autoCancel,std::function<void (int32_t,int32_t)> && callback,const std::set<std::string> & callbacks)1568 void SubwindowOhos::ShowDialog(const std::string& title, const std::string& message,
1569     const std::vector<ButtonInfo>& buttons, bool autoCancel, std::function<void(int32_t, int32_t)>&& callback,
1570     const std::set<std::string>& callbacks)
1571 {
1572     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show dialog, window parent id is %{public}d", parentContainerId_);
1573     if (parentContainerId_ >= MIN_PA_SERVICE_ID || parentContainerId_ < 0) {
1574         ShowDialogForService(title, message, buttons, autoCancel, std::move(callback), callbacks);
1575     } else {
1576         ShowDialogForAbility(title, message, buttons, autoCancel, std::move(callback), callbacks);
1577     }
1578 }
1579 
ShowDialog(const PromptDialogAttr & dialogAttr,const std::vector<ButtonInfo> & buttons,std::function<void (int32_t,int32_t)> && callback,const std::set<std::string> & callbacks)1580 void SubwindowOhos::ShowDialog(const PromptDialogAttr& dialogAttr, const std::vector<ButtonInfo>& buttons,
1581     std::function<void(int32_t, int32_t)>&& callback, const std::set<std::string>& callbacks)
1582 {
1583     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show dialog with attr, window parent id is %{public}d", parentContainerId_);
1584     if (parentContainerId_ >= MIN_PA_SERVICE_ID || parentContainerId_ < 0) {
1585         ShowDialogForService(dialogAttr, buttons, std::move(callback), callbacks);
1586     } else {
1587         ShowDialogForAbility(dialogAttr, buttons, std::move(callback), callbacks);
1588     }
1589 }
1590 
OpenCustomDialogForAbility(const PromptDialogAttr & dialogAttr,std::function<void (int32_t)> && callback)1591 void SubwindowOhos::OpenCustomDialogForAbility(
1592     const PromptDialogAttr& dialogAttr, std::function<void(int32_t)>&& callback)
1593 {
1594     SubwindowManager::GetInstance()->SetCurrentSubwindow(AceType::Claim(this));
1595 
1596     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1597     if (!aceContainer) {
1598         TAG_LOGW(
1599             AceLogTag::ACE_SUB_WINDOW, "open dialog fail, the container %{public}d can not find", childContainerId_);
1600         return;
1601     }
1602 
1603     auto engine = EngineHelper::GetEngine(aceContainer->GetInstanceId());
1604     auto delegate = engine->GetFrontend();
1605     if (!delegate) {
1606         return;
1607     }
1608     delegate->OpenCustomDialog(dialogAttr, std::move(callback));
1609 }
1610 
OpenCustomDialogForService(const PromptDialogAttr & dialogAttr,std::function<void (int32_t)> && callback)1611 void SubwindowOhos::OpenCustomDialogForService(
1612     const PromptDialogAttr& dialogAttr, std::function<void(int32_t)>&& callback)
1613 {
1614     // temporary not support
1615     TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "temporary not support for service by promptAction with CustomBuilder");
1616 }
1617 
OpenCustomDialog(const PromptDialogAttr & dialogAttr,std::function<void (int32_t)> && callback)1618 void SubwindowOhos::OpenCustomDialog(const PromptDialogAttr& dialogAttr, std::function<void(int32_t)>&& callback)
1619 {
1620     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "open custom dialog, window parent id is %{public}d", parentContainerId_);
1621     if (parentContainerId_ >= MIN_PA_SERVICE_ID || parentContainerId_ < 0) {
1622         OpenCustomDialogForService(dialogAttr, std::move(callback));
1623     } else {
1624         OpenCustomDialogForAbility(dialogAttr, std::move(callback));
1625     }
1626 }
1627 
CloseCustomDialog(const int32_t dialogId)1628 void SubwindowOhos::CloseCustomDialog(const int32_t dialogId)
1629 {
1630     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "close custom dialog with id, childContainerId_ is %{public}d",
1631         childContainerId_);
1632     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1633     CHECK_NULL_VOID(aceContainer);
1634     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1635     CHECK_NULL_VOID(context);
1636     auto overlay = context->GetOverlayManager();
1637     CHECK_NULL_VOID(overlay);
1638     ContainerScope scope(childContainerId_);
1639     return overlay->CloseCustomDialog(dialogId);
1640 }
1641 
CloseCustomDialog(const WeakPtr<NG::UINode> & node,std::function<void (int32_t)> && callback)1642 void SubwindowOhos::CloseCustomDialog(const WeakPtr<NG::UINode>& node, std::function<void(int32_t)>&& callback)
1643 {
1644     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "close custom dialog with node, childContainerId_ is %{public}d",
1645         childContainerId_);
1646     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1647     CHECK_NULL_VOID(aceContainer);
1648     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1649     CHECK_NULL_VOID(context);
1650     auto overlay = context->GetOverlayManager();
1651     CHECK_NULL_VOID(overlay);
1652     ContainerScope scope(childContainerId_);
1653     return overlay->CloseCustomDialog(node, std::move(callback));
1654 }
1655 
ShowActionMenuForAbility(const std::string & title,const std::vector<ButtonInfo> & button,std::function<void (int32_t,int32_t)> && callback)1656 void SubwindowOhos::ShowActionMenuForAbility(
1657     const std::string& title, const std::vector<ButtonInfo>& button, std::function<void(int32_t, int32_t)>&& callback)
1658 {
1659     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show action menu for ability enter");
1660     SubwindowManager::GetInstance()->SetCurrentSubwindow(AceType::Claim(this));
1661 
1662     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1663     if (!aceContainer) {
1664         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "get container failed");
1665         return;
1666     }
1667 
1668     auto engine = EngineHelper::GetEngine(aceContainer->GetInstanceId());
1669     auto delegate = engine->GetFrontend();
1670     if (!delegate) {
1671         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "get frontend failed");
1672         return;
1673     }
1674     delegate->ShowActionMenu(title, button, std::move(callback));
1675 }
1676 
ShowActionMenuForService(const std::string & title,const std::vector<ButtonInfo> & button,std::function<void (int32_t,int32_t)> && callback)1677 void SubwindowOhos::ShowActionMenuForService(
1678     const std::string& title, const std::vector<ButtonInfo>& button, std::function<void(int32_t, int32_t)>&& callback)
1679 {
1680     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "show action menu for service enter");
1681     bool ret = CreateEventRunner();
1682     if (!ret) {
1683         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create event runner failed");
1684         return;
1685     }
1686 
1687     SubwindowManager::GetInstance()->SetCurrentDialogSubwindow(AceType::Claim(this));
1688     auto showDialogCallback = [title, &button, callbackParam = std::move(callback)]() {
1689         int32_t posX = 0;
1690         int32_t posY = 0;
1691         int32_t width = 0;
1692         int32_t height = 0;
1693         float density = 1.0f;
1694         auto subwindowOhos =
1695             AceType::DynamicCast<SubwindowOhos>(SubwindowManager::GetInstance()->GetCurrentDialogWindow());
1696         CHECK_NULL_VOID(subwindowOhos);
1697         subwindowOhos->GetToastDialogWindowProperty(width, height, posX, posY, density);
1698         bool ret = subwindowOhos->InitToastDialogWindow(width, height, posX, posY);
1699         if (!ret) {
1700             return;
1701         }
1702         ret = subwindowOhos->InitToastDialogView(width, height, density);
1703         if (!ret) {
1704             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "init toast dialog view failed");
1705             return;
1706         }
1707         auto childContainerId = subwindowOhos->GetChildContainerId();
1708         ContainerScope scope(childContainerId);
1709         auto container = Platform::DialogContainer::GetContainer(childContainerId);
1710         CHECK_NULL_VOID(container);
1711         container->SetFontScaleAndWeightScale(childContainerId);
1712         Platform::DialogContainer::ShowToastDialogWindow(childContainerId, posX, posY, width, height);
1713         Platform::DialogContainer::ShowActionMenu(childContainerId, title, button,
1714             std::move(const_cast<std::function<void(int32_t, int32_t)>&&>(callbackParam)));
1715     };
1716     isToastWindow_ = false;
1717     if (!handler_->PostTask(showDialogCallback)) {
1718         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "create show dialog callback failed");
1719         return;
1720     }
1721 }
1722 
CloseDialog(int32_t instanceId)1723 void SubwindowOhos::CloseDialog(int32_t instanceId)
1724 {
1725     TAG_LOGD(AceLogTag::ACE_SUB_WINDOW, "close dialog enter");
1726     Platform::DialogContainer::CloseWindow(instanceId);
1727 }
1728 
UpdateAceView(int32_t width,int32_t height,float density,int32_t containerId)1729 void SubwindowOhos::UpdateAceView(int32_t width, int32_t height, float density, int32_t containerId)
1730 {
1731     auto container = Platform::DialogContainer::GetContainer(containerId);
1732     CHECK_NULL_VOID(container);
1733     auto aceView = AceType::DynamicCast<Platform::AceViewOhos>(container->GetAceView());
1734     CHECK_NULL_VOID(aceView);
1735     if (aceView->GetWidth() != width || aceView->GetHeight() != height) {
1736         ViewportConfig config(width, height, density);
1737         Platform::AceViewOhos::SetViewportMetrics(aceView, config);
1738         Platform::AceViewOhos::SurfaceChanged(aceView, width, height, 0);
1739     }
1740 }
1741 
ShowActionMenu(const std::string & title,const std::vector<ButtonInfo> & button,std::function<void (int32_t,int32_t)> && callback)1742 void SubwindowOhos::ShowActionMenu(
1743     const std::string& title, const std::vector<ButtonInfo>& button, std::function<void(int32_t, int32_t)>&& callback)
1744 {
1745     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "show custom dialog, window parent id is %{public}d", parentContainerId_);
1746     if (parentContainerId_ >= MIN_PA_SERVICE_ID || parentContainerId_ < 0) {
1747         ShowActionMenuForService(title, button, std::move(callback));
1748     } else {
1749         ShowActionMenuForAbility(title, button, std::move(callback));
1750     }
1751 }
1752 
GetParentWindowRect() const1753 Rect SubwindowOhos::GetParentWindowRect() const
1754 {
1755     Rect rect;
1756     CHECK_NULL_RETURN(parentWindow_, rect);
1757     auto parentWindowRect = parentWindow_->GetRect();
1758     return Rect(parentWindowRect.posX_, parentWindowRect.posY_, parentWindowRect.width_, parentWindowRect.height_);
1759 }
1760 
GetUIExtensionHostWindowRect() const1761 Rect SubwindowOhos::GetUIExtensionHostWindowRect() const
1762 {
1763     Rect rect;
1764     CHECK_NULL_RETURN(parentWindow_, rect);
1765     auto id = GetUIExtensionHostWindowId();
1766     auto hostWindowRect = parentWindow_->GetHostWindowRect(id);
1767     return Rect(hostWindowRect.posX_, hostWindowRect.posY_, hostWindowRect.width_, hostWindowRect.height_);
1768 }
1769 
RequestFocus()1770 void SubwindowOhos::RequestFocus()
1771 {
1772     CHECK_NULL_VOID(window_);
1773     if (window_->IsFocused()) {
1774         TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "subwindow id:%{public}u already focused", window_->GetWindowId());
1775         // already focused, no need to focus
1776         return;
1777     }
1778     OHOS::Rosen::WMError ret = window_->RequestFocus();
1779     if (ret != OHOS::Rosen::WMError::WM_OK) {
1780         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "subindow id:%{public}u request focus failed with WMError: %{public}d",
1781             window_->GetWindowId(), static_cast<int32_t>(ret));
1782         return;
1783     }
1784     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW, "subwindow id:%{public}u request focus successfully.", window_->GetWindowId());
1785 }
1786 
IsFocused()1787 bool SubwindowOhos::IsFocused()
1788 {
1789     CHECK_NULL_RETURN(window_, false);
1790     return window_->IsFocused();
1791 }
1792 
HideFilter(bool isInSubWindow)1793 void SubwindowOhos::HideFilter(bool isInSubWindow)
1794 {
1795     RefPtr<Container> aceContainer = nullptr;
1796     if (isInSubWindow) {
1797         aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1798     } else {
1799         aceContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1800     }
1801 
1802     CHECK_NULL_VOID(aceContainer);
1803     auto pipelineContext = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1804     CHECK_NULL_VOID(pipelineContext);
1805     auto overlayManager = pipelineContext->GetOverlayManager();
1806     CHECK_NULL_VOID(overlayManager);
1807 
1808     auto containerId = isInSubWindow ? childContainerId_ : parentContainerId_;
1809     ContainerScope scope(containerId);
1810     overlayManager->RemoveFilterAnimation();
1811 }
1812 
HidePixelMap(bool startDrag,double x,double y,bool showAnimation)1813 void SubwindowOhos::HidePixelMap(bool startDrag, double x, double y, bool showAnimation)
1814 {
1815     auto parentAceContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1816     CHECK_NULL_VOID(parentAceContainer);
1817     auto parentPipeline = DynamicCast<NG::PipelineContext>(parentAceContainer->GetPipelineContext());
1818     CHECK_NULL_VOID(parentPipeline);
1819     auto manager = parentPipeline->GetOverlayManager();
1820     CHECK_NULL_VOID(manager);
1821     ContainerScope scope(parentContainerId_);
1822     if (!startDrag) {
1823         manager->RemovePreviewBadgeNode();
1824         manager->RemoveGatherNodeWithAnimation();
1825     }
1826     if (showAnimation) {
1827         manager->RemovePixelMapAnimation(startDrag, x, y, true);
1828     } else {
1829         manager->RemovePixelMap();
1830     }
1831 }
1832 
HideEventColumn()1833 void SubwindowOhos::HideEventColumn()
1834 {
1835     auto parentAceContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1836     CHECK_NULL_VOID(parentAceContainer);
1837     auto parentPipeline = DynamicCast<NG::PipelineContext>(parentAceContainer->GetPipelineContext());
1838     CHECK_NULL_VOID(parentPipeline);
1839     auto manager = parentPipeline->GetOverlayManager();
1840     CHECK_NULL_VOID(manager);
1841     ContainerScope scope(parentContainerId_);
1842     manager->RemoveEventColumn();
1843 }
1844 
ResizeWindowForFoldStatus(int32_t parentContainerId)1845 void SubwindowOhos::ResizeWindowForFoldStatus(int32_t parentContainerId)
1846 {
1847     auto callback = []() {
1848         auto subwindowOhos =
1849             AceType::DynamicCast<SubwindowOhos>(SubwindowManager::GetInstance()->GetCurrentDialogWindow());
1850         CHECK_NULL_VOID(subwindowOhos);
1851         auto childContainerId = subwindowOhos->GetChildContainerId();
1852         ContainerScope scope(childContainerId);
1853         auto window = Platform::DialogContainer::GetUIWindow(childContainerId);
1854         CHECK_NULL_VOID(window);
1855         auto defaultDisplay = Rosen::DisplayManager::GetInstance().GetDefaultDisplaySync();
1856         CHECK_NULL_VOID(defaultDisplay);
1857         auto ret = window->Resize(defaultDisplay->GetWidth(), defaultDisplay->GetHeight());
1858         if (ret != Rosen::WMError::WM_OK) {
1859             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Resize window by default display failed with errCode: %{public}d",
1860                 static_cast<int32_t>(ret));
1861             return;
1862         }
1863         auto container = Platform::DialogContainer::GetContainer(childContainerId);
1864         CHECK_NULL_VOID(container);
1865         // get ace_view
1866         auto aceView = AceType::DynamicCast<Platform::AceViewOhos>(container->GetAceView());
1867         CHECK_NULL_VOID(aceView);
1868         Platform::AceViewOhos::SurfaceChanged(aceView, defaultDisplay->GetWidth(), defaultDisplay->GetHeight(), 0);
1869     };
1870     if (parentContainerId > 0) {
1871         ResizeWindowForFoldStatus();
1872         return;
1873     }
1874     if (!handler_->PostTask(callback)) {
1875         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Resize Toast Window failed");
1876     }
1877 }
1878 
ResizeWindowForFoldStatus()1879 void SubwindowOhos::ResizeWindowForFoldStatus()
1880 {
1881     auto defaultDisplay = Rosen::DisplayManager::GetInstance().GetDefaultDisplaySync();
1882     CHECK_NULL_VOID(defaultDisplay);
1883     CHECK_NULL_VOID(window_);
1884     auto ret = window_->Resize(defaultDisplay->GetWidth(), defaultDisplay->GetHeight());
1885     if (ret != Rosen::WMError::WM_OK) {
1886         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Resize window by default display failed with errCode: %{public}d",
1887             static_cast<int32_t>(ret));
1888         return;
1889     }
1890     TAG_LOGI(AceLogTag::ACE_SUB_WINDOW,
1891         "SubwindowOhos window rect is resized to x: %{public}d, y: %{public}d, width: %{public}u, height: %{public}u",
1892         window_->GetRect().posX_, window_->GetRect().posY_, window_->GetRect().width_, window_->GetRect().height_);
1893 }
1894 
MarkDirtyDialogSafeArea()1895 void SubwindowOhos::MarkDirtyDialogSafeArea()
1896 {
1897     auto aceContainer = Platform::AceContainer::GetContainer(childContainerId_);
1898     CHECK_NULL_VOID(aceContainer);
1899     auto context = DynamicCast<NG::PipelineContext>(aceContainer->GetPipelineContext());
1900     CHECK_NULL_VOID(context);
1901     auto rootNode = context->GetRootElement();
1902     CHECK_NULL_VOID(rootNode);
1903     auto lastChild = rootNode->GetLastChild();
1904     CHECK_NULL_VOID(lastChild);
1905     lastChild->MarkDirtyNode(NG::PROPERTY_UPDATE_MEASURE);
1906 }
1907 
CheckHostWindowStatus() const1908 bool SubwindowOhos::CheckHostWindowStatus() const
1909 {
1910     auto parentContainer = Platform::AceContainer::GetContainer(parentContainerId_);
1911     CHECK_NULL_RETURN(parentContainer, false);
1912     sptr<OHOS::Rosen::Window> parentWindow = parentContainer->GetUIWindow(parentContainerId_);
1913     CHECK_NULL_RETURN(parentWindow, false);
1914     if (parentWindow->GetType() == Rosen::WindowType::WINDOW_TYPE_UI_EXTENSION) {
1915         auto parentPipeline = parentContainer->GetPipelineContext();
1916         CHECK_NULL_RETURN(parentPipeline, false);
1917         auto hostWindowId = parentPipeline->GetFocusWindowId();
1918         auto hostWindowRect = parentWindow->GetHostWindowRect(hostWindowId);
1919         auto isValid = GreatNotEqual(hostWindowRect.width_, 0) && GreatNotEqual(hostWindowRect.height_, 0);
1920         if (!isValid) {
1921             TAG_LOGW(AceLogTag::ACE_SUB_WINDOW,
1922                 "UIExtension Window failed to obtain host window information. Please check if permissions are enabled");
1923             return false;
1924         }
1925     }
1926     return true;
1927 }
1928 
Close()1929 bool SubwindowOhos::Close()
1930 {
1931     CHECK_NULL_RETURN(window_, false);
1932     window_->UnregisterSwitchFreeMultiWindowListener(freeMultiWindowListener_);
1933     OHOS::Rosen::WMError ret = window_->Close();
1934     if (ret != OHOS::Rosen::WMError::WM_OK) {
1935         TAG_LOGE(AceLogTag::ACE_SUB_WINDOW, "SubwindowOhos failed to close the dialog subwindow.");
1936         return false;
1937     }
1938     sptr<OHOS::Rosen::Window> uiWindow = nullptr;
1939     Ace::Platform::DialogContainer::SetUIWindow(childContainerId_, uiWindow);
1940     return true;
1941 }
1942 
IsFreeMultiWindow() const1943 bool SubwindowOhos::IsFreeMultiWindow() const
1944 {
1945     if (!parentWindow_) {
1946         TAG_LOGW(AceLogTag::ACE_SUB_WINDOW, "Window is null, failed to get freeMultiWindow status");
1947         return false;
1948     }
1949 
1950     return parentWindow_->GetFreeMultiWindowModeEnabledState();
1951 }
1952 
OnFreeMultiWindowSwitch(bool enable)1953 void SubwindowOhos::OnFreeMultiWindowSwitch(bool enable)
1954 {
1955     for (auto&& [id, callback] : freeMultiWindowSwitchCallbackMap_) {
1956         if (callback) {
1957             callback(enable);
1958         }
1959     }
1960 }
1961 
RegisterFreeMultiWindowSwitchCallback(std::function<void (bool)> && callback)1962 int32_t SubwindowOhos::RegisterFreeMultiWindowSwitchCallback(std::function<void(bool)>&& callback)
1963 {
1964     if (callback) {
1965         freeMultiWindowSwitchCallbackMap_.emplace(++callbackId_, std::move(callback));
1966         return callbackId_;
1967     }
1968     return 0;
1969 }
1970 
UnRegisterFreeMultiWindowSwitchCallback(int32_t callbackId)1971 void SubwindowOhos::UnRegisterFreeMultiWindowSwitchCallback(int32_t callbackId)
1972 {
1973     freeMultiWindowSwitchCallbackMap_.erase(callbackId);
1974 }
1975 } // namespace OHOS::Ace
1976