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 
16 #include "window_session_impl.h"
17 
18 #include <cstdlib>
19 #include <optional>
20 
21 #include <common/rs_common_def.h>
22 #include <filesystem>
23 #include <fstream>
24 #include <ipc_skeleton.h>
25 #include <hisysevent.h>
26 #include <parameters.h>
27 #ifdef IMF_ENABLE
28 #include <input_method_controller.h>
29 #endif // IMF_ENABLE
30 #include <transaction/rs_interfaces.h>
31 #include <transaction/rs_transaction.h>
32 
33 #include "anr_handler.h"
34 #include "color_parser.h"
35 #include "display_info.h"
36 #include "display_manager.h"
37 #include "hitrace_meter.h"
38 #include "session_permission.h"
39 #include "key_event.h"
40 #include "session/container/include/window_event_channel.h"
41 #include "session_manager/include/session_manager.h"
42 #include "vsync_station.h"
43 #include "window_adapter.h"
44 #include "window_manager_hilog.h"
45 #include "window_helper.h"
46 #include "color_parser.h"
47 #include "singleton_container.h"
48 #include "perform_reporter.h"
49 #include "picture_in_picture_manager.h"
50 #include "parameters.h"
51 
52 namespace OHOS::Accessibility {
53 class AccessibilityEventInfo;
54 }
55 namespace OHOS {
56 namespace Rosen {
57 namespace {
58 constexpr HiviewDFX::HiLogLabel LABEL = {LOG_CORE, HILOG_DOMAIN_WINDOW, "WindowSessionImpl"};
59 constexpr int32_t FULL_CIRCLE_DEGREE = 360;
60 constexpr int32_t ONE_FOURTH_FULL_CIRCLE_DEGREE = 90;
61 constexpr int32_t FORCE_SPLIT_MODE = 5;
62 
63 /**
64  * DFX
65  */
66 const std::string SET_UIEXTENSION_DESTROY_TIMEOUT_LISTENER_TASK_NAME = "SetUIExtDestroyTimeoutListener";
67 constexpr int64_t SET_UIEXTENSION_DESTROY_TIMEOUT_TIME_MS = 4000;
68 
CheckIfNeedCommitRsTransaction(WindowSizeChangeReason wmReason)69 bool CheckIfNeedCommitRsTransaction(WindowSizeChangeReason wmReason)
70 {
71     if (wmReason == WindowSizeChangeReason::FULL_TO_SPLIT ||
72         wmReason == WindowSizeChangeReason::FULL_TO_FLOATING || wmReason == WindowSizeChangeReason::RECOVER ||
73         wmReason == WindowSizeChangeReason::MAXIMIZE) {
74         return false;
75     }
76     return true;
77 }
78 
FillViewportConfig(Rect rect,float density,int32_t orientation,uint32_t transformHint)79 Ace::ViewportConfig FillViewportConfig(Rect rect, float density, int32_t orientation, uint32_t transformHint)
80 {
81     Ace::ViewportConfig config;
82     config.SetSize(rect.width_, rect.height_);
83     config.SetPosition(rect.posX_, rect.posY_);
84     config.SetDensity(density);
85     config.SetOrientation(orientation);
86     config.SetTransformHint(transformHint);
87     return config;
88 }
89 
GetAceContentInfoType(BackupAndRestoreType type)90 Ace::ContentInfoType GetAceContentInfoType(BackupAndRestoreType type)
91 {
92     auto contentInfoType = Ace::ContentInfoType::NONE;
93     switch (type) {
94         case BackupAndRestoreType::CONTINUATION:
95             contentInfoType = Ace::ContentInfoType::CONTINUATION;
96             break;
97         case BackupAndRestoreType::APP_RECOVERY:
98             contentInfoType = Ace::ContentInfoType::APP_RECOVERY;
99             break;
100         case BackupAndRestoreType::RESOURCESCHEDULE_RECOVERY:
101             contentInfoType = Ace::ContentInfoType::RESOURCESCHEDULE_RECOVERY;
102             break;
103         case BackupAndRestoreType::NONE:
104             [[fallthrough]];
105         default:
106             break;
107     }
108     return contentInfoType;
109 }
110 }
111 
112 std::map<int32_t, std::vector<sptr<IWindowLifeCycle>>> WindowSessionImpl::lifecycleListeners_;
113 std::map<int32_t, std::vector<sptr<IDisplayMoveListener>>> WindowSessionImpl::displayMoveListeners_;
114 std::map<int32_t, std::vector<sptr<IWindowChangeListener>>> WindowSessionImpl::windowChangeListeners_;
115 std::map<int32_t, std::vector<sptr<IAvoidAreaChangedListener>>> WindowSessionImpl::avoidAreaChangeListeners_;
116 std::map<int32_t, std::vector<sptr<IDialogDeathRecipientListener>>> WindowSessionImpl::dialogDeathRecipientListeners_;
117 std::map<int32_t, std::vector<sptr<IDialogTargetTouchListener>>> WindowSessionImpl::dialogTargetTouchListener_;
118 std::map<int32_t, std::vector<sptr<IOccupiedAreaChangeListener>>> WindowSessionImpl::occupiedAreaChangeListeners_;
119 std::map<int32_t, std::vector<sptr<IScreenshotListener>>> WindowSessionImpl::screenshotListeners_;
120 std::map<int32_t, std::vector<sptr<ITouchOutsideListener>>> WindowSessionImpl::touchOutsideListeners_;
121 std::map<int32_t, std::vector<IWindowVisibilityListenerSptr>> WindowSessionImpl::windowVisibilityChangeListeners_;
122 std::mutex WindowSessionImpl::displayIdChangeListenerMutex_;
123 std::map<int32_t, std::vector<IDisplayIdChangeListenerSptr>> WindowSessionImpl::displayIdChangeListeners_;
124 std::map<int32_t, std::vector<IWindowNoInteractionListenerSptr>> WindowSessionImpl::windowNoInteractionListeners_;
125 std::map<int32_t, std::vector<sptr<IWindowTitleButtonRectChangedListener>>>
126     WindowSessionImpl::windowTitleButtonRectChangeListeners_;
127 std::map<int32_t, std::vector<sptr<IWindowRectChangeListener>>> WindowSessionImpl::windowRectChangeListeners_;
128 std::map<int32_t, sptr<ISubWindowCloseListener>> WindowSessionImpl::subWindowCloseListeners_;
129 std::map<int32_t, sptr<IMainWindowCloseListener>> WindowSessionImpl::mainWindowCloseListeners_;
130 std::map<int32_t, std::vector<sptr<ISwitchFreeMultiWindowListener>>> WindowSessionImpl::switchFreeMultiWindowListeners_;
131 std::recursive_mutex WindowSessionImpl::lifeCycleListenerMutex_;
132 std::recursive_mutex WindowSessionImpl::windowChangeListenerMutex_;
133 std::recursive_mutex WindowSessionImpl::avoidAreaChangeListenerMutex_;
134 std::recursive_mutex WindowSessionImpl::dialogDeathRecipientListenerMutex_;
135 std::recursive_mutex WindowSessionImpl::dialogTargetTouchListenerMutex_;
136 std::recursive_mutex WindowSessionImpl::occupiedAreaChangeListenerMutex_;
137 std::recursive_mutex WindowSessionImpl::screenshotListenerMutex_;
138 std::recursive_mutex WindowSessionImpl::touchOutsideListenerMutex_;
139 std::recursive_mutex WindowSessionImpl::windowVisibilityChangeListenerMutex_;
140 std::recursive_mutex WindowSessionImpl::windowNoInteractionListenerMutex_;
141 std::recursive_mutex WindowSessionImpl::windowStatusChangeListenerMutex_;
142 std::recursive_mutex WindowSessionImpl::windowTitleButtonRectChangeListenerMutex_;
143 std::mutex WindowSessionImpl::displayMoveListenerMutex_;
144 std::mutex WindowSessionImpl::windowRectChangeListenerMutex_;
145 std::mutex WindowSessionImpl::subWindowCloseListenersMutex_;
146 std::mutex WindowSessionImpl::mainWindowCloseListenersMutex_;
147 std::mutex WindowSessionImpl::switchFreeMultiWindowListenerMutex_;
148 std::map<std::string, std::pair<int32_t, sptr<WindowSessionImpl>>> WindowSessionImpl::windowSessionMap_;
149 std::shared_mutex WindowSessionImpl::windowSessionMutex_;
150 std::set<sptr<WindowSessionImpl>> WindowSessionImpl::windowExtensionSessionSet_;
151 std::shared_mutex WindowSessionImpl::windowExtensionSessionMutex_;
152 std::map<int32_t, std::vector<sptr<WindowSessionImpl>>> WindowSessionImpl::subWindowSessionMap_;
153 std::map<int32_t, std::vector<sptr<IWindowStatusChangeListener>>> WindowSessionImpl::windowStatusChangeListeners_;
154 bool WindowSessionImpl::isUIExtensionAbilityProcess_ = false;
155 
156 #define CALL_LIFECYCLE_LISTENER(windowLifecycleCb, listeners) \
157     do {                                                      \
158         for (auto& listener : (listeners)) {                  \
159             if (listener != nullptr) {            \
160                 listener->windowLifecycleCb();    \
161             }                                                 \
162         }                                                     \
163     } while (0)
164 
165 #define CALL_LIFECYCLE_LISTENER_WITH_PARAM(windowLifecycleCb, listeners, param) \
166     do {                                                                        \
167         for (auto& listener : (listeners)) {                                    \
168             if (listener != nullptr) {                                         \
169                 listener->windowLifecycleCb(param);                 \
170             }                                                                   \
171         }                                                                       \
172     } while (0)
173 
174 #define CALL_UI_CONTENT(uiContentCb)                                           \
175     do {                                                                       \
176         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();   \
177         if (uiContent != nullptr) {                                            \
178             uiContent->uiContentCb();                                          \
179         }                                                                      \
180     } while (0)
181 
182 #define CHECK_HOST_SESSION_RETURN_IF_NULL(hostSession)                         \
183     do {                                                                       \
184         if ((hostSession) == nullptr) {                                        \
185             TLOGE(WmsLogTag::DEFAULT, "hostSession is null");                  \
186             return;                                                            \
187         }                                                                      \
188     } while (false)
189 
190 #define CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, ret)              \
191     do {                                                                       \
192         if ((hostSession) == nullptr) {                                        \
193             TLOGE(WmsLogTag::DEFAULT, "hostSession is null");                  \
194             return ret;                                                        \
195         }                                                                      \
196     } while (false)
197 
WindowSessionImpl(const sptr<WindowOption> & option)198 WindowSessionImpl::WindowSessionImpl(const sptr<WindowOption>& option)
199 {
200     WLOGFD("[WMSCom]WindowSessionImpl");
201     property_ = new (std::nothrow) WindowSessionProperty();
202     if (property_ == nullptr) {
203         WLOGFE("[WMSCom]Property is null");
204         return;
205     }
206     WindowType optionWindowType = option->GetWindowType();
207     SessionInfo sessionInfo;
208     sessionInfo.bundleName_ = option->GetBundleName();
209     property_->SetSessionInfo(sessionInfo);
210     property_->SetWindowName(option->GetWindowName());
211     property_->SetRequestRect(option->GetWindowRect());
212     property_->SetWindowType(optionWindowType);
213     property_->SetFocusable(option->GetFocusable());
214     property_->SetTouchable(option->GetTouchable());
215     property_->SetDisplayId(option->GetDisplayId());
216     property_->SetParentId(option->GetParentId());
217     property_->SetTurnScreenOn(option->IsTurnScreenOn());
218     property_->SetKeepScreenOn(option->IsKeepScreenOn());
219     property_->SetWindowMode(option->GetWindowMode());
220     property_->SetWindowFlags(option->GetWindowFlags());
221     property_->SetCallingSessionId(option->GetCallingWindow());
222     property_->SetExtensionFlag(option->GetExtensionTag());
223     property_->SetTopmost(option->GetWindowTopmost());
224     property_->SetRealParentId(option->GetRealParentId());
225     property_->SetParentWindowType(option->GetParentWindowType());
226     property_->SetUIExtensionUsage(static_cast<UIExtensionUsage>(option->GetUIExtensionUsage()));
227     layoutCallback_ = sptr<FutureCallback>::MakeSptr();
228     property_->SetIsUIExtensionSubWindowFlag(option->GetIsUIExtensionSubWindowFlag());
229     isMainHandlerAvailable_ = option->GetMainHandlerAvailable();
230     isIgnoreSafeArea_ = WindowHelper::IsSubWindow(optionWindowType);
231     windowOption_ = option;
232     surfaceNode_ = CreateSurfaceNode(property_->GetWindowName(), optionWindowType);
233     handler_ = std::make_shared<AppExecFwk::EventHandler>(AppExecFwk::EventRunner::GetMainEventRunner());
234     if (surfaceNode_ != nullptr) {
235         vsyncStation_ = std::make_shared<VsyncStation>(surfaceNode_->GetId());
236         if (WindowHelper::IsSubWindow(GetType())) {
237             surfaceNode_->SetFrameGravity(Gravity::TOP_LEFT);
238         }
239     }
240 }
241 
IsPcWindow() const242 bool WindowSessionImpl::IsPcWindow() const
243 {
244     return (windowSystemConfig_.uiType_ == UI_TYPE_PC);
245 }
246 
IsPcOrPadCapabilityEnabled() const247 bool WindowSessionImpl::IsPcOrPadCapabilityEnabled() const
248 {
249     return WindowSessionImpl::IsPcOrPadFreeMultiWindowMode() || property_->GetIsPcAppInPad();
250 }
251 
IsPcOrPadFreeMultiWindowMode() const252 bool WindowSessionImpl::IsPcOrPadFreeMultiWindowMode() const
253 {
254     return windowSystemConfig_.uiType_ == UI_TYPE_PC || IsFreeMultiWindowMode();
255 }
256 
MakeSubOrDialogWindowDragableAndMoveble()257 void WindowSessionImpl::MakeSubOrDialogWindowDragableAndMoveble()
258 {
259     TLOGI(WmsLogTag::WMS_LIFE, "Called %{public}d.", GetPersistentId());
260     if (IsPcOrPadCapabilityEnabled() && windowOption_ != nullptr) {
261         if (WindowHelper::IsSubWindow(property_->GetWindowType())) {
262             TLOGI(WmsLogTag::WMS_LIFE, "create subwindow, title: %{public}s, decorEnable: %{public}d",
263                 windowOption_->GetSubWindowTitle().c_str(), windowOption_->GetSubWindowDecorEnable());
264             property_->SetDecorEnable(windowOption_->GetSubWindowDecorEnable());
265             property_->SetDragEnabled(windowOption_->GetSubWindowDecorEnable());
266             subWindowTitle_ = windowOption_->GetSubWindowTitle();
267         }
268         bool isDialog = WindowHelper::IsDialogWindow(property_->GetWindowType());
269         if (isDialog) {
270             bool dialogDecorEnable = windowOption_->GetDialogDecorEnable();
271             property_->SetDecorEnable(dialogDecorEnable);
272             property_->SetDragEnabled(dialogDecorEnable);
273             dialogTitle_ = windowOption_->GetDialogTitle();
274             TLOGI(WmsLogTag::WMS_LIFE, "create dialogWindow, title: %{public}s, decorEnable: %{public}d",
275                 dialogTitle_.c_str(), dialogDecorEnable);
276         }
277     }
278 }
279 
CreateSurfaceNode(std::string name,WindowType type)280 RSSurfaceNode::SharedPtr WindowSessionImpl::CreateSurfaceNode(std::string name, WindowType type)
281 {
282     struct RSSurfaceNodeConfig rsSurfaceNodeConfig;
283     rsSurfaceNodeConfig.SurfaceNodeName = name;
284     RSSurfaceNodeType rsSurfaceNodeType = RSSurfaceNodeType::DEFAULT;
285     switch (type) {
286         case WindowType::WINDOW_TYPE_BOOT_ANIMATION:
287         case WindowType::WINDOW_TYPE_POINTER:
288             rsSurfaceNodeType = RSSurfaceNodeType::SELF_DRAWING_WINDOW_NODE;
289             break;
290         case WindowType::WINDOW_TYPE_APP_MAIN_WINDOW:
291             rsSurfaceNodeType = RSSurfaceNodeType::APP_WINDOW_NODE;
292             break;
293         case WindowType::WINDOW_TYPE_UI_EXTENSION:
294             TLOGI(WmsLogTag::WMS_LIFE, "uiExtensionUsage = %{public}u", property_->GetUIExtensionUsage());
295             if (property_->GetUIExtensionUsage() == UIExtensionUsage::CONSTRAINED_EMBEDDED) {
296                 rsSurfaceNodeType = RSSurfaceNodeType::UI_EXTENSION_SECURE_NODE;
297             } else {
298                 rsSurfaceNodeType = RSSurfaceNodeType::UI_EXTENSION_COMMON_NODE;
299             }
300             break;
301         case WindowType::WINDOW_TYPE_PIP:
302             rsSurfaceNodeType = RSSurfaceNodeType::APP_WINDOW_NODE;
303             break;
304         default:
305             rsSurfaceNodeType = RSSurfaceNodeType::DEFAULT;
306             break;
307     }
308     return RSSurfaceNode::Create(rsSurfaceNodeConfig, rsSurfaceNodeType);
309 }
310 
~WindowSessionImpl()311 WindowSessionImpl::~WindowSessionImpl()
312 {
313     WLOGFD("[WMSCom]~WindowSessionImpl, id: %{public}d", GetPersistentId());
314     Destroy(true, false);
315 }
316 
GetWindowId() const317 uint32_t WindowSessionImpl::GetWindowId() const
318 {
319     return static_cast<uint32_t>(GetPersistentId()) & 0xffffffff; // 0xffffffff: to get low 32 bits
320 }
321 
GetDisplayId() const322 uint64_t WindowSessionImpl::GetDisplayId() const
323 {
324     return property_->GetDisplayId();
325 }
326 
GetParentId() const327 int32_t WindowSessionImpl::GetParentId() const
328 {
329     // 0xffffffff: to get low 32 bits
330     uint32_t parentID = static_cast<uint32_t>(property_->GetParentPersistentId()) & 0x7fffffff;
331     return static_cast<int32_t>(parentID);
332 }
333 
IsWindowSessionInvalid() const334 bool WindowSessionImpl::IsWindowSessionInvalid() const
335 {
336     bool res = ((GetHostSession() == nullptr) || (GetPersistentId() == INVALID_SESSION_ID) ||
337         (state_ == WindowState::STATE_DESTROYED));
338     if (res) {
339         TLOGW(WmsLogTag::WMS_LIFE, "already destroyed or not created! id: %{public}d state_: %{public}u",
340             GetPersistentId(), state_);
341     }
342     return res;
343 }
344 
IsMainHandlerAvailable() const345 bool WindowSessionImpl::IsMainHandlerAvailable() const
346 {
347     TLOGI(WmsLogTag::DEFAULT, "id:%{public}d, isAvailable:%{public}u",
348         GetPersistentId(), isMainHandlerAvailable_);
349     return isMainHandlerAvailable_;
350 }
351 
GetPersistentId() const352 int32_t WindowSessionImpl::GetPersistentId() const
353 {
354     if (property_) {
355         return property_->GetPersistentId();
356     }
357     return INVALID_SESSION_ID;
358 }
359 
GetProperty() const360 sptr<WindowSessionProperty> WindowSessionImpl::GetProperty() const
361 {
362     return property_;
363 }
364 
GetSystemSessionConfig() const365 SystemSessionConfig WindowSessionImpl::GetSystemSessionConfig() const
366 {
367     return windowSystemConfig_;
368 }
369 
GetHostSession() const370 sptr<ISession> WindowSessionImpl::GetHostSession() const
371 {
372     std::lock_guard<std::mutex> lock(hostSessionMutex_);
373     return hostSession_;
374 }
375 
GetColorSpaceFromSurfaceGamut(GraphicColorGamut colorGamut)376 ColorSpace WindowSessionImpl::GetColorSpaceFromSurfaceGamut(GraphicColorGamut colorGamut)
377 {
378     if (colorGamut == GraphicColorGamut::GRAPHIC_COLOR_GAMUT_SRGB) {
379         return ColorSpace::COLOR_SPACE_DEFAULT;
380     } else if (colorGamut == GraphicColorGamut::GRAPHIC_COLOR_GAMUT_DCI_P3) {
381         return ColorSpace::COLOR_SPACE_WIDE_GAMUT;
382     } else {
383         WLOGFE("try to get not exist ColorSpace");
384         return ColorSpace::COLOR_SPACE_DEFAULT;
385     }
386 }
387 
GetSurfaceGamutFromColorSpace(ColorSpace colorSpace)388 GraphicColorGamut WindowSessionImpl::GetSurfaceGamutFromColorSpace(ColorSpace colorSpace)
389 {
390     if (colorSpace == ColorSpace::COLOR_SPACE_DEFAULT) {
391         return GraphicColorGamut::GRAPHIC_COLOR_GAMUT_SRGB;
392     } else if (colorSpace == ColorSpace::COLOR_SPACE_WIDE_GAMUT) {
393         return GraphicColorGamut::GRAPHIC_COLOR_GAMUT_DCI_P3;
394     } else {
395         WLOGFE("try to get not exist colorGamut");
396         return GraphicColorGamut::GRAPHIC_COLOR_GAMUT_SRGB;
397     }
398 }
399 
IsSupportWideGamut()400 bool WindowSessionImpl::IsSupportWideGamut()
401 {
402     return true;
403 }
404 
SetColorSpace(ColorSpace colorSpace)405 void WindowSessionImpl::SetColorSpace(ColorSpace colorSpace)
406 {
407     if (IsWindowSessionInvalid() || surfaceNode_ == nullptr) {
408         TLOGE(WmsLogTag::DEFAULT, "session is invalid");
409         return;
410     }
411     auto colorGamut = GetSurfaceGamutFromColorSpace(colorSpace);
412     surfaceNode_->SetColorSpace(colorGamut);
413 }
414 
GetColorSpace()415 ColorSpace WindowSessionImpl::GetColorSpace()
416 {
417     if (IsWindowSessionInvalid() || surfaceNode_ == nullptr) {
418         TLOGE(WmsLogTag::DEFAULT, "session is invalid");
419         return ColorSpace::COLOR_SPACE_DEFAULT;
420     }
421     GraphicColorGamut colorGamut = surfaceNode_->GetColorSpace();
422     return GetColorSpaceFromSurfaceGamut(colorGamut);
423 }
424 
WindowSessionCreateCheck()425 WMError WindowSessionImpl::WindowSessionCreateCheck()
426 {
427     if (!property_ || vsyncStation_ == nullptr || !vsyncStation_->IsVsyncReceiverCreated()) {
428         return WMError::WM_ERROR_NULLPTR;
429     }
430     const auto& name = property_->GetWindowName();
431     std::shared_lock<std::shared_mutex> lock(windowSessionMutex_);
432     // check window name, same window names are forbidden
433     if (windowSessionMap_.find(name) != windowSessionMap_.end()) {
434         WLOGFE("WindowName(%{public}s) already exists.", name.c_str());
435         return WMError::WM_ERROR_REPEAT_OPERATION;
436     }
437 
438     // check if camera floating window is already exists
439     if (property_->GetWindowType() == WindowType::WINDOW_TYPE_FLOAT_CAMERA ||
440         property_->GetWindowType() == WindowType::WINDOW_TYPE_PIP) {
441         for (const auto& item : windowSessionMap_) {
442             if (item.second.second && item.second.second->property_ &&
443                 item.second.second->property_->GetWindowType() == WindowType::WINDOW_TYPE_FLOAT_CAMERA) {
444                     WLOGFE("Camera floating window is already exists.");
445                 return WMError::WM_ERROR_REPEAT_OPERATION;
446             }
447         }
448         uint32_t accessTokenId = static_cast<uint32_t>(IPCSkeleton::GetCallingTokenID());
449         property_->SetAccessTokenId(accessTokenId);
450         TLOGI(WmsLogTag::DEFAULT, "Create camera float window, TokenId = %{private}u", accessTokenId);
451     }
452     return WMError::WM_OK;
453 }
454 
SetDefaultDisplayIdIfNeed()455 void WindowSessionImpl::SetDefaultDisplayIdIfNeed()
456 {
457     TLOGI(WmsLogTag::WMS_LIFE, "Called");
458     auto displayId = property_->GetDisplayId();
459     if (displayId == DISPLAY_ID_INVALID) {
460         auto defaultDisplayId = SingletonContainer::IsDestroyed() ? DISPLAY_ID_INVALID :
461             SingletonContainer::Get<DisplayManager>().GetDefaultDisplayId();
462         defaultDisplayId = (defaultDisplayId == DISPLAY_ID_INVALID) ? 0 : defaultDisplayId;
463         property_->SetDisplayId(defaultDisplayId);
464         TLOGI(WmsLogTag::WMS_LIFE, "Reset displayId to %{public}" PRIu64, defaultDisplayId);
465     }
466 }
467 
Create(const std::shared_ptr<AbilityRuntime::Context> & context,const sptr<Rosen::ISession> & iSession,const std::string & identityToken)468 WMError WindowSessionImpl::Create(const std::shared_ptr<AbilityRuntime::Context>& context,
469     const sptr<Rosen::ISession>& iSession, const std::string& identityToken)
470 {
471     return WMError::WM_OK;
472 }
473 
Connect()474 WMError WindowSessionImpl::Connect()
475 {
476     TLOGI(WmsLogTag::WMS_LIFE, "Called");
477     auto hostSession = GetHostSession();
478     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_NULLPTR);
479     sptr<ISessionStage> iSessionStage(this);
480     auto windowEventChannel = new (std::nothrow) WindowEventChannel(iSessionStage);
481     if (windowEventChannel && property_) {
482         windowEventChannel->SetIsUIExtension(property_->GetWindowType() == WindowType::WINDOW_TYPE_UI_EXTENSION);
483         windowEventChannel->SetUIExtensionUsage(property_->GetUIExtensionUsage());
484     }
485     sptr<IWindowEventChannel> iWindowEventChannel(windowEventChannel);
486     sptr<IRemoteObject> token = context_ ? context_->GetToken() : nullptr;
487     if (token) {
488         property_->SetTokenState(true);
489     }
490     auto ret = hostSession->Connect(
491         iSessionStage, iWindowEventChannel, surfaceNode_, windowSystemConfig_, property_,
492         token, identityToken_);
493     TLOGI(WmsLogTag::WMS_LIFE, "Window Connect [name:%{public}s, id:%{public}d, type:%{public}u], ret:%{public}u",
494         property_->GetWindowName().c_str(), GetPersistentId(), property_->GetWindowType(), ret);
495     return static_cast<WMError>(ret);
496 }
497 
ConsumePointerEvent(const std::shared_ptr<MMI::PointerEvent> & pointerEvent)498 void WindowSessionImpl::ConsumePointerEvent(const std::shared_ptr<MMI::PointerEvent>& pointerEvent)
499 {
500     NotifyPointerEvent(pointerEvent);
501 }
502 
ConsumeKeyEvent(std::shared_ptr<MMI::KeyEvent> & keyEvent)503 void WindowSessionImpl::ConsumeKeyEvent(std::shared_ptr<MMI::KeyEvent>& keyEvent)
504 {
505     bool isConsumed = false;
506     NotifyKeyEvent(keyEvent, isConsumed, false);
507 }
508 
PreNotifyKeyEvent(const std::shared_ptr<MMI::KeyEvent> & keyEvent)509 bool WindowSessionImpl::PreNotifyKeyEvent(const std::shared_ptr<MMI::KeyEvent>& keyEvent)
510 {
511     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
512     if (uiContent != nullptr) {
513         return uiContent->ProcessKeyEvent(keyEvent, true);
514     }
515     return false;
516 }
517 
NotifyOnKeyPreImeEvent(const std::shared_ptr<MMI::KeyEvent> & keyEvent)518 bool WindowSessionImpl::NotifyOnKeyPreImeEvent(const std::shared_ptr<MMI::KeyEvent>& keyEvent)
519 {
520     return PreNotifyKeyEvent(keyEvent);
521 }
522 
UpdateSubWindowStateAndNotify(int32_t parentPersistentId,const WindowState newState)523 void WindowSessionImpl::UpdateSubWindowStateAndNotify(int32_t parentPersistentId, const WindowState newState)
524 {
525     auto iter = subWindowSessionMap_.find(parentPersistentId);
526     if (iter == subWindowSessionMap_.end()) {
527         TLOGD(WmsLogTag::WMS_SUB, "parent window: %{public}d has no child node", parentPersistentId);
528         return;
529     }
530     const auto& subWindows = iter->second;
531     if (subWindows.empty()) {
532         TLOGD(WmsLogTag::WMS_SUB, "parent window: %{public}d, its subWindowMap is empty", parentPersistentId);
533         return;
534     }
535 
536     // when parent window hide and subwindow whose state is shown should hide and notify user
537     if (newState == WindowState::STATE_HIDDEN) {
538         for (auto subwindow : subWindows) {
539             if (subwindow != nullptr && subwindow->GetWindowState() == WindowState::STATE_SHOWN) {
540                 subwindow->state_ = WindowState::STATE_HIDDEN;
541                 subwindow->NotifyAfterBackground();
542                 TLOGD(WmsLogTag::WMS_SUB, "Notify subWindow background, id:%{public}d", subwindow->GetPersistentId());
543                 UpdateSubWindowStateAndNotify(subwindow->GetPersistentId(), newState);
544             }
545         }
546     // when parent window show and subwindow whose state is shown should show and notify user
547     } else if (newState == WindowState::STATE_SHOWN) {
548         for (auto subwindow : subWindows) {
549             if (subwindow != nullptr && subwindow->GetWindowState() == WindowState::STATE_HIDDEN &&
550                 subwindow->GetRequestWindowState() == WindowState::STATE_SHOWN) {
551                 subwindow->state_ = WindowState::STATE_SHOWN;
552                 subwindow->NotifyAfterForeground();
553                 TLOGD(WmsLogTag::WMS_SUB, "Notify subWindow foreground, id:%{public}d", subwindow->GetPersistentId());
554                 UpdateSubWindowStateAndNotify(subwindow->GetPersistentId(), newState);
555             }
556         }
557     }
558 }
559 
Show(uint32_t reason,bool withAnimation,bool withFocus)560 WMError WindowSessionImpl::Show(uint32_t reason, bool withAnimation, bool withFocus)
561 {
562     TLOGI(WmsLogTag::WMS_LIFE, "name:%{public}s, id:%{public}d, type:%{public}u, reason:%{public}u, state:%{public}u",
563         property_->GetWindowName().c_str(), property_->GetPersistentId(), GetType(), reason, state_);
564     if (IsWindowSessionInvalid()) {
565         WLOGFE("session is invalid");
566         return WMError::WM_ERROR_INVALID_WINDOW;
567     }
568     if (state_ == WindowState::STATE_SHOWN) {
569         TLOGD(WmsLogTag::WMS_LIFE, "window session is alreay shown [name:%{public}s, id:%{public}d, type: %{public}u]",
570             property_->GetWindowName().c_str(), GetPersistentId(), property_->GetWindowType());
571         NotifyAfterForeground(true, false);
572         return WMError::WM_OK;
573     }
574 
575     auto hostSession = GetHostSession();
576     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_INVALID_WINDOW);
577     WSError ret = hostSession->Foreground(property_);
578     // delete after replace WSError with WMError
579     WMError res = static_cast<WMError>(ret);
580     if (res == WMError::WM_OK) {
581         UpdateSubWindowStateAndNotify(GetPersistentId(), WindowState::STATE_SHOWN);
582         state_ = WindowState::STATE_SHOWN;
583         requestState_ = WindowState::STATE_SHOWN;
584         NotifyAfterForeground();
585     } else {
586         NotifyForegroundFailed(res);
587     }
588     return res;
589 }
590 
Hide(uint32_t reason,bool withAnimation,bool isFromInnerkits)591 WMError WindowSessionImpl::Hide(uint32_t reason, bool withAnimation, bool isFromInnerkits)
592 {
593     TLOGI(WmsLogTag::WMS_LIFE, "id:%{public}d Hide, reason:%{public}u, state:%{public}u",
594         GetPersistentId(), reason, state_);
595     if (IsWindowSessionInvalid()) {
596         WLOGFE("session is invalid");
597         return WMError::WM_ERROR_INVALID_WINDOW;
598     }
599     if (state_ == WindowState::STATE_HIDDEN || state_ == WindowState::STATE_CREATED) {
600         TLOGD(WmsLogTag::WMS_LIFE, "window session is alreay hidden [name:%{public}s, id:%{public}d, type: %{public}u]",
601             property_->GetWindowName().c_str(), GetPersistentId(), property_->GetWindowType());
602         NotifyBackgroundFailed(WMError::WM_DO_NOTHING);
603         return WMError::WM_OK;
604     }
605     UpdateSubWindowStateAndNotify(GetPersistentId(), WindowState::STATE_HIDDEN);
606     state_ = WindowState::STATE_HIDDEN;
607     requestState_ = WindowState::STATE_HIDDEN;
608     NotifyAfterBackground();
609     return WMError::WM_OK;
610 }
611 
DestroySubWindow()612 void WindowSessionImpl::DestroySubWindow()
613 {
614     int32_t parentPersistentId = property_->GetParentPersistentId();
615     const int32_t persistentId = GetPersistentId();
616     if (property_->GetExtensionFlag() == true) {
617         auto extensionWindow = FindExtensionWindowWithContext();
618         if (extensionWindow != nullptr) {
619             parentPersistentId = extensionWindow->GetPersistentId();
620         }
621     }
622     TLOGI(WmsLogTag::WMS_SUB, "Id: %{public}d, parentId: %{public}d", persistentId, parentPersistentId);
623     // remove from subWindowMap_ when destroy sub window
624     auto subIter = subWindowSessionMap_.find(parentPersistentId);
625     if (subIter != subWindowSessionMap_.end()) {
626         auto& subWindows = subIter->second;
627         for (auto iter = subWindows.begin(); iter != subWindows.end(); iter++) {
628             auto subWindow = *iter;
629             if (subWindow == nullptr) {
630                 continue;
631             }
632             if (subWindow->GetPersistentId() == persistentId) {
633                 TLOGD(WmsLogTag::WMS_SUB, "Destroy sub window, persistentId: %{public}d", persistentId);
634                 subWindows.erase(iter);
635                 break;
636             } else {
637                 TLOGD(WmsLogTag::WMS_SUB, "Exists other sub window, persistentId: %{public}d", persistentId);
638             }
639         }
640         if (property_->GetExtensionFlag() && subWindowSessionMap_.empty()) {
641             auto extensionWindow = FindExtensionWindowWithContext();
642             if (extensionWindow != nullptr && extensionWindow->GetUIContentSharedPtr() == nullptr) {
643                 extensionWindow->AddSetUIExtensionDestroyTimeoutCheck();
644             }
645         }
646     }
647     // remove from subWindowMap_ when destroy parent window
648     auto mainIter = subWindowSessionMap_.find(persistentId);
649     if (mainIter != subWindowSessionMap_.end()) {
650         auto& subWindows = mainIter->second;
651         for (auto iter = subWindows.begin(); iter != subWindows.end(); iter = subWindows.begin()) {
652             auto subWindow = *iter;
653             if (subWindow == nullptr) {
654                 TLOGW(WmsLogTag::WMS_SUB, "Destroy sub window which is nullptr");
655                 subWindows.erase(iter);
656                 continue;
657             }
658             bool isExtDestroyed = subWindow->property_->GetExtensionFlag();
659             TLOGD(WmsLogTag::WMS_SUB, "Destroy sub window, persistentId: %{public}d, isExtDestroyed: %{public}d",
660                 subWindow->GetPersistentId(), isExtDestroyed);
661             auto ret = subWindow->Destroy(isExtDestroyed);
662             if (ret != WMError::WM_OK) {
663                 TLOGE(WmsLogTag::WMS_SUB, "Destroy failed. persistentId: %{public}d", subWindow->GetPersistentId());
664                 subWindows.erase(iter);
665             }
666         }
667         mainIter->second.clear();
668         subWindowSessionMap_.erase(mainIter);
669     }
670 }
671 
Destroy(bool needNotifyServer,bool needClearListener)672 WMError WindowSessionImpl::Destroy(bool needNotifyServer, bool needClearListener)
673 {
674     TLOGI(WmsLogTag::WMS_LIFE, "Id: %{public}d Destroy, state_:%{public}u, needNotifyServer: %{public}d, "
675         "needClearListener: %{public}d", GetPersistentId(), state_, needNotifyServer, needClearListener);
676     if (IsWindowSessionInvalid()) {
677         WLOGFW("[WMSLife]session is invalid");
678         return WMError::WM_ERROR_INVALID_WINDOW;
679     }
680     {
681         auto hostSession = GetHostSession();
682         if (hostSession != nullptr) {
683             hostSession->Disconnect();
684         }
685     }
686     NotifyBeforeDestroy(GetWindowName());
687     {
688         std::lock_guard<std::recursive_mutex> lock(mutex_);
689         state_ = WindowState::STATE_DESTROYED;
690         requestState_ = WindowState::STATE_DESTROYED;
691     }
692     DestroySubWindow();
693     {
694         std::lock_guard<std::mutex> lock(hostSessionMutex_);
695         hostSession_ = nullptr;
696     }
697     {
698         std::unique_lock<std::shared_mutex> lock(windowSessionMutex_);
699         windowSessionMap_.erase(property_->GetWindowName());
700     }
701     NotifyAfterDestroy();
702     if (needClearListener) {
703         ClearListenersById(GetPersistentId());
704     }
705     if (context_) {
706         context_.reset();
707     }
708     ClearVsyncStation();
709     return WMError::WM_OK;
710 }
711 
Destroy()712 WMError WindowSessionImpl::Destroy()
713 {
714     return Destroy(true);
715 }
716 
SetActive(bool active)717 WSError WindowSessionImpl::SetActive(bool active)
718 {
719     WLOGFD("active status: %{public}d", active);
720     if (active) {
721         NotifyAfterActive();
722     } else {
723         NotifyAfterInactive();
724     }
725     return WSError::WS_OK;
726 }
727 
UpdateRect(const WSRect & rect,SizeChangeReason reason,const SceneAnimationConfig & config)728 WSError WindowSessionImpl::UpdateRect(const WSRect& rect, SizeChangeReason reason,
729     const SceneAnimationConfig& config)
730 {
731     // delete after replace ws_common.h with wm_common.h
732     auto wmReason = static_cast<WindowSizeChangeReason>(reason);
733     Rect wmRect = { rect.posX_, rect.posY_, rect.width_, rect.height_ };
734     auto preRect = GetRect();
735     if (preRect.width_ != wmRect.width_ || preRect.height_ != wmRect.height_) {
736         windowSizeChanged_ = true;
737     }
738     property_->SetWindowRect(wmRect);
739     property_->SetRequestRect(wmRect);
740 
741     TLOGI(WmsLogTag::WMS_LAYOUT, "%{public}s, preRect:%{public}s, reason:%{public}u, hasRSTransaction:%{public}d"
742         ",duration:%{public}d, [name:%{public}s, id:%{public}d]", rect.ToString().c_str(), preRect.ToString().c_str(),
743         wmReason, config.rsTransaction_ != nullptr, config.animationDuration_,
744         GetWindowName().c_str(), GetPersistentId());
745     HITRACE_METER_FMT(HITRACE_TAG_WINDOW_MANAGER,
746         "WindowSessionImpl::UpdateRect id: %d [%d, %d, %u, %u] reason: %u hasRSTransaction: %u", GetPersistentId(),
747         wmRect.posX_, wmRect.posY_, wmRect.width_, wmRect.height_, wmReason, config.rsTransaction_ != nullptr);
748     if (handler_ != nullptr && wmReason == WindowSizeChangeReason::ROTATION) {
749         postTaskDone_ = false;
750         UpdateRectForRotation(wmRect, preRect, wmReason, config);
751     } else {
752         UpdateRectForOtherReason(wmRect, preRect, wmReason, config.rsTransaction_);
753     }
754 
755     if (wmReason == WindowSizeChangeReason::MOVE || wmReason == WindowSizeChangeReason::RESIZE) {
756         layoutCallback_->OnUpdateSessionRect(wmRect, wmReason, GetPersistentId());
757     }
758 
759     return WSError::WS_OK;
760 }
761 
762 /** @note @window.layout */
UpdateVirtualPixelRatio(const sptr<Display> & display)763 void WindowSessionImpl::UpdateVirtualPixelRatio(const sptr<Display>& display)
764 {
765     if (display == nullptr) {
766         TLOGE(WmsLogTag::WMS_LAYOUT, "display is null when rotation!");
767         return;
768     }
769     sptr<DisplayInfo> displayInfo = display->GetDisplayInfo();
770     if (displayInfo == nullptr) {
771         TLOGE(WmsLogTag::WMS_LAYOUT, "displayInfo is null when rotation!");
772         return;
773     }
774     virtualPixelRatio_ = GetVirtualPixelRatio(displayInfo);
775     TLOGD(WmsLogTag::WMS_LAYOUT, "virtualPixelRatio: %{public}f", virtualPixelRatio_);
776 }
777 
UpdateRectForRotation(const Rect & wmRect,const Rect & preRect,WindowSizeChangeReason wmReason,const SceneAnimationConfig & config)778 void WindowSessionImpl::UpdateRectForRotation(const Rect& wmRect, const Rect& preRect,
779     WindowSizeChangeReason wmReason, const SceneAnimationConfig& config)
780 {
781     handler_->PostTask([weak = wptr(this), wmReason, wmRect, preRect, config]() mutable {
782         HITRACE_METER_NAME(HITRACE_TAG_WINDOW_MANAGER, "WindowSessionImpl::UpdateRectForRotation");
783         auto window = weak.promote();
784         if (!window) {
785             return;
786         }
787         auto display = SingletonContainer::Get<DisplayManager>().GetDisplayById(window->property_->GetDisplayId());
788         sptr<DisplayInfo> displayInfo = display ? display->GetDisplayInfo() : nullptr;
789         window->UpdateVirtualPixelRatio(display);
790         const std::shared_ptr<RSTransaction>& rsTransaction = config.rsTransaction_;
791         if (rsTransaction) {
792             RSTransaction::FlushImplicitTransaction();
793             rsTransaction->Begin();
794         }
795         window->rotationAnimationCount_++;
796         RSAnimationTimingProtocol protocol;
797         protocol.SetDuration(config.animationDuration_);
798         // animation curve: cubic [0.2, 0.0, 0.2, 1.0]
799         auto curve = RSAnimationTimingCurve::CreateCubicCurve(0.2, 0.0, 0.2, 1.0);
800         RSNode::OpenImplicitAnimation(protocol, curve, [weak]() {
801             auto window = weak.promote();
802             if (!window) {
803                 return;
804             }
805             window->rotationAnimationCount_--;
806             if (window->rotationAnimationCount_ == 0) {
807                 window->NotifyRotationAnimationEnd();
808             }
809         });
810         if ((wmRect != preRect) || (wmReason != window->lastSizeChangeReason_)) {
811             window->NotifySizeChange(wmRect, wmReason);
812             window->lastSizeChangeReason_ = wmReason;
813         }
814         window->UpdateViewportConfig(wmRect, wmReason, rsTransaction, displayInfo);
815         RSNode::CloseImplicitAnimation();
816         if (rsTransaction) {
817             rsTransaction->Commit();
818         } else {
819             RSTransaction::FlushImplicitTransaction();
820         }
821         window->postTaskDone_ = true;
822     }, "WMS_WindowSessionImpl_UpdateRectForRotation");
823 }
824 
UpdateRectForOtherReasonTask(const Rect & wmRect,const Rect & preRect,WindowSizeChangeReason wmReason,const std::shared_ptr<RSTransaction> & rsTransaction)825 void WindowSessionImpl::UpdateRectForOtherReasonTask(const Rect& wmRect, const Rect& preRect,
826     WindowSizeChangeReason wmReason, const std::shared_ptr<RSTransaction>& rsTransaction)
827 {
828     if ((wmRect != preRect) || (wmReason != lastSizeChangeReason_) || !postTaskDone_) {
829         NotifySizeChange(wmRect, wmReason);
830         lastSizeChangeReason_ = wmReason;
831         postTaskDone_ = true;
832     }
833     UpdateViewportConfig(wmRect, wmReason, rsTransaction);
834     UpdateFrameLayoutCallbackIfNeeded(wmReason);
835 }
836 
UpdateRectForOtherReason(const Rect & wmRect,const Rect & preRect,WindowSizeChangeReason wmReason,const std::shared_ptr<RSTransaction> & rsTransaction)837 void WindowSessionImpl::UpdateRectForOtherReason(const Rect& wmRect, const Rect& preRect,
838     WindowSizeChangeReason wmReason, const std::shared_ptr<RSTransaction>& rsTransaction)
839 {
840     if (handler_ == nullptr) {
841         UpdateRectForOtherReasonTask(wmRect, preRect, wmReason, rsTransaction);
842         return;
843     }
844 
845     auto task = [weak = wptr(this), wmReason, wmRect, preRect, rsTransaction] {
846         auto window = weak.promote();
847         if (!window) {
848             TLOGE(WmsLogTag::WMS_LAYOUT, "window is null, updateViewPortConfig failed");
849             return;
850         }
851         bool ifNeedCommitRsTransaction = CheckIfNeedCommitRsTransaction(wmReason);
852         if (rsTransaction && ifNeedCommitRsTransaction) {
853             RSTransaction::FlushImplicitTransaction();
854             rsTransaction->Begin();
855         }
856         window->UpdateRectForOtherReasonTask(wmRect, preRect, wmReason, rsTransaction);
857         if (rsTransaction && ifNeedCommitRsTransaction) {
858             rsTransaction->Commit();
859         }
860     };
861     handler_->PostTask(task, "WMS_WindowSessionImpl_UpdateRectForOtherReason");
862 }
863 
NotifyRotationAnimationEnd()864 void WindowSessionImpl::NotifyRotationAnimationEnd()
865 {
866     auto task = [weak = wptr(this)] {
867         auto window = weak.promote();
868         if (!window) {
869             TLOGE(WmsLogTag::WMS_LAYOUT, "window is null");
870             return;
871         }
872         std::shared_ptr<Ace::UIContent> uiContent = window->GetUIContentSharedPtr();
873         if (uiContent == nullptr) {
874             WLOGFW("uiContent is null!");
875             return;
876         }
877         uiContent->NotifyRotationAnimationEnd();
878     };
879     if (handler_ == nullptr) {
880         TLOGW(WmsLogTag::WMS_LAYOUT, "handler is null!");
881         task();
882     } else {
883         handler_->PostTask(task, "WMS_WindowSessionImpl_NotifyRotationAnimationEnd");
884     }
885 }
886 
FlushLayoutSize(int32_t width,int32_t height)887 void WindowSessionImpl::FlushLayoutSize(int32_t width, int32_t height)
888 {
889     if (!WindowHelper::IsMainWindow(GetType())) {
890         return;
891     }
892     WSRect rect = { 0, 0, width, height };
893     bool windowSizeChanged = true;
894     bool enableFrameLayoutFinishCb = true;
895     if (windowSizeChanged_.compare_exchange_strong(windowSizeChanged, false) ||
896         enableFrameLayoutFinishCb_.compare_exchange_strong(enableFrameLayoutFinishCb, false) || layoutRect_ != rect) {
897         HITRACE_METER_FMT(HITRACE_TAG_WINDOW_MANAGER,
898             "NotifyFrameLayoutFinishFromApp, id: %u, rect: %s, notifyListener: %d",
899             GetWindowId(), rect.ToString().c_str(), enableFrameLayoutFinishCb_.load());
900         TLOGI(WmsLogTag::WMS_LAYOUT,
901             "NotifyFrameLayoutFinishFromApp, id: %{public}u, rect: %{public}s, notifyListener: %{public}d",
902             GetWindowId(), rect.ToString().c_str(), enableFrameLayoutFinishCb_.load());
903         if (auto session = GetHostSession()) {
904             session->NotifyFrameLayoutFinishFromApp(enableFrameLayoutFinishCb_, rect);
905         }
906         layoutRect_ = rect;
907         enableFrameLayoutFinishCb_ = false;
908     }
909 }
910 
GetTitleButtonVisible(bool & hideMaximizeButton,bool & hideMinimizeButton,bool & hideSplitButton,bool & hideCloseButton)911 void WindowSessionImpl::GetTitleButtonVisible(bool& hideMaximizeButton, bool& hideMinimizeButton,
912     bool& hideSplitButton, bool& hideCloseButton)
913 {
914     if (!IsPcOrPadFreeMultiWindowMode()) {
915         TLOGE(WmsLogTag::WMS_LAYOUT, "device not support");
916         return;
917     }
918     if (hideMaximizeButton > !windowTitleVisibleFlags_.isMaximizeVisible) {
919         TLOGW(WmsLogTag::WMS_LAYOUT, "isMaximizeVisible param INVALID");
920     }
921     hideMaximizeButton = hideMaximizeButton || (!windowTitleVisibleFlags_.isMaximizeVisible);
922     if (hideMinimizeButton > !windowTitleVisibleFlags_.isMinimizeVisible) {
923         TLOGW(WmsLogTag::WMS_LAYOUT, "isMinimizeVisible param INVALID");
924     }
925     hideMinimizeButton = hideMinimizeButton || (!windowTitleVisibleFlags_.isMinimizeVisible);
926     if (hideSplitButton > !windowTitleVisibleFlags_.isSplitVisible) {
927         TLOGW(WmsLogTag::WMS_LAYOUT, "isSplitVisible param INVALID");
928     }
929     hideSplitButton = hideSplitButton || (!windowTitleVisibleFlags_.isSplitVisible);
930     if (hideCloseButton > !windowTitleVisibleFlags_.isCloseVisible) {
931         TLOGW(WmsLogTag::WMS_LAYOUT, "isCloseVisible param INVALID");
932     }
933     hideCloseButton = hideCloseButton || (!windowTitleVisibleFlags_.isCloseVisible);
934 }
935 
UpdateDensity()936 void WindowSessionImpl::UpdateDensity()
937 {
938     auto preRect = GetRect();
939     UpdateViewportConfig(preRect, WindowSizeChangeReason::UNDEFINED);
940     WLOGFI("WindowSessionImpl::UpdateDensity [%{public}d, %{public}d, %{public}u, %{public}u]",
941         preRect.posX_, preRect.posY_, preRect.width_, preRect.height_);
942 }
943 
SetUniqueVirtualPixelRatio(bool useUniqueDensity,float virtualPixelRatio)944 void WindowSessionImpl::SetUniqueVirtualPixelRatio(bool useUniqueDensity, float virtualPixelRatio)
945 {
946     TLOGI(WmsLogTag::DEFAULT, "old {useUniqueDensity: %{public}d, virtualPixelRatio: %{public}f}, "\
947         "new {useUniqueDensity: %{public}d, virtualPixelRatio: %{public}f}",
948         useUniqueDensity_, virtualPixelRatio_, useUniqueDensity, virtualPixelRatio);
949     bool oldUseUniqueDensity = useUniqueDensity_;
950     useUniqueDensity_ = useUniqueDensity;
951     if (useUniqueDensity_) {
952         float oldVirtualPixelRatio = virtualPixelRatio_;
953         virtualPixelRatio_ = virtualPixelRatio;
954         if (!MathHelper::NearZero(oldVirtualPixelRatio - virtualPixelRatio)) {
955             UpdateDensity();
956             SetUniqueVirtualPixelRatioForSub(useUniqueDensity, virtualPixelRatio);
957         }
958     } else {
959         if (oldUseUniqueDensity) {
960             UpdateDensity();
961             SetUniqueVirtualPixelRatioForSub(useUniqueDensity, virtualPixelRatio);
962         }
963     }
964 }
965 
CopyUniqueDensityParameter(sptr<WindowSessionImpl> parentWindow)966 void WindowSessionImpl::CopyUniqueDensityParameter(sptr<WindowSessionImpl> parentWindow)
967 {
968     if (parentWindow) {
969         useUniqueDensity_ = parentWindow->useUniqueDensity_;
970         virtualPixelRatio_ = parentWindow->virtualPixelRatio_;
971     }
972 }
973 
FindMainWindowWithContext()974 sptr<WindowSessionImpl> WindowSessionImpl::FindMainWindowWithContext()
975 {
976     if (context_ == nullptr) {
977         return nullptr;
978     }
979     std::shared_lock<std::shared_mutex> lock(windowSessionMutex_);
980     for (const auto& winPair : windowSessionMap_) {
981         auto win = winPair.second.second;
982         if (win && win->GetType() == WindowType::WINDOW_TYPE_APP_MAIN_WINDOW &&
983             context_.get() == win->GetContext().get()) {
984             return win;
985         }
986     }
987     WLOGFW("Can not find main window, not app type");
988     return nullptr;
989 }
990 
FindExtensionWindowWithContext()991 sptr<WindowSessionImpl> WindowSessionImpl::FindExtensionWindowWithContext()
992 {
993     if (context_ == nullptr) {
994         return nullptr;
995     }
996     std::shared_lock<std::shared_mutex> lock(windowExtensionSessionMutex_);
997     for (const auto& window : windowExtensionSessionSet_) {
998         if (window && context_.get() == window->GetContext().get()) {
999             return window;
1000         }
1001     }
1002     return nullptr;
1003 }
1004 
SetUniqueVirtualPixelRatioForSub(bool useUniqueDensity,float virtualPixelRatio)1005 void WindowSessionImpl::SetUniqueVirtualPixelRatioForSub(bool useUniqueDensity, float virtualPixelRatio)
1006 {
1007     if (subWindowSessionMap_.count(GetPersistentId()) == 0) {
1008         return;
1009     }
1010     for (auto& subWindowSession : subWindowSessionMap_.at(GetPersistentId())) {
1011         subWindowSession->SetUniqueVirtualPixelRatio(useUniqueDensity, virtualPixelRatio);
1012     }
1013 }
1014 
UpdateOrientation()1015 WSError WindowSessionImpl::UpdateOrientation()
1016 {
1017     TLOGD(WmsLogTag::DMS, "UpdateOrientation, wid: %{public}d", GetPersistentId());
1018     return WSError::WS_OK;
1019 }
1020 
UpdateDisplayId(uint64_t displayId)1021 WSError WindowSessionImpl::UpdateDisplayId(uint64_t displayId)
1022 {
1023     property_->SetDisplayId(displayId);
1024     return WSError::WS_OK;
1025 }
1026 
UpdateFocus(bool isFocused)1027 WSError WindowSessionImpl::UpdateFocus(bool isFocused)
1028 {
1029     TLOGI(WmsLogTag::WMS_FOCUS, "Report update focus: %{public}u, id: %{public}d", isFocused, GetPersistentId());
1030     isFocused_ = isFocused;
1031     if (isFocused) {
1032         HiSysEventWrite(
1033             OHOS::HiviewDFX::HiSysEvent::Domain::WINDOW_MANAGER,
1034             "FOCUS_WINDOW",
1035             OHOS::HiviewDFX::HiSysEvent::EventType::BEHAVIOR,
1036             "PID", getpid(),
1037             "UID", getuid(),
1038             "BUNDLE_NAME", property_->GetSessionInfo().bundleName_);
1039         NotifyAfterFocused();
1040     } else {
1041         NotifyAfterUnfocused();
1042     }
1043     return WSError::WS_OK;
1044 }
1045 
IsFocused() const1046 bool WindowSessionImpl::IsFocused() const
1047 {
1048     if (IsWindowSessionInvalid()) {
1049         TLOGE(WmsLogTag::DEFAULT, "Session is invalid");
1050         return false;
1051     }
1052 
1053     TLOGD(WmsLogTag::WMS_FOCUS, "window id = %{public}d, isFocused = %{public}d", GetPersistentId(), isFocused_.load());
1054     return isFocused_;
1055 }
1056 
RequestFocus() const1057 WMError WindowSessionImpl::RequestFocus() const
1058 {
1059     if (IsWindowSessionInvalid()) {
1060         WLOGFD("session is invalid");
1061         return WMError::WM_ERROR_INVALID_WINDOW;
1062     }
1063     return SingletonContainer::Get<WindowAdapter>().RequestFocusStatus(GetPersistentId(), true);
1064 }
1065 
1066 /** @note @window.focus */
RequestFocusByClient(bool isFocused) const1067 WMError WindowSessionImpl::RequestFocusByClient(bool isFocused) const
1068 {
1069     if (!SessionPermission::IsSystemCalling()) {
1070         TLOGE(WmsLogTag::WMS_FOCUS, "permission denied!");
1071         return WMError::WM_ERROR_NOT_SYSTEM_APP;
1072     }
1073     if (IsWindowSessionInvalid()) {
1074         TLOGD(WmsLogTag::WMS_FOCUS, "session is invalid");
1075         return WMError::WM_ERROR_INVALID_WINDOW;
1076     }
1077     auto hostSession = GetHostSession();
1078     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_INVALID_WINDOW);
1079     auto ret = hostSession->RequestFocus(isFocused);
1080     return static_cast<WMError>(ret);
1081 }
1082 
IsNotifyInteractiveDuplicative(bool interactive)1083 bool WindowSessionImpl::IsNotifyInteractiveDuplicative(bool interactive)
1084 {
1085     if (interactive == interactive_ && hasFirstNotifyInteractive_) {
1086         return true;
1087     }
1088     hasFirstNotifyInteractive_ = true;
1089     if (interactive_ != interactive) {
1090         interactive_ = interactive;
1091     }
1092     return false;
1093 }
1094 
NotifyForegroundInteractiveStatus(bool interactive)1095 void WindowSessionImpl::NotifyForegroundInteractiveStatus(bool interactive)
1096 {
1097     WLOGFI("NotifyForegroundInteractiveStatus %{public}d", interactive);
1098     if (IsWindowSessionInvalid() || state_ != WindowState::STATE_SHOWN) {
1099         return;
1100     }
1101     if (IsNotifyInteractiveDuplicative(interactive)) {
1102         return;
1103     }
1104     if (interactive) {
1105         NotifyAfterResumed();
1106     } else {
1107         NotifyAfterPaused();
1108     }
1109 }
1110 
UpdateWindowMode(WindowMode mode)1111 WSError WindowSessionImpl::UpdateWindowMode(WindowMode mode)
1112 {
1113     return WSError::WS_OK;
1114 }
1115 
1116 /** @note @window.layout */
GetVirtualPixelRatio()1117 float WindowSessionImpl::GetVirtualPixelRatio()
1118 {
1119     TLOGD(WmsLogTag::WMS_LAYOUT, "virtualPixelRatio: %{public}f", virtualPixelRatio_);
1120     return virtualPixelRatio_;
1121 }
1122 
GetVirtualPixelRatio(sptr<DisplayInfo> displayInfo)1123 float WindowSessionImpl::GetVirtualPixelRatio(sptr<DisplayInfo> displayInfo)
1124 {
1125     if (useUniqueDensity_) {
1126         return virtualPixelRatio_;
1127     }
1128     return displayInfo->GetVirtualPixelRatio();
1129 }
1130 
UpdateViewportConfig(const Rect & rect,WindowSizeChangeReason reason,const std::shared_ptr<RSTransaction> & rsTransaction,const sptr<DisplayInfo> & info,const std::map<AvoidAreaType,AvoidArea> & avoidAreas)1131 void WindowSessionImpl::UpdateViewportConfig(const Rect& rect, WindowSizeChangeReason reason,
1132     const std::shared_ptr<RSTransaction>& rsTransaction, const sptr<DisplayInfo>& info,
1133     const std::map<AvoidAreaType, AvoidArea>& avoidAreas)
1134 {
1135     sptr<DisplayInfo> displayInfo;
1136     if (info == nullptr) {
1137         auto display = SingletonContainer::Get<DisplayManager>().GetDisplayById(property_->GetDisplayId());
1138         if (display == nullptr) {
1139             WLOGFE("display is null!");
1140             return;
1141         }
1142         displayInfo = display->GetDisplayInfo();
1143     } else {
1144         displayInfo = info;
1145     }
1146     if (displayInfo == nullptr) {
1147         WLOGFE("displayInfo is null!");
1148         return;
1149     }
1150     if (rect.width_ <= 0 || rect.height_ <= 0) {
1151         TLOGW(WmsLogTag::WMS_LAYOUT, "invalid width: %{public}d, height: %{public}d, id: %{public}d",
1152               rect.width_, rect.height_, GetPersistentId());
1153         return;
1154     }
1155     auto rotation =  ONE_FOURTH_FULL_CIRCLE_DEGREE * static_cast<uint32_t>(displayInfo->GetRotation());
1156     auto deviceRotation = static_cast<uint32_t>(displayInfo->GetDefaultDeviceRotationOffset());
1157     uint32_t transformHint = (rotation + deviceRotation) % FULL_CIRCLE_DEGREE;
1158     float density = GetVirtualPixelRatio(displayInfo);
1159     int32_t orientation = static_cast<int32_t>(displayInfo->GetDisplayOrientation());
1160     virtualPixelRatio_ = density;
1161     TLOGI(WmsLogTag::WMS_LAYOUT, "[rotation,deviceRotation,transformHint,virtualPixelRatio]:[%{public}u,"
1162         "%{public}u,%{public}u,%{public}f]", rotation, deviceRotation, transformHint, virtualPixelRatio_);
1163     auto config = FillViewportConfig(rect, density, orientation, transformHint);
1164     std::map<AvoidAreaType, AvoidArea> avoidAreasToUpdate;
1165     if (reason == WindowSizeChangeReason::ROTATION) {
1166         if (auto hostSession = GetHostSession()) {
1167             hostSession->GetAllAvoidAreas(avoidAreasToUpdate);
1168         }
1169     } else {
1170         avoidAreasToUpdate = avoidAreas;
1171     }
1172     for (const auto& [type, avoidArea] : avoidAreasToUpdate) {
1173         TLOGD(WmsLogTag::WMS_IMMS, "avoid type %{public}u area %{public}s",
1174             type, avoidArea.ToString().c_str());
1175     }
1176     {
1177         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1178         if (uiContent == nullptr) {
1179             WLOGFW("uiContent is null!");
1180             return;
1181         }
1182         uiContent->UpdateViewportConfig(config, reason, rsTransaction, avoidAreasToUpdate);
1183     }
1184     if (WindowHelper::IsUIExtensionWindow(GetType())) {
1185         TLOGD(WmsLogTag::WMS_LAYOUT, "Id:%{public}d reason:%{public}d windowRect:[%{public}d,%{public}d,"
1186             "%{public}u,%{public}u] displayOrientation:%{public}d",
1187             GetPersistentId(), reason, rect.posX_, rect.posY_, rect.width_, rect.height_, orientation);
1188     } else {
1189         TLOGI(WmsLogTag::WMS_LAYOUT, "Id:%{public}d reason:%{public}d windowRect:[%{public}d,%{public}d,"
1190             "%{public}u,%{public}u] displayOrientation:%{public}d",
1191             GetPersistentId(), reason, rect.posX_, rect.posY_, rect.width_, rect.height_, orientation);
1192     }
1193 }
1194 
GetFloatingWindowParentId()1195 int32_t WindowSessionImpl::GetFloatingWindowParentId()
1196 {
1197     if (context_.get() == nullptr) {
1198         return INVALID_SESSION_ID;
1199     }
1200     std::shared_lock<std::shared_mutex> lock(windowSessionMutex_);
1201     for (const auto& winPair : windowSessionMap_) {
1202         if (winPair.second.second && WindowHelper::IsMainWindow(winPair.second.second->GetType()) &&
1203             winPair.second.second->GetProperty() &&
1204             context_.get() == winPair.second.second->GetContext().get()) {
1205             WLOGFD("Find parent, [parentName: %{public}s, selfPersistentId: %{public}d]",
1206                 winPair.second.second->GetProperty()->GetWindowName().c_str(), GetPersistentId());
1207             return winPair.second.second->GetProperty()->GetPersistentId();
1208         }
1209     }
1210     return INVALID_SESSION_ID;
1211 }
1212 
GetRect() const1213 Rect WindowSessionImpl::GetRect() const
1214 {
1215     return property_->GetWindowRect();
1216 }
1217 
UpdateTitleButtonVisibility()1218 void WindowSessionImpl::UpdateTitleButtonVisibility()
1219 {
1220     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1221     if (uiContent == nullptr || !IsDecorEnable()) {
1222         return;
1223     }
1224     WindowType windowType = GetType();
1225     bool isSubWindow = WindowHelper::IsSubWindow(windowType);
1226     bool isDialogWindow = WindowHelper::IsDialogWindow(windowType);
1227     if (IsPcOrPadCapabilityEnabled() && (isSubWindow || isDialogWindow)) {
1228         WLOGFD("hide other buttons except close");
1229         uiContent->HideWindowTitleButton(true, true, true, false);
1230         return;
1231     }
1232     auto windowModeSupportType = property_->GetWindowModeSupportType();
1233     bool hideSplitButton = !(windowModeSupportType & WindowModeSupport::WINDOW_MODE_SUPPORT_SPLIT_PRIMARY);
1234     // not support fullscreen in split and floating mode, or not support float in fullscreen mode
1235     bool hideMaximizeButton = (!(windowModeSupportType & WindowModeSupport::WINDOW_MODE_SUPPORT_FULLSCREEN) &&
1236         (GetMode() == WindowMode::WINDOW_MODE_FLOATING || WindowHelper::IsSplitWindowMode(GetMode()))) ||
1237         (!(windowModeSupportType & WindowModeSupport::WINDOW_MODE_SUPPORT_FLOATING) &&
1238         GetMode() == WindowMode::WINDOW_MODE_FULLSCREEN);
1239     bool hideMinimizeButton = false;
1240     bool hideCloseButton = false;
1241     GetTitleButtonVisible(hideMaximizeButton, hideMinimizeButton, hideSplitButton, hideCloseButton);
1242     TLOGI(WmsLogTag::WMS_LAYOUT, "[hideSplit, hideMaximize, hideMinimizeButton, hideCloseButton]:"
1243         "[%{public}d, %{public}d, %{public}d, %{public}d]",
1244         hideSplitButton, hideMaximizeButton, hideMinimizeButton, hideCloseButton);
1245     if (property_->GetCompatibleModeInPc()) {
1246         if (IsFreeMultiWindowMode()) {
1247             uiContent->HideWindowTitleButton(true, hideMaximizeButton, hideMinimizeButton, hideCloseButton);
1248         } else {
1249             uiContent->HideWindowTitleButton(hideSplitButton, true, hideMinimizeButton, hideCloseButton);
1250         }
1251     } else {
1252         uiContent->HideWindowTitleButton(hideSplitButton, hideMaximizeButton, hideMinimizeButton, hideCloseButton);
1253     }
1254 }
1255 
NapiSetUIContent(const std::string & contentInfo,napi_env env,napi_value storage,BackupAndRestoreType type,sptr<IRemoteObject> token,AppExecFwk::Ability * ability)1256 WMError WindowSessionImpl::NapiSetUIContent(const std::string& contentInfo, napi_env env, napi_value storage,
1257     BackupAndRestoreType type, sptr<IRemoteObject> token, AppExecFwk::Ability* ability)
1258 {
1259     return SetUIContentInner(contentInfo, env, storage,
1260         type == BackupAndRestoreType::NONE ? WindowSetUIContentType::DEFAULT : WindowSetUIContentType::RESTORE,
1261         type, ability);
1262 }
1263 
SetUIContentByName(const std::string & contentInfo,napi_env env,napi_value storage,AppExecFwk::Ability * ability)1264 WMError WindowSessionImpl::SetUIContentByName(
1265     const std::string& contentInfo, napi_env env, napi_value storage, AppExecFwk::Ability* ability)
1266 {
1267     return SetUIContentInner(contentInfo, env, storage, WindowSetUIContentType::BY_NAME,
1268         BackupAndRestoreType::NONE, ability);
1269 }
1270 
SetUIContentByAbc(const std::string & contentInfo,napi_env env,napi_value storage,AppExecFwk::Ability * ability)1271 WMError WindowSessionImpl::SetUIContentByAbc(
1272     const std::string& contentInfo, napi_env env, napi_value storage, AppExecFwk::Ability* ability)
1273 {
1274     return SetUIContentInner(contentInfo, env, storage, WindowSetUIContentType::BY_ABC,
1275         BackupAndRestoreType::NONE, ability);
1276 }
1277 
DestroyExistUIContent()1278 void WindowSessionImpl::DestroyExistUIContent()
1279 {
1280     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1281     if (uiContent) {
1282         uiContent->Destroy();
1283     }
1284 }
1285 
InitUIContent(const std::string & contentInfo,napi_env env,napi_value storage,WindowSetUIContentType setUIContentType,BackupAndRestoreType restoreType,AppExecFwk::Ability * ability,OHOS::Ace::UIContentErrorCode & aceRet)1286 WMError WindowSessionImpl::InitUIContent(const std::string& contentInfo, napi_env env, napi_value storage,
1287     WindowSetUIContentType setUIContentType, BackupAndRestoreType restoreType, AppExecFwk::Ability* ability,
1288     OHOS::Ace::UIContentErrorCode& aceRet)
1289 {
1290     DestroyExistUIContent();
1291     std::unique_ptr<Ace::UIContent> uiContent = ability != nullptr ? Ace::UIContent::Create(ability) :
1292         Ace::UIContent::Create(context_.get(), reinterpret_cast<NativeEngine*>(env));
1293     if (uiContent == nullptr) {
1294         TLOGE(WmsLogTag::WMS_LIFE, "fail to NapiSetUIContent id: %{public}d", GetPersistentId());
1295         return WMError::WM_ERROR_NULLPTR;
1296     }
1297     switch (setUIContentType) {
1298         default:
1299         case WindowSetUIContentType::DEFAULT: {
1300             if (isUIExtensionAbilityProcess_ && property_->GetExtensionFlag() == true) {
1301                 // subWindow created by UIExtensionAbility
1302                 uiContent->SetUIExtensionSubWindow(true);
1303                 uiContent->SetUIExtensionAbilityProcess(true);
1304             } else {
1305                 auto routerStack = GetRestoredRouterStack();
1306                 auto type = GetAceContentInfoType(BackupAndRestoreType::RESOURCESCHEDULE_RECOVERY);
1307                 if (!routerStack.empty() &&
1308                     uiContent->Restore(this, routerStack, storage, type) == Ace::UIContentErrorCode::NO_ERRORS) {
1309                     TLOGI(WmsLogTag::WMS_LIFE, "Restore router stack succeed.");
1310                     break;
1311                 }
1312             }
1313             aceRet = uiContent->Initialize(this, contentInfo, storage);
1314             break;
1315         }
1316         case WindowSetUIContentType::RESTORE:
1317             aceRet = uiContent->Restore(this, contentInfo, storage, GetAceContentInfoType(restoreType));
1318             break;
1319         case WindowSetUIContentType::BY_NAME:
1320             aceRet = uiContent->InitializeByName(this, contentInfo, storage);
1321             break;
1322         case WindowSetUIContentType::BY_ABC:
1323             auto abcContent = GetAbcContent(contentInfo);
1324             aceRet = uiContent->Initialize(this, abcContent, storage, contentInfo);
1325             break;
1326     }
1327     // make uiContent available after Initialize/Restore
1328     {
1329         std::unique_lock<std::shared_mutex> lock(uiContentMutex_);
1330         uiContent_ = std::move(uiContent);
1331         WLOGFI("UIContent Initialize, isUIExtensionSubWindow:%{public}d, isUIExtensionAbilityProcess:%{public}d",
1332             uiContent_->IsUIExtensionSubWindow(), uiContent_->IsUIExtensionAbilityProcess());
1333     }
1334     return WMError::WM_OK;
1335 }
1336 
SetUIContentInner(const std::string & contentInfo,napi_env env,napi_value storage,WindowSetUIContentType setUIContentType,BackupAndRestoreType restoreType,AppExecFwk::Ability * ability)1337 WMError WindowSessionImpl::SetUIContentInner(const std::string& contentInfo, napi_env env, napi_value storage,
1338     WindowSetUIContentType setUIContentType, BackupAndRestoreType restoreType, AppExecFwk::Ability* ability)
1339 {
1340     TLOGD(WmsLogTag::WMS_LIFE, "NapiSetUIContent: %{public}s state:%{public}u", contentInfo.c_str(), state_);
1341     if (IsWindowSessionInvalid()) {
1342         WLOGFE("[WMSLife]interrupt set uicontent because window is invalid! window state: %{public}d", state_);
1343         return WMError::WM_ERROR_INVALID_WINDOW;
1344     }
1345     NotifySetUIContentComplete();
1346     OHOS::Ace::UIContentErrorCode aceRet = OHOS::Ace::UIContentErrorCode::NO_ERRORS;
1347     WMError initUIContentRet = InitUIContent(contentInfo, env, storage, setUIContentType, restoreType, ability, aceRet);
1348     if (initUIContentRet != WMError::WM_OK) {
1349         TLOGE(WmsLogTag::WMS_LIFE, "Init UIContent fail, ret:%{public}u", initUIContentRet);
1350         return initUIContentRet;
1351     }
1352     WindowType winType = GetType();
1353     bool isSubWindow = WindowHelper::IsSubWindow(winType);
1354     bool isDialogWindow = WindowHelper::IsDialogWindow(winType);
1355     if (IsDecorEnable()) {
1356         if (isSubWindow) {
1357             SetAPPWindowLabel(subWindowTitle_);
1358         } else if (isDialogWindow) {
1359             SetAPPWindowLabel(dialogTitle_);
1360         }
1361     }
1362 
1363     AppForceLandscapeConfig config = {};
1364     if (WindowHelper::IsMainWindow(winType) && GetAppForceLandscapeConfig(config) == WMError::WM_OK &&
1365         config.mode_ == FORCE_SPLIT_MODE) {
1366         SetForceSplitEnable(true, config.homePage_);
1367     }
1368 
1369     uint32_t version = 0;
1370     if ((context_ != nullptr) && (context_->GetApplicationInfo() != nullptr)) {
1371         version = context_->GetApplicationInfo()->apiCompatibleVersion;
1372     }
1373     // 10 ArkUI new framework support after API10
1374     if (version < 10) {
1375         SetLayoutFullScreenByApiVersion(isIgnoreSafeArea_);
1376         if (!isSystembarPropertiesSet_) {
1377             SetSystemBarProperty(WindowType::WINDOW_TYPE_STATUS_BAR, SystemBarProperty());
1378         }
1379     } else if (isIgnoreSafeAreaNeedNotify_) {
1380         SetLayoutFullScreenByApiVersion(isIgnoreSafeArea_);
1381     } else if (isSubWindow) {
1382         SetLayoutFullScreenByApiVersion(isIgnoreSafeArea_);
1383         isIgnoreSafeAreaNeedNotify_ = false;
1384     }
1385 
1386     // UIContent may be nullptr on setting system bar properties, need to set menubar color on UIContent init.
1387     if (auto uiContent = GetUIContentSharedPtr()) {
1388         auto property = GetSystemBarPropertyByType(WindowType::WINDOW_TYPE_STATUS_BAR);
1389         uiContent->SetStatusBarItemColor(property.contentColor_);
1390     }
1391 
1392     UpdateDecorEnable(true);
1393     if (state_ == WindowState::STATE_SHOWN) {
1394         // UIContent may be nullptr when show window, need to notify again when window is shown
1395         {
1396             std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1397             if (uiContent != nullptr) {
1398                 uiContent->Foreground();
1399             }
1400         }
1401         UpdateTitleButtonVisibility();
1402     }
1403     UpdateViewportConfig(GetRect(), WindowSizeChangeReason::UNDEFINED);
1404     if (shouldReNotifyFocus_) {
1405         // uiContent may be nullptr when notify focus status, need to notify again when uiContent is not empty.
1406         NotifyUIContentFocusStatus();
1407         shouldReNotifyFocus_ = false;
1408     }
1409     if (aceRet != OHOS::Ace::UIContentErrorCode::NO_ERRORS) {
1410         WLOGFE("failed to init or restore uicontent with file %{public}s. errorCode: %{public}d",
1411             contentInfo.c_str(), static_cast<uint16_t>(aceRet));
1412         return WMError::WM_ERROR_INVALID_PARAM;
1413     }
1414     TLOGD(WmsLogTag::WMS_LIFE, "notify uiContent window size change end");
1415     return WMError::WM_OK;
1416 }
1417 
GetAbcContent(const std::string & abcPath)1418 std::shared_ptr<std::vector<uint8_t>> WindowSessionImpl::GetAbcContent(const std::string& abcPath)
1419 {
1420     std::filesystem::path abcFile { abcPath };
1421     if (abcFile.empty() || !abcFile.is_absolute() || !std::filesystem::exists(abcFile)) {
1422         WLOGFE("abc file path is not valid");
1423         return nullptr;
1424     }
1425     int begin, end;
1426     std::fstream file(abcFile, std::ios::in | std::ios::binary);
1427     if (!file) {
1428         WLOGFE("abc file is not valid");
1429         return nullptr;
1430     }
1431     begin = file.tellg();
1432     file.seekg(0, std::ios::end);
1433     end = file.tellg();
1434     int len = end - begin;
1435     WLOGFD("abc file: %{public}s, size: %{public}d", abcPath.c_str(), len);
1436 
1437     if (len <= 0) {
1438         WLOGFE("abc file size is 0");
1439         return nullptr;
1440     }
1441     std::vector<uint8_t> abcBytes(len);
1442     file.seekg(0, std::ios::beg);
1443     file.read(reinterpret_cast<char *>(abcBytes.data()), len);
1444     return std::make_shared<std::vector<uint8_t>>(abcBytes);
1445 }
1446 
UpdateDecorEnableToAce(bool isDecorEnable)1447 void WindowSessionImpl::UpdateDecorEnableToAce(bool isDecorEnable)
1448 {
1449     {
1450         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1451         if (uiContent != nullptr) {
1452             WindowMode mode = GetMode();
1453             bool decorVisible = mode == WindowMode::WINDOW_MODE_FLOATING ||
1454                 mode == WindowMode::WINDOW_MODE_SPLIT_PRIMARY || mode == WindowMode::WINDOW_MODE_SPLIT_SECONDARY ||
1455                 (mode == WindowMode::WINDOW_MODE_FULLSCREEN && !property_->IsLayoutFullScreen());
1456             WLOGFD("[WSLayout]Notify uiContent window mode change end,decorVisible:%{public}d", decorVisible);
1457             if (windowSystemConfig_.freeMultiWindowSupport_) {
1458                 auto isSubWindow = WindowHelper::IsSubWindow(GetType());
1459                 decorVisible = decorVisible && ((property_->GetIsPcAppInPad() && isSubWindow) ||
1460                     (windowSystemConfig_.freeMultiWindowEnable_ && mode != WindowMode::WINDOW_MODE_FULLSCREEN));
1461             }
1462             uiContent->UpdateDecorVisible(decorVisible, isDecorEnable);
1463             return;
1464         }
1465     }
1466     std::lock_guard<std::recursive_mutex> lockListener(windowChangeListenerMutex_);
1467     auto windowChangeListeners = GetListeners<IWindowChangeListener>();
1468     for (auto& listener : windowChangeListeners) {
1469         if (listener.GetRefPtr() != nullptr) {
1470             listener.GetRefPtr()->OnModeChange(GetMode(), isDecorEnable);
1471         }
1472     }
1473 }
1474 
UpdateDecorEnable(bool needNotify,WindowMode mode)1475 void WindowSessionImpl::UpdateDecorEnable(bool needNotify, WindowMode mode)
1476 {
1477     if (mode == WindowMode::WINDOW_MODE_UNDEFINED) {
1478         mode = GetMode();
1479     }
1480     if (needNotify) {
1481         {
1482             std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1483             if (uiContent != nullptr) {
1484                 bool decorVisible = mode == WindowMode::WINDOW_MODE_FLOATING ||
1485                     mode == WindowMode::WINDOW_MODE_SPLIT_PRIMARY || mode == WindowMode::WINDOW_MODE_SPLIT_SECONDARY ||
1486                     (mode == WindowMode::WINDOW_MODE_FULLSCREEN && !property_->IsLayoutFullScreen());
1487                 if (windowSystemConfig_.freeMultiWindowSupport_) {
1488                     auto isSubWindow = WindowHelper::IsSubWindow(GetType());
1489                     decorVisible = decorVisible && ((property_->GetIsPcAppInPad() && isSubWindow) ||
1490                         (windowSystemConfig_.freeMultiWindowEnable_ && mode != WindowMode::WINDOW_MODE_FULLSCREEN));
1491                 }
1492                 WLOGFD("[WSLayout]Notify uiContent window mode change end,decorVisible:%{public}d", decorVisible);
1493                 uiContent->UpdateDecorVisible(decorVisible, IsDecorEnable());
1494             }
1495         }
1496         NotifyModeChange(mode, IsDecorEnable());
1497     }
1498 }
1499 
NotifyModeChange(WindowMode mode,bool hasDeco)1500 void WindowSessionImpl::NotifyModeChange(WindowMode mode, bool hasDeco)
1501 {
1502     {
1503         std::lock_guard<std::recursive_mutex> lockListener(windowChangeListenerMutex_);
1504         auto windowChangeListeners = GetListeners<IWindowChangeListener>();
1505         for (auto& listener : windowChangeListeners) {
1506             if (listener.GetRefPtr() != nullptr) {
1507                 listener.GetRefPtr()->OnModeChange(mode, hasDeco);
1508             }
1509         }
1510     }
1511 
1512     if (GetHostSession()) {
1513         property_->SetWindowMode(mode);
1514         property_->SetDecorEnable(hasDeco);
1515     }
1516     UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_MODE);
1517     UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_DECOR_ENABLE);
1518 }
1519 
GetSurfaceNode() const1520 std::shared_ptr<RSSurfaceNode> WindowSessionImpl::GetSurfaceNode() const
1521 {
1522     TLOGI(WmsLogTag::DEFAULT, "name:%{public}s, id:%{public}d",
1523         property_->GetWindowName().c_str(), GetPersistentId());
1524     return surfaceNode_;
1525 }
1526 
GetContext() const1527 const std::shared_ptr<AbilityRuntime::Context> WindowSessionImpl::GetContext() const
1528 {
1529     TLOGI(WmsLogTag::DEFAULT, "name:%{public}s, id:%{public}d",
1530         property_->GetWindowName().c_str(), GetPersistentId());
1531     return context_;
1532 }
1533 
GetRequestRect() const1534 Rect WindowSessionImpl::GetRequestRect() const
1535 {
1536     return property_->GetRequestRect();
1537 }
1538 
GetType() const1539 WindowType WindowSessionImpl::GetType() const
1540 {
1541     return property_->GetWindowType();
1542 }
1543 
GetWindowName() const1544 const std::string& WindowSessionImpl::GetWindowName() const
1545 {
1546     return property_->GetWindowName();
1547 }
1548 
GetWindowState() const1549 WindowState WindowSessionImpl::GetWindowState() const
1550 {
1551     return state_;
1552 }
1553 
GetRequestWindowState() const1554 WindowState WindowSessionImpl::GetRequestWindowState() const
1555 {
1556     return requestState_;
1557 }
1558 
SetFocusable(bool isFocusable)1559 WMError WindowSessionImpl::SetFocusable(bool isFocusable)
1560 {
1561     if (IsWindowSessionInvalid()) {
1562         return WMError::WM_ERROR_INVALID_WINDOW;
1563     }
1564     TLOGI(WmsLogTag::WMS_FOCUS, "set focusable: windowId = %{public}d, isFocusable = %{public}d",
1565         property_->GetPersistentId(), isFocusable);
1566     property_->SetFocusable(isFocusable);
1567     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_FOCUSABLE);
1568 }
1569 
GetFocusable() const1570 bool WindowSessionImpl::GetFocusable() const
1571 {
1572     bool isFocusable = property_->GetFocusable();
1573     TLOGD(WmsLogTag::WMS_FOCUS, "get focusable: windowId = %{public}d, isFocusable = %{public}d",
1574         property_->GetPersistentId(), isFocusable);
1575     return isFocusable;
1576 }
1577 
SetTouchable(bool isTouchable)1578 WMError WindowSessionImpl::SetTouchable(bool isTouchable)
1579 {
1580     WLOGFD("set touchable");
1581     if (IsWindowSessionInvalid()) {
1582         return WMError::WM_ERROR_INVALID_WINDOW;
1583     }
1584     property_->SetTouchable(isTouchable);
1585     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_TOUCHABLE);
1586 }
1587 
1588 /** @note @window.hierarchy */
SetTopmost(bool topmost)1589 WMError WindowSessionImpl::SetTopmost(bool topmost)
1590 {
1591     TLOGD(WmsLogTag::WMS_LAYOUT, "set topmost");
1592     auto isPC = windowSystemConfig_.uiType_ == UI_TYPE_PC;
1593     if (!isPC) {
1594         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
1595     }
1596     if (IsWindowSessionInvalid()) {
1597         return WMError::WM_ERROR_INVALID_WINDOW;
1598     }
1599     property_->SetTopmost(topmost);
1600     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_TOPMOST);
1601 }
1602 
1603 /** @note @window.hierarchy */
IsTopmost() const1604 bool WindowSessionImpl::IsTopmost() const
1605 {
1606     return property_->IsTopmost();
1607 }
1608 
1609 /** @note @window.hierarchy */
SetMainWindowTopmost(bool isTopmost)1610 WMError WindowSessionImpl::SetMainWindowTopmost(bool isTopmost)
1611 {
1612     if (IsWindowSessionInvalid()) {
1613         return WMError::WM_ERROR_INVALID_WINDOW;
1614     }
1615     if (!IsPcOrPadFreeMultiWindowMode()) {
1616         TLOGE(WmsLogTag::WMS_HIERARCHY, "device not support");
1617         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
1618     }
1619     if (!WindowHelper::IsMainWindow(GetType())) {
1620         TLOGE(WmsLogTag::WMS_HIERARCHY, "window type is not supported");
1621         return WMError::WM_ERROR_INVALID_CALLING;
1622     }
1623     property_->SetMainWindowTopmost(isTopmost);
1624     uint32_t accessTokenId = static_cast<uint32_t>(IPCSkeleton::GetCallingTokenID());
1625     property_->SetAccessTokenId(accessTokenId);
1626     TLOGD(WmsLogTag::WMS_HIERARCHY, "tokenId=%{private}u, isTopmost=%{public}d", accessTokenId, isTopmost);
1627     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_MAIN_WINDOW_TOPMOST);
1628 }
1629 
IsMainWindowTopmost() const1630 bool WindowSessionImpl::IsMainWindowTopmost() const
1631 {
1632     return property_->IsMainWindowTopmost();
1633 }
1634 
SetResizeByDragEnabled(bool dragEnabled)1635 WMError WindowSessionImpl::SetResizeByDragEnabled(bool dragEnabled)
1636 {
1637     TLOGD(WmsLogTag::DEFAULT, "%{public}d", dragEnabled);
1638     if (IsWindowSessionInvalid()) {
1639         TLOGE(WmsLogTag::DEFAULT, "Session is invalid");
1640         return WMError::WM_ERROR_INVALID_WINDOW;
1641     }
1642     if (WindowHelper::IsMainWindow(GetType()) ||
1643         (WindowHelper::IsSubWindow(GetType()) && windowOption_->GetSubWindowDecorEnable())) {
1644         property_->SetDragEnabled(dragEnabled);
1645     } else {
1646         TLOGE(WmsLogTag::DEFAULT, "This is not main window or decor enabled sub window.");
1647         return WMError::WM_ERROR_INVALID_TYPE;
1648     }
1649     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_DRAGENABLED);
1650 }
1651 
1652 /** @note @window.hierarchy */
SetRaiseByClickEnabled(bool raiseEnabled)1653 WMError WindowSessionImpl::SetRaiseByClickEnabled(bool raiseEnabled)
1654 {
1655     WLOGFD("%{public}d", raiseEnabled);
1656     auto parentId = GetParentId();
1657     if (parentId == INVALID_SESSION_ID) {
1658         TLOGE(WmsLogTag::WMS_HIERARCHY, "Window id: %{public}d Parent id is invalid!",
1659               GetPersistentId());
1660         return WMError::WM_ERROR_INVALID_PARENT;
1661     }
1662     if (!WindowHelper::IsSubWindow(GetType())) {
1663         TLOGE(WmsLogTag::WMS_HIERARCHY, "Window id: %{public}d Must be app sub window!",
1664               GetPersistentId());
1665         return WMError::WM_ERROR_INVALID_CALLING;
1666     }
1667     if (state_ != WindowState::STATE_SHOWN) {
1668         TLOGE(WmsLogTag::WMS_HIERARCHY, "Window id: %{public}d The sub window must be shown!",
1669               GetPersistentId());
1670         return WMError::WM_DO_NOTHING;
1671     }
1672     if (IsWindowSessionInvalid()) {
1673         return WMError::WM_ERROR_INVALID_WINDOW;
1674     }
1675 
1676     property_->SetRaiseEnabled(raiseEnabled);
1677     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_RAISEENABLED);
1678 }
1679 
HideNonSystemFloatingWindows(bool shouldHide)1680 WMError WindowSessionImpl::HideNonSystemFloatingWindows(bool shouldHide)
1681 {
1682     WLOGFD("hide non-system floating windows");
1683     if (IsWindowSessionInvalid()) {
1684         return WMError::WM_ERROR_INVALID_WINDOW;
1685     }
1686     property_->SetHideNonSystemFloatingWindows(shouldHide);
1687     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_HIDE_NON_SYSTEM_FLOATING_WINDOWS);
1688 }
1689 
SetLandscapeMultiWindow(bool isLandscapeMultiWindow)1690 WMError WindowSessionImpl::SetLandscapeMultiWindow(bool isLandscapeMultiWindow)
1691 {
1692     TLOGI(WmsLogTag::WMS_MULTI_WINDOW, "SetLandscapeMultiWindow, isLandscapeMultiWindow:%{public}d",
1693         isLandscapeMultiWindow);
1694     if (IsWindowSessionInvalid()) {
1695         TLOGE(WmsLogTag::WMS_MULTI_WINDOW, "Session is invalid");
1696         return WMError::WM_ERROR_INVALID_WINDOW;
1697     }
1698     auto hostSession = GetHostSession();
1699     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_INVALID_WINDOW);
1700     hostSession->SetLandscapeMultiWindow(isLandscapeMultiWindow);
1701     return WMError::WM_OK;
1702 }
1703 
SetSingleFrameComposerEnabled(bool enable)1704 WMError WindowSessionImpl::SetSingleFrameComposerEnabled(bool enable)
1705 {
1706     WLOGFD("Set the enable flag of single frame composer.");
1707     if (IsWindowSessionInvalid()) {
1708         WLOGE("The window state is invalid ");
1709         return WMError::WM_ERROR_INVALID_WINDOW;
1710     }
1711 
1712     if (surfaceNode_ == nullptr) {
1713         WLOGE("The surface node is nullptr");
1714         return WMError::WM_ERROR_INVALID_WINDOW;
1715     }
1716 
1717     surfaceNode_->MarkNodeSingleFrameComposer(enable);
1718     RSTransaction::FlushImplicitTransaction();
1719     return WMError::WM_OK;
1720 }
1721 
IsFloatingWindowAppType() const1722 bool WindowSessionImpl::IsFloatingWindowAppType() const
1723 {
1724     if (IsWindowSessionInvalid()) {
1725         return false;
1726     }
1727     return property_ != nullptr && property_->IsFloatingWindowAppType();
1728 }
1729 
GetTouchable() const1730 bool WindowSessionImpl::GetTouchable() const
1731 {
1732     return property_->GetTouchable();
1733 }
1734 
SetWindowType(WindowType type)1735 WMError WindowSessionImpl::SetWindowType(WindowType type)
1736 {
1737     TLOGD(WmsLogTag::DEFAULT, "SetWindowType %{public}u type %{public}u", GetWindowId(), static_cast<uint32_t>(type));
1738     if (type != WindowType::WINDOW_TYPE_SYSTEM_ALARM_WINDOW && !SessionPermission::IsSystemCalling()) {
1739         TLOGE(WmsLogTag::DEFAULT, "set window type permission denied!");
1740         return WMError::WM_ERROR_NOT_SYSTEM_APP;
1741     }
1742     if (IsWindowSessionInvalid()) {
1743         TLOGE(WmsLogTag::DEFAULT, "Session is invalid");
1744         return WMError::WM_ERROR_INVALID_WINDOW;
1745     }
1746     property_->SetWindowType(type);
1747     UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_OTHER_PROPS);
1748     return WMError::WM_OK;
1749 }
1750 
SetBrightness(float brightness)1751 WMError WindowSessionImpl::SetBrightness(float brightness)
1752 {
1753     if ((brightness < MINIMUM_BRIGHTNESS &&
1754         std::fabs(brightness - UNDEFINED_BRIGHTNESS) >= std::numeric_limits<float>::min()) ||
1755         brightness > MAXIMUM_BRIGHTNESS) {
1756         TLOGE(WmsLogTag::DEFAULT, "invalid brightness value: %{public}f", brightness);
1757         return WMError::WM_ERROR_INVALID_PARAM;
1758     }
1759     if (!WindowHelper::IsAppWindow(GetType())) {
1760         TLOGE(WmsLogTag::DEFAULT, "non app window does not support set brightness, type: %{public}u", GetType());
1761         return WMError::WM_ERROR_INVALID_TYPE;
1762     }
1763     if (!property_) {
1764         TLOGE(WmsLogTag::DEFAULT, "window property is not existed");
1765         return WMError::WM_ERROR_NULLPTR;
1766     }
1767     property_->SetBrightness(brightness);
1768     return UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_SET_BRIGHTNESS);
1769 }
1770 
GetBrightness() const1771 float WindowSessionImpl::GetBrightness() const
1772 {
1773     return property_->GetBrightness();
1774 }
1775 
SetRequestedOrientation(Orientation orientation)1776 void WindowSessionImpl::SetRequestedOrientation(Orientation orientation)
1777 {
1778     if (IsWindowSessionInvalid()) {
1779         TLOGE(WmsLogTag::DEFAULT, "windowSession is invalid");
1780         return;
1781     }
1782     TLOGI(WmsLogTag::WMS_MAIN, "id:%{public}u lastReqOrientation:%{public}u target:%{public}u state:%{public}u",
1783         GetPersistentId(), property_->GetRequestedOrientation(), orientation, state_);
1784     bool isUserOrientation = IsUserOrientation(orientation);
1785     if (property_->GetRequestedOrientation() == orientation && !isUserOrientation) {
1786         return;
1787     }
1788     property_->SetRequestedOrientation(orientation);
1789     UpdateProperty(WSPropertyChangeAction::ACTION_UPDATE_ORIENTATION);
1790 }
1791 
GetRequestedOrientation()1792 Orientation WindowSessionImpl::GetRequestedOrientation()
1793 {
1794     if (IsWindowSessionInvalid()) {
1795         TLOGE(WmsLogTag::DEFAULT, "windowSession is invalid");
1796         return Orientation::UNSPECIFIED;
1797     }
1798     return property_->GetRequestedOrientation();
1799 }
1800 
GetContentInfo(BackupAndRestoreType type)1801 std::string WindowSessionImpl::GetContentInfo(BackupAndRestoreType type)
1802 {
1803     WLOGFD("GetContentInfo");
1804     if (type == BackupAndRestoreType::NONE) {
1805         return "";
1806     }
1807     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1808     if (uiContent == nullptr) {
1809         WLOGFE("fail to GetContentInfo id: %{public}d", GetPersistentId());
1810         return "";
1811     }
1812     return uiContent->GetContentInfo(GetAceContentInfoType(type));
1813 }
1814 
SetRestoredRouterStack(const std::string & routerStack)1815 WMError WindowSessionImpl::SetRestoredRouterStack(const std::string& routerStack)
1816 {
1817     TLOGD(WmsLogTag::WMS_LIFE, "Set restored router stack.");
1818     restoredRouterStack_ = routerStack;
1819     return WMError::WM_OK;
1820 }
1821 
GetRestoredRouterStack()1822 std::string WindowSessionImpl::GetRestoredRouterStack()
1823 {
1824     TLOGD(WmsLogTag::WMS_LIFE, "Get restored router stack.");
1825     return std::move(restoredRouterStack_);
1826 }
1827 
GetUIContent() const1828 Ace::UIContent* WindowSessionImpl::GetUIContent() const
1829 {
1830     std::shared_lock<std::shared_mutex> lock(uiContentMutex_);
1831     return uiContent_.get();
1832 }
1833 
GetUIContentSharedPtr() const1834 std::shared_ptr<Ace::UIContent> WindowSessionImpl::GetUIContentSharedPtr() const
1835 {
1836     std::shared_lock<std::shared_mutex> lock(uiContentMutex_);
1837     return uiContent_;
1838 }
1839 
GetUIContentWithId(uint32_t winId) const1840 Ace::UIContent* WindowSessionImpl::GetUIContentWithId(uint32_t winId) const
1841 {
1842     sptr<Window> targetWindow = FindWindowById(winId);
1843     if (targetWindow == nullptr) {
1844         WLOGE("target window is null");
1845         return nullptr;
1846     }
1847     return targetWindow->GetUIContent();
1848 }
1849 
OnNewWant(const AAFwk::Want & want)1850 void WindowSessionImpl::OnNewWant(const AAFwk::Want& want)
1851 {
1852     WLOGFI("Window [name:%{public}s, id:%{public}d]",
1853         property_->GetWindowName().c_str(), GetPersistentId());
1854     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1855     if (uiContent != nullptr) {
1856         uiContent->OnNewWant(want);
1857     }
1858 }
1859 
SetAPPWindowLabel(const std::string & label)1860 WMError WindowSessionImpl::SetAPPWindowLabel(const std::string& label)
1861 {
1862     TLOGI(WmsLogTag::DEFAULT, "Enter");
1863     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1864     if (uiContent == nullptr) {
1865         WLOGFE("uicontent is empty");
1866         return WMError::WM_ERROR_NULLPTR;
1867     }
1868     uiContent->SetAppWindowTitle(label);
1869     return WMError::WM_OK;
1870 }
1871 
SetAPPWindowIcon(const std::shared_ptr<Media::PixelMap> & icon)1872 WMError WindowSessionImpl::SetAPPWindowIcon(const std::shared_ptr<Media::PixelMap>& icon)
1873 {
1874     if (icon == nullptr) {
1875         WLOGFE("window icon is empty");
1876         return WMError::WM_ERROR_NULLPTR;
1877     }
1878     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1879     if (uiContent == nullptr) {
1880         WLOGFE("uicontent is empty");
1881         return WMError::WM_ERROR_NULLPTR;
1882     }
1883     uiContent->SetAppWindowIcon(icon);
1884     WLOGI("Set app window icon success");
1885     return WMError::WM_OK;
1886 }
1887 
RegisterLifeCycleListener(const sptr<IWindowLifeCycle> & listener)1888 WMError WindowSessionImpl::RegisterLifeCycleListener(const sptr<IWindowLifeCycle>& listener)
1889 {
1890     WLOGFD("Start register");
1891     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
1892     return RegisterListener(lifecycleListeners_[GetPersistentId()], listener);
1893 }
1894 
RegisterDisplayMoveListener(sptr<IDisplayMoveListener> & listener)1895 WMError WindowSessionImpl::RegisterDisplayMoveListener(sptr<IDisplayMoveListener>& listener)
1896 {
1897     WLOGFD("Start register");
1898     std::lock_guard<std::mutex> lockListener(displayMoveListenerMutex_);
1899     return RegisterListener(displayMoveListeners_[GetPersistentId()], listener);
1900 }
1901 
UnregisterDisplayMoveListener(sptr<IDisplayMoveListener> & listener)1902 WMError WindowSessionImpl::UnregisterDisplayMoveListener(sptr<IDisplayMoveListener>& listener)
1903 {
1904     WLOGFD("Start unregister");
1905     std::lock_guard<std::mutex> lockListener(displayMoveListenerMutex_);
1906     return UnregisterListener(displayMoveListeners_[GetPersistentId()], listener);
1907 }
1908 
1909 /**
1910  * Currently only supports system windows.
1911  */
EnableDrag(bool enableDrag)1912 WMError WindowSessionImpl::EnableDrag(bool enableDrag)
1913 {
1914     bool isPC = windowSystemConfig_.uiType_ == UI_TYPE_PC;
1915     if (!isPC && !IsFreeMultiWindowMode()) {
1916         TLOGE(WmsLogTag::WMS_LAYOUT, "The device is not supported");
1917         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
1918     }
1919     property_->SetDragEnabled(enableDrag);
1920     auto hostSession = GetHostSession();
1921     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_INVALID_WINDOW);
1922     WMError errorCode = hostSession->SetSystemWindowEnableDrag(enableDrag);
1923     TLOGI(WmsLogTag::WMS_LAYOUT, "Id:%{public}d, enableDrag:%{public}d, errcode:%{public}d",
1924         GetPersistentId(), enableDrag, static_cast<int>(errorCode));
1925     return static_cast<WMError>(errorCode);
1926 }
1927 
RegisterOccupiedAreaChangeListener(const sptr<IOccupiedAreaChangeListener> & listener)1928 WMError WindowSessionImpl::RegisterOccupiedAreaChangeListener(const sptr<IOccupiedAreaChangeListener>& listener)
1929 {
1930     WLOGFD("Start register");
1931     std::lock_guard<std::recursive_mutex> lockListener(occupiedAreaChangeListenerMutex_);
1932     return RegisterListener(occupiedAreaChangeListeners_[GetPersistentId()], listener);
1933 }
1934 
UnregisterOccupiedAreaChangeListener(const sptr<IOccupiedAreaChangeListener> & listener)1935 WMError WindowSessionImpl::UnregisterOccupiedAreaChangeListener(const sptr<IOccupiedAreaChangeListener>& listener)
1936 {
1937     WLOGFD("Start unregister");
1938     std::lock_guard<std::recursive_mutex> lockListener(occupiedAreaChangeListenerMutex_);
1939     return UnregisterListener(occupiedAreaChangeListeners_[GetPersistentId()], listener);
1940 }
1941 
UnregisterLifeCycleListener(const sptr<IWindowLifeCycle> & listener)1942 WMError WindowSessionImpl::UnregisterLifeCycleListener(const sptr<IWindowLifeCycle>& listener)
1943 {
1944     WLOGFD("Start unregister");
1945     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
1946     return UnregisterListener(lifecycleListeners_[GetPersistentId()], listener);
1947 }
1948 
RegisterWindowChangeListener(const sptr<IWindowChangeListener> & listener)1949 WMError WindowSessionImpl::RegisterWindowChangeListener(const sptr<IWindowChangeListener>& listener)
1950 {
1951     WLOGFD("Start register");
1952     std::lock_guard<std::recursive_mutex> lockListener(windowChangeListenerMutex_);
1953     return RegisterListener(windowChangeListeners_[GetPersistentId()], listener);
1954 }
1955 
UnregisterWindowChangeListener(const sptr<IWindowChangeListener> & listener)1956 WMError WindowSessionImpl::UnregisterWindowChangeListener(const sptr<IWindowChangeListener>& listener)
1957 {
1958     WLOGFD("Start register");
1959     std::lock_guard<std::recursive_mutex> lockListener(windowChangeListenerMutex_);
1960     return UnregisterListener(windowChangeListeners_[GetPersistentId()], listener);
1961 }
1962 
RegisterWindowStatusChangeListener(const sptr<IWindowStatusChangeListener> & listener)1963 WMError WindowSessionImpl::RegisterWindowStatusChangeListener(const sptr<IWindowStatusChangeListener>& listener)
1964 {
1965     WLOGFD("Start register");
1966     std::lock_guard<std::recursive_mutex> lockListener(windowStatusChangeListenerMutex_);
1967     return RegisterListener(windowStatusChangeListeners_[GetPersistentId()], listener);
1968 }
1969 
UnregisterWindowStatusChangeListener(const sptr<IWindowStatusChangeListener> & listener)1970 WMError WindowSessionImpl::UnregisterWindowStatusChangeListener(const sptr<IWindowStatusChangeListener>& listener)
1971 {
1972     WLOGFD("Start register");
1973     std::lock_guard<std::recursive_mutex> lockListener(windowStatusChangeListenerMutex_);
1974     return UnregisterListener(windowStatusChangeListeners_[GetPersistentId()], listener);
1975 }
1976 
SetDecorVisible(bool isVisible)1977 WMError WindowSessionImpl::SetDecorVisible(bool isVisible)
1978 {
1979     if (IsWindowSessionInvalid()) {
1980         return WMError::WM_ERROR_INVALID_WINDOW;
1981     }
1982     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
1983     if (uiContent == nullptr) {
1984         WLOGFE("uicontent is empty");
1985         return WMError::WM_ERROR_NULLPTR;
1986     }
1987     uiContent->SetContainerModalTitleVisible(isVisible, true);
1988     WLOGI("Change the visibility of decor success");
1989     return WMError::WM_OK;
1990 }
1991 
SetWindowTitleMoveEnabled(bool enable)1992 WMError WindowSessionImpl::SetWindowTitleMoveEnabled(bool enable)
1993 {
1994     if (IsWindowSessionInvalid()) {
1995         return WMError::WM_ERROR_INVALID_WINDOW;
1996     }
1997     if (!IsPcOrPadFreeMultiWindowMode()) {
1998         TLOGE(WmsLogTag::WMS_LAYOUT, "The device is not supported");
1999         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
2000     }
2001     if (!WindowHelper::IsMainWindow(GetType()) && !WindowHelper::IsSubWindow(GetType())) {
2002         TLOGE(WmsLogTag::WMS_LAYOUT, "called by invalid window type, type:%{public}d", GetType());
2003         return WMError::WM_ERROR_INVALID_CALLING;
2004     }
2005     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2006     if (uiContent == nullptr) {
2007         TLOGE(WmsLogTag::WMS_LAYOUT, "uicontent is null");
2008         return WMError::WM_ERROR_NULLPTR;
2009     }
2010     uiContent->EnableContainerModalGesture(enable);
2011     TLOGI(WmsLogTag::WMS_LAYOUT, "enable:%{public}d end", enable);
2012     return WMError::WM_OK;
2013 }
2014 
SetSubWindowModal(bool isModal,ModalityType modalityType)2015 WMError WindowSessionImpl::SetSubWindowModal(bool isModal, ModalityType modalityType)
2016 {
2017     if (IsWindowSessionInvalid()) {
2018         return WMError::WM_ERROR_INVALID_WINDOW;
2019     }
2020     if (!WindowHelper::IsSubWindow(GetType())) {
2021         TLOGE(WmsLogTag::WMS_SUB, "called by invalid window type, type:%{public}d", GetType());
2022         return WMError::WM_ERROR_INVALID_CALLING;
2023     }
2024     if (modalityType == ModalityType::APPLICATION_MODALITY && !IsPcOrPadFreeMultiWindowMode()) {
2025         TLOGE(WmsLogTag::WMS_SUB, "device not support");
2026         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
2027     }
2028 
2029     WMError modalRet = isModal ?
2030         AddWindowFlag(WindowFlag::WINDOW_FLAG_IS_MODAL) :
2031         RemoveWindowFlag(WindowFlag::WINDOW_FLAG_IS_MODAL);
2032     if (modalRet != WMError::WM_OK) {
2033         return modalRet;
2034     }
2035     modalRet = isModal && modalityType == ModalityType::APPLICATION_MODALITY ?
2036         AddWindowFlag(WindowFlag::WINDOW_FLAG_IS_APPLICATION_MODAL) :
2037         RemoveWindowFlag(WindowFlag::WINDOW_FLAG_IS_APPLICATION_MODAL);
2038     auto hostSession = GetHostSession();
2039     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_INVALID_WINDOW);
2040     SubWindowModalType subWindowModalType = SubWindowModalType::TYPE_NORMAL;
2041     if (isModal) {
2042         subWindowModalType = modalityType == ModalityType::WINDOW_MODALITY ?
2043             SubWindowModalType::TYPE_WINDOW_MODALITY :
2044             SubWindowModalType::TYPE_APPLICATION_MODALITY;
2045     }
2046     hostSession->NotifySubModalTypeChange(subWindowModalType);
2047     return modalRet;
2048 }
2049 
SetWindowModal(bool isModal)2050 WMError WindowSessionImpl::SetWindowModal(bool isModal)
2051 {
2052     if (IsWindowSessionInvalid()) {
2053         return WMError::WM_ERROR_INVALID_WINDOW;
2054     }
2055     if (!IsPcOrPadFreeMultiWindowMode()) {
2056         TLOGE(WmsLogTag::WMS_MAIN, "device not support");
2057         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
2058     }
2059     if (!WindowHelper::IsMainWindow(GetType())) {
2060         TLOGE(WmsLogTag::WMS_MAIN, "called by invalid window type, type:%{public}d", GetType());
2061         return WMError::WM_ERROR_INVALID_CALLING;
2062     }
2063     WMError modalRet = isModal ?
2064         AddWindowFlag(WindowFlag::WINDOW_FLAG_IS_MODAL) :
2065         RemoveWindowFlag(WindowFlag::WINDOW_FLAG_IS_MODAL);
2066     if (modalRet != WMError::WM_OK) {
2067         return modalRet;
2068     }
2069     auto hostSession = GetHostSession();
2070     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_SYSTEM_ABNORMALLY);
2071     hostSession->NotifyMainModalTypeChange(isModal);
2072     return modalRet;
2073 }
2074 
SetDecorHeight(int32_t decorHeight)2075 WMError WindowSessionImpl::SetDecorHeight(int32_t decorHeight)
2076 {
2077     if (IsWindowSessionInvalid()) {
2078         return WMError::WM_ERROR_INVALID_WINDOW;
2079     }
2080     auto display = SingletonContainer::Get<DisplayManager>().GetDisplayById(property_->GetDisplayId());
2081     if (display == nullptr) {
2082         WLOGFE("get display failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2083         return WMError::WM_ERROR_NULLPTR;
2084     }
2085     auto displayInfo = display->GetDisplayInfo();
2086     if (displayInfo == nullptr) {
2087         WLOGFE("get display info failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2088         return WMError::WM_ERROR_NULLPTR;
2089     }
2090     float vpr = GetVirtualPixelRatio(displayInfo);
2091     int32_t decorHeightWithPx = static_cast<int32_t>(decorHeight * vpr);
2092     {
2093         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2094         if (uiContent == nullptr) {
2095             WLOGFE("uicontent is empty");
2096             return WMError::WM_ERROR_NULLPTR;
2097         }
2098         uiContent->SetContainerModalTitleHeight(decorHeightWithPx);
2099     }
2100     auto hostSession = GetHostSession();
2101     if (hostSession != nullptr) {
2102         hostSession->SetCustomDecorHeight(decorHeight);
2103     }
2104     WLOGI("Set app window decor height success, height : %{public}d", decorHeight);
2105     return WMError::WM_OK;
2106 }
2107 
GetDecorHeight(int32_t & height)2108 WMError WindowSessionImpl::GetDecorHeight(int32_t& height)
2109 {
2110     if (IsWindowSessionInvalid()) {
2111         return WMError::WM_ERROR_INVALID_WINDOW;
2112     }
2113     {
2114         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2115         if (uiContent == nullptr) {
2116             WLOGFE("uiContent is nullptr, windowId: %{public}u", GetWindowId());
2117             return WMError::WM_ERROR_NULLPTR;
2118         }
2119         height = uiContent->GetContainerModalTitleHeight();
2120     }
2121     if (height == -1) {
2122         height = 0;
2123         WLOGFE("Get app window decor height failed");
2124         return WMError::WM_OK;
2125     }
2126     auto display = SingletonContainer::Get<DisplayManager>().GetDisplayById(property_->GetDisplayId());
2127     if (display == nullptr) {
2128         WLOGFE("get display failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2129         return WMError::WM_ERROR_NULLPTR;
2130     }
2131     auto displayInfo = display->GetDisplayInfo();
2132     if (displayInfo == nullptr) {
2133         WLOGFE("get display info failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2134         return WMError::WM_ERROR_NULLPTR;
2135     }
2136     float vpr = GetVirtualPixelRatio(displayInfo);
2137     if (MathHelper::NearZero(vpr)) {
2138         WLOGFE("get decor height failed, because of wrong vpr: %{public}f", vpr);
2139         return WMError::WM_ERROR_INVALID_WINDOW;
2140     }
2141     height = static_cast<int32_t>(height / vpr);
2142     WLOGI("Get app window decor height success, height : %{public}d", height);
2143     return WMError::WM_OK;
2144 }
2145 
GetTitleButtonArea(TitleButtonRect & titleButtonRect)2146 WMError WindowSessionImpl::GetTitleButtonArea(TitleButtonRect& titleButtonRect)
2147 {
2148     if (IsWindowSessionInvalid()) {
2149         return WMError::WM_ERROR_INVALID_WINDOW;
2150     }
2151     Rect decorRect;
2152     Rect titleButtonLeftRect;
2153     bool res = false;
2154     {
2155         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2156         if (uiContent == nullptr) {
2157             WLOGFE("uicontent is empty");
2158             return WMError::WM_ERROR_NULLPTR;
2159         }
2160         res = uiContent->GetContainerModalButtonsRect(decorRect, titleButtonLeftRect);
2161     }
2162     if (!res) {
2163         WLOGFE("get window title buttons area failed");
2164         titleButtonRect.IsUninitializedRect();
2165         return WMError::WM_OK;
2166     }
2167     auto display = SingletonContainer::Get<DisplayManager>().GetDisplayById(property_->GetDisplayId());
2168     if (display == nullptr) {
2169         WLOGFE("get display failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2170         return WMError::WM_ERROR_NULLPTR;
2171     }
2172     auto displayInfo = display->GetDisplayInfo();
2173     if (displayInfo == nullptr) {
2174         WLOGFE("get display info failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2175         return WMError::WM_ERROR_NULLPTR;
2176     }
2177     float vpr = GetVirtualPixelRatio(displayInfo);
2178     if (MathHelper::NearZero(vpr)) {
2179         WLOGFE("get title buttons area failed, because of wrong vpr: %{public}f", vpr);
2180         return WMError::WM_ERROR_INVALID_WINDOW;
2181     }
2182     titleButtonRect.posX_ = static_cast<int32_t>(decorRect.width_) -
2183         static_cast<int32_t>(titleButtonLeftRect.width_) - titleButtonLeftRect.posX_;
2184     titleButtonRect.posX_ = static_cast<int32_t>(titleButtonRect.posX_ / vpr);
2185     titleButtonRect.posY_ = static_cast<int32_t>(titleButtonLeftRect.posY_ / vpr);
2186     titleButtonRect.width_ = static_cast<uint32_t>(titleButtonLeftRect.width_ / vpr);
2187     titleButtonRect.height_ = static_cast<uint32_t>(titleButtonLeftRect.height_ / vpr);
2188     return WMError::WM_OK;
2189 }
2190 
GetUIContentRemoteObj(sptr<IRemoteObject> & uiContentRemoteObj)2191 WSError WindowSessionImpl::GetUIContentRemoteObj(sptr<IRemoteObject>& uiContentRemoteObj)
2192 {
2193     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2194     if (uiContent == nullptr) {
2195         TLOGE(WmsLogTag::DEFAULT, "uiContent is nullptr. Failed to get uiContentRemoteObj");
2196         return WSError::WS_ERROR_NULLPTR;
2197     }
2198     uiContentRemoteObj = uiContent->GetRemoteObj();
2199     return WSError::WS_OK;
2200 }
2201 
RegisterWindowTitleButtonRectChangeListener(const sptr<IWindowTitleButtonRectChangedListener> & listener)2202 WMError WindowSessionImpl::RegisterWindowTitleButtonRectChangeListener(
2203     const sptr<IWindowTitleButtonRectChangedListener>& listener)
2204 {
2205     if (IsWindowSessionInvalid()) {
2206         return WMError::WM_ERROR_INVALID_WINDOW;
2207     }
2208     auto persistentId = GetPersistentId();
2209     WLOGFD("Start register windowTitleButtonRectChange listener, id:%{public}d", persistentId);
2210     if (listener == nullptr) {
2211         WLOGFE("listener is nullptr");
2212         return WMError::WM_ERROR_NULLPTR;
2213     }
2214 
2215     {
2216         std::lock_guard<std::recursive_mutex> lockListener(windowTitleButtonRectChangeListenerMutex_);
2217         WMError ret = RegisterListener(windowTitleButtonRectChangeListeners_[persistentId], listener);
2218         if (ret != WMError::WM_OK) {
2219             WLOGFE("register the listener of window title button rect change failed");
2220             return ret;
2221         }
2222     }
2223     auto display = SingletonContainer::Get<DisplayManager>().GetDisplayById(property_->GetDisplayId());
2224     if (display == nullptr) {
2225         WLOGFE("get display failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2226         return WMError::WM_ERROR_NULLPTR;
2227     }
2228     auto displayInfo = display->GetDisplayInfo();
2229     if (displayInfo == nullptr) {
2230         WLOGFE("get display info failed displayId:%{public}" PRIu64, property_->GetDisplayId());
2231         return WMError::WM_ERROR_NULLPTR;
2232     }
2233     float vpr = GetVirtualPixelRatio(displayInfo);
2234     if (MathHelper::NearZero(vpr)) {
2235         WLOGFE("register title button rect change listener failed, because of wrong vpr: %{public}f", vpr);
2236         return WMError::WM_ERROR_INVALID_WINDOW;
2237     }
2238     if (auto uiContent = GetUIContentSharedPtr()) {
2239         uiContent->SubscribeContainerModalButtonsRectChange(
2240             [vpr, weakThis = wptr(this)](Rect& decorRect, Rect& titleButtonLeftRect) {
2241             auto window = weakThis.promote();
2242             if (!window) {
2243                 TLOGNE(WmsLogTag::WMS_LAYOUT, "window is null");
2244                 return;
2245             }
2246             TitleButtonRect titleButtonRect;
2247             titleButtonRect.posX_ = static_cast<int32_t>(decorRect.width_) -
2248                 static_cast<int32_t>(titleButtonLeftRect.width_) - titleButtonLeftRect.posX_;
2249             titleButtonRect.posX_ = static_cast<int32_t>(titleButtonRect.posX_ / vpr);
2250             titleButtonRect.posY_ = static_cast<int32_t>(titleButtonLeftRect.posY_ / vpr);
2251             titleButtonRect.width_ = static_cast<uint32_t>(titleButtonLeftRect.width_ / vpr);
2252             titleButtonRect.height_ = static_cast<uint32_t>(titleButtonLeftRect.height_ / vpr);
2253             window->NotifyWindowTitleButtonRectChange(titleButtonRect);
2254         });
2255     }
2256     return WMError::WM_OK;
2257 }
2258 
UnregisterWindowTitleButtonRectChangeListener(const sptr<IWindowTitleButtonRectChangedListener> & listener)2259 WMError WindowSessionImpl::UnregisterWindowTitleButtonRectChangeListener(
2260     const sptr<IWindowTitleButtonRectChangedListener>& listener)
2261 {
2262     if (IsWindowSessionInvalid()) {
2263         return WMError::WM_ERROR_INVALID_WINDOW;
2264     }
2265     WMError ret = WMError::WM_OK;
2266     auto persistentId = GetPersistentId();
2267     WLOGFD("Start unregister windowTitleButtonRectChange listener, id:%{public}d", persistentId);
2268     if (listener == nullptr) {
2269         WLOGFE("listener is nullptr");
2270         return WMError::WM_ERROR_NULLPTR;
2271     }
2272     {
2273         std::lock_guard<std::recursive_mutex> lockListener(windowTitleButtonRectChangeListenerMutex_);
2274         ret = UnregisterListener(windowTitleButtonRectChangeListeners_[persistentId], listener);
2275         if (ret != WMError::WM_OK) {
2276             WLOGFE("unregister the listener of window title button rect change failed");
2277             return ret;
2278         }
2279     }
2280     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2281     if (uiContent != nullptr) {
2282         uiContent->SubscribeContainerModalButtonsRectChange(nullptr);
2283     }
2284     return ret;
2285 }
2286 
2287 template<typename T>
2288 EnableIfSame<T, IWindowTitleButtonRectChangedListener,
GetListeners()2289     std::vector<sptr<IWindowTitleButtonRectChangedListener>>> WindowSessionImpl::GetListeners()
2290 {
2291     std::vector<sptr<IWindowTitleButtonRectChangedListener>> windowTitleButtonRectListeners;
2292         for (auto& listener : windowTitleButtonRectChangeListeners_[GetPersistentId()]) {
2293             windowTitleButtonRectListeners.push_back(listener);
2294         }
2295     return windowTitleButtonRectListeners;
2296 }
2297 
NotifyWindowTitleButtonRectChange(TitleButtonRect titleButtonRect)2298 void WindowSessionImpl::NotifyWindowTitleButtonRectChange(TitleButtonRect titleButtonRect)
2299 {
2300     std::lock_guard<std::recursive_mutex> lockListener(windowTitleButtonRectChangeListenerMutex_);
2301     auto windowTitleButtonRectListeners = GetListeners<IWindowTitleButtonRectChangedListener>();
2302     for (auto& listener : windowTitleButtonRectListeners) {
2303         if (listener != nullptr) {
2304             listener->OnWindowTitleButtonRectChanged(titleButtonRect);
2305         }
2306     }
2307 }
2308 
2309 template<typename T>
2310 EnableIfSame<T, IWindowRectChangeListener,
GetListeners()2311     std::vector<sptr<IWindowRectChangeListener>>> WindowSessionImpl::GetListeners()
2312 {
2313     std::vector<sptr<IWindowRectChangeListener>> windowRectChangeListeners;
2314     for (auto& listener : windowRectChangeListeners_[GetPersistentId()]) {
2315         windowRectChangeListeners.push_back(listener);
2316     }
2317     return windowRectChangeListeners;
2318 }
2319 
RegisterWindowRectChangeListener(const sptr<IWindowRectChangeListener> & listener)2320 WMError WindowSessionImpl::RegisterWindowRectChangeListener(const sptr<IWindowRectChangeListener>& listener)
2321 {
2322     WMError ret = WMError::WM_OK;
2323     {
2324         std::lock_guard<std::mutex> lockListener(windowRectChangeListenerMutex_);
2325         ret = RegisterListener(windowRectChangeListeners_[GetPersistentId()], listener);
2326     }
2327     auto hostSession = GetHostSession();
2328     if (hostSession != nullptr && ret == WMError::WM_OK) {
2329         hostSession->UpdateRectChangeListenerRegistered(true);
2330     }
2331     return ret;
2332 }
2333 
UnregisterWindowRectChangeListener(const sptr<IWindowRectChangeListener> & listener)2334 WMError WindowSessionImpl::UnregisterWindowRectChangeListener(const sptr<IWindowRectChangeListener>& listener)
2335 {
2336     WMError ret = WMError::WM_OK;
2337     bool windowRectChangeListenersEmpty = false;
2338     {
2339         std::lock_guard<std::mutex> lockListener(windowRectChangeListenerMutex_);
2340         ret = UnregisterListener(windowRectChangeListeners_[GetPersistentId()], listener);
2341         windowRectChangeListenersEmpty = windowRectChangeListeners_.count(GetPersistentId()) == 0 ||
2342                                          windowRectChangeListeners_[GetPersistentId()].empty();
2343     }
2344     auto hostSession = GetHostSession();
2345     if (hostSession != nullptr && windowRectChangeListenersEmpty) {
2346         hostSession->UpdateRectChangeListenerRegistered(false);
2347     }
2348     return ret;
2349 }
2350 
2351 template<typename T>
GetListeners()2352 EnableIfSame<T, ISubWindowCloseListener, sptr<ISubWindowCloseListener>> WindowSessionImpl::GetListeners()
2353 {
2354     sptr<ISubWindowCloseListener> subWindowCloseListeners;
2355     subWindowCloseListeners = subWindowCloseListeners_[GetPersistentId()];
2356     return subWindowCloseListeners;
2357 }
2358 
RegisterSubWindowCloseListeners(const sptr<ISubWindowCloseListener> & listener)2359 WMError WindowSessionImpl::RegisterSubWindowCloseListeners(const sptr<ISubWindowCloseListener>& listener)
2360 {
2361     if (listener == nullptr) {
2362         WLOGFE("listener is nullptr");
2363         return WMError::WM_ERROR_NULLPTR;
2364     }
2365     if (!WindowHelper::IsSubWindow(GetType()) && !WindowHelper::IsSystemSubWindow(GetType())) {
2366         WLOGFE("window type is not supported");
2367         return WMError::WM_ERROR_INVALID_CALLING;
2368     }
2369     std::lock_guard<std::mutex> lockListener(subWindowCloseListenersMutex_);
2370     subWindowCloseListeners_[GetPersistentId()] = listener;
2371     return WMError::WM_OK;
2372 }
2373 
UnregisterSubWindowCloseListeners(const sptr<ISubWindowCloseListener> & listener)2374 WMError WindowSessionImpl::UnregisterSubWindowCloseListeners(const sptr<ISubWindowCloseListener>& listener)
2375 {
2376     if (listener == nullptr) {
2377         WLOGFE("listener could not be null");
2378         return WMError::WM_ERROR_NULLPTR;
2379     }
2380     if (!WindowHelper::IsSubWindow(GetType()) && !WindowHelper::IsSystemSubWindow(GetType())) {
2381         WLOGFE("window type is not supported");
2382         return WMError::WM_ERROR_INVALID_CALLING;
2383     }
2384     std::lock_guard<std::mutex> lockListener(subWindowCloseListenersMutex_);
2385     subWindowCloseListeners_[GetPersistentId()] = nullptr;
2386     return WMError::WM_OK;
2387 }
2388 
2389 template<typename T>
GetListeners()2390 EnableIfSame<T, IMainWindowCloseListener, sptr<IMainWindowCloseListener>> WindowSessionImpl::GetListeners()
2391 {
2392     return mainWindowCloseListeners_[GetPersistentId()];
2393 }
2394 
RegisterMainWindowCloseListeners(const sptr<IMainWindowCloseListener> & listener)2395 WMError WindowSessionImpl::RegisterMainWindowCloseListeners(const sptr<IMainWindowCloseListener>& listener)
2396 {
2397     if (IsWindowSessionInvalid()) {
2398         return WMError::WM_ERROR_INVALID_WINDOW;
2399     }
2400     if (listener == nullptr) {
2401         TLOGE(WmsLogTag::DEFAULT, "listener is null");
2402         return WMError::WM_ERROR_NULLPTR;
2403     }
2404     if (!WindowHelper::IsMainWindow(GetType())) {
2405         TLOGE(WmsLogTag::DEFAULT, "window type is not supported");
2406         return WMError::WM_ERROR_INVALID_CALLING;
2407     }
2408     auto isPC = windowSystemConfig_.uiType_ == UI_TYPE_PC;
2409     if (!(isPC|| IsFreeMultiWindowMode())) {
2410         TLOGE(WmsLogTag::DEFAULT, "The device is not supported");
2411         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
2412     }
2413     std::lock_guard<std::mutex> lockListener(mainWindowCloseListenersMutex_);
2414     mainWindowCloseListeners_[GetPersistentId()] = listener;
2415     return WMError::WM_OK;
2416 }
2417 
UnregisterMainWindowCloseListeners(const sptr<IMainWindowCloseListener> & listener)2418 WMError WindowSessionImpl::UnregisterMainWindowCloseListeners(const sptr<IMainWindowCloseListener>& listener)
2419 {
2420     if (IsWindowSessionInvalid()) {
2421         return WMError::WM_ERROR_INVALID_WINDOW;
2422     }
2423     if (listener == nullptr) {
2424         TLOGE(WmsLogTag::DEFAULT, "listener could not be null");
2425         return WMError::WM_ERROR_NULLPTR;
2426     }
2427     auto isPC = windowSystemConfig_.uiType_ == UI_TYPE_PC;
2428     if (!(isPC|| IsFreeMultiWindowMode())) {
2429         TLOGE(WmsLogTag::DEFAULT, "The device is not supported");
2430         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
2431     }
2432     if (!WindowHelper::IsMainWindow(GetType())) {
2433         TLOGE(WmsLogTag::DEFAULT, "window type is not supported");
2434         return WMError::WM_ERROR_INVALID_CALLING;
2435     }
2436     std::lock_guard<std::mutex> lockListener(mainWindowCloseListenersMutex_);
2437     mainWindowCloseListeners_[GetPersistentId()] = nullptr;
2438     return WMError::WM_OK;
2439 }
2440 
2441 template<typename T>
2442 EnableIfSame<T, ISwitchFreeMultiWindowListener,
GetListeners()2443     std::vector<sptr<ISwitchFreeMultiWindowListener>>> WindowSessionImpl::GetListeners()
2444 {
2445     std::vector<sptr<ISwitchFreeMultiWindowListener>> switchFreeMultiWindowListeners;
2446     for (auto& listener : switchFreeMultiWindowListeners_[GetPersistentId()]) {
2447         switchFreeMultiWindowListeners.push_back(listener);
2448     }
2449     return switchFreeMultiWindowListeners;
2450 }
2451 
RegisterSwitchFreeMultiWindowListener(const sptr<ISwitchFreeMultiWindowListener> & listener)2452 WMError WindowSessionImpl::RegisterSwitchFreeMultiWindowListener(const sptr<ISwitchFreeMultiWindowListener>& listener)
2453 {
2454     if (listener == nullptr) {
2455         WLOGFE("listener is nullptr");
2456         return WMError::WM_ERROR_NULLPTR;
2457     }
2458     if (!WindowHelper::IsMainWindow(GetType())) {
2459         WLOGFE("window type is not supported");
2460         return WMError::WM_ERROR_INVALID_CALLING;
2461     }
2462     WLOGFD("Start register");
2463     std::lock_guard<std::mutex> lockListener(switchFreeMultiWindowListenerMutex_);
2464     return RegisterListener(switchFreeMultiWindowListeners_[GetPersistentId()], listener);
2465 }
2466 
UnregisterSwitchFreeMultiWindowListener(const sptr<ISwitchFreeMultiWindowListener> & listener)2467 WMError WindowSessionImpl::UnregisterSwitchFreeMultiWindowListener(const sptr<ISwitchFreeMultiWindowListener>& listener)
2468 {
2469     if (listener == nullptr) {
2470         WLOGFE("listener could not be null");
2471         return WMError::WM_ERROR_NULLPTR;
2472     }
2473     if (!WindowHelper::IsMainWindow(GetType())) {
2474         WLOGFE("window type is not supported");
2475         return WMError::WM_ERROR_INVALID_CALLING;
2476     }
2477     WLOGFD("Start unregister");
2478     std::lock_guard<std::mutex> lockListener(switchFreeMultiWindowListenerMutex_);
2479     return UnregisterListener(switchFreeMultiWindowListeners_[GetPersistentId()], listener);
2480 }
2481 
RecoverSessionListener()2482 void WindowSessionImpl::RecoverSessionListener()
2483 {
2484     auto persistentId = GetPersistentId();
2485     TLOGI(WmsLogTag::WMS_RECOVER, "with persistentId=%{public}d", persistentId);
2486     {
2487         std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
2488         if (avoidAreaChangeListeners_.find(persistentId) != avoidAreaChangeListeners_.end() &&
2489             !avoidAreaChangeListeners_[persistentId].empty()) {
2490             SingletonContainer::Get<WindowAdapter>().UpdateSessionAvoidAreaListener(persistentId, true);
2491         }
2492     }
2493     {
2494         std::lock_guard<std::recursive_mutex> lockListener(touchOutsideListenerMutex_);
2495         if (touchOutsideListeners_.find(persistentId) != touchOutsideListeners_.end() &&
2496             !touchOutsideListeners_[persistentId].empty()) {
2497             SingletonContainer::Get<WindowAdapter>().UpdateSessionTouchOutsideListener(persistentId, true);
2498         }
2499     }
2500     {
2501         std::lock_guard<std::recursive_mutex> lockListener(windowVisibilityChangeListenerMutex_);
2502         if (windowVisibilityChangeListeners_.find(persistentId) != windowVisibilityChangeListeners_.end() &&
2503             !windowVisibilityChangeListeners_[persistentId].empty()) {
2504             SingletonContainer::Get<WindowAdapter>().UpdateSessionWindowVisibilityListener(persistentId, true);
2505         }
2506     }
2507     {
2508         std::lock_guard<std::mutex> lockListener(windowRectChangeListenerMutex_);
2509         if (windowRectChangeListeners_.find(persistentId) != windowRectChangeListeners_.end() &&
2510             !windowRectChangeListeners_[persistentId].empty()) {
2511             if (auto hostSession = GetHostSession()) {
2512                 hostSession->UpdateRectChangeListenerRegistered(true);
2513             }
2514         }
2515     }
2516 }
2517 
2518 template<typename T>
GetListeners()2519 EnableIfSame<T, IWindowLifeCycle, std::vector<sptr<IWindowLifeCycle>>> WindowSessionImpl::GetListeners()
2520 {
2521     std::vector<sptr<IWindowLifeCycle>> lifecycleListeners;
2522     for (auto& listener : lifecycleListeners_[GetPersistentId()]) {
2523         lifecycleListeners.push_back(listener);
2524     }
2525     return lifecycleListeners;
2526 }
2527 
2528 template<typename T>
GetListeners()2529 EnableIfSame<T, IWindowChangeListener, std::vector<sptr<IWindowChangeListener>>> WindowSessionImpl::GetListeners()
2530 {
2531     std::vector<sptr<IWindowChangeListener>> windowChangeListeners;
2532     for (auto& listener : windowChangeListeners_[GetPersistentId()]) {
2533         windowChangeListeners.push_back(listener);
2534     }
2535     return windowChangeListeners;
2536 }
2537 
2538 template<typename T>
2539 EnableIfSame<T, IOccupiedAreaChangeListener,
GetListeners()2540     std::vector<sptr<IOccupiedAreaChangeListener>>> WindowSessionImpl::GetListeners()
2541 {
2542     std::vector<sptr<IOccupiedAreaChangeListener>> occupiedAreaChangeListeners;
2543     for (auto& listener : occupiedAreaChangeListeners_[GetPersistentId()]) {
2544         occupiedAreaChangeListeners.push_back(listener);
2545     }
2546     return occupiedAreaChangeListeners;
2547 }
2548 
2549 template<typename T>
RegisterListener(std::vector<sptr<T>> & holder,const sptr<T> & listener)2550 WMError WindowSessionImpl::RegisterListener(std::vector<sptr<T>>& holder, const sptr<T>& listener)
2551 {
2552     if (listener == nullptr) {
2553         WLOGFE("listener is nullptr");
2554         return WMError::WM_ERROR_NULLPTR;
2555     }
2556     if (std::find(holder.begin(), holder.end(), listener) != holder.end()) {
2557         WLOGFE("Listener already registered");
2558         return WMError::WM_OK;
2559     }
2560     holder.emplace_back(listener);
2561     return WMError::WM_OK;
2562 }
2563 
2564 template<typename T>
UnregisterListener(std::vector<sptr<T>> & holder,const sptr<T> & listener)2565 WMError WindowSessionImpl::UnregisterListener(std::vector<sptr<T>>& holder, const sptr<T>& listener)
2566 {
2567     if (listener == nullptr) {
2568         WLOGFE("listener could not be null");
2569         return WMError::WM_ERROR_NULLPTR;
2570     }
2571     holder.erase(std::remove_if(holder.begin(), holder.end(),
2572         [listener](sptr<T> registeredListener) {
2573             return registeredListener == listener;
2574         }), holder.end());
2575     return WMError::WM_OK;
2576 }
2577 
2578 template<typename T>
ClearUselessListeners(std::map<int32_t,T> & listeners,int32_t persistentId)2579 void WindowSessionImpl::ClearUselessListeners(std::map<int32_t, T>& listeners, int32_t persistentId)
2580 {
2581     listeners.erase(persistentId);
2582 }
2583 
2584 template<typename T>
GetListeners()2585 EnableIfSame<T, IWindowStatusChangeListener, std::vector<sptr<IWindowStatusChangeListener>>> WindowSessionImpl::GetListeners()
2586 {
2587     std::vector<sptr<IWindowStatusChangeListener>> windowStatusChangeListeners;
2588     for (auto& listener : windowStatusChangeListeners_[GetPersistentId()]) {
2589         windowStatusChangeListeners.push_back(listener);
2590     }
2591     return windowStatusChangeListeners;
2592 }
2593 
ClearListenersById(int32_t persistentId)2594 void WindowSessionImpl::ClearListenersById(int32_t persistentId)
2595 {
2596     TLOGI(WmsLogTag::WMS_LIFE, "Called id: %{public}d.", GetPersistentId());
2597     {
2598         std::lock_guard<std::mutex> lockListener(displayMoveListenerMutex_);
2599         ClearUselessListeners(displayMoveListeners_, persistentId);
2600     }
2601     {
2602         std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2603         ClearUselessListeners(lifecycleListeners_, persistentId);
2604     }
2605     {
2606         std::lock_guard<std::recursive_mutex> lockListener(windowChangeListenerMutex_);
2607         ClearUselessListeners(windowChangeListeners_, persistentId);
2608     }
2609     {
2610         std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
2611         ClearUselessListeners(avoidAreaChangeListeners_, persistentId);
2612     }
2613     {
2614         std::lock_guard<std::recursive_mutex> lockListener(dialogDeathRecipientListenerMutex_);
2615         ClearUselessListeners(dialogDeathRecipientListeners_, persistentId);
2616     }
2617     {
2618         std::lock_guard<std::recursive_mutex> lockListener(dialogTargetTouchListenerMutex_);
2619         ClearUselessListeners(dialogTargetTouchListener_, persistentId);
2620     }
2621     {
2622         std::lock_guard<std::recursive_mutex> lockListener(screenshotListenerMutex_);
2623         ClearUselessListeners(screenshotListeners_, persistentId);
2624     }
2625     {
2626         std::lock_guard<std::recursive_mutex> lockListener(windowStatusChangeListenerMutex_);
2627         ClearUselessListeners(windowStatusChangeListeners_, persistentId);
2628     }
2629     {
2630         std::lock_guard<std::recursive_mutex> lockListener(windowTitleButtonRectChangeListenerMutex_);
2631         ClearUselessListeners(windowTitleButtonRectChangeListeners_, persistentId);
2632     }
2633     {
2634         std::lock_guard<std::mutex> lockListener(displayIdChangeListenerMutex_);
2635         ClearUselessListeners(displayIdChangeListeners_, persistentId);
2636     }
2637     {
2638         std::lock_guard<std::recursive_mutex> lockListener(windowNoInteractionListenerMutex_);
2639         ClearUselessListeners(windowNoInteractionListeners_, persistentId);
2640     }
2641     {
2642         std::lock_guard<std::mutex> lockListener(windowRectChangeListenerMutex_);
2643         ClearUselessListeners(windowRectChangeListeners_, persistentId);
2644     }
2645     {
2646         std::lock_guard<std::mutex> lockListener(subWindowCloseListenersMutex_);
2647         ClearUselessListeners(subWindowCloseListeners_, persistentId);
2648     }
2649     {
2650         std::lock_guard<std::mutex> lockListener(mainWindowCloseListenersMutex_);
2651         ClearUselessListeners(mainWindowCloseListeners_, persistentId);
2652     }
2653     {
2654         std::lock_guard<std::recursive_mutex> lockListener(occupiedAreaChangeListenerMutex_);
2655         ClearUselessListeners(occupiedAreaChangeListeners_, persistentId);
2656     }
2657     ClearSwitchFreeMultiWindowListenersById(persistentId);
2658     TLOGI(WmsLogTag::WMS_LIFE, "Clear success, id: %{public}d.", GetPersistentId());
2659 }
2660 
ClearSwitchFreeMultiWindowListenersById(int32_t persistentId)2661 void WindowSessionImpl::ClearSwitchFreeMultiWindowListenersById(int32_t persistentId)
2662 {
2663     std::lock_guard<std::mutex> lockListener(switchFreeMultiWindowListenerMutex_);
2664     ClearUselessListeners(switchFreeMultiWindowListeners_, persistentId);
2665 }
2666 
RegisterWindowDestroyedListener(const NotifyNativeWinDestroyFunc & func)2667 void WindowSessionImpl::RegisterWindowDestroyedListener(const NotifyNativeWinDestroyFunc& func)
2668 {
2669     notifyNativeFunc_ = std::move(func);
2670 }
2671 
ClearVsyncStation()2672 void WindowSessionImpl::ClearVsyncStation()
2673 {
2674     std::lock_guard<std::recursive_mutex> lock(mutex_);
2675     if (vsyncStation_ != nullptr) {
2676         vsyncStation_.reset();
2677     }
2678 }
2679 
SetInputEventConsumer(const std::shared_ptr<IInputEventConsumer> & inputEventConsumer)2680 void WindowSessionImpl::SetInputEventConsumer(const std::shared_ptr<IInputEventConsumer>& inputEventConsumer)
2681 {
2682     TLOGI(WmsLogTag::WMS_EVENT, "called");
2683     std::lock_guard<std::recursive_mutex> lock(mutex_);
2684     inputEventConsumer_ = inputEventConsumer;
2685 }
2686 
SetTitleButtonVisible(bool isMaximizeVisible,bool isMinimizeVisible,bool isSplitVisible,bool isCloseVisible)2687 WMError WindowSessionImpl::SetTitleButtonVisible(bool isMaximizeVisible, bool isMinimizeVisible, bool isSplitVisible,
2688     bool isCloseVisible)
2689 {
2690     if (IsWindowSessionInvalid()) {
2691         return WMError::WM_ERROR_INVALID_WINDOW;
2692     }
2693     if (!WindowHelper::IsMainWindow(GetType())) {
2694         return WMError::WM_ERROR_INVALID_CALLING;
2695     }
2696     if (!IsPcOrPadCapabilityEnabled()) {
2697         return WMError::WM_ERROR_DEVICE_NOT_SUPPORT;
2698     }
2699     if (GetUIContentSharedPtr() == nullptr || !IsDecorEnable()) {
2700         return WMError::WM_ERROR_INVALID_WINDOW;
2701     }
2702     windowTitleVisibleFlags_ = { isMaximizeVisible, isMinimizeVisible, isSplitVisible, isCloseVisible };
2703     UpdateTitleButtonVisibility();
2704     return WMError::WM_OK;
2705 }
2706 
NotifyAfterForeground(bool needNotifyListeners,bool needNotifyUiContent)2707 void WindowSessionImpl::NotifyAfterForeground(bool needNotifyListeners, bool needNotifyUiContent)
2708 {
2709     if (needNotifyListeners) {
2710         std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2711         auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2712         CALL_LIFECYCLE_LISTENER(AfterForeground, lifecycleListeners);
2713     }
2714     if (needNotifyUiContent) {
2715         CALL_UI_CONTENT(Foreground);
2716     }
2717     if (vsyncStation_ == nullptr) {
2718         TLOGE(WmsLogTag::WMS_MAIN, "SetFrameRateLinkerEnable true failed, vsyncStation is nullptr");
2719         return;
2720     }
2721     TLOGD(WmsLogTag::WMS_MAIN, "SetFrameRateLinkerEnable: true, linkerId = %{public}" PRIu64,
2722         vsyncStation_->GetFrameRateLinkerId());
2723     vsyncStation_->SetFrameRateLinkerEnable(true);
2724     if (WindowHelper::IsMainWindow(GetType())) {
2725         TLOGD(WmsLogTag::WMS_MAIN, "IsMainWindow: %{public}d, WindowType: %{public}d",
2726             WindowHelper::IsMainWindow(GetType()), GetType());
2727         vsyncStation_->SetDisplaySoloistFrameRateLinkerEnable(true);
2728     }
2729 }
2730 
NotifyAfterBackground(bool needNotifyListeners,bool needNotifyUiContent)2731 void WindowSessionImpl::NotifyAfterBackground(bool needNotifyListeners, bool needNotifyUiContent)
2732 {
2733     if (needNotifyListeners) {
2734         std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2735         auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2736         CALL_LIFECYCLE_LISTENER(AfterBackground, lifecycleListeners);
2737     }
2738     if (needNotifyUiContent) {
2739         CALL_UI_CONTENT(Background);
2740     }
2741     if (vsyncStation_ == nullptr) {
2742         TLOGE(WmsLogTag::WMS_MAIN, "SetFrameRateLinkerEnable false failed, vsyncStation is nullptr");
2743         return;
2744     }
2745     TLOGD(WmsLogTag::WMS_MAIN, "SetFrameRateLinkerEnable: false, linkerId = %{public}" PRIu64,
2746         vsyncStation_->GetFrameRateLinkerId());
2747     vsyncStation_->SetFrameRateLinkerEnable(false);
2748     if (WindowHelper::IsMainWindow(GetType())) {
2749         TLOGD(WmsLogTag::WMS_MAIN, "IsMainWindow: %{public}d, WindowType: %{public}d",
2750             WindowHelper::IsMainWindow(GetType()), GetType());
2751         vsyncStation_->SetDisplaySoloistFrameRateLinkerEnable(false);
2752     }
2753 }
2754 
RequestInputMethodCloseKeyboard(bool isNeedKeyboard,bool keepKeyboardFlag)2755 static void RequestInputMethodCloseKeyboard(bool isNeedKeyboard, bool keepKeyboardFlag)
2756 {
2757     if (!isNeedKeyboard && !keepKeyboardFlag) {
2758 #ifdef IMF_ENABLE
2759         TLOGI(WmsLogTag::WMS_KEYBOARD, "Notify InputMethod framework close keyboard start.");
2760         if (MiscServices::InputMethodController::GetInstance()) {
2761             MiscServices::InputMethodController::GetInstance()->RequestHideInput();
2762             TLOGI(WmsLogTag::WMS_KEYBOARD, "Notify InputMethod framework close keyboard end.");
2763         }
2764 #endif
2765     }
2766 }
2767 
NotifyUIContentFocusStatus()2768 void WindowSessionImpl::NotifyUIContentFocusStatus()
2769 {
2770     if (!isFocused_) {
2771         CALL_UI_CONTENT(UnFocus);
2772         return;
2773     }
2774     CALL_UI_CONTENT(Focus);
2775     auto task = [weak = wptr(this)]() {
2776         auto window = weak.promote();
2777         if (!window) {
2778             return;
2779         }
2780         bool isNeedKeyboard = false;
2781         {
2782             std::shared_ptr<Ace::UIContent> uiContent = window->GetUIContentSharedPtr();
2783             if (uiContent != nullptr) {
2784                 // isNeedKeyboard is set by arkui and indicates whether the window needs a keyboard or not.
2785                 isNeedKeyboard = uiContent->NeedSoftKeyboard();
2786             }
2787         }
2788         // whether keep the keyboard created by other windows, support system window and app subwindow.
2789         bool keepKeyboardFlag = (window->property_) ? window->property_->GetKeepKeyboardFlag() : false;
2790         TLOGI(WmsLogTag::WMS_KEYBOARD, "isNeedKeyboard: %{public}d, keepKeyboardFlag: %{public}d",
2791             isNeedKeyboard, keepKeyboardFlag);
2792         RequestInputMethodCloseKeyboard(isNeedKeyboard, keepKeyboardFlag);
2793     };
2794     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2795     if (uiContent != nullptr) {
2796         uiContent->SetOnWindowFocused(task);
2797     }
2798 }
2799 
NotifyAfterFocused()2800 void WindowSessionImpl::NotifyAfterFocused()
2801 {
2802     NotifyWindowAfterFocused();
2803     if (GetUIContentSharedPtr() != nullptr) {
2804         NotifyUIContentFocusStatus();
2805     } else {
2806         shouldReNotifyFocus_ = true;
2807     }
2808 }
2809 
NotifyAfterUnfocused(bool needNotifyUiContent)2810 void WindowSessionImpl::NotifyAfterUnfocused(bool needNotifyUiContent)
2811 {
2812     NotifyWindowAfterUnfocused();
2813     if (needNotifyUiContent) {
2814         if (GetUIContentSharedPtr() == nullptr) {
2815             shouldReNotifyFocus_ = true;
2816         } else {
2817             CALL_UI_CONTENT(UnFocus);
2818         }
2819     }
2820 }
2821 
NotifyWindowAfterFocused()2822 void WindowSessionImpl::NotifyWindowAfterFocused()
2823 {
2824     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2825     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2826     CALL_LIFECYCLE_LISTENER(AfterFocused, lifecycleListeners);
2827 }
2828 
NotifyWindowAfterUnfocused()2829 void WindowSessionImpl::NotifyWindowAfterUnfocused()
2830 {
2831     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2832     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2833     // use needNotifyUinContent to separate ui content callbacks
2834     CALL_LIFECYCLE_LISTENER(AfterUnfocused, lifecycleListeners);
2835 }
2836 
NotifyBeforeDestroy(std::string windowName)2837 void WindowSessionImpl::NotifyBeforeDestroy(std::string windowName)
2838 {
2839     auto task = [this]() {
2840         {
2841             std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
2842             if (uiContent != nullptr) {
2843                 uiContent->Destroy();
2844             }
2845         }
2846         {
2847             std::unique_lock<std::shared_mutex> lock(uiContentMutex_);
2848             if (uiContent_ != nullptr) {
2849                 uiContent_ = nullptr;
2850                 TLOGD(WmsLogTag::WMS_LIFE, "NotifyBeforeDestroy: uiContent destroy success, persistentId:%{public}d",
2851                     GetPersistentId());
2852             }
2853         }
2854     };
2855     if (handler_) {
2856         handler_->PostSyncTask(task, "wms:NotifyBeforeDestroy");
2857     } else {
2858         task();
2859     }
2860     TLOGI(WmsLogTag::WMS_LIFE, "Release uicontent successfully, id: %{public}d.", GetPersistentId());
2861     if (notifyNativeFunc_) {
2862         notifyNativeFunc_(windowName);
2863     }
2864     TLOGI(WmsLogTag::WMS_LIFE, "successed with id: %{public}d.", GetPersistentId());
2865 }
2866 
NotifyAfterDestroy()2867 void WindowSessionImpl::NotifyAfterDestroy()
2868 {
2869     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2870     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2871     CALL_LIFECYCLE_LISTENER(AfterDestroyed, lifecycleListeners);
2872 }
2873 
NotifyAfterActive()2874 void WindowSessionImpl::NotifyAfterActive()
2875 {
2876     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2877     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2878     CALL_LIFECYCLE_LISTENER(AfterActive, lifecycleListeners);
2879 }
2880 
NotifyAfterInactive()2881 void WindowSessionImpl::NotifyAfterInactive()
2882 {
2883     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2884     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2885     CALL_LIFECYCLE_LISTENER(AfterInactive, lifecycleListeners);
2886 }
2887 
NotifyForegroundFailed(WMError ret)2888 void WindowSessionImpl::NotifyForegroundFailed(WMError ret)
2889 {
2890     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2891     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2892     CALL_LIFECYCLE_LISTENER_WITH_PARAM(ForegroundFailed, lifecycleListeners, static_cast<int32_t>(ret));
2893 }
2894 
NotifyBackgroundFailed(WMError ret)2895 void WindowSessionImpl::NotifyBackgroundFailed(WMError ret)
2896 {
2897     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2898     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2899     CALL_LIFECYCLE_LISTENER_WITH_PARAM(BackgroundFailed, lifecycleListeners, static_cast<int32_t>(ret));
2900 }
2901 
NotifyAfterResumed()2902 void WindowSessionImpl::NotifyAfterResumed()
2903 {
2904     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2905     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2906     CALL_LIFECYCLE_LISTENER(AfterResumed, lifecycleListeners);
2907 }
2908 
NotifyAfterPaused()2909 void WindowSessionImpl::NotifyAfterPaused()
2910 {
2911     std::lock_guard<std::recursive_mutex> lockListener(lifeCycleListenerMutex_);
2912     auto lifecycleListeners = GetListeners<IWindowLifeCycle>();
2913     CALL_LIFECYCLE_LISTENER(AfterPaused, lifecycleListeners);
2914 }
2915 
MarkProcessed(int32_t eventId)2916 WSError WindowSessionImpl::MarkProcessed(int32_t eventId)
2917 {
2918     if (IsWindowSessionInvalid()) {
2919         WLOGFE("HostSession is invalid");
2920         return WSError::WS_DO_NOTHING;
2921     }
2922     auto hostSession = GetHostSession();
2923     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WSError::WS_DO_NOTHING);
2924     return hostSession->MarkProcessed(eventId);
2925 }
2926 
RegisterDialogDeathRecipientListener(const sptr<IDialogDeathRecipientListener> & listener)2927 void WindowSessionImpl::RegisterDialogDeathRecipientListener(const sptr<IDialogDeathRecipientListener>& listener)
2928 {
2929     TLOGI(WmsLogTag::WMS_DIALOG, "window %{public}s id %{public}d register DialogDeathRecipientListener",
2930         GetWindowName().c_str(), GetPersistentId());
2931     if (listener == nullptr) {
2932         WLOGFE("listener is nullptr");
2933         return;
2934     }
2935     std::lock_guard<std::recursive_mutex> lockListener(dialogDeathRecipientListenerMutex_);
2936     RegisterListener(dialogDeathRecipientListeners_[GetPersistentId()], listener);
2937 }
2938 
UnregisterDialogDeathRecipientListener(const sptr<IDialogDeathRecipientListener> & listener)2939 void WindowSessionImpl::UnregisterDialogDeathRecipientListener(const sptr<IDialogDeathRecipientListener>& listener)
2940 {
2941     TLOGI(WmsLogTag::WMS_DIALOG, "window %{public}s id %{public}d unregister DialogDeathRecipientListener",
2942         GetWindowName().c_str(), GetPersistentId());
2943     std::lock_guard<std::recursive_mutex> lockListener(dialogDeathRecipientListenerMutex_);
2944     UnregisterListener(dialogDeathRecipientListeners_[GetPersistentId()], listener);
2945 }
2946 
RegisterDialogTargetTouchListener(const sptr<IDialogTargetTouchListener> & listener)2947 WMError WindowSessionImpl::RegisterDialogTargetTouchListener(const sptr<IDialogTargetTouchListener>& listener)
2948 {
2949     TLOGI(WmsLogTag::WMS_DIALOG, "window %{public}s id %{public}d register DialogTargetTouchListener",
2950         GetWindowName().c_str(), GetPersistentId());
2951     if (listener == nullptr) {
2952         WLOGFE("listener is nullptr");
2953         return WMError::WM_ERROR_NULLPTR;
2954     }
2955     std::lock_guard<std::recursive_mutex> lockListener(dialogTargetTouchListenerMutex_);
2956     return RegisterListener(dialogTargetTouchListener_[GetPersistentId()], listener);
2957 }
2958 
UnregisterDialogTargetTouchListener(const sptr<IDialogTargetTouchListener> & listener)2959 WMError WindowSessionImpl::UnregisterDialogTargetTouchListener(const sptr<IDialogTargetTouchListener>& listener)
2960 {
2961     TLOGI(WmsLogTag::WMS_DIALOG, "window %{public}s id %{public}d unregister DialogTargetTouchListener",
2962         GetWindowName().c_str(), GetPersistentId());
2963     std::lock_guard<std::recursive_mutex> lockListener(dialogTargetTouchListenerMutex_);
2964     return UnregisterListener(dialogTargetTouchListener_[GetPersistentId()], listener);
2965 }
2966 
RegisterScreenshotListener(const sptr<IScreenshotListener> & listener)2967 WMError WindowSessionImpl::RegisterScreenshotListener(const sptr<IScreenshotListener>& listener)
2968 {
2969     WLOGFD("Start register ScreenshotListener");
2970     std::lock_guard<std::recursive_mutex> lockListener(screenshotListenerMutex_);
2971     return RegisterListener(screenshotListeners_[GetPersistentId()], listener);
2972 }
2973 
UnregisterScreenshotListener(const sptr<IScreenshotListener> & listener)2974 WMError WindowSessionImpl::UnregisterScreenshotListener(const sptr<IScreenshotListener>& listener)
2975 {
2976     WLOGFD("Start unregister ScreenshotListener");
2977     std::lock_guard<std::recursive_mutex> lockListener(screenshotListenerMutex_);
2978     return UnregisterListener(screenshotListeners_[GetPersistentId()], listener);
2979 }
2980 
2981 template<typename T>
2982 EnableIfSame<T, IDialogDeathRecipientListener, std::vector<sptr<IDialogDeathRecipientListener>>> WindowSessionImpl::
GetListeners()2983     GetListeners()
2984 {
2985     std::vector<sptr<IDialogDeathRecipientListener>> dialogDeathRecipientListener;
2986     for (auto& listener : dialogDeathRecipientListeners_[GetPersistentId()]) {
2987         dialogDeathRecipientListener.push_back(listener);
2988     }
2989     return dialogDeathRecipientListener;
2990 }
2991 
2992 template<typename T>
2993 EnableIfSame<T, IDialogTargetTouchListener,
GetListeners()2994     std::vector<sptr<IDialogTargetTouchListener>>> WindowSessionImpl::GetListeners()
2995 {
2996     std::vector<sptr<IDialogTargetTouchListener>> dialogTargetTouchListener;
2997     for (auto& listener : dialogTargetTouchListener_[GetPersistentId()]) {
2998         dialogTargetTouchListener.push_back(listener);
2999     }
3000     return dialogTargetTouchListener;
3001 }
3002 
3003 template<typename T>
GetListeners()3004 EnableIfSame<T, IScreenshotListener, std::vector<sptr<IScreenshotListener>>> WindowSessionImpl::GetListeners()
3005 {
3006     std::vector<sptr<IScreenshotListener>> screenshotListeners;
3007     for (auto& listener : screenshotListeners_[GetPersistentId()]) {
3008         screenshotListeners.push_back(listener);
3009     }
3010     return screenshotListeners;
3011 }
3012 
NotifyDestroy()3013 WSError WindowSessionImpl::NotifyDestroy()
3014 {
3015     if (WindowHelper::IsDialogWindow(property_->GetWindowType())) {
3016         std::lock_guard<std::recursive_mutex> lockListener(dialogDeathRecipientListenerMutex_);
3017         auto dialogDeathRecipientListener = GetListeners<IDialogDeathRecipientListener>();
3018         for (auto& listener : dialogDeathRecipientListener) {
3019             if (listener != nullptr) {
3020                 listener->OnDialogDeathRecipient();
3021             }
3022         }
3023     } else if (WindowHelper::IsSubWindow(property_->GetWindowType())) {
3024         if (property_->GetExtensionFlag() == true && !isUIExtensionAbilityProcess_) {
3025             Destroy();
3026         }
3027     }
3028     return WSError::WS_OK;
3029 }
3030 
3031 template<typename T>
GetListeners()3032 EnableIfSame<T, IDisplayMoveListener, std::vector<sptr<IDisplayMoveListener>>> WindowSessionImpl::GetListeners()
3033 {
3034     std::vector<sptr<IDisplayMoveListener>> displayMoveListeners;
3035     for (auto& listener : displayMoveListeners_[GetPersistentId()]) {
3036         displayMoveListeners.push_back(listener);
3037     }
3038     return displayMoveListeners;
3039 }
3040 
NotifyDisplayMove(DisplayId from,DisplayId to)3041 void WindowSessionImpl::NotifyDisplayMove(DisplayId from, DisplayId to)
3042 {
3043     WLOGFD("Notify display move from %{public}" PRIu64 " to %{public}" PRIu64, from, to);
3044     std::lock_guard<std::mutex> lockListener(displayMoveListenerMutex_);
3045     auto displayMoveListeners = GetListeners<IDisplayMoveListener>();
3046     for (auto& listener : displayMoveListeners) {
3047         if (listener != nullptr) {
3048             listener->OnDisplayMove(from, to);
3049         }
3050     }
3051 }
3052 
NotifyCloseExistPipWindow()3053 WSError WindowSessionImpl::NotifyCloseExistPipWindow()
3054 {
3055     TLOGI(WmsLogTag::WMS_PIP, "WindowSessionImpl::NotifyCloseExistPipWindow");
3056     auto task = []() {
3057         PictureInPictureManager::DoClose(true, true);
3058     };
3059     handler_->PostTask(task, "WMS_WindowSessionImpl_NotifyCloseExistPipWindow");
3060     return WSError::WS_OK;
3061 }
3062 
NotifyTouchDialogTarget(int32_t posX,int32_t posY)3063 void WindowSessionImpl::NotifyTouchDialogTarget(int32_t posX, int32_t posY)
3064 {
3065     TLOGI(WmsLogTag::WMS_DIALOG, "window %{public}s id %{public}d", GetWindowName().c_str(), GetPersistentId());
3066     auto hostSession = GetHostSession();
3067     if (hostSession != nullptr) {
3068         hostSession->ProcessPointDownSession(posX, posY);
3069     }
3070     std::lock_guard<std::recursive_mutex> lockListener(dialogTargetTouchListenerMutex_);
3071     auto dialogTargetTouchListener = GetListeners<IDialogTargetTouchListener>();
3072     for (auto& listener : dialogTargetTouchListener) {
3073         if (listener != nullptr) {
3074             listener->OnDialogTargetTouch();
3075         }
3076     }
3077 }
3078 
NotifyScreenshot()3079 void WindowSessionImpl::NotifyScreenshot()
3080 {
3081     std::lock_guard<std::recursive_mutex> lockListener(screenshotListenerMutex_);
3082     auto screenshotListeners = GetListeners<IScreenshotListener>();
3083     for (auto& listener : screenshotListeners) {
3084         if (listener != nullptr) {
3085             listener->OnScreenshot();
3086         }
3087     }
3088 }
3089 
NotifySizeChange(Rect rect,WindowSizeChangeReason reason)3090 void WindowSessionImpl::NotifySizeChange(Rect rect, WindowSizeChangeReason reason)
3091 {
3092     {
3093         std::lock_guard<std::recursive_mutex> lockListener(windowChangeListenerMutex_);
3094         auto windowChangeListeners = GetListeners<IWindowChangeListener>();
3095         for (auto& listener : windowChangeListeners) {
3096             if (listener != nullptr) {
3097                 listener->OnSizeChange(rect, reason);
3098             }
3099         }
3100     }
3101     {
3102         std::lock_guard<std::mutex> lockRectListener(windowRectChangeListenerMutex_);
3103         auto windowRectChangeListeners = GetListeners<IWindowRectChangeListener>();
3104         for (auto& listener : windowRectChangeListeners) {
3105             if (listener != nullptr) {
3106                 listener->OnRectChange(rect, reason);
3107             }
3108         }
3109     }
3110 }
3111 
NotifySubWindowClose(bool & terminateCloseProcess)3112 void WindowSessionImpl::NotifySubWindowClose(bool& terminateCloseProcess)
3113 {
3114     WLOGFD("WindowSessionImpl::NotifySubWindowClose");
3115     std::lock_guard<std::mutex> lockListener(subWindowCloseListenersMutex_);
3116     auto subWindowCloseListeners = GetListeners<ISubWindowCloseListener>();
3117     if (subWindowCloseListeners != nullptr) {
3118         subWindowCloseListeners->OnSubWindowClose(terminateCloseProcess);
3119     }
3120 }
3121 
NotifyMainWindowClose(bool & terminateCloseProcess)3122 WMError WindowSessionImpl::NotifyMainWindowClose(bool& terminateCloseProcess)
3123 {
3124     std::lock_guard<std::mutex> lockListener(mainWindowCloseListenersMutex_);
3125     auto mainWindowCloseListener = GetListeners<IMainWindowCloseListener>();
3126     if (mainWindowCloseListener != nullptr) {
3127         mainWindowCloseListener->OnMainWindowClose(terminateCloseProcess);
3128         return WMError::WM_OK;
3129     }
3130     return WMError::WM_ERROR_NULLPTR;
3131 }
3132 
NotifySwitchFreeMultiWindow(bool enable)3133 void WindowSessionImpl::NotifySwitchFreeMultiWindow(bool enable)
3134 {
3135     std::lock_guard<std::mutex> lockListener(switchFreeMultiWindowListenerMutex_);
3136     auto switchFreeMultiWindowListeners = GetListeners<ISwitchFreeMultiWindowListener>();
3137     for (auto& listener : switchFreeMultiWindowListeners) {
3138         if (listener != nullptr) {
3139             listener->OnSwitchFreeMultiWindow(enable);
3140         }
3141     }
3142 }
3143 
RegisterAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener> & listener)3144 WMError WindowSessionImpl::RegisterAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener>& listener)
3145 {
3146     bool isUpdate = false;
3147     WMError ret = WMError::WM_OK;
3148     auto persistentId = GetPersistentId();
3149     TLOGI(WmsLogTag::WMS_IMMS, "Start register avoidAreaChange listener, id:%{public}d", persistentId);
3150     if (listener == nullptr) {
3151         TLOGE(WmsLogTag::WMS_IMMS, "listener is nullptr");
3152         return WMError::WM_ERROR_NULLPTR;
3153     }
3154 
3155     {
3156         std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
3157         ret = RegisterListener(avoidAreaChangeListeners_[persistentId], listener);
3158         if (ret != WMError::WM_OK) {
3159             return ret;
3160         }
3161         if (avoidAreaChangeListeners_[persistentId].size() == 1) {
3162             isUpdate = true;
3163         }
3164     }
3165     if (isUpdate) {
3166         ret = SingletonContainer::Get<WindowAdapter>().UpdateSessionAvoidAreaListener(persistentId, true);
3167     }
3168     return ret;
3169 }
3170 
UnregisterAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener> & listener)3171 WMError WindowSessionImpl::UnregisterAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener>& listener)
3172 {
3173     bool isUpdate = false;
3174     WMError ret = WMError::WM_OK;
3175     auto persistentId = GetPersistentId();
3176     TLOGI(WmsLogTag::WMS_IMMS, "Start unregister avoidAreaChange listener, id:%{public}d", persistentId);
3177     if (listener == nullptr) {
3178         WLOGFE("listener is nullptr");
3179         return WMError::WM_ERROR_NULLPTR;
3180     }
3181 
3182     {
3183         std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
3184         ret = UnregisterListener(avoidAreaChangeListeners_[persistentId], listener);
3185         if (ret != WMError::WM_OK) {
3186             return ret;
3187         }
3188         if (avoidAreaChangeListeners_[persistentId].empty()) {
3189             isUpdate = true;
3190         }
3191     }
3192     if (isUpdate) {
3193         ret = SingletonContainer::Get<WindowAdapter>().UpdateSessionAvoidAreaListener(persistentId, false);
3194     }
3195     return ret;
3196 }
3197 
RegisterExtensionAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener> & listener)3198 WMError WindowSessionImpl::RegisterExtensionAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener>& listener)
3199 {
3200     auto persistentId = GetPersistentId();
3201     WLOGI("Start register extension avoidAreaChange listener, id:%{public}d", persistentId);
3202     std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
3203     return RegisterListener(avoidAreaChangeListeners_[persistentId], listener);
3204 }
3205 
UnregisterExtensionAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener> & listener)3206 WMError WindowSessionImpl::UnregisterExtensionAvoidAreaChangeListener(sptr<IAvoidAreaChangedListener>& listener)
3207 {
3208     auto persistentId = GetPersistentId();
3209     WLOGI("Start unregister extension avoidAreaChange listener, id:%{public}d", persistentId);
3210     std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
3211     return UnregisterListener(avoidAreaChangeListeners_[persistentId], listener);
3212 }
3213 
3214 template<typename T>
3215 EnableIfSame<T, IAvoidAreaChangedListener,
GetListeners()3216     std::vector<sptr<IAvoidAreaChangedListener>>> WindowSessionImpl::GetListeners()
3217 {
3218     std::vector<sptr<IAvoidAreaChangedListener>> windowChangeListeners;
3219     for (auto& listener : avoidAreaChangeListeners_[GetPersistentId()]) {
3220         windowChangeListeners.push_back(listener);
3221     }
3222     return windowChangeListeners;
3223 }
3224 
NotifyAvoidAreaChange(const sptr<AvoidArea> & avoidArea,AvoidAreaType type)3225 void WindowSessionImpl::NotifyAvoidAreaChange(const sptr<AvoidArea>& avoidArea, AvoidAreaType type)
3226 {
3227     TLOGI(WmsLogTag::WMS_IMMS,
3228           "window [%{public}d, %{public}s] type %{public}d area %{public}s",
3229           GetPersistentId(), GetWindowName().c_str(), type, avoidArea->ToString().c_str());
3230     std::lock_guard<std::recursive_mutex> lockListener(avoidAreaChangeListenerMutex_);
3231     auto avoidAreaChangeListeners = GetListeners<IAvoidAreaChangedListener>();
3232     for (auto& listener : avoidAreaChangeListeners) {
3233         if (listener != nullptr) {
3234             listener->OnAvoidAreaChanged(*avoidArea, type);
3235         }
3236     }
3237 }
3238 
NotifyTransferComponentData(const AAFwk::WantParams & wantParams)3239 WSError WindowSessionImpl::NotifyTransferComponentData(const AAFwk::WantParams& wantParams)
3240 {
3241     return WSError::WS_OK;
3242 }
3243 
NotifyTransferComponentDataSync(const AAFwk::WantParams & wantParams,AAFwk::WantParams & reWantParams)3244 WSErrorCode WindowSessionImpl::NotifyTransferComponentDataSync(const AAFwk::WantParams& wantParams,
3245     AAFwk::WantParams& reWantParams)
3246 {
3247     return WSErrorCode::WS_OK;
3248 }
3249 
UpdateAvoidArea(const sptr<AvoidArea> & avoidArea,AvoidAreaType type)3250 WSError WindowSessionImpl::UpdateAvoidArea(const sptr<AvoidArea>& avoidArea, AvoidAreaType type)
3251 {
3252     UpdateViewportConfig(GetRect(), WindowSizeChangeReason::UNDEFINED, nullptr, nullptr, {{type, *avoidArea}});
3253     NotifyAvoidAreaChange(avoidArea, type);
3254     return WSError::WS_OK;
3255 }
3256 
SetPipActionEvent(const std::string & action,int32_t status)3257 WSError WindowSessionImpl::SetPipActionEvent(const std::string& action, int32_t status)
3258 {
3259     TLOGI(WmsLogTag::WMS_PIP, "action: %{public}s, status: %{public}d", action.c_str(), status);
3260     auto task = [action, status]() {
3261         PictureInPictureManager::DoActionEvent(action, status);
3262     };
3263     handler_->PostTask(task, "WMS_WindowSessionImpl_SetPipActionEvent");
3264     return WSError::WS_OK;
3265 }
3266 
SetPiPControlEvent(WsPiPControlType controlType,WsPiPControlStatus status)3267 WSError WindowSessionImpl::SetPiPControlEvent(WsPiPControlType controlType, WsPiPControlStatus status)
3268 {
3269     TLOGI(WmsLogTag::WMS_PIP, "controlType:%{public}u, enabled:%{public}d", controlType, status);
3270     auto task = [controlType, status]() {
3271         PictureInPictureManager::DoControlEvent(static_cast<PiPControlType>(controlType),
3272             static_cast<PiPControlStatus>(status));
3273     };
3274     handler_->PostTask(task, "WMS_WindowSessionImpl_SetPiPControlEvent");
3275     return WSError::WS_OK;
3276 }
3277 
RegisterTouchOutsideListener(const sptr<ITouchOutsideListener> & listener)3278 WMError WindowSessionImpl::RegisterTouchOutsideListener(const sptr<ITouchOutsideListener>& listener)
3279 {
3280     bool isUpdate = false;
3281     WMError ret = WMError::WM_OK;
3282     auto persistentId = GetPersistentId();
3283     TLOGI(WmsLogTag::WMS_EVENT, "Start register touchOutside listener, window: name=%{public}s, id=%{public}u",
3284         GetWindowName().c_str(), GetPersistentId());
3285     if (listener == nullptr) {
3286         TLOGE(WmsLogTag::WMS_EVENT, "listener is nullptr");
3287         return WMError::WM_ERROR_NULLPTR;
3288     }
3289 
3290     {
3291         std::lock_guard<std::recursive_mutex> lockListener(touchOutsideListenerMutex_);
3292         ret = RegisterListener(touchOutsideListeners_[persistentId], listener);
3293         if (ret != WMError::WM_OK) {
3294             TLOGE(WmsLogTag::WMS_EVENT, "Register touchOutside listener fail, ret:%{public}u", ret);
3295             return ret;
3296         }
3297         if (touchOutsideListeners_[persistentId].size() == 1) {
3298             isUpdate = true;
3299         }
3300     }
3301     if (isUpdate) {
3302         ret = SingletonContainer::Get<WindowAdapter>().UpdateSessionTouchOutsideListener(persistentId, true);
3303     }
3304     return ret;
3305 }
3306 
UnregisterTouchOutsideListener(const sptr<ITouchOutsideListener> & listener)3307 WMError WindowSessionImpl::UnregisterTouchOutsideListener(const sptr<ITouchOutsideListener>& listener)
3308 {
3309     bool isUpdate = false;
3310     WMError ret = WMError::WM_OK;
3311     auto persistentId = GetPersistentId();
3312     TLOGI(WmsLogTag::WMS_EVENT, "Start unregister touchOutside listener, window: name=%{public}s, id=%{public}u",
3313         GetWindowName().c_str(), GetPersistentId());
3314     if (listener == nullptr) {
3315         TLOGE(WmsLogTag::WMS_EVENT, "listener is nullptr");
3316         return WMError::WM_ERROR_NULLPTR;
3317     }
3318 
3319     {
3320         std::lock_guard<std::recursive_mutex> lockListener(touchOutsideListenerMutex_);
3321         ret = UnregisterListener(touchOutsideListeners_[persistentId], listener);
3322         if (ret != WMError::WM_OK) {
3323             TLOGE(WmsLogTag::WMS_EVENT, "Unregister touchOutside listener fail, ret:%{public}u", ret);
3324             return ret;
3325         }
3326         if (touchOutsideListeners_[persistentId].empty()) {
3327             isUpdate = true;
3328         }
3329     }
3330     if (isUpdate) {
3331         ret = SingletonContainer::Get<WindowAdapter>().UpdateSessionTouchOutsideListener(persistentId, false);
3332     }
3333     return ret;
3334 }
3335 
3336 template<typename T>
GetListeners()3337 EnableIfSame<T, ITouchOutsideListener, std::vector<sptr<ITouchOutsideListener>>> WindowSessionImpl::GetListeners()
3338 {
3339     std::vector<sptr<ITouchOutsideListener>> windowChangeListeners;
3340     for (auto& listener : touchOutsideListeners_[GetPersistentId()]) {
3341         windowChangeListeners.push_back(listener);
3342     }
3343     return windowChangeListeners;
3344 }
3345 
NotifyTouchOutside()3346 WSError WindowSessionImpl::NotifyTouchOutside()
3347 {
3348     TLOGI(WmsLogTag::WMS_EVENT, "Notify touch outside, window: name=%{public}s, id=%{public}u",
3349         GetWindowName().c_str(), GetPersistentId());
3350     std::lock_guard<std::recursive_mutex> lockListener(touchOutsideListenerMutex_);
3351     auto touchOutsideListeners = GetListeners<ITouchOutsideListener>();
3352     for (auto& listener : touchOutsideListeners) {
3353         if (listener != nullptr) {
3354             listener->OnTouchOutside();
3355         }
3356     }
3357     return WSError::WS_OK;
3358 }
3359 
RegisterWindowVisibilityChangeListener(const IWindowVisibilityListenerSptr & listener)3360 WMError WindowSessionImpl::RegisterWindowVisibilityChangeListener(const IWindowVisibilityListenerSptr& listener)
3361 {
3362     auto persistentId = GetPersistentId();
3363     WLOGFD("Start to register window visibility change listener, persistentId=%{public}d.", persistentId);
3364     WMError ret = WMError::WM_OK;
3365     bool isFirstRegister = false;
3366     {
3367         std::lock_guard<std::recursive_mutex> lockListener(windowVisibilityChangeListenerMutex_);
3368         ret = RegisterListener(windowVisibilityChangeListeners_[persistentId], listener);
3369         if (ret != WMError::WM_OK) {
3370             return ret;
3371         }
3372         isFirstRegister = windowVisibilityChangeListeners_[persistentId].size() == 1;
3373     }
3374 
3375     if (isFirstRegister) {
3376         ret = SingletonContainer::Get<WindowAdapter>().UpdateSessionWindowVisibilityListener(persistentId, true);
3377     }
3378     return ret;
3379 }
3380 
UnregisterWindowVisibilityChangeListener(const IWindowVisibilityListenerSptr & listener)3381 WMError WindowSessionImpl::UnregisterWindowVisibilityChangeListener(const IWindowVisibilityListenerSptr& listener)
3382 {
3383     auto persistentId = GetPersistentId();
3384     WLOGFD("Start to unregister window visibility change listener, persistentId=%{public}d.", persistentId);
3385     WMError ret = WMError::WM_OK;
3386     bool isLastUnregister = false;
3387     {
3388         std::lock_guard<std::recursive_mutex> lockListener(windowVisibilityChangeListenerMutex_);
3389         ret = UnregisterListener(windowVisibilityChangeListeners_[persistentId], listener);
3390         if (ret != WMError::WM_OK) {
3391             return ret;
3392         }
3393         isLastUnregister = windowVisibilityChangeListeners_[persistentId].empty();
3394     }
3395 
3396     if (isLastUnregister) {
3397         ret = SingletonContainer::Get<WindowAdapter>().UpdateSessionWindowVisibilityListener(persistentId, false);
3398     }
3399     return ret;
3400 }
3401 
RegisterDisplayIdChangeListener(const IDisplayIdChangeListenerSptr & listener)3402 WMError WindowSessionImpl::RegisterDisplayIdChangeListener(const IDisplayIdChangeListenerSptr& listener)
3403 {
3404     TLOGD(WmsLogTag::DEFAULT, "name=%{public}s, id=%{public}u", GetWindowName().c_str(), GetPersistentId());
3405     std::lock_guard<std::mutex> lockListener(displayIdChangeListenerMutex_);
3406     return RegisterListener(displayIdChangeListeners_[GetPersistentId()], listener);
3407 }
3408 
UnregisterDisplayIdChangeListener(const IDisplayIdChangeListenerSptr & listener)3409 WMError WindowSessionImpl::UnregisterDisplayIdChangeListener(const IDisplayIdChangeListenerSptr& listener)
3410 {
3411     TLOGD(WmsLogTag::DEFAULT, "name=%{public}s, id=%{public}u", GetWindowName().c_str(), GetPersistentId());
3412     std::lock_guard<std::mutex> lockListener(displayIdChangeListenerMutex_);
3413     return UnregisterListener(displayIdChangeListeners_[GetPersistentId()], listener);
3414 }
3415 
RegisterWindowNoInteractionListener(const IWindowNoInteractionListenerSptr & listener)3416 WMError WindowSessionImpl::RegisterWindowNoInteractionListener(const IWindowNoInteractionListenerSptr& listener)
3417 {
3418     WLOGFD("Start to register window no interaction listener.");
3419     std::lock_guard<std::recursive_mutex> lockListener(windowNoInteractionListenerMutex_);
3420     WMError ret = RegisterListener(windowNoInteractionListeners_[GetPersistentId()], listener);
3421     if (ret != WMError::WM_OK) {
3422         WLOGFE("register no interaction listener failed.");
3423     } else {
3424         SubmitNoInteractionMonitorTask(this->lastInteractionEventId_.load(), listener);
3425     }
3426     return ret;
3427 }
3428 
UnregisterWindowNoInteractionListener(const IWindowNoInteractionListenerSptr & listener)3429 WMError WindowSessionImpl::UnregisterWindowNoInteractionListener(const IWindowNoInteractionListenerSptr& listener)
3430 {
3431     WLOGFD("Start to unregister window no interaction listener.");
3432     std::lock_guard<std::recursive_mutex> lockListener(windowNoInteractionListenerMutex_);
3433     WMError ret = UnregisterListener(windowNoInteractionListeners_[GetPersistentId()], listener);
3434     if (windowNoInteractionListeners_[GetPersistentId()].empty()) {
3435         lastInteractionEventId_.store(-1);
3436     }
3437     return ret;
3438 }
3439 
3440 template<typename T>
GetListeners()3441 EnableIfSame<T, IWindowVisibilityChangedListener, std::vector<IWindowVisibilityListenerSptr>> WindowSessionImpl::GetListeners()
3442 {
3443     std::vector<IWindowVisibilityListenerSptr> windowVisibilityChangeListeners;
3444     for (auto& listener : windowVisibilityChangeListeners_[GetPersistentId()]) {
3445         windowVisibilityChangeListeners.push_back(listener);
3446     }
3447     return windowVisibilityChangeListeners;
3448 }
3449 
3450 template<typename T>
3451 EnableIfSame<T, IDisplayIdChangeListener,
GetListeners()3452     std::vector<IDisplayIdChangeListenerSptr>> WindowSessionImpl::GetListeners()
3453 {
3454     return displayIdChangeListeners_[GetPersistentId()];
3455 }
3456 
3457 template<typename T>
GetListeners()3458 EnableIfSame<T, IWindowNoInteractionListener, std::vector<IWindowNoInteractionListenerSptr>> WindowSessionImpl::GetListeners()
3459 {
3460     std::vector<IWindowNoInteractionListenerSptr> noInteractionListeners;
3461     for (auto& listener : windowNoInteractionListeners_[GetPersistentId()]) {
3462         noInteractionListeners.push_back(listener);
3463     }
3464     return noInteractionListeners;
3465 }
3466 
NotifyDisplayIdChange(DisplayId displayId)3467 WSError WindowSessionImpl::NotifyDisplayIdChange(DisplayId displayId)
3468 {
3469     TLOGD(WmsLogTag::DEFAULT, "id=%{public}u, displayId=%{public}" PRIu64, GetPersistentId(), displayId);
3470     std::lock_guard<std::mutex> lock(displayIdChangeListenerMutex_);
3471     auto displayIdChangeListeners = GetListeners<IDisplayIdChangeListener>();
3472     for (auto& listener : displayIdChangeListeners) {
3473         if (listener != nullptr) {
3474             listener->OnDisplayIdChanged(displayId);
3475         }
3476     }
3477     return WSError::WS_OK;
3478 }
3479 
NotifyWindowVisibility(bool isVisible)3480 WSError WindowSessionImpl::NotifyWindowVisibility(bool isVisible)
3481 {
3482     TLOGD(WmsLogTag::DEFAULT, "window: name=%{public}s, id=%{public}u, isVisible=%{public}d",
3483         GetWindowName().c_str(), GetPersistentId(), isVisible);
3484     std::lock_guard<std::recursive_mutex> lockListener(windowVisibilityChangeListenerMutex_);
3485     auto windowVisibilityListeners = GetListeners<IWindowVisibilityChangedListener>();
3486     for (auto& listener : windowVisibilityListeners) {
3487         if (listener != nullptr) {
3488             listener->OnWindowVisibilityChangedCallback(isVisible);
3489         }
3490     }
3491     return WSError::WS_OK;
3492 }
3493 
NotifyNoInteractionTimeout(const IWindowNoInteractionListenerSptr & listener)3494 WSError WindowSessionImpl::NotifyNoInteractionTimeout(const IWindowNoInteractionListenerSptr& listener)
3495 {
3496     if (listener == nullptr) {
3497         WLOGFE("invalid listener: nullptr");
3498         return WSError::WS_ERROR_NULLPTR;
3499     }
3500     WLOGFD("Notify window no interaction timeout, window: name=%{public}s, id=%{public}u, timeout=%{public}" PRId64,
3501         GetWindowName().c_str(), GetPersistentId(), listener->GetTimeout());
3502 
3503     listener->OnWindowNoInteractionCallback();
3504     return WSError::WS_OK;
3505 }
3506 
NotifyPointerEvent(const std::shared_ptr<MMI::PointerEvent> & pointerEvent)3507 void WindowSessionImpl::NotifyPointerEvent(const std::shared_ptr<MMI::PointerEvent>& pointerEvent)
3508 {
3509     if (!pointerEvent) {
3510         TLOGE(WmsLogTag::WMS_INPUT_KEY_FLOW, "Pointer event is nullptr");
3511         return;
3512     }
3513 
3514     std::shared_ptr<IInputEventConsumer> inputEventConsumer;
3515     {
3516         std::lock_guard<std::recursive_mutex> lock(mutex_);
3517         inputEventConsumer = inputEventConsumer_;
3518     }
3519     if (inputEventConsumer != nullptr) {
3520         WLOGFD("Transfer pointer event to inputEventConsumer");
3521         if (pointerEvent->GetPointerAction() != MMI::PointerEvent::POINTER_ACTION_MOVE) {
3522             TLOGI(WmsLogTag::WMS_INPUT_KEY_FLOW,
3523                 "Transfer pointer event to inputEventConsumer InputTracking id:%{public}d",
3524                 pointerEvent->GetId());
3525         }
3526         if (!(inputEventConsumer->OnInputEvent(pointerEvent))) {
3527             pointerEvent->MarkProcessed();
3528         }
3529         return;
3530     }
3531 
3532     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
3533     if (uiContent != nullptr) {
3534         if (pointerEvent->GetPointerAction() != MMI::PointerEvent::POINTER_ACTION_MOVE) {
3535             TLOGI(WmsLogTag::WMS_EVENT, "Input id:%{public}d",
3536                 pointerEvent->GetId());
3537         }
3538         if (!(uiContent->ProcessPointerEvent(pointerEvent))) {
3539             TLOGI(WmsLogTag::WMS_INPUT_KEY_FLOW, "UI content dose not consume this pointer event");
3540             pointerEvent->MarkProcessed();
3541         }
3542     } else {
3543         TLOGW(WmsLogTag::WMS_INPUT_KEY_FLOW, "pointerEvent is not consumed, windowId: %{public}u", GetWindowId());
3544         pointerEvent->MarkProcessed();
3545     }
3546 }
3547 
SetKeyEventFilter(KeyEventFilterFunc filter)3548 WMError WindowSessionImpl::SetKeyEventFilter(KeyEventFilterFunc filter)
3549 {
3550     std::unique_lock<std::shared_mutex> lock(keyEventFilterMutex_);
3551     keyEventFilter_ = std::move(filter);
3552     return WMError::WM_OK;
3553 }
3554 
ClearKeyEventFilter()3555 WMError WindowSessionImpl::ClearKeyEventFilter()
3556 {
3557     std::unique_lock<std::shared_mutex> lock(keyEventFilterMutex_);
3558     keyEventFilter_ = nullptr;
3559     return WMError::WM_OK;
3560 }
3561 
FilterKeyEvent(const std::shared_ptr<MMI::KeyEvent> & keyEvent)3562 bool WindowSessionImpl::FilterKeyEvent(const std::shared_ptr<MMI::KeyEvent>& keyEvent)
3563 {
3564     std::shared_lock<std::shared_mutex> lock(keyEventFilterMutex_);
3565     if (keyEventFilter_ != nullptr) {
3566         bool isFilter = keyEventFilter_(*keyEvent.get());
3567         TLOGE(WmsLogTag::WMS_SYSTEM, "keyCode:%{public}d isFilter:%{public}d",
3568             keyEvent->GetKeyCode(), isFilter);
3569         if (isFilter) {
3570             keyEvent->MarkProcessed();
3571             return true;
3572         }
3573     }
3574     return false;
3575 }
3576 
DispatchKeyEventCallback(const std::shared_ptr<MMI::KeyEvent> & keyEvent,bool & isConsumed)3577 void WindowSessionImpl::DispatchKeyEventCallback(const std::shared_ptr<MMI::KeyEvent>& keyEvent, bool& isConsumed)
3578 {
3579     std::shared_ptr<IInputEventConsumer> inputEventConsumer;
3580     {
3581         std::lock_guard<std::recursive_mutex> lock(mutex_);
3582         inputEventConsumer = inputEventConsumer_;
3583     }
3584     int32_t keyCode = keyEvent->GetKeyCode();
3585     int32_t keyAction = keyEvent->GetKeyAction();
3586     if (keyCode == MMI::KeyEvent::KEYCODE_BACK && keyAction == MMI::KeyEvent::KEY_ACTION_UP) {
3587         WLOGFI("input event is consumed by back, return");
3588         if (inputEventConsumer != nullptr) {
3589             WLOGFD("Transfer key event to inputEventConsumer");
3590             if (inputEventConsumer->OnInputEvent(keyEvent)) {
3591                 return;
3592             }
3593             PerformBack();
3594             keyEvent->MarkProcessed();
3595             return;
3596         }
3597         HandleBackEvent();
3598         keyEvent->MarkProcessed();
3599         return;
3600     }
3601 
3602     if (inputEventConsumer != nullptr) {
3603         WLOGD("Transfer key event to inputEventConsumer");
3604         if (!(inputEventConsumer->OnInputEvent(keyEvent))) {
3605             keyEvent->MarkProcessed();
3606         }
3607         return;
3608     }
3609 
3610     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
3611     if (uiContent) {
3612         if (FilterKeyEvent(keyEvent)) return;
3613         isConsumed = uiContent->ProcessKeyEvent(keyEvent);
3614         if (!isConsumed && keyEvent->GetKeyCode() == MMI::KeyEvent::KEYCODE_ESCAPE &&
3615             property_->GetWindowMode() == WindowMode::WINDOW_MODE_FULLSCREEN &&
3616             GetImmersiveModeEnabledState() &&
3617             keyAction == MMI::KeyEvent::KEY_ACTION_DOWN && !escKeyEventTriggered_) {
3618             WLOGI("recover from fullscreen cause KEYCODE_ESCAPE");
3619             Recover();
3620         }
3621         if (!isConsumed) {
3622             keyEvent->MarkProcessed();
3623         }
3624         if (keyEvent->GetKeyCode() == MMI::KeyEvent::KEYCODE_ESCAPE) {
3625             escKeyEventTriggered_ = (keyAction == MMI::KeyEvent::KEY_ACTION_UP) ? false : true;
3626         }
3627     }
3628 }
3629 
HandleBackEvent()3630 WSError WindowSessionImpl::HandleBackEvent()
3631 {
3632     TLOGI(WmsLogTag::WMS_EVENT, "called");
3633     bool isConsumed = false;
3634     std::shared_ptr<IInputEventConsumer> inputEventConsumer;
3635     {
3636         std::lock_guard<std::recursive_mutex> lock(mutex_);
3637         inputEventConsumer = inputEventConsumer_;
3638     }
3639     if (inputEventConsumer != nullptr) {
3640         WLOGFD("Transfer back event to inputEventConsumer");
3641         std::shared_ptr<MMI::KeyEvent> backKeyEvent = MMI::KeyEvent::Create();
3642         if (backKeyEvent == nullptr) {
3643             WLOGFE("backKeyEvent is null");
3644             return WSError::WS_ERROR_NULLPTR;
3645         }
3646         backKeyEvent->SetKeyCode(MMI::KeyEvent::KEYCODE_BACK);
3647         backKeyEvent->SetKeyAction(MMI::KeyEvent::KEY_ACTION_UP);
3648         isConsumed = inputEventConsumer->OnInputEvent(backKeyEvent);
3649     } else {
3650         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
3651         if (uiContent != nullptr) {
3652             WLOGFD("Transfer back event to uiContent");
3653             isConsumed = uiContent->ProcessBackPressed();
3654         } else {
3655             WLOGFE("There is no back event consumer");
3656         }
3657     }
3658 
3659     if (isConsumed) {
3660         WLOGD("Back key event is consumed");
3661         return WSError::WS_OK;
3662     }
3663     WLOGFD("report Back");
3664     SingletonContainer::Get<WindowInfoReporter>().ReportBackButtonInfoImmediately();
3665     if (handler_ == nullptr) {
3666         WLOGFE("HandleBackEvent handler_ is nullptr!");
3667         return WSError::WS_ERROR_INVALID_PARAM;
3668     }
3669     // notify back event to host session
3670     wptr<WindowSessionImpl> weak = this;
3671     auto task = [weak]() {
3672         auto weakSession = weak.promote();
3673         if (weakSession == nullptr) {
3674             WLOGFE("HandleBackEvent session wptr is nullptr");
3675             return;
3676         }
3677         weakSession->PerformBack();
3678     };
3679     if (!handler_->PostTask(task, "wms:PerformBack")) {
3680         WLOGFE("Failed to post PerformBack");
3681         return WSError::WS_ERROR_INVALID_OPERATION;
3682     }
3683     return WSError::WS_OK;
3684 }
3685 
NotifyKeyEvent(const std::shared_ptr<MMI::KeyEvent> & keyEvent,bool & isConsumed,bool notifyInputMethod)3686 void WindowSessionImpl::NotifyKeyEvent(const std::shared_ptr<MMI::KeyEvent>& keyEvent, bool& isConsumed,
3687     bool notifyInputMethod)
3688 {
3689     if (keyEvent == nullptr) {
3690         WLOGFE("keyEvent is nullptr");
3691         return;
3692     }
3693 
3694 #ifdef IMF_ENABLE
3695     bool isKeyboardEvent = IsKeyboardEvent(keyEvent);
3696     if (isKeyboardEvent && notifyInputMethod) {
3697         WLOGD("Async dispatch keyEvent to input method");
3698         auto callback = [weakThis = wptr(this)] (std::shared_ptr<MMI::KeyEvent>& keyEvent, bool consumed) {
3699             if (keyEvent == nullptr) {
3700                 WLOGFW("keyEvent is null, consumed:%{public}" PRId32, consumed);
3701                 return;
3702             }
3703 
3704             if (consumed) {
3705                 WLOGD("Input method has processed key event, id:%{public}" PRId32, keyEvent->GetId());
3706                 return;
3707             }
3708 
3709             auto promoteThis = weakThis.promote();
3710             if (promoteThis == nullptr) {
3711                 WLOGFW("promoteThis is nullptr");
3712                 keyEvent->MarkProcessed();
3713                 return;
3714             }
3715             bool isConsumed = false;
3716             promoteThis->DispatchKeyEventCallback(keyEvent, isConsumed);
3717         };
3718         auto ret = MiscServices::InputMethodController::GetInstance()->DispatchKeyEvent(
3719             const_cast<std::shared_ptr<MMI::KeyEvent>&>(keyEvent), callback);
3720         if (ret != 0) {
3721             WLOGFE("DispatchKeyEvent failed, ret:%{public}" PRId32 ", id:%{public}" PRId32, ret, keyEvent->GetId());
3722             DispatchKeyEventCallback(keyEvent, isConsumed);
3723         }
3724         return;
3725     }
3726 #endif // IMF_ENABLE
3727     DispatchKeyEventCallback(keyEvent, isConsumed);
3728 }
3729 
IsKeyboardEvent(const std::shared_ptr<MMI::KeyEvent> & keyEvent) const3730 bool WindowSessionImpl::IsKeyboardEvent(const std::shared_ptr<MMI::KeyEvent>& keyEvent) const
3731 {
3732     int32_t keyCode = keyEvent->GetKeyCode();
3733     bool isKeyFN = (keyCode == MMI::KeyEvent::KEYCODE_FN);
3734     bool isKeyBack = (keyCode == MMI::KeyEvent::KEYCODE_BACK);
3735     bool isKeyboard = (keyCode >= MMI::KeyEvent::KEYCODE_0 && keyCode <= MMI::KeyEvent::KEYCODE_NUMPAD_RIGHT_PAREN);
3736     bool isKeySound = (keyCode == MMI::KeyEvent::KEYCODE_SOUND);
3737     WLOGD("isKeyFN: %{public}d, isKeyboard: %{public}d", isKeyFN, isKeyboard);
3738     return (isKeyFN || isKeyboard || isKeyBack || isKeySound);
3739 }
3740 
RequestVsync(const std::shared_ptr<VsyncCallback> & vsyncCallback)3741 void WindowSessionImpl::RequestVsync(const std::shared_ptr<VsyncCallback>& vsyncCallback)
3742 {
3743     std::lock_guard<std::recursive_mutex> lock(mutex_);
3744     if (state_ == WindowState::STATE_DESTROYED) {
3745         WLOGFE("Receive vsync request failed, window is destroyed");
3746         return;
3747     }
3748 
3749     if (vsyncStation_ == nullptr) {
3750         TLOGE(WmsLogTag::WMS_MAIN, "Receive vsync request failed, vsyncStation is nullptr");
3751         return;
3752     }
3753     vsyncStation_->RequestVsync(vsyncCallback);
3754 }
3755 
GetVSyncPeriod()3756 int64_t WindowSessionImpl::GetVSyncPeriod()
3757 {
3758     std::lock_guard<std::recursive_mutex> lock(mutex_);
3759     if (vsyncStation_ == nullptr) {
3760         TLOGE(WmsLogTag::WMS_MAIN, "Get vsync period failed, vsyncStation is nullptr");
3761         return 0;
3762     }
3763     return vsyncStation_->GetVSyncPeriod();
3764 }
3765 
FlushFrameRate(uint32_t rate,int32_t animatorExpectedFrameRate,uint32_t rateType)3766 void WindowSessionImpl::FlushFrameRate(uint32_t rate, int32_t animatorExpectedFrameRate, uint32_t rateType)
3767 {
3768     std::lock_guard<std::recursive_mutex> lock(mutex_);
3769     if (vsyncStation_ == nullptr) {
3770         TLOGE(WmsLogTag::WMS_MAIN, "FlushFrameRate failed, vsyncStation is nullptr");
3771         return;
3772     }
3773     vsyncStation_->FlushFrameRate(rate, animatorExpectedFrameRate, rateType);
3774 }
3775 
UpdateProperty(WSPropertyChangeAction action)3776 WMError WindowSessionImpl::UpdateProperty(WSPropertyChangeAction action)
3777 {
3778     TLOGD(WmsLogTag::DEFAULT, "action:%{public}u", action);
3779     if (IsWindowSessionInvalid()) {
3780         TLOGE(WmsLogTag::DEFAULT, "session is invalid");
3781         return WMError::WM_ERROR_INVALID_WINDOW;
3782     }
3783     auto hostSession = GetHostSession();
3784     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_INVALID_WINDOW);
3785     return hostSession->UpdateSessionPropertyByAction(property_, action);
3786 }
3787 
Find(const std::string & name)3788 sptr<Window> WindowSessionImpl::Find(const std::string& name)
3789 {
3790     std::shared_lock<std::shared_mutex> lock(windowSessionMutex_);
3791     TLOGI(WmsLogTag::DEFAULT, "Try to find window %{public}s", name.c_str());
3792     auto iter = windowSessionMap_.find(name);
3793     if (iter == windowSessionMap_.end()) {
3794         TLOGE(WmsLogTag::DEFAULT, "Can not find window %{public}s", name.c_str());
3795         return nullptr;
3796     }
3797     return iter->second.second;
3798 }
3799 
SetAceAbilityHandler(const sptr<IAceAbilityHandler> & handler)3800 void WindowSessionImpl::SetAceAbilityHandler(const sptr<IAceAbilityHandler>& handler)
3801 {
3802     if (handler == nullptr) {
3803         WLOGE("ace ability handler is nullptr");
3804     }
3805     std::lock_guard<std::recursive_mutex> lock(mutex_);
3806     aceAbilityHandler_ = handler;
3807 }
3808 
SetBackgroundColor(const std::string & color)3809 WMError WindowSessionImpl::SetBackgroundColor(const std::string& color)
3810 {
3811     if (IsWindowSessionInvalid()) {
3812         TLOGE(WmsLogTag::DEFAULT, "session is invalid");
3813         return WMError::WM_ERROR_INVALID_WINDOW;
3814     }
3815     uint32_t colorValue;
3816     if (ColorParser::Parse(color, colorValue)) {
3817         TLOGD(WmsLogTag::DEFAULT, "SetBackgroundColor: window: %{public}s, value: [%{public}s, %{public}u]",
3818             GetWindowName().c_str(), color.c_str(), colorValue);
3819         return SetBackgroundColor(colorValue);
3820     }
3821     TLOGE(WmsLogTag::DEFAULT, "invalid color string: %{public}s", color.c_str());
3822     return WMError::WM_ERROR_INVALID_PARAM;
3823 }
3824 
SetBackgroundColor(uint32_t color)3825 WMError WindowSessionImpl::SetBackgroundColor(uint32_t color)
3826 {
3827     TLOGI(WmsLogTag::DEFAULT, "window: %{public}s, value:%{public}u", GetWindowName().c_str(), color);
3828 
3829     // 0xff000000: ARGB style, means Opaque color.
3830     const bool isAlphaZero = !(color & 0xff000000);
3831     std::string bundleName;
3832     std::string abilityName;
3833     if ((context_ != nullptr) && (context_->GetApplicationInfo() != nullptr)) {
3834         bundleName = context_->GetBundleName();
3835         abilityName = context_->GetApplicationInfo()->name;
3836     }
3837 
3838     if (isAlphaZero && WindowHelper::IsMainWindow(GetType())) {
3839         auto& reportInstance = SingletonContainer::Get<WindowInfoReporter>();
3840         reportInstance.ReportZeroOpacityInfoImmediately(bundleName, abilityName);
3841     }
3842     {
3843         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
3844         if (uiContent != nullptr) {
3845             uiContent->SetBackgroundColor(color);
3846             return WMError::WM_OK;
3847         }
3848     }
3849     if (aceAbilityHandler_ != nullptr) {
3850         aceAbilityHandler_->SetBackgroundColor(color);
3851         return WMError::WM_OK;
3852     }
3853     TLOGD(WmsLogTag::DEFAULT, "FA mode could not set bg color: %{public}u", GetWindowId());
3854     return WMError::WM_ERROR_INVALID_OPERATION;
3855 }
3856 
FindWindowById(uint32_t winId)3857 sptr<Window> WindowSessionImpl::FindWindowById(uint32_t winId)
3858 {
3859     std::shared_lock<std::shared_mutex> lock(windowSessionMutex_);
3860     if (windowSessionMap_.empty()) {
3861         WLOGFE("Please create mainWindow First!");
3862         return nullptr;
3863     }
3864     for (auto iter = windowSessionMap_.begin(); iter != windowSessionMap_.end(); iter++) {
3865         if (static_cast<int32_t>(winId) == iter->second.first) {
3866             WLOGD("FindWindow id: %{public}u", winId);
3867             return iter->second.second;
3868         }
3869     }
3870     WLOGFE("Cannot find Window, id: %{public}d", winId);
3871     return nullptr;
3872 }
3873 
GetSubWindow(int parentId)3874 std::vector<sptr<Window>> WindowSessionImpl::GetSubWindow(int parentId)
3875 {
3876     auto iter = subWindowSessionMap_.find(parentId);
3877     if (iter == subWindowSessionMap_.end()) {
3878         return std::vector<sptr<Window>>();
3879     }
3880     return std::vector<sptr<Window>>(subWindowSessionMap_[parentId].begin(), subWindowSessionMap_[parentId].end());
3881 }
3882 
GetBackgroundColor() const3883 uint32_t WindowSessionImpl::GetBackgroundColor() const
3884 {
3885     {
3886         std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
3887         if (uiContent != nullptr) {
3888             return uiContent->GetBackgroundColor();
3889         }
3890     }
3891     WLOGD("uiContent is nullptr, windowId: %{public}u, use FA mode", GetWindowId());
3892     if (aceAbilityHandler_ != nullptr) {
3893         return aceAbilityHandler_->GetBackgroundColor();
3894     }
3895     WLOGFD("FA mode does not get bg color: %{public}u", GetWindowId());
3896     return 0xffffffff; // means no background color been set, default color is white
3897 }
3898 
SetLayoutFullScreenByApiVersion(bool status)3899 WMError WindowSessionImpl::SetLayoutFullScreenByApiVersion(bool status)
3900 {
3901     return WMError::WM_OK;
3902 }
3903 
SetSystemBarProperty(WindowType type,const SystemBarProperty & property)3904 WMError WindowSessionImpl::SetSystemBarProperty(WindowType type, const SystemBarProperty& property)
3905 {
3906     return WMError::WM_OK;
3907 }
3908 
SetSpecificBarProperty(WindowType type,const SystemBarProperty & property)3909 WMError WindowSessionImpl::SetSpecificBarProperty(WindowType type, const SystemBarProperty& property)
3910 {
3911     return WMError::WM_OK;
3912 }
3913 
NotifyOccupiedAreaChangeInfoInner(sptr<OccupiedAreaChangeInfo> info)3914 void WindowSessionImpl::NotifyOccupiedAreaChangeInfoInner(sptr<OccupiedAreaChangeInfo> info)
3915 {
3916     std::lock_guard<std::recursive_mutex> lockListener(occupiedAreaChangeListenerMutex_);
3917     auto occupiedAreaChangeListeners = GetListeners<IOccupiedAreaChangeListener>();
3918     for (auto& listener : occupiedAreaChangeListeners) {
3919         if (listener != nullptr) {
3920             listener->OnSizeChange(info);
3921         }
3922     }
3923 }
3924 
NotifyOccupiedAreaChangeInfo(sptr<OccupiedAreaChangeInfo> info,const std::shared_ptr<RSTransaction> & rsTransaction)3925 void WindowSessionImpl::NotifyOccupiedAreaChangeInfo(sptr<OccupiedAreaChangeInfo> info,
3926                                                      const std::shared_ptr<RSTransaction>& rsTransaction)
3927 {
3928     TLOGI(WmsLogTag::WMS_KEYBOARD, "hasRSTransaction: %{public}d, safeHeight: %{public}u"
3929         ", occupied rect: x %{public}u, y %{public}u, w %{public}u, h %{public}u", rsTransaction != nullptr,
3930         info->safeHeight_, info->rect_.posX_, info->rect_.posY_, info->rect_.width_, info->rect_.height_);
3931     if (handler_ == nullptr) {
3932         TLOGE(WmsLogTag::WMS_KEYBOARD, "handler_ is nullptr, notify occupied area change info failed");
3933         return;
3934     }
3935     auto task = [weak = wptr(this), info, rsTransaction]() {
3936         auto window = weak.promote();
3937         if (!window) {
3938             TLOGE(WmsLogTag::WMS_KEYBOARD, "window is nullptr, notify occupied area change info failed");
3939             return;
3940         }
3941         if (rsTransaction) {
3942             RSTransaction::FlushImplicitTransaction();
3943             rsTransaction->Begin();
3944         }
3945         window->NotifyOccupiedAreaChangeInfoInner(info);
3946         if (rsTransaction) {
3947             rsTransaction->Commit();
3948         }
3949     };
3950     handler_->PostTask(task, "WMS_WindowSessionImpl_NotifyOccupiedAreaChangeInfo");
3951 }
3952 
GetKeyboardAnimationConfig()3953 KeyboardAnimationConfig WindowSessionImpl::GetKeyboardAnimationConfig()
3954 {
3955     return { windowSystemConfig_.animationIn_, windowSystemConfig_.animationOut_ };
3956 }
3957 
DumpSessionElementInfo(const std::vector<std::string> & params)3958 void WindowSessionImpl::DumpSessionElementInfo(const std::vector<std::string>& params)
3959 {
3960     WLOGFD("DumpSessionElementInfo");
3961 }
3962 
UpdateMaximizeMode(MaximizeMode mode)3963 WSError WindowSessionImpl::UpdateMaximizeMode(MaximizeMode mode)
3964 {
3965     return WSError::WS_OK;
3966 }
3967 
TransferAccessibilityEvent(const Accessibility::AccessibilityEventInfo & info,int64_t uiExtensionIdLevel)3968 WMError WindowSessionImpl::TransferAccessibilityEvent(const Accessibility::AccessibilityEventInfo& info,
3969     int64_t uiExtensionIdLevel)
3970 {
3971     return WMError::WM_OK;
3972 }
3973 
NotifySessionForeground(uint32_t reason,bool withAnimation)3974 void WindowSessionImpl::NotifySessionForeground(uint32_t reason, bool withAnimation)
3975 {
3976     WLOGFD("NotifySessionForeground");
3977 }
3978 
NotifySessionBackground(uint32_t reason,bool withAnimation,bool isFromInnerkits)3979 void WindowSessionImpl::NotifySessionBackground(uint32_t reason, bool withAnimation, bool isFromInnerkits)
3980 {
3981     WLOGFD("NotifySessionBackground");
3982 }
3983 
UpdateTitleInTargetPos(bool isShow,int32_t height)3984 WSError WindowSessionImpl::UpdateTitleInTargetPos(bool isShow, int32_t height)
3985 {
3986     return WSError::WS_OK;
3987 }
3988 
SwitchFreeMultiWindow(bool enable)3989 WSError WindowSessionImpl::SwitchFreeMultiWindow(bool enable)
3990 {
3991     return WSError::WS_OK;
3992 }
3993 
NotifyDialogStateChange(bool isForeground)3994 WSError WindowSessionImpl::NotifyDialogStateChange(bool isForeground)
3995 {
3996     return WSError::WS_OK;
3997 }
3998 
UpdatePiPRect(const Rect & rect,WindowSizeChangeReason reason)3999 void WindowSessionImpl::UpdatePiPRect(const Rect& rect, WindowSizeChangeReason reason)
4000 {
4001     if (IsWindowSessionInvalid()) {
4002         TLOGE(WmsLogTag::WMS_PIP, "HostSession is invalid");
4003         return;
4004     }
4005     auto hostSession = GetHostSession();
4006     CHECK_HOST_SESSION_RETURN_IF_NULL(hostSession);
4007     hostSession->UpdatePiPRect(rect, static_cast<SizeChangeReason>(reason));
4008 }
4009 
UpdatePiPControlStatus(PiPControlType controlType,PiPControlStatus status)4010 void WindowSessionImpl::UpdatePiPControlStatus(PiPControlType controlType, PiPControlStatus status)
4011 {
4012     TLOGI(WmsLogTag::WMS_PIP, "controlType:%{public}u, status:%{public}d", controlType, status);
4013     if (IsWindowSessionInvalid()) {
4014         TLOGE(WmsLogTag::WMS_PIP, "HostSession is invalid");
4015         return;
4016     }
4017     auto hostSession = GetHostSession();
4018     CHECK_HOST_SESSION_RETURN_IF_NULL(hostSession);
4019     hostSession->UpdatePiPControlStatus(static_cast<WsPiPControlType>(controlType),
4020         static_cast<WsPiPControlStatus>(status));
4021 }
4022 
SetAutoStartPiP(bool isAutoStart,uint32_t priority)4023 void WindowSessionImpl::SetAutoStartPiP(bool isAutoStart, uint32_t priority)
4024 {
4025     if (IsWindowSessionInvalid()) {
4026         TLOGE(WmsLogTag::WMS_PIP, "session is invalid");
4027         return;
4028     }
4029     if (auto hostSession = GetHostSession()) {
4030         hostSession->SetAutoStartPiP(isAutoStart, priority);
4031     }
4032 }
4033 
GetWindowStatusInner(WindowMode mode)4034 WindowStatus WindowSessionImpl::GetWindowStatusInner(WindowMode mode)
4035 {
4036     auto windowStatus = WindowStatus::WINDOW_STATUS_UNDEFINED;
4037     if (mode == WindowMode::WINDOW_MODE_FLOATING) {
4038         windowStatus = WindowStatus::WINDOW_STATUS_FLOATING;
4039         if (property_->GetMaximizeMode() == MaximizeMode::MODE_AVOID_SYSTEM_BAR) {
4040             windowStatus = WindowStatus::WINDOW_STATUS_MAXIMIZE;
4041         }
4042     } else if (mode == WindowMode::WINDOW_MODE_SPLIT_PRIMARY || mode == WindowMode::WINDOW_MODE_SPLIT_SECONDARY) {
4043         windowStatus = WindowStatus::WINDOW_STATUS_SPLITSCREEN;
4044         if (IsPcOrPadFreeMultiWindowMode() && GetTargetAPIVersion() >= 14) { // 14: isolated version
4045             windowStatus = GetImmersiveModeEnabledState() ? WindowStatus::WINDOW_STATUS_FULLSCREEN :
4046                 WindowStatus::WINDOW_STATUS_MAXIMIZE;
4047         } else {
4048             windowStatus = WindowStatus::WINDOW_STATUS_FULLSCREEN;
4049         }
4050     }
4051     if (mode == WindowMode::WINDOW_MODE_FULLSCREEN) {
4052         windowStatus = WindowStatus::WINDOW_STATUS_FULLSCREEN;
4053     }
4054     if (state_ == WindowState::STATE_HIDDEN) {
4055         windowStatus = WindowStatus::WINDOW_STATUS_MINIMIZE;
4056     }
4057     return windowStatus;
4058 }
4059 
NotifyWindowStatusChange(WindowMode mode)4060 void WindowSessionImpl::NotifyWindowStatusChange(WindowMode mode)
4061 {
4062     auto windowStatus = GetWindowStatusInner(mode);
4063     TLOGD(WmsLogTag::WMS_LAYOUT, "WindowMode: %{public}d, windowStatus: %{public}d", mode, windowStatus);
4064     std::lock_guard<std::recursive_mutex> lockListener(windowStatusChangeListenerMutex_);
4065     auto windowStatusChangeListeners = GetListeners<IWindowStatusChangeListener>();
4066     for (auto& listener : windowStatusChangeListeners) {
4067         if (listener != nullptr) {
4068             listener->OnWindowStatusChange(windowStatus);
4069         }
4070     }
4071 }
4072 
NotifyTransformChange(const Transform & transform)4073 void WindowSessionImpl::NotifyTransformChange(const Transform& transform)
4074 {
4075     WLOGFI("NotifyWindowStatusChange");
4076     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
4077     if (uiContent != nullptr) {
4078         uiContent->UpdateTransform(transform);
4079     }
4080 }
4081 
SubmitNoInteractionMonitorTask(int32_t eventId,const IWindowNoInteractionListenerSptr & listener)4082 void WindowSessionImpl::SubmitNoInteractionMonitorTask(int32_t eventId,
4083     const IWindowNoInteractionListenerSptr& listener)
4084 {
4085     auto task = [sessionWptr = wptr(this), eventId, listenerWptr = wptr(listener)]() {
4086         auto session = sessionWptr.promote();
4087         if (session == nullptr) {
4088             WLOGFE("windowInteractionMonitor task running failed, window session is null");
4089             return;
4090         }
4091         if (eventId != session->lastInteractionEventId_.load()) {
4092             WLOGFD("event id of windowInteractionMonitor has been changed, need not notify!");
4093             return;
4094         }
4095         if (session->state_ != WindowState::STATE_SHOWN) {
4096             WLOGFD("window state is not show, need not notify!");
4097             return;
4098         }
4099         session->NotifyNoInteractionTimeout(listenerWptr.promote());
4100     };
4101     handler_->PostTask(task, listener->GetTimeout());
4102 }
4103 
RefreshNoInteractionTimeoutMonitor()4104 void WindowSessionImpl::RefreshNoInteractionTimeoutMonitor()
4105 {
4106     std::lock_guard<std::recursive_mutex> lockListener(windowNoInteractionListenerMutex_);
4107     if (windowNoInteractionListeners_[GetPersistentId()].empty()) {
4108         return;
4109     }
4110     this->lastInteractionEventId_.fetch_add(1);
4111     int32_t eventId = lastInteractionEventId_.load();
4112     auto noInteractionListeners = GetListeners<IWindowNoInteractionListener>();
4113     for (const auto& listenerItem : noInteractionListeners) {
4114         SubmitNoInteractionMonitorTask(eventId, listenerItem);
4115     }
4116 }
4117 
IsUserOrientation(Orientation orientation) const4118 bool WindowSessionImpl::IsUserOrientation(Orientation orientation) const
4119 {
4120     if (orientation == Orientation::USER_ROTATION_PORTRAIT ||
4121         orientation == Orientation::USER_ROTATION_LANDSCAPE ||
4122         orientation == Orientation::USER_ROTATION_PORTRAIT_INVERTED ||
4123         orientation == Orientation::USER_ROTATION_LANDSCAPE_INVERTED) {
4124         return true;
4125     }
4126     return false;
4127 }
4128 
GetCallingWindowWindowStatus(WindowStatus & windowStatus) const4129 WMError WindowSessionImpl::GetCallingWindowWindowStatus(WindowStatus& windowStatus) const
4130 {
4131     TLOGI(WmsLogTag::WMS_KEYBOARD, "id: %{public}d", GetPersistentId());
4132     if (IsWindowSessionInvalid()) {
4133         TLOGE(WmsLogTag::WMS_KEYBOARD, "session is invalid");
4134         return WMError::WM_ERROR_INVALID_WINDOW;
4135     }
4136     return SingletonContainer::Get<WindowAdapter>().GetCallingWindowWindowStatus(GetPersistentId(), windowStatus);
4137 }
4138 
GetCallingWindowRect(Rect & rect) const4139 WMError WindowSessionImpl::GetCallingWindowRect(Rect& rect) const
4140 {
4141     TLOGI(WmsLogTag::WMS_KEYBOARD, "Get CallingWindow Rect");
4142     if (IsWindowSessionInvalid()) {
4143         TLOGE(WmsLogTag::WMS_KEYBOARD, "session is invalid");
4144         return WMError::WM_ERROR_INVALID_WINDOW;
4145     }
4146     return SingletonContainer::Get<WindowAdapter>().GetCallingWindowRect(GetPersistentId(), rect);
4147 }
4148 
SetUiDvsyncSwitch(bool dvsyncSwitch)4149 void WindowSessionImpl::SetUiDvsyncSwitch(bool dvsyncSwitch)
4150 {
4151     std::lock_guard<std::recursive_mutex> lock(mutex_);
4152     if (vsyncStation_ == nullptr) {
4153         TLOGE(WmsLogTag::WMS_MAIN, "vsyncStation is nullptr");
4154         return;
4155     }
4156     vsyncStation_->SetUiDvsyncSwitch(dvsyncSwitch);
4157 }
4158 
GetAppForceLandscapeConfig(AppForceLandscapeConfig & config)4159 WMError WindowSessionImpl::GetAppForceLandscapeConfig(AppForceLandscapeConfig& config)
4160 {
4161     if (IsWindowSessionInvalid()) {
4162         TLOGE(WmsLogTag::DEFAULT, "HostSession is invalid");
4163         return WMError::WM_ERROR_INVALID_WINDOW;
4164     }
4165     auto hostSession = GetHostSession();
4166     CHECK_HOST_SESSION_RETURN_ERROR_IF_NULL(hostSession, WMError::WM_ERROR_NULLPTR);
4167     return hostSession->GetAppForceLandscapeConfig(config);
4168 }
4169 
SetForceSplitEnable(bool isForceSplit,const std::string & homePage)4170 void WindowSessionImpl::SetForceSplitEnable(bool isForceSplit, const std::string& homePage)
4171 {
4172     std::shared_ptr<Ace::UIContent> uiContent = GetUIContentSharedPtr();
4173     if (uiContent == nullptr) {
4174         TLOGE(WmsLogTag::DEFAULT, "uiContent is null!");
4175         return;
4176     }
4177     TLOGI(WmsLogTag::DEFAULT, "isForceSplit: %{public}u, homePage: %{public}s",
4178         isForceSplit, homePage.c_str());
4179     uiContent->SetForceSplitEnable(isForceSplit, homePage);
4180 }
4181 
SetFrameLayoutCallbackEnable(bool enable)4182 void WindowSessionImpl::SetFrameLayoutCallbackEnable(bool enable)
4183 {
4184     enableFrameLayoutFinishCb_ = enable;
4185 }
4186 
UpdateFrameLayoutCallbackIfNeeded(WindowSizeChangeReason wmReason)4187 void WindowSessionImpl::UpdateFrameLayoutCallbackIfNeeded(WindowSizeChangeReason wmReason)
4188 {
4189     bool isDragInPcmode = IsFreeMultiWindowMode() && (wmReason == WindowSizeChangeReason::DRAG_END);
4190     if (wmReason == WindowSizeChangeReason::FULL_TO_SPLIT || wmReason == WindowSizeChangeReason::SPLIT_TO_FULL ||
4191         wmReason == WindowSizeChangeReason::FULL_TO_FLOATING || wmReason == WindowSizeChangeReason::FLOATING_TO_FULL ||
4192         isDragInPcmode) {
4193         TLOGI(WmsLogTag::WMS_MULTI_WINDOW, "enable framelayoutfinish callback reason:%{public}u", wmReason);
4194         SetFrameLayoutCallbackEnable(true);
4195     }
4196 }
4197 
SetContinueState(int32_t continueState)4198 WMError WindowSessionImpl::SetContinueState(int32_t continueState)
4199 {
4200     if (continueState > ContinueState::CONTINUESTATE_MAX || continueState < ContinueState::CONTINUESTATE_UNKNOWN) {
4201         TLOGE(WmsLogTag::WMS_MAIN, "continueState is invalid: %{public}d", continueState);
4202         return WMError::WM_ERROR_INVALID_PARAM;
4203     }
4204     property_->EditSessionInfo().continueState = static_cast<ContinueState>(continueState);
4205     return WMError::WM_OK;
4206 }
4207 
SetUIContentComplete()4208 void WindowSessionImpl::SetUIContentComplete()
4209 {
4210     bool setUIContentCompleted = false;
4211     if (setUIContentCompleted_.compare_exchange_strong(setUIContentCompleted, true)) {
4212         TLOGI(WmsLogTag::WMS_LIFE, "persistentId=%{public}d", GetPersistentId());
4213         handler_->RemoveTask(SET_UICONTENT_TIMEOUT_LISTENER_TASK_NAME + std::to_string(GetPersistentId()));
4214     } else {
4215         TLOGI(WmsLogTag::WMS_LIFE, "already SetUIContent, persistentId=%{public}d", GetPersistentId());
4216     }
4217 }
4218 
AddSetUIContentTimeoutCheck()4219 void WindowSessionImpl::AddSetUIContentTimeoutCheck()
4220 {
4221     const auto checkBeginTime =
4222         std::chrono::time_point_cast<std::chrono::milliseconds>(std::chrono::system_clock::now())
4223             .time_since_epoch().count();
4224     auto task = [weakThis = wptr(this), checkBeginTime] {
4225         auto window = weakThis.promote();
4226         if (window == nullptr) {
4227             TLOGNI(WmsLogTag::WMS_LIFE, "window is nullptr");
4228             return;
4229         }
4230         if (window->setUIContentCompleted_.load()) {
4231             TLOGNI(WmsLogTag::WMS_LIFE, "already SetUIContent, persistentId=%{public}d", window->GetPersistentId());
4232             return;
4233         }
4234 
4235         const auto checkEndTime =
4236             std::chrono::time_point_cast<std::chrono::milliseconds>(std::chrono::system_clock::now())
4237                 .time_since_epoch().count();
4238         if (checkEndTime - checkBeginTime > SET_UICONTENT_TIMEOUT_TIME_AFTER_FREEZE_MS) {
4239             TLOGNI(WmsLogTag::WMS_LIFE, "will start re-check after freeze, persistentId=%{public}d",
4240                 window->GetPersistentId());
4241             window->AddSetUIContentTimeoutCheck();
4242             return;
4243         }
4244 
4245         TLOGNI(WmsLogTag::WMS_LIFE, "SetUIContent timeout, persistentId=%{public}d", window->GetPersistentId());
4246         std::ostringstream oss;
4247         oss << "SetUIContent timeout uid: " << getuid();
4248         oss << ", windowName: " << window->GetWindowName();
4249         if (window->context_) {
4250             oss << ", bundleName: " << window->context_->GetBundleName();
4251             if (window->context_->GetApplicationInfo()) {
4252                 oss << ", abilityName: " << window->context_->GetApplicationInfo()->name;
4253             }
4254         }
4255         SingletonContainer::Get<WindowInfoReporter>().ReportWindowException(
4256             static_cast<int32_t>(WindowDFXHelperType::WINDOW_TRANSPARENT_CHECK), getpid(), oss.str());
4257 
4258         if (WindowHelper::IsUIExtensionWindow(window->GetType())) {
4259             window->NotifyExtensionTimeout(TimeoutErrorCode::SET_UICONTENT_TIMEOUT);
4260         }
4261     };
4262     handler_->PostTask(task, SET_UICONTENT_TIMEOUT_LISTENER_TASK_NAME + std::to_string(GetPersistentId()),
4263         SET_UICONTENT_TIMEOUT_TIME_MS, AppExecFwk::EventQueue::Priority::HIGH);
4264 }
4265 
NotifySetUIContentComplete()4266 void WindowSessionImpl::NotifySetUIContentComplete()
4267 {
4268     if (WindowHelper::IsSubWindow(GetType()) || WindowHelper::IsSystemWindow(GetType())) {
4269         // created by UIExtension
4270         auto extWindow = FindExtensionWindowWithContext();
4271         if (extWindow != nullptr) {
4272             extWindow->SetUIContentComplete();
4273         }
4274     }
4275     SetUIContentComplete();
4276 }
4277 
SetUIExtensionDestroyComplete()4278 void WindowSessionImpl::SetUIExtensionDestroyComplete()
4279 {
4280     bool setUIExtensionDestroyCompleted = false;
4281     if (setUIExtensionDestroyCompleted_.compare_exchange_strong(setUIExtensionDestroyCompleted, true)) {
4282         TLOGI(WmsLogTag::WMS_LIFE, "persistentId=%{public}d", GetPersistentId());
4283         handler_->RemoveTask(SET_UIEXTENSION_DESTROY_TIMEOUT_LISTENER_TASK_NAME + std::to_string(GetPersistentId()));
4284     } else {
4285         TLOGI(WmsLogTag::WMS_LIFE, "already, persistentId=%{public}d", GetPersistentId());
4286     }
4287 }
4288 
SetUIExtensionDestroyCompleteInSubWindow()4289 void WindowSessionImpl::SetUIExtensionDestroyCompleteInSubWindow()
4290 {
4291     if (WindowHelper::IsSubWindow(GetType()) || WindowHelper::IsSystemWindow(GetType())) {
4292         bool startUIExtensionDestroyTimer = true;
4293         auto extensionWindow = FindExtensionWindowWithContext();
4294         if (extensionWindow != nullptr && extensionWindow->startUIExtensionDestroyTimer_.compare_exchange_strong(
4295             startUIExtensionDestroyTimer, false)) {
4296             TLOGI(WmsLogTag::WMS_LIFE, "called");
4297             extensionWindow->SetUIExtensionDestroyComplete();
4298             extensionWindow->setUIExtensionDestroyCompleted_.store(false);
4299         }
4300     }
4301 }
4302 
AddSetUIExtensionDestroyTimeoutCheck()4303 void WindowSessionImpl::AddSetUIExtensionDestroyTimeoutCheck()
4304 {
4305     const char* const where = __func__;
4306     auto task = [weakThis = wptr(this), where] {
4307         auto window = weakThis.promote();
4308         if (window == nullptr) {
4309             TLOGNE(WmsLogTag::WMS_LIFE, "%{public}s: window is nullptr", where);
4310             return;
4311         }
4312         if (window->setUIExtensionDestroyCompleted_.load()) {
4313             TLOGNI(WmsLogTag::WMS_LIFE, "%{public}s: already, persistentId=%{public}d", where,
4314                 window->GetPersistentId());
4315             return;
4316         }
4317 
4318         TLOGNI(WmsLogTag::WMS_LIFE, "%{public}s: timeout, persistentId=%{public}d", where, window->GetPersistentId());
4319         std::ostringstream oss;
4320         oss << "SetUIExtDestroy timeout uid: " << getuid();
4321         oss << ", windowName: " << window->GetWindowName();
4322         if (window->context_) {
4323             oss << ", bundleName: " << window->context_->GetBundleName();
4324             if (window->context_->GetApplicationInfo()) {
4325                 oss << ", abilityName: " << window->context_->GetApplicationInfo()->name;
4326             }
4327         }
4328         SingletonContainer::Get<WindowInfoReporter>().ReportWindowException(
4329             static_cast<int32_t>(WindowDFXHelperType::WINDOW_TRANSPARENT_CHECK), getpid(), oss.str());
4330 
4331         if (WindowHelper::IsUIExtensionWindow(window->GetType())) {
4332             window->NotifyExtensionTimeout(TimeoutErrorCode::SET_UIEXTENSION_DESTROY_TIMEOUT);
4333         }
4334     };
4335     handler_->PostTask(task, SET_UIEXTENSION_DESTROY_TIMEOUT_LISTENER_TASK_NAME + std::to_string(GetPersistentId()),
4336         SET_UIEXTENSION_DESTROY_TIMEOUT_TIME_MS, AppExecFwk::EventQueue::Priority::HIGH);
4337     startUIExtensionDestroyTimer_.store(true);
4338 }
4339 
SetEnableDragBySystem(bool enableDrag)4340 WSError WindowSessionImpl::SetEnableDragBySystem(bool enableDrag)
4341 {
4342     TLOGI(WmsLogTag::WMS_LAYOUT, "enableDrag:%{publlic}d", enableDrag);
4343     property_->SetDragEnabled(enableDrag);
4344     return WSError::WS_OK;
4345 }
4346 
SetTargetAPIVersion(uint32_t targetAPIVersion)4347 void WindowSessionImpl::SetTargetAPIVersion(uint32_t targetAPIVersion)
4348 {
4349     targetAPIVersion_ = targetAPIVersion;
4350 }
4351 
GetTargetAPIVersion() const4352 uint32_t WindowSessionImpl::GetTargetAPIVersion() const
4353 {
4354     return targetAPIVersion_;
4355 }
4356 } // namespace Rosen
4357 } // namespace OHOS
4358