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 "session/screen/include/screen_session.h"
17 #include <hisysevent.h>
18 
19 #include "screen_cache.h"
20 #include <hitrace_meter.h>
21 #include <surface_capture_future.h>
22 #include <transaction/rs_interfaces.h>
23 #include <transaction/rs_transaction.h>
24 #include "window_manager_hilog.h"
25 #include "dm_common.h"
26 #include "dms_xcollie.h"
27 #include "fold_screen_state_internel.h"
28 #include <parameters.h>
29 #include "sys_cap_util.h"
30 #include <ipc_skeleton.h>
31 
32 namespace OHOS::Rosen {
33 namespace {
34 constexpr HiviewDFX::HiLogLabel LABEL = { LOG_CORE, HILOG_DOMAIN_WINDOW, "ScreenSession" };
35 static const int32_t g_screenRotationOffSet = system::GetIntParameter<int32_t>("const.fold.screen_rotation.offset", 0);
36 static const int32_t ROTATION_90 = 1;
37 static const int32_t ROTATION_270 = 3;
38 const unsigned int XCOLLIE_TIMEOUT_5S = 5;
39 const static int32_t MAX_INTERVAL_US = 1800000000; //30分钟
40 const int32_t MAP_SIZE = 300;
41 const int32_t NO_EXIT_UID_VERSION = -1;
42 ScreenCache g_uidVersionMap(MAP_SIZE, NO_EXIT_UID_VERSION);
43 }
ScreenSession(const ScreenSessionConfig & config,ScreenSessionReason reason)44 ScreenSession::ScreenSession(const ScreenSessionConfig& config, ScreenSessionReason reason)
45     : name_(config.name), screenId_(config.screenId), rsId_(config.rsId), defaultScreenId_(config.defaultScreenId),
46     property_(config.property), displayNode_(config.displayNode)
47 {
48     TLOGI(WmsLogTag::DMS,
49         "[DPNODE]Create Session, reason: %{public}d, screenId: %{public}" PRIu64", rsId: %{public}" PRIu64"",
50         reason, screenId_, rsId_);
51     TLOGI(WmsLogTag::DMS,
52         "[DPNODE]Config name: %{public}s, defaultId: %{public}" PRIu64", mirrorNodeId: %{public}" PRIu64"",
53         name_.c_str(), defaultScreenId_, config.mirrorNodeId);
54     Rosen::RSDisplayNodeConfig rsConfig;
55     bool isNeedCreateDisplayNode = true;
56     switch (reason) {
57         case ScreenSessionReason::CREATE_SESSION_FOR_CLIENT: {
58             TLOGI(WmsLogTag::DMS, "create screen session for client. noting to do.");
59             return;
60         }
61         case ScreenSessionReason::CREATE_SESSION_FOR_VIRTUAL: {
62             // create virtual screen should use rsid
63             rsConfig.screenId = rsId_;
64             break;
65         }
66         case ScreenSessionReason::CREATE_SESSION_FOR_MIRROR: {
67             rsConfig.screenId = screenId_;
68             rsConfig.isMirrored = true;
69             rsConfig.mirrorNodeId = config.mirrorNodeId;
70             rsConfig.isSync = true;
71             break;
72         }
73         case ScreenSessionReason::CREATE_SESSION_FOR_REAL: {
74             rsConfig.screenId = screenId_;
75             break;
76         }
77         case ScreenSessionReason::CREATE_SESSION_WITHOUT_DISPLAY_NODE: {
78             TLOGI(WmsLogTag::DMS, "screen session no need create displayNode.");
79             isNeedCreateDisplayNode = false;
80             break;
81         }
82         default : {
83             TLOGE(WmsLogTag::DMS, "INVALID invalid screen session config.");
84             break;
85         }
86     }
87     if (isNeedCreateDisplayNode) {
88         CreateDisplayNode(rsConfig);
89     }
90 }
91 
CreateDisplayNode(const Rosen::RSDisplayNodeConfig & config)92 void ScreenSession::CreateDisplayNode(const Rosen::RSDisplayNodeConfig& config)
93 {
94     TLOGI(WmsLogTag::DMS,
95         "[DPNODE]config screenId: %{public}" PRIu64", mirrorNodeId: %{public}" PRIu64", isMirrored: %{public}d",
96         config.screenId, config.mirrorNodeId, static_cast<int32_t>(config.isMirrored));
97     {
98         std::unique_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
99         displayNode_ = Rosen::RSDisplayNode::Create(config);
100         if (displayNode_) {
101             displayNode_->SetFrame(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
102                 property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
103             displayNode_->SetBounds(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
104                 property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
105         } else {
106             TLOGE(WmsLogTag::DMS, "Failed to create displayNode, displayNode is null!");
107         }
108     }
109     RSTransaction::FlushImplicitTransaction();
110 }
111 
~ScreenSession()112 ScreenSession::~ScreenSession()
113 {
114     WLOGI("~ScreenSession");
115 }
116 
ScreenSession(ScreenId screenId,ScreenId rsId,const std::string & name,const ScreenProperty & property,const std::shared_ptr<RSDisplayNode> & displayNode)117 ScreenSession::ScreenSession(ScreenId screenId, ScreenId rsId, const std::string& name,
118     const ScreenProperty& property, const std::shared_ptr<RSDisplayNode>& displayNode)
119     : name_(name), screenId_(screenId), rsId_(rsId), property_(property), displayNode_(displayNode)
120 {
121     WLOGFI("Success to create screenSession in constructor_0, screenid is %{public}" PRIu64"", screenId_);
122 }
123 
ScreenSession(ScreenId screenId,const ScreenProperty & property,ScreenId defaultScreenId)124 ScreenSession::ScreenSession(ScreenId screenId, const ScreenProperty& property, ScreenId defaultScreenId)
125     : screenId_(screenId), defaultScreenId_(defaultScreenId), property_(property)
126 {
127     Rosen::RSDisplayNodeConfig config = { .screenId = screenId_ };
128     displayNode_ = Rosen::RSDisplayNode::Create(config);
129     if (displayNode_) {
130         WLOGI("Success to create displayNode in constructor_1, screenid is %{public}" PRIu64"", screenId_);
131         displayNode_->SetFrame(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
132             property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
133         displayNode_->SetBounds(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
134             property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
135     } else {
136         WLOGFE("Failed to create displayNode, displayNode is null!");
137     }
138     RSTransaction::FlushImplicitTransaction();
139 }
140 
ScreenSession(ScreenId screenId,const ScreenProperty & property,NodeId nodeId,ScreenId defaultScreenId)141 ScreenSession::ScreenSession(ScreenId screenId, const ScreenProperty& property,
142     NodeId nodeId, ScreenId defaultScreenId)
143     : screenId_(screenId), defaultScreenId_(defaultScreenId), property_(property)
144 {
145     rsId_ = screenId;
146     Rosen::RSDisplayNodeConfig config = { .screenId = screenId_, .isMirrored = true, .mirrorNodeId = nodeId,
147         .isSync = true};
148     displayNode_ = Rosen::RSDisplayNode::Create(config);
149     if (displayNode_) {
150         WLOGI("Success to create displayNode in constructor_2, screenid is %{public}" PRIu64"", screenId_);
151         displayNode_->SetFrame(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
152             property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
153         displayNode_->SetBounds(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
154             property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
155     } else {
156         WLOGFE("Failed to create displayNode, displayNode is null!");
157     }
158     RSTransaction::FlushImplicitTransaction();
159 }
160 
ScreenSession(const std::string & name,ScreenId smsId,ScreenId rsId,ScreenId defaultScreenId)161 ScreenSession::ScreenSession(const std::string& name, ScreenId smsId, ScreenId rsId, ScreenId defaultScreenId)
162     : name_(name), screenId_(smsId), rsId_(rsId), defaultScreenId_(defaultScreenId)
163 {
164     (void)rsId_;
165     // 虚拟屏的screen id和rs id不一致,displayNode的创建应使用rs id
166     Rosen::RSDisplayNodeConfig config = { .screenId = rsId_ };
167     displayNode_ = Rosen::RSDisplayNode::Create(config);
168     if (displayNode_) {
169         WLOGI("Success to create displayNode in constructor_3, rs id is %{public}" PRIu64"", rsId_);
170         displayNode_->SetFrame(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
171             property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
172         displayNode_->SetBounds(property_.GetBounds().rect_.left_, property_.GetBounds().rect_.top_,
173             property_.GetBounds().rect_.width_, property_.GetBounds().rect_.height_);
174     } else {
175         WLOGFE("Failed to create displayNode, displayNode is null!");
176     }
177     RSTransaction::FlushImplicitTransaction();
178 }
179 
SetMirrorScreenType(MirrorScreenType mirrorType)180 void ScreenSession::SetMirrorScreenType(MirrorScreenType mirrorType)
181 {
182     mirrorScreenType_ = mirrorType;
183 }
184 
GetMirrorScreenType()185 MirrorScreenType ScreenSession::GetMirrorScreenType()
186 {
187     return mirrorScreenType_;
188 }
189 
SetDisplayNodeScreenId(ScreenId screenId)190 void ScreenSession::SetDisplayNodeScreenId(ScreenId screenId)
191 {
192     std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
193     if (displayNode_ != nullptr) {
194         WLOGFI("SetDisplayNodeScreenId %{public}" PRIu64"", screenId);
195         displayNode_->SetScreenId(screenId);
196     }
197 }
198 
RegisterScreenChangeListener(IScreenChangeListener * screenChangeListener)199 void ScreenSession::RegisterScreenChangeListener(IScreenChangeListener* screenChangeListener)
200 {
201     if (screenChangeListener == nullptr) {
202         WLOGFE("Failed to register screen change listener, listener is null!");
203         return;
204     }
205 
206     if (std::find(screenChangeListenerList_.begin(), screenChangeListenerList_.end(), screenChangeListener) !=
207         screenChangeListenerList_.end()) {
208         WLOGFI("Repeat to register screen change listener!");
209         return;
210     }
211 
212     screenChangeListenerList_.emplace_back(screenChangeListener);
213     if (screenState_ == ScreenState::CONNECTION) {
214         screenChangeListener->OnConnect(screenId_);
215         WLOGFI("Success to call onconnect callback.");
216     }
217     WLOGFI("Success to register screen change listener.");
218 }
219 
UnregisterScreenChangeListener(IScreenChangeListener * screenChangeListener)220 void ScreenSession::UnregisterScreenChangeListener(IScreenChangeListener* screenChangeListener)
221 {
222     if (screenChangeListener == nullptr) {
223         WLOGFE("Failed to unregister screen change listener, listener is null!");
224         return;
225     }
226 
227     screenChangeListenerList_.erase(
228         std::remove_if(screenChangeListenerList_.begin(), screenChangeListenerList_.end(),
229             [screenChangeListener](IScreenChangeListener* listener) { return screenChangeListener == listener; }),
230         screenChangeListenerList_.end());
231 }
232 
ConvertToDisplayInfo()233 sptr<DisplayInfo> ScreenSession::ConvertToDisplayInfo()
234 {
235     sptr<DisplayInfo> displayInfo = new(std::nothrow) DisplayInfo();
236     if (displayInfo == nullptr) {
237         return displayInfo;
238     }
239     displayInfo->name_ = name_;
240     displayInfo->SetWidth(property_.GetBounds().rect_.GetWidth());
241     displayInfo->SetHeight(property_.GetBounds().rect_.GetHeight());
242     displayInfo->SetPhysicalWidth(property_.GetPhyBounds().rect_.GetWidth());
243     displayInfo->SetPhysicalHeight(property_.GetPhyBounds().rect_.GetHeight());
244     displayInfo->SetScreenId(screenId_);
245     displayInfo->SetDisplayId(screenId_);
246     displayInfo->SetRefreshRate(property_.GetRefreshRate());
247     displayInfo->SetVirtualPixelRatio(property_.GetVirtualPixelRatio());
248     displayInfo->SetDensityInCurResolution(property_.GetDensityInCurResolution());
249     displayInfo->SetDefaultVirtualPixelRatio(property_.GetDefaultDensity());
250     displayInfo->SetXDpi(property_.GetXDpi());
251     displayInfo->SetYDpi(property_.GetYDpi());
252     displayInfo->SetDpi(property_.GetVirtualPixelRatio() * DOT_PER_INCH);
253     int32_t apiVersion = GetApiVersion();
254     if (apiVersion >= 14 || apiVersion == 0) { // 14 is API version
255         displayInfo->SetRotation(property_.GetDeviceRotation());
256         displayInfo->SetDisplayOrientation(property_.GetDeviceOrientation());
257     } else {
258         displayInfo->SetRotation(property_.GetScreenRotation());
259         displayInfo->SetDisplayOrientation(property_.GetDisplayOrientation());
260     }
261     displayInfo->SetOrientation(property_.GetOrientation());
262     displayInfo->SetOffsetX(property_.GetOffsetX());
263     displayInfo->SetOffsetY(property_.GetOffsetY());
264     displayInfo->SetHdrFormats(hdrFormats_);
265     displayInfo->SetColorSpaces(colorSpaces_);
266     displayInfo->SetDisplayState(property_.GetDisplayState());
267     displayInfo->SetDefaultDeviceRotationOffset(property_.GetDefaultDeviceRotationOffset());
268     displayInfo->SetAvailableWidth(property_.GetAvailableArea().width_);
269     displayInfo->SetAvailableHeight(property_.GetAvailableArea().height_);
270     displayInfo->SetScaleX(property_.GetScaleX());
271     displayInfo->SetScaleY(property_.GetScaleY());
272     displayInfo->SetPivotX(property_.GetPivotX());
273     displayInfo->SetPivotY(property_.GetPivotY());
274     displayInfo->SetTranslateX(property_.GetTranslateX());
275     displayInfo->SetTranslateY(property_.GetTranslateY());
276     return displayInfo;
277 }
278 
GetScreenSupportedColorGamuts(std::vector<ScreenColorGamut> & colorGamuts)279 DMError ScreenSession::GetScreenSupportedColorGamuts(std::vector<ScreenColorGamut>& colorGamuts)
280 {
281     auto ret = RSInterfaces::GetInstance().GetScreenSupportedColorGamuts(rsId_, colorGamuts);
282     if (ret != StatusCode::SUCCESS) {
283         WLOGE("SCB: ScreenSession::GetScreenSupportedColorGamuts fail! rsId %{public}" PRIu64", ret:%{public}d",
284             rsId_, ret);
285         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
286     }
287     WLOGI("SCB: ScreenSession::GetScreenSupportedColorGamuts ok! rsId %{public}" PRIu64", size %{public}u",
288         rsId_, static_cast<uint32_t>(colorGamuts.size()));
289 
290     return DMError::DM_OK;
291 }
292 
SetIsExtend(bool isExtend)293 void ScreenSession::SetIsExtend(bool isExtend)
294 {
295     isExtended_ = isExtend;
296 }
297 
GetIsExtend() const298 bool ScreenSession::GetIsExtend() const
299 {
300     return isExtended_;
301 }
302 
GetName()303 std::string ScreenSession::GetName()
304 {
305     return name_;
306 }
307 
SetName(std::string name)308 void ScreenSession::SetName(std::string name)
309 {
310     name_ = name;
311 }
312 
GetScreenId()313 ScreenId ScreenSession::GetScreenId()
314 {
315     return screenId_;
316 }
317 
GetRSScreenId()318 ScreenId ScreenSession::GetRSScreenId()
319 {
320     return rsId_;
321 }
322 
GetScreenProperty() const323 ScreenProperty ScreenSession::GetScreenProperty() const
324 {
325     return property_;
326 }
327 
SetScreenScale(float scaleX,float scaleY,float pivotX,float pivotY,float translateX,float translateY)328 void ScreenSession::SetScreenScale(float scaleX, float scaleY, float pivotX, float pivotY, float translateX,
329                                    float translateY)
330 {
331     property_.SetScaleX(scaleX);
332     property_.SetScaleY(scaleY);
333     property_.SetPivotX(pivotX);
334     property_.SetPivotY(pivotY);
335     property_.SetTranslateX(translateX);
336     property_.SetTranslateY(translateY);
337 }
338 
SetDefaultDeviceRotationOffset(uint32_t defaultRotationOffset)339 void ScreenSession::SetDefaultDeviceRotationOffset(uint32_t defaultRotationOffset)
340 {
341     WLOGFI("set device default rotation offset: %{public}u", defaultRotationOffset);
342     property_.SetDefaultDeviceRotationOffset(defaultRotationOffset);
343 }
344 
UpdatePropertyByActiveMode()345 void ScreenSession::UpdatePropertyByActiveMode()
346 {
347     sptr<SupportedScreenModes> mode = GetActiveScreenMode();
348     if (mode != nullptr) {
349         auto screeBounds = property_.GetBounds();
350         screeBounds.rect_.width_ = mode->width_;
351         screeBounds.rect_.height_ = mode->height_;
352         property_.SetBounds(screeBounds);
353     }
354 }
355 
UpdatePropertyByFoldControl(const ScreenProperty & updatedProperty)356 void ScreenSession::UpdatePropertyByFoldControl(const ScreenProperty& updatedProperty)
357 {
358     property_.SetDpiPhyBounds(updatedProperty.GetPhyWidth(), updatedProperty.GetPhyHeight());
359     property_.SetPhyBounds(updatedProperty.GetPhyBounds());
360     property_.SetBounds(updatedProperty.GetBounds());
361 }
362 
UpdateDisplayState(DisplayState displayState)363 void ScreenSession::UpdateDisplayState(DisplayState displayState)
364 {
365     property_.SetDisplayState(displayState);
366 }
367 
UpdateRefreshRate(uint32_t refreshRate)368 void ScreenSession::UpdateRefreshRate(uint32_t refreshRate)
369 {
370     property_.SetRefreshRate(refreshRate);
371 }
372 
GetRefreshRate()373 uint32_t ScreenSession::GetRefreshRate()
374 {
375     return property_.GetRefreshRate();
376 }
377 
UpdatePropertyByResolution(uint32_t width,uint32_t height)378 void ScreenSession::UpdatePropertyByResolution(uint32_t width, uint32_t height)
379 {
380     auto screenBounds = property_.GetBounds();
381     screenBounds.rect_.width_ = width;
382     screenBounds.rect_.height_ = height;
383     property_.SetBounds(screenBounds);
384 }
385 
GetDisplayNode() const386 std::shared_ptr<RSDisplayNode> ScreenSession::GetDisplayNode() const
387 {
388     std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
389     return displayNode_;
390 }
391 
ReleaseDisplayNode()392 void ScreenSession::ReleaseDisplayNode()
393 {
394     std::unique_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
395     displayNode_ = nullptr;
396     WLOGFI("displayNode_ is released.");
397 }
398 
Connect()399 void ScreenSession::Connect()
400 {
401     screenState_ = ScreenState::CONNECTION;
402     if (screenChangeListenerList_.empty()) {
403         WLOGFE("screenChangeListenerList is empty.");
404         return;
405     }
406     for (auto& listener : screenChangeListenerList_) {
407         listener->OnConnect(screenId_);
408     }
409 }
410 
Disconnect()411 void ScreenSession::Disconnect()
412 {
413     screenState_ = ScreenState::DISCONNECTION;
414     for (auto& listener : screenChangeListenerList_) {
415         if (!listener) {
416             continue;
417         }
418         listener->OnDisconnect(screenId_);
419     }
420 }
421 
PropertyChange(const ScreenProperty & newProperty,ScreenPropertyChangeReason reason)422 void ScreenSession::PropertyChange(const ScreenProperty& newProperty, ScreenPropertyChangeReason reason)
423 {
424     property_ = newProperty;
425     for (auto& listener : screenChangeListenerList_) {
426         if (!listener) {
427             continue;
428         }
429         listener->OnPropertyChange(newProperty, reason, screenId_);
430     }
431 }
432 
PowerStatusChange(DisplayPowerEvent event,EventStatus status,PowerStateChangeReason reason)433 void ScreenSession::PowerStatusChange(DisplayPowerEvent event, EventStatus status, PowerStateChangeReason reason)
434 {
435     for (auto& listener : screenChangeListenerList_) {
436         if (!listener) {
437             continue;
438         }
439         listener->OnPowerStatusChange(event, status, reason);
440     }
441 }
442 
ConvertRotationToFloat(Rotation sensorRotation)443 float ScreenSession::ConvertRotationToFloat(Rotation sensorRotation)
444 {
445     float rotation = 0.f;
446     switch (sensorRotation) {
447         case Rotation::ROTATION_90:
448             rotation = 90.f; // degree 90
449             break;
450         case Rotation::ROTATION_180:
451             rotation = 180.f; // degree 180
452             break;
453         case Rotation::ROTATION_270:
454             rotation = 270.f; // degree 270
455             break;
456         default:
457             rotation = 0.f;
458             break;
459     }
460     return rotation;
461 }
462 
HandleSensorRotation(float sensorRotation)463 void ScreenSession::HandleSensorRotation(float sensorRotation)
464 {
465     SensorRotationChange(sensorRotation);
466 }
467 
SensorRotationChange(Rotation sensorRotation)468 void ScreenSession::SensorRotationChange(Rotation sensorRotation)
469 {
470     float rotation = ConvertRotationToFloat(sensorRotation);
471     SensorRotationChange(rotation);
472 }
473 
SensorRotationChange(float sensorRotation)474 void ScreenSession::SensorRotationChange(float sensorRotation)
475 {
476     if (sensorRotation >= 0.0f) {
477         currentValidSensorRotation_ = sensorRotation;
478     }
479     currentSensorRotation_ = sensorRotation;
480     for (auto& listener : screenChangeListenerList_) {
481         listener->OnSensorRotationChange(sensorRotation, screenId_);
482     }
483 }
484 
HandleHoverStatusChange(int32_t hoverStatus)485 void ScreenSession::HandleHoverStatusChange(int32_t hoverStatus)
486 {
487     HoverStatusChange(hoverStatus);
488 }
489 
HoverStatusChange(int32_t hoverStatus)490 void ScreenSession::HoverStatusChange(int32_t hoverStatus)
491 {
492     for (auto& listener : screenChangeListenerList_) {
493         listener->OnHoverStatusChange(hoverStatus, screenId_);
494     }
495 }
496 
ScreenOrientationChange(Orientation orientation,FoldDisplayMode foldDisplayMode)497 void ScreenSession::ScreenOrientationChange(Orientation orientation, FoldDisplayMode foldDisplayMode)
498 {
499     Rotation rotationAfter = CalcRotation(orientation, foldDisplayMode);
500     float screenRotation = ConvertRotationToFloat(rotationAfter);
501     ScreenOrientationChange(screenRotation);
502 }
503 
ScreenOrientationChange(float orientation)504 void ScreenSession::ScreenOrientationChange(float orientation)
505 {
506     for (auto& listener : screenChangeListenerList_) {
507         listener->OnScreenOrientationChange(orientation, screenId_);
508     }
509 }
510 
ConvertIntToRotation(int rotation)511 Rotation ScreenSession::ConvertIntToRotation(int rotation)
512 {
513     Rotation targetRotation = Rotation::ROTATION_0;
514     switch (rotation) {
515         case 90: // Rotation 90 degree
516             targetRotation = Rotation::ROTATION_90;
517             break;
518         case 180: // Rotation 180 degree
519             targetRotation = Rotation::ROTATION_180;
520             break;
521         case 270: // Rotation 270 degree
522             targetRotation = Rotation::ROTATION_270;
523             break;
524         default:
525             targetRotation = Rotation::ROTATION_0;
526             break;
527     }
528     return targetRotation;
529 }
530 
SetUpdateToInputManagerCallback(std::function<void (float)> updateToInputManagerCallback)531 void ScreenSession::SetUpdateToInputManagerCallback(std::function<void(float)> updateToInputManagerCallback)
532 {
533     updateToInputManagerCallback_ = updateToInputManagerCallback;
534 }
535 
SetUpdateScreenPivotCallback(std::function<void (float,float)> && updateScreenPivotCallback)536 void ScreenSession::SetUpdateScreenPivotCallback(std::function<void(float, float)>&& updateScreenPivotCallback)
537 {
538     updateScreenPivotCallback_ = std::move(updateScreenPivotCallback);
539 }
540 
GetVirtualScreenFlag()541 VirtualScreenFlag ScreenSession::GetVirtualScreenFlag()
542 {
543     return screenFlag_;
544 }
545 
SetVirtualScreenFlag(VirtualScreenFlag screenFlag)546 void ScreenSession::SetVirtualScreenFlag(VirtualScreenFlag screenFlag)
547 {
548     screenFlag_ = screenFlag;
549 }
550 
UpdateToInputManager(RRect bounds,int rotation,int deviceRotation,FoldDisplayMode foldDisplayMode)551 void ScreenSession::UpdateToInputManager(RRect bounds, int rotation, int deviceRotation,
552     FoldDisplayMode foldDisplayMode)
553 {
554     bool needUpdateToInputManager = false;
555     if (foldDisplayMode == FoldDisplayMode::FULL && g_screenRotationOffSet == ROTATION_270 &&
556         property_.GetBounds() == bounds && property_.GetRotation() != static_cast<float>(rotation)) {
557         needUpdateToInputManager = true;
558     }
559     Rotation targetRotation = ConvertIntToRotation(rotation);
560     DisplayOrientation displayOrientation = CalcDisplayOrientation(targetRotation, foldDisplayMode);
561     property_.SetBounds(bounds);
562     property_.SetRotation(static_cast<float>(rotation));
563     property_.UpdateScreenRotation(targetRotation);
564     property_.SetDisplayOrientation(displayOrientation);
565     Rotation targetDeviceRotation = ConvertIntToRotation(deviceRotation);
566     DisplayOrientation deviceOrientation = CalcDeviceOrientation(targetDeviceRotation);
567     property_.UpdateDeviceRotation(targetDeviceRotation);
568     property_.SetDeviceOrientation(deviceOrientation);
569     if (needUpdateToInputManager && updateToInputManagerCallback_ != nullptr) {
570         // fold phone need fix 90 degree by remainder 360 degree
571         int foldRotation = (rotation + 90) % 360;
572         updateToInputManagerCallback_(static_cast<float>(foldRotation));
573         WLOGFI("updateToInputManagerCallback_:%{public}d", foldRotation);
574     }
575 }
576 
SetPhysicalRotation(int rotation)577 void ScreenSession::SetPhysicalRotation(int rotation)
578 {
579     property_.SetPhysicalRotation(static_cast<float>(rotation));
580     WLOGFI("physicalrotation :%{public}f", property_.GetPhysicalRotation());
581 }
582 
SetScreenComponentRotation(int rotation)583 void ScreenSession::SetScreenComponentRotation(int rotation)
584 {
585     property_.SetScreenComponentRotation(static_cast<float>(rotation));
586     WLOGFI("screenComponentRotation :%{public}f ", property_.GetScreenComponentRotation());
587 }
588 
UpdatePropertyAfterRotation(RRect bounds,int rotation,FoldDisplayMode foldDisplayMode)589 void ScreenSession::UpdatePropertyAfterRotation(RRect bounds, int rotation, FoldDisplayMode foldDisplayMode)
590 {
591     Rotation targetRotation = ConvertIntToRotation(rotation);
592     DisplayOrientation displayOrientation = CalcDisplayOrientation(targetRotation, foldDisplayMode);
593     property_.SetBounds(bounds);
594     property_.SetRotation(static_cast<float>(rotation));
595     property_.UpdateScreenRotation(targetRotation);
596     property_.SetDisplayOrientation(displayOrientation);
597     {
598         std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
599         if (!displayNode_) {
600             WLOGFI("update failed since null display node with rotation:%{public}d displayOrientation:%{public}u",
601                 rotation, displayOrientation);
602             return;
603         }
604     }
605     auto transactionProxy = RSTransactionProxy::GetInstance();
606     if (transactionProxy != nullptr) {
607         transactionProxy->Begin();
608         {
609             std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
610             displayNode_->SetScreenRotation(static_cast<uint32_t>(property_.GetDeviceRotation()));
611         }
612         transactionProxy->Commit();
613     } else {
614         {
615             std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
616             displayNode_->SetScreenRotation(static_cast<uint32_t>(property_.GetDeviceRotation()));
617         }
618     }
619     WLOGFI("bounds:[%{public}f %{public}f %{public}f %{public}f],rotation:%{public}d,displayOrientation:%{public}u",
620         property_.GetBounds().rect_.GetLeft(), property_.GetBounds().rect_.GetTop(),
621         property_.GetBounds().rect_.GetWidth(), property_.GetBounds().rect_.GetHeight(),
622         rotation, displayOrientation);
623     ReportNotifyModeChange(displayOrientation);
624 }
625 
UpdatePropertyOnly(RRect bounds,int rotation,FoldDisplayMode foldDisplayMode)626 void ScreenSession::UpdatePropertyOnly(RRect bounds, int rotation, FoldDisplayMode foldDisplayMode)
627 {
628     Rotation targetRotation = ConvertIntToRotation(rotation);
629     DisplayOrientation displayOrientation = CalcDisplayOrientation(targetRotation, foldDisplayMode);
630     property_.SetBounds(bounds);
631     property_.SetRotation(static_cast<float>(rotation));
632     property_.UpdateScreenRotation(targetRotation);
633     property_.SetDisplayOrientation(displayOrientation);
634     WLOGFI("bounds:[%{public}f %{public}f %{public}f %{public}f],rotation:%{public}d,displayOrientation:%{public}u",
635         property_.GetBounds().rect_.GetLeft(), property_.GetBounds().rect_.GetTop(),
636         property_.GetBounds().rect_.GetWidth(), property_.GetBounds().rect_.GetHeight(),
637         rotation, displayOrientation);
638 }
639 
UpdateRotationOrientation(int rotation)640 void ScreenSession::UpdateRotationOrientation(int rotation)
641 {
642     Rotation targetRotation = ConvertIntToRotation(rotation);
643     DisplayOrientation deviceOrientation = CalcDeviceOrientation(targetRotation);
644     property_.UpdateDeviceRotation(targetRotation);
645     property_.SetDeviceOrientation(deviceOrientation);
646     WLOGFI("rotation:%{public}d, orientation:%{public}u", rotation, deviceOrientation);
647 }
648 
ReportNotifyModeChange(DisplayOrientation displayOrientation)649 void ScreenSession::ReportNotifyModeChange(DisplayOrientation displayOrientation)
650 {
651     int32_t vhMode = 1;
652     if (displayOrientation == DisplayOrientation::PORTRAIT_INVERTED ||
653         displayOrientation == DisplayOrientation::PORTRAIT) {
654         vhMode = 0;
655     }
656     int32_t ret = HiSysEventWrite(
657         OHOS::HiviewDFX::HiSysEvent::Domain::WINDOW_MANAGER,
658         "VH_MODE",
659         OHOS::HiviewDFX::HiSysEvent::EventType::BEHAVIOR,
660         "MODE", vhMode);
661     if (ret != 0) {
662         TLOGE(WmsLogTag::DMS, "ReportNotifyModeChange Write HiSysEvent error, ret: %{public}d", ret);
663     }
664 }
665 
UpdateRotationAfterBoot(bool foldToExpand)666 void ScreenSession::UpdateRotationAfterBoot(bool foldToExpand)
667 {
668     TLOGI(WmsLogTag::DMS, "foldToExpand: %{public}d, Rotation: %{public}f",
669         static_cast<int32_t>(foldToExpand), currentSensorRotation_);
670     if (foldToExpand) {
671         SensorRotationChange(currentSensorRotation_);
672     }
673 }
674 
UpdateValidRotationToScb()675 void ScreenSession::UpdateValidRotationToScb()
676 {
677     TLOGI(WmsLogTag::DMS, "Rotation: %{public}f", currentValidSensorRotation_);
678     SensorRotationChange(currentValidSensorRotation_);
679 }
680 
GetActiveScreenMode() const681 sptr<SupportedScreenModes> ScreenSession::GetActiveScreenMode() const
682 {
683     if (activeIdx_ < 0 || activeIdx_ >= static_cast<int32_t>(modes_.size())) {
684         WLOGW("SCB: ScreenSession::GetActiveScreenMode active mode index is wrong: %{public}d", activeIdx_);
685         return nullptr;
686     }
687     return modes_[activeIdx_];
688 }
689 
GetOrientation() const690 Orientation ScreenSession::GetOrientation() const
691 {
692     return property_.GetOrientation();
693 }
694 
SetOrientation(Orientation orientation)695 void ScreenSession::SetOrientation(Orientation orientation)
696 {
697     property_.SetOrientation(orientation);
698 }
699 
GetRotation() const700 Rotation ScreenSession::GetRotation() const
701 {
702     return property_.GetScreenRotation();
703 }
704 
SetRotation(Rotation rotation)705 void ScreenSession::SetRotation(Rotation rotation)
706 {
707     property_.SetScreenRotation(rotation);
708 }
709 
SetRotationAndScreenRotationOnly(Rotation rotation)710 void ScreenSession::SetRotationAndScreenRotationOnly(Rotation rotation)
711 {
712     property_.SetRotationAndScreenRotationOnly(rotation);
713 }
714 
SetScreenRequestedOrientation(Orientation orientation)715 void ScreenSession::SetScreenRequestedOrientation(Orientation orientation)
716 {
717     property_.SetScreenRequestedOrientation(orientation);
718 }
719 
SetScreenRotationLocked(bool isLocked)720 void ScreenSession::SetScreenRotationLocked(bool isLocked)
721 {
722     isScreenLocked_ = isLocked;
723     for (auto& listener : screenChangeListenerList_) {
724         if (!listener) {
725             continue;
726         }
727         listener->OnScreenRotationLockedChange(isLocked, screenId_);
728     }
729 }
730 
SetScreenRotationLockedFromJs(bool isLocked)731 void ScreenSession::SetScreenRotationLockedFromJs(bool isLocked)
732 {
733     isScreenLocked_ = isLocked;
734 }
735 
IsScreenRotationLocked()736 bool ScreenSession::IsScreenRotationLocked()
737 {
738     return isScreenLocked_;
739 }
740 
SetTouchEnabledFromJs(bool isTouchEnabled)741 void ScreenSession::SetTouchEnabledFromJs(bool isTouchEnabled)
742 {
743     TLOGI(WmsLogTag::WMS_EVENT, "isTouchEnabled:%{public}u", static_cast<uint32_t>(isTouchEnabled));
744     touchEnabled_.store(isTouchEnabled);
745 }
746 
IsTouchEnabled()747 bool ScreenSession::IsTouchEnabled()
748 {
749     return touchEnabled_.load();
750 }
751 
GetScreenRequestedOrientation() const752 Orientation ScreenSession::GetScreenRequestedOrientation() const
753 {
754     return property_.GetScreenRequestedOrientation();
755 }
756 
SetVirtualPixelRatio(float virtualPixelRatio)757 void ScreenSession::SetVirtualPixelRatio(float virtualPixelRatio)
758 {
759     property_.SetVirtualPixelRatio(virtualPixelRatio);
760 }
761 
SetScreenSceneDpiChangeListener(const SetScreenSceneDpiFunc & func)762 void ScreenSession::SetScreenSceneDpiChangeListener(const SetScreenSceneDpiFunc& func)
763 {
764     SetScreenSceneDpiCallback_ = func;
765     TLOGI(WmsLogTag::DMS, "SetScreenSceneDpiChangeListener");
766 }
767 
SetScreenSceneDpi(float density)768 void ScreenSession::SetScreenSceneDpi(float density)
769 {
770     if (SetScreenSceneDpiCallback_ == nullptr) {
771         TLOGI(WmsLogTag::DMS, "SetScreenSceneDpiCallback_ is nullptr");
772         return;
773     }
774     SetScreenSceneDpiCallback_(density);
775 }
776 
SetScreenSceneDestroyListener(const DestroyScreenSceneFunc & func)777 void ScreenSession::SetScreenSceneDestroyListener(const DestroyScreenSceneFunc& func)
778 {
779     destroyScreenSceneCallback_ = func;
780     TLOGI(WmsLogTag::DMS, "SetScreenSceneDestroyListener");
781 }
782 
DestroyScreenScene()783 void ScreenSession::DestroyScreenScene()
784 {
785     if (destroyScreenSceneCallback_ == nullptr) {
786         TLOGI(WmsLogTag::DMS, "destroyScreenSceneCallback_ is nullptr");
787         return;
788     }
789     destroyScreenSceneCallback_();
790 }
791 
SetDensityInCurResolution(float densityInCurResolution)792 void ScreenSession::SetDensityInCurResolution(float densityInCurResolution)
793 {
794     property_.SetDensityInCurResolution(densityInCurResolution);
795 }
796 
SetScreenType(ScreenType type)797 void ScreenSession::SetScreenType(ScreenType type)
798 {
799     property_.SetScreenType(type);
800 }
801 
CalcRotation(Orientation orientation,FoldDisplayMode foldDisplayMode) const802 Rotation ScreenSession::CalcRotation(Orientation orientation, FoldDisplayMode foldDisplayMode) const
803 {
804     sptr<SupportedScreenModes> info = GetActiveScreenMode();
805     if (info == nullptr) {
806         return Rotation::ROTATION_0;
807     }
808     // vertical: phone(Plugin screen); horizontal: pad & external screen
809     bool isVerticalScreen = info->width_ < info->height_;
810     if (foldDisplayMode != FoldDisplayMode::UNKNOWN &&
811         (g_screenRotationOffSet == ROTATION_90 || g_screenRotationOffSet == ROTATION_270)) {
812         isVerticalScreen = info->width_ > info->height_;
813     }
814     switch (orientation) {
815         case Orientation::UNSPECIFIED: {
816             return Rotation::ROTATION_0;
817         }
818         case Orientation::VERTICAL: {
819             return isVerticalScreen ? Rotation::ROTATION_0 : Rotation::ROTATION_90;
820         }
821         case Orientation::HORIZONTAL: {
822             return isVerticalScreen ? Rotation::ROTATION_90 : Rotation::ROTATION_0;
823         }
824         case Orientation::REVERSE_VERTICAL: {
825             return isVerticalScreen ? Rotation::ROTATION_180 : Rotation::ROTATION_270;
826         }
827         case Orientation::REVERSE_HORIZONTAL: {
828             return isVerticalScreen ? Rotation::ROTATION_270 : Rotation::ROTATION_180;
829         }
830         default: {
831             WLOGE("unknown orientation %{public}u", orientation);
832             return Rotation::ROTATION_0;
833         }
834     }
835 }
836 
CalcDisplayOrientation(Rotation rotation,FoldDisplayMode foldDisplayMode) const837 DisplayOrientation ScreenSession::CalcDisplayOrientation(Rotation rotation, FoldDisplayMode foldDisplayMode) const
838 {
839     // vertical: phone(Plugin screen); horizontal: pad & external screen
840     bool isVerticalScreen = property_.GetPhyWidth() < property_.GetPhyHeight();
841     if (foldDisplayMode != FoldDisplayMode::UNKNOWN
842         && (g_screenRotationOffSet == ROTATION_90 || g_screenRotationOffSet == ROTATION_270)) {
843         WLOGD("foldDisplay is verticalScreen when width is greater than height");
844         isVerticalScreen = property_.GetPhyWidth() > property_.GetPhyHeight();
845     }
846     switch (rotation) {
847         case Rotation::ROTATION_0: {
848             return isVerticalScreen ? DisplayOrientation::PORTRAIT : DisplayOrientation::LANDSCAPE;
849         }
850         case Rotation::ROTATION_90: {
851             return isVerticalScreen ? DisplayOrientation::LANDSCAPE : DisplayOrientation::PORTRAIT;
852         }
853         case Rotation::ROTATION_180: {
854             return isVerticalScreen ? DisplayOrientation::PORTRAIT_INVERTED : DisplayOrientation::LANDSCAPE_INVERTED;
855         }
856         case Rotation::ROTATION_270: {
857             return isVerticalScreen ? DisplayOrientation::LANDSCAPE_INVERTED : DisplayOrientation::PORTRAIT_INVERTED;
858         }
859         default: {
860             WLOGE("unknown rotation %{public}u", rotation);
861             return DisplayOrientation::UNKNOWN;
862         }
863     }
864 }
865 
CalcDeviceOrientation(Rotation rotation) const866 DisplayOrientation ScreenSession::CalcDeviceOrientation(Rotation rotation) const
867 {
868     DisplayOrientation displayRotation = DisplayOrientation::UNKNOWN;
869     switch (rotation) {
870         case Rotation::ROTATION_0: {
871             displayRotation = DisplayOrientation::PORTRAIT;
872             break;
873         }
874         case Rotation::ROTATION_90: {
875             displayRotation = DisplayOrientation::LANDSCAPE;
876             break;
877         }
878         case Rotation::ROTATION_180: {
879             displayRotation = DisplayOrientation::PORTRAIT_INVERTED;
880             break;
881         }
882         case Rotation::ROTATION_270: {
883             displayRotation = DisplayOrientation::LANDSCAPE_INVERTED;
884             break;
885         }
886         default: {
887             WLOGE("unknown rotation %{public}u", rotation);
888         }
889     }
890     return displayRotation;
891 }
892 
GetSourceMode() const893 ScreenSourceMode ScreenSession::GetSourceMode() const
894 {
895     if (screenId_ == defaultScreenId_) {
896         return ScreenSourceMode::SCREEN_MAIN;
897     }
898     ScreenCombination combination = GetScreenCombination();
899     switch (combination) {
900         case ScreenCombination::SCREEN_MIRROR: {
901             return ScreenSourceMode::SCREEN_MIRROR;
902         }
903         case ScreenCombination::SCREEN_EXPAND: {
904             return ScreenSourceMode::SCREEN_EXTEND;
905         }
906         case ScreenCombination::SCREEN_ALONE: {
907             return ScreenSourceMode::SCREEN_ALONE;
908         }
909         case ScreenCombination::SCREEN_UNIQUE: {
910             return ScreenSourceMode::SCREEN_UNIQUE;
911         }
912         default: {
913             return ScreenSourceMode::SCREEN_ALONE;
914         }
915     }
916 }
917 
SetScreenCombination(ScreenCombination combination)918 void ScreenSession::SetScreenCombination(ScreenCombination combination)
919 {
920     combination_ = combination;
921 }
922 
GetScreenCombination() const923 ScreenCombination ScreenSession::GetScreenCombination() const
924 {
925     return combination_;
926 }
927 
FillScreenInfo(sptr<ScreenInfo> info) const928 void ScreenSession::FillScreenInfo(sptr<ScreenInfo> info) const
929 {
930     if (info == nullptr) {
931         WLOGE("FillScreenInfo failed! info is nullptr");
932         return;
933     }
934     info->SetScreenId(screenId_);
935     info->SetName(name_);
936     uint32_t width = 0;
937     uint32_t height = 0;
938     sptr<SupportedScreenModes> screenSessionModes = GetActiveScreenMode();
939     if (screenSessionModes != nullptr) {
940         height = screenSessionModes->height_;
941         width = screenSessionModes->width_;
942     }
943     float virtualPixelRatio = property_.GetVirtualPixelRatio();
944     // "< 1e-set6" means virtualPixelRatio is 0.
945     if (fabsf(virtualPixelRatio) < 1e-6) {
946         virtualPixelRatio = 1.0f;
947     }
948     ScreenSourceMode sourceMode = GetSourceMode();
949     info->SetVirtualPixelRatio(property_.GetVirtualPixelRatio());
950     info->SetVirtualHeight(height / virtualPixelRatio);
951     info->SetVirtualWidth(width / virtualPixelRatio);
952     info->SetRotation(property_.GetScreenRotation());
953     info->SetOrientation(static_cast<Orientation>(property_.GetDisplayOrientation()));
954     info->SetSourceMode(sourceMode);
955     info->SetType(property_.GetScreenType());
956     info->SetModeId(activeIdx_);
957 
958     info->lastParent_ = lastGroupSmsId_;
959     info->parent_ = groupSmsId_;
960     info->isScreenGroup_ = isScreenGroup_;
961     info->modes_ = modes_;
962 }
963 
ConvertToScreenInfo() const964 sptr<ScreenInfo> ScreenSession::ConvertToScreenInfo() const
965 {
966     sptr<ScreenInfo> info = new(std::nothrow) ScreenInfo();
967     if (info == nullptr) {
968         return nullptr;
969     }
970     FillScreenInfo(info);
971     return info;
972 }
973 
GetScreenColorGamut(ScreenColorGamut & colorGamut)974 DMError ScreenSession::GetScreenColorGamut(ScreenColorGamut& colorGamut)
975 {
976     auto ret = RSInterfaces::GetInstance().GetScreenColorGamut(rsId_, colorGamut);
977     if (ret != StatusCode::SUCCESS) {
978         WLOGE("GetScreenColorGamut fail! rsId %{public}" PRIu64"", rsId_);
979         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
980     }
981     WLOGI("GetScreenColorGamut ok! rsId %{public}" PRIu64", colorGamut %{public}u",
982         rsId_, static_cast<uint32_t>(colorGamut));
983     return DMError::DM_OK;
984 }
985 
SetScreenColorGamut(int32_t colorGamutIdx)986 DMError ScreenSession::SetScreenColorGamut(int32_t colorGamutIdx)
987 {
988     std::vector<ScreenColorGamut> colorGamuts;
989     DMError res = GetScreenSupportedColorGamuts(colorGamuts);
990     if (res != DMError::DM_OK) {
991         WLOGE("SetScreenColorGamut fail! rsId %{public}" PRIu64"", rsId_);
992         return res;
993     }
994     if (colorGamutIdx < 0 || colorGamutIdx >= static_cast<int32_t>(colorGamuts.size())) {
995         WLOGE("SetScreenColorGamut fail! rsId %{public}" PRIu64" colorGamutIdx %{public}d invalid.",
996             rsId_, colorGamutIdx);
997         return DMError::DM_ERROR_INVALID_PARAM;
998     }
999     auto ret = RSInterfaces::GetInstance().SetScreenColorGamut(rsId_, colorGamutIdx);
1000     if (ret != StatusCode::SUCCESS) {
1001         WLOGE("SetScreenColorGamut fail! rsId %{public}" PRIu64"", rsId_);
1002         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1003     }
1004     WLOGI("SetScreenColorGamut ok! rsId %{public}" PRIu64", colorGamutIdx %{public}u",
1005         rsId_, colorGamutIdx);
1006     return DMError::DM_OK;
1007 }
1008 
GetScreenGamutMap(ScreenGamutMap & gamutMap)1009 DMError ScreenSession::GetScreenGamutMap(ScreenGamutMap& gamutMap)
1010 {
1011     auto ret = RSInterfaces::GetInstance().GetScreenGamutMap(rsId_, gamutMap);
1012     if (ret != StatusCode::SUCCESS) {
1013         WLOGE("GetScreenGamutMap fail! rsId %{public}" PRIu64"", rsId_);
1014         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1015     }
1016     WLOGI("GetScreenGamutMap ok! rsId %{public}" PRIu64", gamutMap %{public}u",
1017         rsId_, static_cast<uint32_t>(gamutMap));
1018     return DMError::DM_OK;
1019 }
1020 
SetScreenGamutMap(ScreenGamutMap gamutMap)1021 DMError ScreenSession::SetScreenGamutMap(ScreenGamutMap gamutMap)
1022 {
1023     if (gamutMap > GAMUT_MAP_HDR_EXTENSION) {
1024         return DMError::DM_ERROR_INVALID_PARAM;
1025     }
1026     auto ret = RSInterfaces::GetInstance().SetScreenGamutMap(rsId_, gamutMap);
1027     if (ret != StatusCode::SUCCESS) {
1028         WLOGE("SetScreenGamutMap fail! rsId %{public}" PRIu64"", rsId_);
1029         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1030     }
1031     WLOGI("SetScreenGamutMap ok! rsId %{public}" PRIu64", gamutMap %{public}u",
1032         rsId_, static_cast<uint32_t>(gamutMap));
1033     return DMError::DM_OK;
1034 }
1035 
SetScreenColorTransform()1036 DMError ScreenSession::SetScreenColorTransform()
1037 {
1038     WLOGI("SetScreenColorTransform ok! rsId %{public}" PRIu64"", rsId_);
1039     return DMError::DM_OK;
1040 }
1041 
GetPixelFormat(GraphicPixelFormat & pixelFormat)1042 DMError ScreenSession::GetPixelFormat(GraphicPixelFormat& pixelFormat)
1043 {
1044     auto ret = RSInterfaces::GetInstance().GetPixelFormat(rsId_, pixelFormat);
1045     if (ret != StatusCode::SUCCESS) {
1046         WLOGE("GetPixelFormat fail! rsId %{public}" PRIu64, rsId_);
1047         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1048     }
1049     WLOGI("GetPixelFormat ok! rsId %{public}" PRIu64 ", pixelFormat %{public}u",
1050         rsId_, static_cast<uint32_t>(pixelFormat));
1051     return DMError::DM_OK;
1052 }
1053 
SetPixelFormat(GraphicPixelFormat pixelFormat)1054 DMError ScreenSession::SetPixelFormat(GraphicPixelFormat pixelFormat)
1055 {
1056     if (pixelFormat > GRAPHIC_PIXEL_FMT_VENDER_MASK) {
1057         return DMError::DM_ERROR_INVALID_PARAM;
1058     }
1059     auto ret = RSInterfaces::GetInstance().SetPixelFormat(rsId_, pixelFormat);
1060     if (ret != StatusCode::SUCCESS) {
1061         WLOGE("SetPixelFormat fail! rsId %{public}" PRIu64, rsId_);
1062         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1063     }
1064     WLOGI("SetPixelFormat ok! rsId %{public}" PRIu64 ", gamutMap %{public}u",
1065         rsId_, static_cast<uint32_t>(pixelFormat));
1066     return DMError::DM_OK;
1067 }
1068 
GetSupportedHDRFormats(std::vector<ScreenHDRFormat> & hdrFormats)1069 DMError ScreenSession::GetSupportedHDRFormats(std::vector<ScreenHDRFormat>& hdrFormats)
1070 {
1071     auto ret = RSInterfaces::GetInstance().GetScreenSupportedHDRFormats(rsId_, hdrFormats);
1072     if (ret != StatusCode::SUCCESS) {
1073         WLOGE("SCB: ScreenSession::GetSupportedHDRFormats fail! rsId %{public}" PRIu64 ", ret:%{public}d",
1074             rsId_, ret);
1075         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1076     }
1077     WLOGI("SCB: ScreenSession::GetSupportedHDRFormats ok! rsId %{public}" PRIu64 ", size %{public}u",
1078         rsId_, static_cast<uint32_t>(hdrFormats.size()));
1079 
1080     return DMError::DM_OK;
1081 }
1082 
GetScreenHDRFormat(ScreenHDRFormat & hdrFormat)1083 DMError ScreenSession::GetScreenHDRFormat(ScreenHDRFormat& hdrFormat)
1084 {
1085     auto ret = RSInterfaces::GetInstance().GetScreenHDRFormat(rsId_, hdrFormat);
1086     if (ret != StatusCode::SUCCESS) {
1087         WLOGE("GetScreenHDRFormat fail! rsId %{public}" PRIu64, rsId_);
1088         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1089     }
1090     WLOGI("GetScreenHDRFormat ok! rsId %{public}" PRIu64 ", colorSpace %{public}u",
1091         rsId_, static_cast<uint32_t>(hdrFormat));
1092     return DMError::DM_OK;
1093 }
1094 
SetScreenHDRFormat(int32_t modeIdx)1095 DMError ScreenSession::SetScreenHDRFormat(int32_t modeIdx)
1096 {
1097     std::vector<ScreenHDRFormat> hdrFormats;
1098     DMError res = GetSupportedHDRFormats(hdrFormats);
1099     if (res != DMError::DM_OK) {
1100         WLOGE("SetScreenHDRFormat fail! rsId %{public}" PRIu64, rsId_);
1101         return res;
1102     }
1103     if (modeIdx < 0 || modeIdx >= static_cast<int32_t>(hdrFormats.size())) {
1104         WLOGE("SetScreenHDRFormat fail! rsId %{public}" PRIu64 " modeIdx %{public}d invalid.",
1105             rsId_, modeIdx);
1106         return DMError::DM_ERROR_INVALID_PARAM;
1107     }
1108     auto ret = RSInterfaces::GetInstance().SetScreenHDRFormat(rsId_, modeIdx);
1109     if (ret != StatusCode::SUCCESS) {
1110         WLOGE("SetScreenHDRFormat fail! rsId %{public}" PRIu64, rsId_);
1111         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1112     }
1113     WLOGI("SetScreenHDRFormat ok! rsId %{public}" PRIu64 ", modeIdx %{public}u",
1114         rsId_, modeIdx);
1115     return DMError::DM_OK;
1116 }
1117 
GetSupportedColorSpaces(std::vector<GraphicCM_ColorSpaceType> & colorSpaces)1118 DMError ScreenSession::GetSupportedColorSpaces(std::vector<GraphicCM_ColorSpaceType>& colorSpaces)
1119 {
1120     auto ret = RSInterfaces::GetInstance().GetScreenSupportedColorSpaces(rsId_, colorSpaces);
1121     if (ret != StatusCode::SUCCESS) {
1122         WLOGE("SCB: ScreenSession::GetSupportedColorSpaces fail! rsId %{public}" PRIu64 ", ret:%{public}d",
1123             rsId_, ret);
1124         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1125     }
1126     WLOGI("SCB: ScreenSession::GetSupportedColorSpaces ok! rsId %{public}" PRIu64 ", size %{public}u",
1127         rsId_, static_cast<uint32_t>(colorSpaces.size()));
1128     return DMError::DM_OK;
1129 }
1130 
GetScreenColorSpace(GraphicCM_ColorSpaceType & colorSpace)1131 DMError ScreenSession::GetScreenColorSpace(GraphicCM_ColorSpaceType& colorSpace)
1132 {
1133     auto ret = RSInterfaces::GetInstance().GetScreenColorSpace(rsId_, colorSpace);
1134     if (ret != StatusCode::SUCCESS) {
1135         WLOGE("GetScreenColorSpace fail! rsId %{public}" PRIu64, rsId_);
1136         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1137     }
1138     WLOGI("GetScreenColorSpace ok! rsId %{public}" PRIu64 ", colorSpace %{public}u",
1139         rsId_, static_cast<uint32_t>(colorSpace));
1140     return DMError::DM_OK;
1141 }
1142 
SetScreenColorSpace(GraphicCM_ColorSpaceType colorSpace)1143 DMError ScreenSession::SetScreenColorSpace(GraphicCM_ColorSpaceType colorSpace)
1144 {
1145     std::vector<GraphicCM_ColorSpaceType> colorSpaces;
1146     DMError res = GetSupportedColorSpaces(colorSpaces);
1147     if (res != DMError::DM_OK) {
1148         WLOGE("SetScreenColorSpace fail! rsId %{public}" PRIu64, rsId_);
1149         return res;
1150     }
1151     if (colorSpace < 0 || static_cast<int32_t>(colorSpace) >= static_cast<int32_t>(colorSpaces.size())) {
1152         WLOGE("SetScreenColorSpace fail! rsId %{public}" PRIu64 " colorSpace %{public}d invalid.",
1153             rsId_, colorSpace);
1154         return DMError::DM_ERROR_INVALID_PARAM;
1155     }
1156     auto ret = RSInterfaces::GetInstance().SetScreenColorSpace(rsId_, colorSpace);
1157     if (ret != StatusCode::SUCCESS) {
1158         WLOGE("SetScreenColorSpace fail! rsId %{public}" PRIu64, rsId_);
1159         return DMError::DM_ERROR_RENDER_SERVICE_FAILED;
1160     }
1161     WLOGI("SetScreenColorSpace ok! rsId %{public}" PRIu64 ", colorSpace %{public}u",
1162         rsId_, colorSpace);
1163     return DMError::DM_OK;
1164 }
1165 
HasPrivateSessionForeground() const1166 bool ScreenSession::HasPrivateSessionForeground() const
1167 {
1168     return hasPrivateWindowForeground_;
1169 }
1170 
SetPrivateSessionForeground(bool hasPrivate)1171 void ScreenSession::SetPrivateSessionForeground(bool hasPrivate)
1172 {
1173     hasPrivateWindowForeground_ = hasPrivate;
1174 }
1175 
InitRSDisplayNode(RSDisplayNodeConfig & config,Point & startPoint)1176 void ScreenSession::InitRSDisplayNode(RSDisplayNodeConfig& config, Point& startPoint)
1177 {
1178     std::unique_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
1179     if (displayNode_ != nullptr) {
1180         displayNode_->SetDisplayNodeMirrorConfig(config);
1181         if (screenId_ == 0 && isFold_) {
1182             WLOGFI("Return InitRSDisplayNode foldScreen0");
1183             return;
1184         }
1185     } else {
1186         std::shared_ptr<RSDisplayNode> rsDisplayNode = RSDisplayNode::Create(config);
1187         if (rsDisplayNode == nullptr) {
1188             WLOGE("fail to add child. create rsDisplayNode fail!");
1189             return;
1190         }
1191         displayNode_ = rsDisplayNode;
1192     }
1193     WLOGFI("SetDisplayOffset: posX:%{public}d, posY:%{public}d", startPoint.posX_, startPoint.posY_);
1194     displayNode_->SetDisplayOffset(startPoint.posX_, startPoint.posY_);
1195     uint32_t width = 0;
1196     uint32_t height = 0;
1197     sptr<SupportedScreenModes> abstractScreenModes = GetActiveScreenMode();
1198     if (abstractScreenModes != nullptr) {
1199         height = abstractScreenModes->height_;
1200         width = abstractScreenModes->width_;
1201     }
1202     RSScreenType screenType;
1203     DmsXcollie dmsXcollie("DMS:InitRSDisplayNode:GetScreenType", XCOLLIE_TIMEOUT_5S);
1204     auto ret = RSInterfaces::GetInstance().GetScreenType(rsId_, screenType);
1205     if (ret == StatusCode::SUCCESS && screenType == RSScreenType::VIRTUAL_TYPE_SCREEN) {
1206         displayNode_->SetSecurityDisplay(true);
1207         WLOGFI("virtualScreen SetSecurityDisplay success");
1208     }
1209     // If setDisplayOffset is not valid for SetFrame/SetBounds
1210     WLOGFI("InitRSDisplayNode screenId:%{public}" PRIu64" width:%{public}u height:%{public}u",
1211         screenId_, width, height);
1212     displayNode_->SetFrame(0, 0, width, height);
1213     displayNode_->SetBounds(0, 0, width, height);
1214     auto transactionProxy = RSTransactionProxy::GetInstance();
1215     if (transactionProxy != nullptr) {
1216         transactionProxy->FlushImplicitTransaction();
1217     }
1218 }
1219 
ScreenSessionGroup(ScreenId screenId,ScreenId rsId,std::string name,ScreenCombination combination)1220 ScreenSessionGroup::ScreenSessionGroup(ScreenId screenId, ScreenId rsId,
1221     std::string name, ScreenCombination combination) : combination_(combination)
1222 {
1223     name_ = name;
1224     screenId_ = screenId;
1225     rsId_ = rsId;
1226     SetScreenType(ScreenType::UNDEFINED);
1227     isScreenGroup_ = true;
1228 }
1229 
~ScreenSessionGroup()1230 ScreenSessionGroup::~ScreenSessionGroup()
1231 {
1232     ReleaseDisplayNode();
1233     screenSessionMap_.clear();
1234 }
1235 
GetRSDisplayNodeConfig(sptr<ScreenSession> & screenSession,struct RSDisplayNodeConfig & config,sptr<ScreenSession> defaultScreenSession)1236 bool ScreenSessionGroup::GetRSDisplayNodeConfig(sptr<ScreenSession>& screenSession, struct RSDisplayNodeConfig& config,
1237                                                 sptr<ScreenSession> defaultScreenSession)
1238 {
1239     if (screenSession == nullptr) {
1240         WLOGE("screenSession is nullptr.");
1241         return false;
1242     }
1243     config = { screenSession->rsId_ };
1244     switch (combination_) {
1245         case ScreenCombination::SCREEN_ALONE:
1246             [[fallthrough]];
1247         case ScreenCombination::SCREEN_EXPAND:
1248             break;
1249         case ScreenCombination::SCREEN_UNIQUE:
1250             break;
1251         case ScreenCombination::SCREEN_MIRROR: {
1252             if (GetChildCount() == 0 || mirrorScreenId_ == screenSession->screenId_) {
1253                 WLOGI("SCREEN_MIRROR, config is not mirror");
1254                 break;
1255             }
1256             if (defaultScreenSession == nullptr) {
1257                 WLOGFE("defaultScreenSession is nullptr");
1258                 break;
1259             }
1260             std::shared_ptr<RSDisplayNode> displayNode = defaultScreenSession->GetDisplayNode();
1261             if (displayNode == nullptr) {
1262                 WLOGFE("displayNode is nullptr, cannot get DisplayNode");
1263                 break;
1264             }
1265             NodeId nodeId = displayNode->GetId();
1266             WLOGI("mirrorScreenId_:%{public}" PRIu64", rsId_:%{public}" PRIu64", nodeId:%{public}" PRIu64"",
1267                 mirrorScreenId_, screenSession->rsId_, nodeId);
1268             config = {screenSession->rsId_, true, nodeId, true};
1269             break;
1270         }
1271         default:
1272             WLOGE("fail to add child. invalid group combination:%{public}u", combination_);
1273             return false;
1274     }
1275     return true;
1276 }
1277 
AddChild(sptr<ScreenSession> & smsScreen,Point & startPoint,sptr<ScreenSession> defaultScreenSession)1278 bool ScreenSessionGroup::AddChild(sptr<ScreenSession>& smsScreen, Point& startPoint,
1279                                   sptr<ScreenSession> defaultScreenSession)
1280 {
1281     if (smsScreen == nullptr) {
1282         WLOGE("AddChild, smsScreen is nullptr.");
1283         return false;
1284     }
1285     ScreenId screenId = smsScreen->screenId_;
1286     auto iter = screenSessionMap_.find(screenId);
1287     if (iter != screenSessionMap_.end()) {
1288         WLOGE("AddChild, screenSessionMap_ has smsScreen:%{public}" PRIu64"", screenId);
1289         return false;
1290     }
1291     struct RSDisplayNodeConfig config;
1292     if (!GetRSDisplayNodeConfig(smsScreen, config, defaultScreenSession)) {
1293         return false;
1294     }
1295     smsScreen->InitRSDisplayNode(config, startPoint);
1296     smsScreen->lastGroupSmsId_ = smsScreen->groupSmsId_;
1297     smsScreen->groupSmsId_ = screenId_;
1298     screenSessionMap_.insert(std::make_pair(screenId, std::make_pair(smsScreen, startPoint)));
1299     return true;
1300 }
1301 
AddChildren(std::vector<sptr<ScreenSession>> & smsScreens,std::vector<Point> & startPoints)1302 bool ScreenSessionGroup::AddChildren(std::vector<sptr<ScreenSession>>& smsScreens, std::vector<Point>& startPoints)
1303 {
1304     size_t size = smsScreens.size();
1305     if (size != startPoints.size()) {
1306         WLOGE("AddChildren, unequal size.");
1307         return false;
1308     }
1309     bool res = true;
1310     for (size_t i = 0; i < size; i++) {
1311         res = AddChild(smsScreens[i], startPoints[i], nullptr) && res;
1312     }
1313     return res;
1314 }
1315 
RemoveChild(sptr<ScreenSession> & smsScreen)1316 bool ScreenSessionGroup::RemoveChild(sptr<ScreenSession>& smsScreen)
1317 {
1318     if (smsScreen == nullptr) {
1319         WLOGE("RemoveChild, smsScreen is nullptr.");
1320         return false;
1321     }
1322     ScreenId screenId = smsScreen->screenId_;
1323     smsScreen->lastGroupSmsId_ = smsScreen->groupSmsId_;
1324     smsScreen->groupSmsId_ = SCREEN_ID_INVALID;
1325     std::shared_ptr<RSDisplayNode> displayNode = smsScreen->GetDisplayNode();
1326     if (displayNode != nullptr) {
1327         displayNode->SetDisplayOffset(0, 0);
1328         displayNode->RemoveFromTree();
1329         smsScreen->ReleaseDisplayNode();
1330     }
1331     displayNode = nullptr;
1332     // attention: make sure reference count 0
1333     RSTransaction::FlushImplicitTransaction();
1334     return screenSessionMap_.erase(screenId);
1335 }
1336 
HasChild(ScreenId childScreen) const1337 bool ScreenSessionGroup::HasChild(ScreenId childScreen) const
1338 {
1339     return screenSessionMap_.find(childScreen) != screenSessionMap_.end();
1340 }
1341 
GetChildren() const1342 std::vector<sptr<ScreenSession>> ScreenSessionGroup::GetChildren() const
1343 {
1344     std::vector<sptr<ScreenSession>> res;
1345     for (auto iter = screenSessionMap_.begin(); iter != screenSessionMap_.end(); iter++) {
1346         res.push_back(iter->second.first);
1347     }
1348     return res;
1349 }
1350 
GetChildrenPosition() const1351 std::vector<Point> ScreenSessionGroup::GetChildrenPosition() const
1352 {
1353     std::vector<Point> res;
1354     for (auto iter = screenSessionMap_.begin(); iter != screenSessionMap_.end(); iter++) {
1355         res.push_back(iter->second.second);
1356     }
1357     return res;
1358 }
1359 
GetChildPosition(ScreenId screenId) const1360 Point ScreenSessionGroup::GetChildPosition(ScreenId screenId) const
1361 {
1362     Point point;
1363     auto iter = screenSessionMap_.find(screenId);
1364     if (iter != screenSessionMap_.end()) {
1365         point = iter->second.second;
1366     }
1367     return point;
1368 }
1369 
GetChildCount() const1370 size_t ScreenSessionGroup::GetChildCount() const
1371 {
1372     return screenSessionMap_.size();
1373 }
1374 
GetScreenCombination() const1375 ScreenCombination ScreenSessionGroup::GetScreenCombination() const
1376 {
1377     return combination_;
1378 }
1379 
ConvertToScreenGroupInfo() const1380 sptr<ScreenGroupInfo> ScreenSessionGroup::ConvertToScreenGroupInfo() const
1381 {
1382     sptr<ScreenGroupInfo> screenGroupInfo = new(std::nothrow) ScreenGroupInfo();
1383     if (screenGroupInfo == nullptr) {
1384         return nullptr;
1385     }
1386     FillScreenInfo(screenGroupInfo);
1387     screenGroupInfo->combination_ = combination_;
1388     for (auto iter = screenSessionMap_.begin(); iter != screenSessionMap_.end(); iter++) {
1389         screenGroupInfo->children_.push_back(iter->first);
1390     }
1391     auto positions = GetChildrenPosition();
1392     screenGroupInfo->position_.insert(screenGroupInfo->position_.end(), positions.begin(), positions.end());
1393     return screenGroupInfo;
1394 }
1395 
SetDisplayBoundary(const RectF & rect,const uint32_t & offsetY)1396 void ScreenSession::SetDisplayBoundary(const RectF& rect, const uint32_t& offsetY)
1397 {
1398     property_.SetOffsetY(offsetY);
1399     property_.SetBounds(RRect(rect, 0.0f, 0.0f));
1400 }
1401 
Resize(uint32_t width,uint32_t height)1402 void ScreenSession::Resize(uint32_t width, uint32_t height)
1403 {
1404     sptr<SupportedScreenModes> screenMode = GetActiveScreenMode();
1405     if (screenMode != nullptr) {
1406         screenMode->width_ = width;
1407         screenMode->height_ = height;
1408         UpdatePropertyByActiveMode();
1409         {
1410             std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
1411             if (displayNode_ == nullptr) {
1412                 WLOGFE("displayNode_ is null, resize failed");
1413                 return;
1414             }
1415             displayNode_->SetFrame(0, 0, static_cast<float>(width), static_cast<float>(height));
1416             displayNode_->SetBounds(0, 0, static_cast<float>(width), static_cast<float>(height));
1417         }
1418         RSTransaction::FlushImplicitTransaction();
1419     }
1420 }
1421 
UpdateAvailableArea(DMRect area)1422 bool ScreenSession::UpdateAvailableArea(DMRect area)
1423 {
1424     if (property_.GetAvailableArea() == area) {
1425         return false;
1426     }
1427     property_.SetAvailableArea(area);
1428     return true;
1429 }
1430 
SetAvailableArea(DMRect area)1431 void ScreenSession::SetAvailableArea(DMRect area)
1432 {
1433     property_.SetAvailableArea(area);
1434 }
1435 
GetAvailableArea()1436 DMRect ScreenSession::GetAvailableArea()
1437 {
1438     return property_.GetAvailableArea();
1439 }
1440 
SetFoldScreen(bool isFold)1441 void ScreenSession::SetFoldScreen(bool isFold)
1442 {
1443     WLOGFI("SetFoldScreen %{public}u", isFold);
1444     isFold_ = isFold;
1445 }
1446 
SetHdrFormats(std::vector<uint32_t> && hdrFormats)1447 void ScreenSession::SetHdrFormats(std::vector<uint32_t>&& hdrFormats)
1448 {
1449     hdrFormats_ = std::move(hdrFormats);
1450 }
1451 
SetColorSpaces(std::vector<uint32_t> && colorSpaces)1452 void ScreenSession::SetColorSpaces(std::vector<uint32_t>&& colorSpaces)
1453 {
1454     colorSpaces_ = std::move(colorSpaces);
1455 }
1456 
GetScreenSnapshot(float scaleX,float scaleY)1457 std::shared_ptr<Media::PixelMap> ScreenSession::GetScreenSnapshot(float scaleX, float scaleY)
1458 {
1459     {
1460         std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
1461         if (displayNode_ == nullptr) {
1462             WLOGFE("get screen snapshot displayNode_ is null");
1463             return nullptr;
1464         }
1465     }
1466 
1467     HITRACE_METER_FMT(HITRACE_TAG_WINDOW_MANAGER, "ss:GetScreenSnapshot");
1468     auto callback = std::make_shared<SurfaceCaptureFuture>();
1469     RSSurfaceCaptureConfig config = {
1470         .scaleX = scaleX,
1471         .scaleY = scaleY,
1472     };
1473     {
1474         DmsXcollie dmsXcollie("DMS:GetScreenSnapshot:TakeSurfaceCapture", XCOLLIE_TIMEOUT_5S);
1475         std::shared_lock<std::shared_mutex> displayNodeLock(displayNodeMutex_);
1476         bool ret = RSInterfaces::GetInstance().TakeSurfaceCapture(displayNode_, callback, config);
1477         if (!ret) {
1478             WLOGFE("get screen snapshot TakeSurfaceCapture failed");
1479             return nullptr;
1480         }
1481     }
1482 
1483     auto pixelMap = callback->GetResult(2000);
1484     if (pixelMap != nullptr) {
1485         WLOGFD("save pixelMap WxH = %{public}dx%{public}d", pixelMap->GetWidth(), pixelMap->GetHeight());
1486     } else {
1487         WLOGFE("failed to get pixelMap, return nullptr");
1488     }
1489     return pixelMap;
1490 }
1491 
ScreenCaptureNotify(ScreenId mainScreenId,int32_t uid,const std::string & clientName)1492 void ScreenSession::ScreenCaptureNotify(ScreenId mainScreenId, int32_t uid, const std::string& clientName)
1493 {
1494     for (auto& listener : screenChangeListenerList_) {
1495         if (!listener) {
1496             continue;
1497         }
1498         listener->OnScreenCaptureNotify(mainScreenId, uid, clientName);
1499     }
1500 }
1501 
GetApiVersion()1502 int32_t ScreenSession::GetApiVersion()
1503 {
1504     static std::chrono::steady_clock::time_point lastReauestTime = std::chrono::steady_clock::now();
1505     auto currentTime = std::chrono::steady_clock::now();
1506     auto interval = std::chrono::duration_cast<std::chrono::microseconds>(currentTime - lastReauestTime).count();
1507     int32_t apiVersion = NO_EXIT_UID_VERSION;
1508     int32_t currentPid = IPCSkeleton::GetCallingPid();
1509     if (interval < MAX_INTERVAL_US) {
1510         apiVersion = g_uidVersionMap.Get(currentPid);
1511     }
1512     if (apiVersion == NO_EXIT_UID_VERSION) {
1513         apiVersion = static_cast<int32_t>(SysCapUtil::GetApiCompatibleVersion());
1514         WLOGFI("Get version from IPC");
1515         g_uidVersionMap.Set(currentPid, apiVersion);
1516     }
1517     lastReauestTime = currentTime;
1518     return apiVersion;
1519 }
1520 } // namespace OHOS::Rosen
1521