• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 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 #include "core/components_ng/pattern/dialog/custom_dialog_controller_model_ng.h"
16 #include "core/components_ng/pattern/dialog/dialog_pattern.h"
17 #include "core/components_ng/pattern/overlay/dialog_manager.h"
18 
19 #include "base/memory/ace_type.h"
20 #include "base/subwindow/subwindow_manager.h"
21 #include "base/thread/task_executor.h"
22 #include "core/common/container_scope.h"
23 
24 namespace OHOS::Ace::NG {
SetOpenDialog(DialogProperties & dialogProperties,const WeakPtr<AceType> & controller,std::vector<WeakPtr<AceType>> & dialogs,bool & pending,bool & isShown,std::function<void ()> && cancelTask,std::function<void ()> && buildFunc,RefPtr<AceType> & dialogComponent,RefPtr<AceType> & customDialog,std::list<DialogOperation> & dialogOperation)25 void CustomDialogControllerModelNG::SetOpenDialog(DialogProperties& dialogProperties,
26     const WeakPtr<AceType>& controller, std::vector<WeakPtr<AceType>>& dialogs,
27     bool& pending, bool& isShown, std::function<void()>&& cancelTask, std::function<void()>&& buildFunc,
28     RefPtr<AceType>& dialogComponent, RefPtr<AceType>& customDialog, std::list<DialogOperation>& dialogOperation)
29 {
30     auto container = Container::Current();
31     auto currentId = Container::CurrentId();
32     CHECK_NULL_VOID(container);
33     if (container->IsSubContainer() && !dialogProperties.isShowInSubWindow) {
34         currentId = SubwindowManager::GetInstance()->GetParentContainerId(Container::CurrentId());
35         container = AceEngine::Get().GetContainer(currentId);
36         CHECK_NULL_VOID(container);
37     }
38     ContainerScope scope(currentId);
39     auto pipelineContext = container->GetPipelineContext();
40     CHECK_NULL_VOID(pipelineContext);
41     auto context = AceType::DynamicCast<NG::PipelineContext>(pipelineContext);
42     CHECK_NULL_VOID(context);
43     auto overlayManager = context->GetOverlayManager();
44     CHECK_NULL_VOID(overlayManager);
45     if (dialogProperties.dialogLevelMode == LevelMode::EMBEDDED) {
46         auto embeddedOverlay = NG::DialogManager::GetEmbeddedOverlay(dialogProperties.dialogLevelUniqueId, context);
47         if (embeddedOverlay) {
48             overlayManager = embeddedOverlay;
49         }
50     }
51     dialogProperties.onStatusChanged = [&isShown](bool isShownStatus) {
52         if (!isShownStatus) {
53             isShown = isShownStatus;
54         }
55     };
56 
57     auto executor = context->GetTaskExecutor();
58     if (!executor) {
59         TAG_LOGE(AceLogTag::ACE_DIALOG, "Task executor is null.");
60         return;
61     }
62     auto task = [currentId, controller, &dialogProperties, &dialogs, func = std::move(buildFunc),
63                     weakOverlayManager = AceType::WeakClaim(AceType::RawPtr(overlayManager))]() mutable {
64         ContainerScope scope(currentId);
65         RefPtr<NG::FrameNode> dialog;
66         auto overlayManager = weakOverlayManager.Upgrade();
67         CHECK_NULL_VOID(overlayManager);
68         auto controllerPtr = controller.Upgrade();
69         CHECK_NULL_VOID(controllerPtr);
70         auto container = Container::Current();
71         CHECK_NULL_VOID(container);
72         if (dialogProperties.isShowInSubWindow) {
73             dialog = SubwindowManager::GetInstance()->ShowDialogNG(dialogProperties, std::move(func));
74             CHECK_NULL_VOID(dialog);
75             if (dialogProperties.isModal && !dialogProperties.isScenceBoardDialog &&
76                 !container->IsUIExtensionWindow()) {
77                 auto mask = overlayManager->SetDialogMask(dialogProperties);
78                 CHECK_NULL_VOID(mask);
79                 overlayManager->SetMaskNodeId(dialog->GetId(), mask->GetId());
80             }
81         } else {
82             dialog = overlayManager->ShowDialog(dialogProperties, std::move(func), false);
83         }
84         CHECK_NULL_VOID(dialog);
85         dialogs.emplace_back(dialog);
86     };
87     executor->PostTask(task, TaskExecutor::TaskType::UI, "ArkUIDialogShowCustomDialog");
88 }
89 
SetOpenDialogWithNode(DialogProperties & dialogProperties,const RefPtr<UINode> & customNode)90 RefPtr<UINode> CustomDialogControllerModelNG::SetOpenDialogWithNode(DialogProperties& dialogProperties,
91     const RefPtr<UINode>& customNode)
92 {
93     ContainerScope scope(Container::CurrentIdSafely());
94     auto container = Container::Current();
95     CHECK_NULL_RETURN(container, nullptr);
96     if (container->IsSubContainer() && !dialogProperties.isShowInSubWindow) {
97         auto currentId = SubwindowManager::GetInstance()->GetParentContainerId(Container::CurrentId());
98         container = AceEngine::Get().GetContainer(currentId);
99         CHECK_NULL_RETURN(container, nullptr);
100     }
101     auto pipelineContext = container->GetPipelineContext();
102     CHECK_NULL_RETURN(pipelineContext, nullptr);
103     auto context = AceType::DynamicCast<NG::PipelineContext>(pipelineContext);
104     CHECK_NULL_RETURN(context, nullptr);
105     auto overlayManager = context->GetOverlayManager();
106     CHECK_NULL_RETURN(overlayManager, nullptr);
107     if (dialogProperties.dialogLevelMode == LevelMode::EMBEDDED) {
108         auto embeddedOverlay = NG::DialogManager::GetEmbeddedOverlay(dialogProperties.dialogLevelUniqueId, context);
109         if (embeddedOverlay) {
110             overlayManager = embeddedOverlay;
111         }
112     }
113     RefPtr<NG::FrameNode> dialog;
114     if (dialogProperties.isShowInSubWindow) {
115         dialog = SubwindowManager::GetInstance()->ShowDialogNGWithNode(dialogProperties, customNode);
116         if (dialogProperties.isModal && !dialogProperties.isScenceBoardDialog && !container->IsUIExtensionWindow()) {
117             DialogProperties Maskarg;
118             Maskarg.isMask = true;
119             Maskarg.autoCancel = dialogProperties.autoCancel;
120             Maskarg.maskColor = dialogProperties.maskColor;
121             auto mask = overlayManager->ShowDialogWithNode(Maskarg, nullptr, false);
122             CHECK_NULL_RETURN(mask, dialog);
123             overlayManager->SetMaskNodeId(dialog->GetId(), mask->GetId());
124         }
125     } else {
126         dialog = overlayManager->ShowDialogWithNode(dialogProperties, customNode, false);
127     }
128     return dialog;
129 }
130 
SetCloseDialog(DialogProperties & dialogProperties,const WeakPtr<AceType> & controller,std::vector<WeakPtr<AceType>> & dialogs,bool & pending,bool & isShown,std::function<void ()> && cancelTask,RefPtr<AceType> & dialogComponent,RefPtr<AceType> & customDialog,std::list<DialogOperation> & dialogOperation)131 void CustomDialogControllerModelNG::SetCloseDialog(DialogProperties& dialogProperties,
132     const WeakPtr<AceType>& controller, std::vector<WeakPtr<AceType>>& dialogs,
133     bool& pending, bool& isShown, std::function<void()>&& cancelTask, RefPtr<AceType>& dialogComponent,
134     RefPtr<AceType>& customDialog, std::list<DialogOperation>& dialogOperation)
135 {
136     auto container = Container::Current();
137     auto currentId = Container::CurrentId();
138     CHECK_NULL_VOID(container);
139     if (container->IsSubContainer() && !dialogProperties.isShowInSubWindow) {
140         currentId = SubwindowManager::GetInstance()->GetParentContainerId(Container::CurrentId());
141         container = AceEngine::Get().GetContainer(currentId);
142         CHECK_NULL_VOID(container);
143     }
144     ContainerScope scope(currentId);
145     auto pipelineContext = container->GetPipelineContext();
146     CHECK_NULL_VOID(pipelineContext);
147     auto context = AceType::DynamicCast<NG::PipelineContext>(pipelineContext);
148     CHECK_NULL_VOID(context);
149     auto overlayManager = context->GetOverlayManager();
150     CHECK_NULL_VOID(overlayManager);
151     auto executor = context->GetTaskExecutor();
152     CHECK_NULL_VOID(executor);
153     auto task = [controller, &dialogs, &dialogProperties,
154                     weakOverlayManager = AceType::WeakClaim(AceType::RawPtr(overlayManager))]() {
155         auto overlayManager = weakOverlayManager.Upgrade();
156         CHECK_NULL_VOID(overlayManager);
157         auto controllerPtr = controller.Upgrade();
158         CHECK_NULL_VOID(controllerPtr);
159         RefPtr<NG::FrameNode> dialog;
160         while (!dialogs.empty()) {
161             dialog = AceType::DynamicCast<NG::FrameNode>(dialogs.back().Upgrade());
162             if (dialog && !dialog->IsRemoving()) {
163                 // get the dialog not removed currently
164                 break;
165             }
166             dialogs.pop_back();
167         }
168         if (dialogs.empty()) {
169             return;
170         }
171         CHECK_NULL_VOID(dialog);
172         if (dialogProperties.isShowInSubWindow) {
173             SubwindowManager::GetInstance()->CloseDialogNG(dialog);
174             dialogs.pop_back();
175         } else {
176             auto dialogPattern = dialog->GetPattern<DialogPattern>();
177             if (dialogProperties.dialogLevelMode == LevelMode::EMBEDDED && dialogPattern) {
178                 overlayManager = dialogPattern->GetEmbeddedOverlay(overlayManager);
179             }
180             overlayManager->CloseDialog(dialog);
181         }
182     };
183     executor->PostTask(task, TaskExecutor::TaskType::UI, "ArkUIDialogCloseCustomDialog");
184 }
185 
SetCloseDialogForNDK(FrameNode * dialogNode)186 void CustomDialogControllerModelNG::SetCloseDialogForNDK(FrameNode* dialogNode)
187 {
188     CHECK_NULL_VOID(dialogNode);
189     ContainerScope scope(Container::CurrentIdSafely());
190     auto container = Container::Current();
191     dialogNode->SetIsUseTransitionAnimator(true);
192     auto dialogRef = AceType::Claim(dialogNode);
193     CHECK_NULL_VOID(container);
194     auto pipelineContext = container->GetPipelineContext();
195     CHECK_NULL_VOID(pipelineContext);
196     auto context = AceType::DynamicCast<NG::PipelineContext>(pipelineContext);
197     CHECK_NULL_VOID(context);
198     auto overlayManager = context->GetOverlayManager();
199     CHECK_NULL_VOID(overlayManager);
200     auto currentOverlay = DialogManager::GetInstance().GetEmbeddedOverlayWithNode(dialogRef);
201     if (currentOverlay) {
202         overlayManager = currentOverlay;
203     }
204     overlayManager->CloseDialog(dialogRef);
205 }
206 } // namespace OHOS::Ace::NG
207