1 /*
2  * Copyright (c) 2021-2024 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 "pointer_drawing_manager.h"
17 
18 #include <parameters.h>
19 
20 #include "image/bitmap.h"
21 #include "image_source.h"
22 #include "image_type.h"
23 #include "image_utils.h"
24 #include "table_dump.h"
25 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
26 #include "magic_pointer_drawing_manager.h"
27 #include "magic_pointer_velocity_tracker.h"
28 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
29 
30 #include "define_multimodal.h"
31 #include "i_multimodal_input_connect.h"
32 #include "input_device_manager.h"
33 #include "i_input_windows_manager.h"
34 #include "ipc_skeleton.h"
35 #include "mmi_log.h"
36 #include "i_preference_manager.h"
37 #include "parameters.h"
38 #include "pipeline/rs_recording_canvas.h"
39 #include "preferences.h"
40 #include "preferences_errno.h"
41 #include "preferences_helper.h"
42 #include "render/rs_pixel_map_util.h"
43 #include "scene_board_judgement.h"
44 #include "setting_datashare.h"
45 #include "util.h"
46 #include "dfx_hisysevent.h"
47 #include "timer_manager.h"
48 
49 #undef MMI_LOG_DOMAIN
50 #define MMI_LOG_DOMAIN MMI_LOG_CURSOR
51 #undef MMI_LOG_TAG
52 #define MMI_LOG_TAG "PointerDrawingManager"
53 #define FOCUS_COORDINATES(FOCUS_COORDINATES_, CHANGE) float FOCUS_COORDINATES_##CHANGE
54 #define CALCULATE_CANVAS_SIZE(CALCULATE_CANVAS_SIZE_, CHANGE) float CALCULATE_CANVAS_SIZE_##CHANGE
55 
56 namespace OHOS {
57 namespace MMI {
58 namespace {
59 const std::string FOLD_SCREEN_FLAG = system::GetParameter("const.window.foldscreen.type", "");
60 const std::string IMAGE_POINTER_DEFAULT_PATH = "/system/etc/multimodalinput/mouse_icon/";
61 const std::string DefaultIconPath = IMAGE_POINTER_DEFAULT_PATH + "Default.svg";
62 const std::string CursorIconPath = IMAGE_POINTER_DEFAULT_PATH + "Cursor_Circle.png";
63 const std::string POINTER_COLOR { "pointerColor" };
64 const std::string POINTER_SIZE { "pointerSize" };
65 const std::string MAGIC_POINTER_COLOR { "magicPointerColor" };
66 const std::string MAGIC_POINTER_SIZE { "magicPointerSize"};
67 const std::string POINTER_CURSOR_RENDER_RECEIVER_NAME { "PointerCursorReceiver" };
68 const std::string DEVICE_TYPE_HARDEN { "HAD" };
69 const int32_t ROTATE_POLICY = system::GetIntParameter("const.window.device.rotate_policy", 0);
70 const std::string FOLDABLE_DEVICE_POLICY = system::GetParameter("const.window.foldabledevice.rotate_policy", "");
71 constexpr int32_t WINDOW_ROTATE { 0 };
72 constexpr char ROTATE_WINDOW_ROTATE { '0' };
73 constexpr int32_t FOLDABLE_DEVICE { 2 };
74 constexpr int32_t BASELINE_DENSITY { 160 };
75 constexpr int32_t CALCULATE_MIDDLE { 2 };
76 [[ maybe_unused ]] constexpr int32_t MAGIC_INDEPENDENT_PIXELS { 30 };
77 constexpr int32_t DEVICE_INDEPENDENT_PIXELS { 40 };
78 constexpr int32_t POINTER_WINDOW_INIT_SIZE { 64 };
79 constexpr int32_t DEFAULT_POINTER_SIZE { 1 };
80 constexpr int32_t MIN_POINTER_SIZE { 1 };
81 constexpr int32_t MAX_POINTER_SIZE { 7 };
82 constexpr int32_t DEFAULT_VALUE { -1 };
83 constexpr int32_t ANIMATION_DURATION { 500 };
84 constexpr int32_t DEFAULT_POINTER_STYLE { 0 };
85 constexpr int32_t CURSOR_CIRCLE_STYLE { 41 };
86 constexpr int32_t MOUSE_ICON_BAIS { 5 };
87 constexpr int32_t VISIBLE_LIST_MAX_SIZE { 100 };
88 [[ maybe_unused ]] constexpr int32_t WAIT_TIME_FOR_MAGIC_CURSOR { 6000 };
89 constexpr float ROTATION_ANGLE { 360.f };
90 constexpr float LOADING_CENTER_RATIO { 0.5f };
91 constexpr float RUNNING_X_RATIO { 0.3f };
92 constexpr float RUNNING_Y_RATIO { 0.675f };
93 constexpr float INCREASE_RATIO { 1.22f };
94 constexpr float ROTATION_ANGLE90 { 90.f };
95 constexpr int32_t MIN_POINTER_COLOR { 0x000000 };
96 constexpr int32_t MAX_POINTER_COLOR { 0x00ffffff };
97 constexpr int32_t MIN_CURSOR_SIZE { 64 };
98 constexpr uint32_t RGB_CHANNEL_BITS_LENGTH { 24 };
99 constexpr float MAX_ALPHA_VALUE { 255.f };
100 constexpr int32_t MOUSE_STYLE_OPT { 0 };
101 constexpr int32_t MAGIC_STYLE_OPT { 1 };
102 constexpr size_t RETRY_TIMES { 3 };
103 const std::string MOUSE_FILE_NAME { "mouse_settings.xml" };
104 bool g_isRsRemoteDied { false };
105 bool g_isHdiRemoteDied { false };
106 bool g_isReStartVsync { false };
107 constexpr uint64_t FOLD_SCREEN_ID_FULL { 0 };
108 constexpr uint64_t FOLD_SCREEN_ID_MAIN { 5 };
109 constexpr float IMAGE_PIXEL { 0.0f };
110 constexpr float CALCULATE_IMAGE_MIDDLE { 2.0f };
111 constexpr int32_t QUEUE_SIZE { 5 };
112 constexpr int32_t DYNAMIC_ROTATION_ANGLE { 12 };
113 constexpr float CALCULATE_MOUSE_ICON_BAIS { 5.0f };
114 constexpr int32_t SYNC_FENCE_WAIT_TIME { 3000 };
115 float g_hardwareCanvasSize = { 512.0f };
116 float g_focalPoint = { 256.0f };
117 } // namespace
118 } // namespace MMI
119 } // namespace OHOS
120 
121 namespace OHOS {
122 namespace MMI {
123 
IsSingleDisplayFoldDevice()124 static bool IsSingleDisplayFoldDevice()
125 {
126     return (!FOLD_SCREEN_FLAG.empty() && FOLD_SCREEN_FLAG[0] == '1');
127 }
128 
RsRemoteDiedCallback()129 void RsRemoteDiedCallback()
130 {
131     CALL_INFO_TRACE;
132     g_isRsRemoteDied = true;
133     g_isHdiRemoteDied = true;
134     g_isReStartVsync = true;
135 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
136     MAGIC_CURSOR->RsRemoteDiedCallbackForMagicCursor();
137 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
138     IPointerDrawingManager::GetInstance()->DestroyPointerWindow();
139 }
140 
InitPointerCallback()141 void PointerDrawingManager::InitPointerCallback()
142 {
143     MMI_HILOGI("Init RS Callback start");
144     g_isRsRemoteDied = false;
145     Rosen::OnRemoteDiedCallback callback = RsRemoteDiedCallback;
146     Rosen::RSInterfaces::GetInstance().SetOnRemoteDiedCallback(callback);
147 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
148     if (HasMagicCursor() && surfaceNode_ != nullptr) {
149         surfaceNode_ = nullptr;
150         MAGIC_CURSOR->RsRemoteInitCallbackForMagicCursor();
151     }
152 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
153 }
154 
DestroyPointerWindow()155 void PointerDrawingManager::DestroyPointerWindow()
156 {
157     CALL_INFO_TRACE;
158     CHKPV(delegateProxy_);
159     delegateProxy_->OnPostSyncTask([this] {
160         if (surfaceNode_ != nullptr) {
161             MMI_HILOGI("Pointer window destroy start");
162             g_isRsRemoteDied = false;
163             surfaceNode_->DetachToDisplay(screenId_);
164             surfaceNode_ = nullptr;
165             Rosen::RSTransaction::FlushImplicitTransaction();
166             MMI_HILOGI("Pointer window destroy success");
167         }
168         return RET_OK;
169     });
170 }
171 
IsNum(const std::string &str)172 static inline bool IsNum(const std::string &str)
173 {
174     std::istringstream sin(str);
175     double num;
176     return (sin >> num) && sin.eof();
177 }
178 
GetCanvasSize()179 static float GetCanvasSize()
180 {
181     auto ret = system::GetParameter("rosen.multimodalinput.pc.setcanvassize", "512.0");
182     if (IsNum(ret)) {
183         return g_hardwareCanvasSize;
184     }
185     return std::atoi(ret.c_str());
186 }
187 
GetFocusCoordinates()188 static float GetFocusCoordinates()
189 {
190     auto ret = system::GetParameter("rosen.multimodalinput.pc.setfocuscoordinates", "256.0");
191     if (IsNum(ret)) {
192         return g_focalPoint;
193     }
194     return std::atoi(ret.c_str());
195 }
196 
PointerDrawingManager()197 PointerDrawingManager::PointerDrawingManager()
198 {
199 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
200     MMI_HILOGI("magiccurosr InitStyle");
201     hasMagicCursor_.name = "isMagicCursor";
202     MAGIC_CURSOR->InitStyle();
203 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
204     InitStyle();
205 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
206     hardwareCursorPointerManager_ = std::make_shared<HardwareCursorPointerManager>();
207     g_hardwareCanvasSize = GetCanvasSize();
208     g_focalPoint = GetFocusCoordinates();
209 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
210 }
211 
~PointerDrawingManager()212 PointerDrawingManager::~PointerDrawingManager()
213 {
214 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
215     if (runner_ != nullptr) {
216         runner_->Stop();
217     }
218     if ((renderThread_ != nullptr) && renderThread_->joinable()) {
219         renderThread_->join();
220     }
221 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
222 }
223 
GetLastMouseStyle()224 PointerStyle PointerDrawingManager::GetLastMouseStyle()
225 {
226     CALL_DEBUG_ENTER;
227     return lastMouseStyle_;
228 }
229 
CalculateHardwareXOffset(ICON_TYPE iconType)230 float PointerDrawingManager::CalculateHardwareXOffset(ICON_TYPE iconType)
231 {
232     int32_t width = imageWidth_;
233     int32_t userIconHotSpotX = 0;
234 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
235     if (hardwareCursorPointerManager_->IsSupported() &&
236         currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
237         width = cursorWidth_;
238         userIconHotSpotX = userIconHotSpotX_;
239     }
240 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
241     switch (iconType) {
242         case ANGLE_E:
243             return g_focalPoint;
244         case ANGLE_S:
245             return (g_focalPoint - (width / CALCULATE_IMAGE_MIDDLE));
246         case ANGLE_W:
247             return (g_focalPoint - width);
248         case ANGLE_N:
249             return (g_focalPoint - (width / CALCULATE_IMAGE_MIDDLE));
250         case ANGLE_SE:
251             return (g_focalPoint - width);
252         case ANGLE_NE:
253             return (g_focalPoint - width);
254         case ANGLE_SW:
255             return g_focalPoint;
256         case ANGLE_NW:
257             return g_focalPoint - userIconHotSpotX;
258         case ANGLE_CENTER:
259             return (g_focalPoint - (width / CALCULATE_IMAGE_MIDDLE));
260         case ANGLE_NW_RIGHT:
261             return g_focalPoint - CALCULATE_MOUSE_ICON_BAIS;
262         default:
263             MMI_HILOGW("No need calculate physicalX offset, iconType:%{public}d", iconType);
264             return g_focalPoint;
265     }
266 }
267 
CalculateHardwareYOffset(ICON_TYPE iconType)268 float PointerDrawingManager::CalculateHardwareYOffset(ICON_TYPE iconType)
269 {
270     int32_t height = imageHeight_;
271     int32_t userIconHotSpotY = 0;
272 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
273     if (hardwareCursorPointerManager_->IsSupported() &&
274         currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
275         height = cursorHeight_;
276         userIconHotSpotY = userIconHotSpotY_;
277     }
278 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
279     switch (iconType) {
280         case ANGLE_E:
281             return (g_focalPoint - (height / CALCULATE_IMAGE_MIDDLE));
282         case ANGLE_S:
283             return g_focalPoint;
284         case ANGLE_W:
285             return (g_focalPoint - height);
286         case ANGLE_N:
287             return (g_focalPoint - height);
288         case ANGLE_SE:
289             return (g_focalPoint - height);
290         case ANGLE_NE:
291             return g_focalPoint;
292         case ANGLE_SW:
293             return (g_focalPoint - height);
294         case ANGLE_NW:
295             return g_focalPoint - userIconHotSpotY;
296         case ANGLE_CENTER:
297             return (g_focalPoint - (height / CALCULATE_IMAGE_MIDDLE));
298         case ANGLE_NW_RIGHT:
299             return g_focalPoint;
300         default:
301             MMI_HILOGW("No need calculate physicalY offset, iconType:%{public}d", iconType);
302             return g_focalPoint;
303     }
304 }
305 
306 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
SetDynamicHardWareCursorLocation(int32_t physicalX, int32_t physicalY, MOUSE_ICON mouseStyle)307 bool PointerDrawingManager::SetDynamicHardWareCursorLocation
308     (int32_t physicalX, int32_t physicalY, MOUSE_ICON mouseStyle)
309 {
310     CHKPF(hardwareCursorPointerManager_);
311     CHKPF(surfaceNode_);
312     if (g_isHdiRemoteDied) {
313         hardwareCursorPointerManager_->SetHdiServiceState(false);
314     }
315     ICON_TYPE iconType = ICON_TYPE::ANGLE_NW;
316     if (mouseStyle == MOUSE_ICON::LOADING) {
317         iconType = ICON_TYPE::ANGLE_CENTER;
318     } else {
319         iconType = ICON_TYPE::ANGLE_NW;
320     }
321     if (hardwareCursorPointerManager_->IsSupported()) {
322     surfaceNode_->SetBounds((physicalX - CalculateHardwareXOffset(iconType)), (physicalY -
323         CalculateHardwareYOffset(iconType)), g_hardwareCanvasSize, g_hardwareCanvasSize);
324     }
325     Rosen::RSTransaction::FlushImplicitTransaction();
326     return true;
327 }
328 
PostTaskRSLocation(int32_t physicalX, int32_t physicalY, std::shared_ptr<Rosen::RSSurfaceNode> surfaceNode)329 void PointerDrawingManager::PostTaskRSLocation(int32_t physicalX, int32_t physicalY,
330     std::shared_ptr<Rosen::RSSurfaceNode> surfaceNode)
331 {
332     hardwareCanvasSize_ = g_hardwareCanvasSize;
333     PostTask([this, physicalX, physicalY, surfaceNode]() -> void {
334         CHKPV(surfaceNode);
335         surfaceNode->SetBounds(physicalX, physicalY, hardwareCanvasSize_, hardwareCanvasSize_);
336         Rosen::RSTransaction::FlushImplicitTransaction();
337     });
338 }
339 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
340 
SetTraditionsHardWareCursorLocation(int32_t displayId, int32_t physicalX, int32_t physicalY, ICON_TYPE iconType)341 bool PointerDrawingManager::SetTraditionsHardWareCursorLocation(int32_t displayId, int32_t physicalX,
342     int32_t physicalY, ICON_TYPE iconType)
343 {
344     bool magicCursorSetBounds = false;
345     if (UpdateSurfaceNodeBounds(physicalX, physicalY) == RET_OK) {
346         magicCursorSetBounds = true;
347         Rosen::RSTransaction::FlushImplicitTransaction();
348     }
349 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
350     CHKPF(hardwareCursorPointerManager_);
351     CHKPF(surfaceNode_);
352     if (g_isHdiRemoteDied) {
353         hardwareCursorPointerManager_->SetHdiServiceState(false);
354     }
355     if (hardwareCursorPointerManager_->IsSupported() && (hasLoadingPointerStyle_ || hasHardwareCursorAnimate_)) {
356         if (hardwareCursorPointerManager_->SetPosition((physicalX -
357             CalculateHardwareXOffset(iconType)), (physicalY -
358             CalculateHardwareYOffset(iconType))) != RET_OK) {
359             MMI_HILOGE("Set hardware cursor position fail");
360             return false;
361         }
362         return true;
363     }
364     if (!magicCursorSetBounds) {
365         if (hardwareCursorPointerManager_->IsSupported()) {
366             // Change the coordinates issued by RS to asynchronous,
367             // without blocking the issuance of HardwareCursor coordinates.
368             PostTaskRSLocation((physicalX - CalculateHardwareXOffset(iconType)), (physicalY -
369                 CalculateHardwareYOffset(iconType)), surfaceNode_);
370         } else {
371             surfaceNode_->SetBounds(physicalX, physicalY, surfaceNode_->GetStagingProperties().GetBounds().z_,
372                 surfaceNode_->GetStagingProperties().GetBounds().w_);
373             Rosen::RSTransaction::FlushImplicitTransaction();
374         }
375     }
376 #else
377     if (!magicCursorSetBounds) {
378         surfaceNode_->SetBounds(physicalX, physicalY,
379             surfaceNode_->GetStagingProperties().GetBounds().z_, surfaceNode_->GetStagingProperties().GetBounds().w_);
380         Rosen::RSTransaction::FlushImplicitTransaction();
381     }
382 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
383 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
384     CHKPF(hardwareCursorPointerManager_);
385     hardwareCursorPointerManager_->SetTargetDevice(displayId);
386     if (hardwareCursorPointerManager_->IsSupported()) {
387         if (hardwareCursorPointerManager_->SetPosition((physicalX - CalculateHardwareXOffset(
388             iconType)), (physicalY - CalculateHardwareYOffset(iconType))) != RET_OK) {
389             MMI_HILOGE("Set hardware cursor position error");
390         }
391     }
392 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
393     return true;
394 }
395 
ForceClearPointerVisiableStatus()396 void PointerDrawingManager::ForceClearPointerVisiableStatus()
397 {
398     MMI_HILOGI("force clear all pointer visiable status");
399     pidInfos_.clear();
400     UpdatePointerVisible();
401 }
402 
SetSurfaceNodeVisible(bool visible)403 void PointerDrawingManager::SetSurfaceNodeVisible(bool visible)
404 {
405 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
406     CHKPV(hardwareCursorPointerManager_);
407     CHKPV(surfaceNode_);
408     if (!hardwareCursorPointerManager_->IsSupported()) {
409         surfaceNode_->SetVisible(visible);
410     }
411 #else
412     surfaceNode_->SetVisible(visible);
413 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
414 }
415 
DrawMovePointer(int32_t displayId, int32_t physicalX, int32_t physicalY, PointerStyle pointerStyle, Direction direction)416 int32_t PointerDrawingManager::DrawMovePointer(int32_t displayId, int32_t physicalX, int32_t physicalY,
417     PointerStyle pointerStyle, Direction direction)
418 {
419     CHKPR(surfaceNode_, RET_ERR);
420     MMI_HILOGD("Pointer window move success, pointerStyle id: %{public}d", pointerStyle.id);
421     displayId_ = displayId;
422 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
423     bool cursorEnlarged = MAGIC_POINTER_VELOCITY_TRACKER->GetCursorEnlargedStatus();
424     if (cursorEnlarged) {
425         MAGIC_POINTER_VELOCITY_TRACKER->SetLastPointerStyle(pointerStyle);
426         MAGIC_POINTER_VELOCITY_TRACKER->SetDirection(direction);
427         if (pointerStyle.id != MOUSE_ICON::DEFAULT && pointerStyle.id != MOUSE_ICON::CROSS) {
428             pointerStyle.id = MOUSE_ICON::DEFAULT;
429         }
430     }
431 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
432 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
433     UpdateBindDisplayId(displayId);
434 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
435     if (lastMouseStyle_ == pointerStyle && !mouseIconUpdate_ && lastDirection_ == direction) {
436         if (!SetTraditionsHardWareCursorLocation(displayId, physicalX, physicalY,
437             ICON_TYPE(mouseIcons_[MOUSE_ICON(pointerStyle.id)].alignmentWay))) {
438             return RET_ERR;
439         }
440         MMI_HILOGD("The lastpointerStyle is equal with pointerStyle, id:%{public}d, size:%{public}d",
441             pointerStyle.id, pointerStyle.size);
442         return RET_OK;
443     }
444     if (lastDirection_ != direction) {
445         RotateDegree(direction);
446         lastDirection_ = direction;
447     }
448     lastMouseStyle_ = pointerStyle;
449     SetSurfaceNodeVisible(false);
450     if (InitLayer(MOUSE_ICON(lastMouseStyle_.id)) != RET_OK) {
451         mouseIconUpdate_ = false;
452         MMI_HILOGE("Init layer failed");
453         return RET_ERR;
454     }
455     SetSurfaceNodeVisible(true);
456     if (!SetTraditionsHardWareCursorLocation(displayId, physicalX, physicalY,
457         ICON_TYPE(mouseIcons_[MOUSE_ICON(lastMouseStyle_.id)].alignmentWay))) {
458         MMI_HILOGE("Set traditions hardware cursor location error");
459         return RET_ERR;
460     }
461     UpdatePointerVisible();
462     mouseIconUpdate_ = false;
463     MMI_HILOGD("Leave, display:%{public}d, physicalX:%{public}d, physicalY:%{public}d",
464         displayId, physicalX, physicalY);
465     return RET_OK;
466 }
467 
UpdateSurfaceNodeBounds(int32_t physicalX, int32_t physicalY)468 int32_t PointerDrawingManager::UpdateSurfaceNodeBounds(int32_t physicalX, int32_t physicalY)
469 {
470 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
471     if (HasMagicCursor()) {
472         if (currentMouseStyle_.id == DEVELOPER_DEFINED_ICON) {
473             surfaceNode_->SetBounds(physicalX, physicalY,
474                 canvasWidth_, canvasHeight_);
475         } else {
476             surfaceNode_->SetBounds(physicalX, physicalY,
477                 imageWidth_, imageHeight_);
478         }
479         return RET_OK;
480     }
481 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
482     return RET_ERR;
483 }
484 
DrawMovePointer(int32_t displayId, int32_t physicalX, int32_t physicalY)485 void PointerDrawingManager::DrawMovePointer(int32_t displayId, int32_t physicalX, int32_t physicalY)
486 {
487     CALL_DEBUG_ENTER;
488     if (surfaceNode_ != nullptr) {
489         if (!SetTraditionsHardWareCursorLocation(displayId, physicalX, physicalY,
490             ICON_TYPE(mouseIcons_[MOUSE_ICON(lastMouseStyle_.id)].alignmentWay))) {
491             return;
492         }
493         MMI_HILOGD("Move pointer, physicalX:%d, physicalY:%d", physicalX, physicalY);
494     }
495 }
496 
SetHardwareCursorPosition(int32_t displayId, int32_t physicalX, int32_t physicalY, PointerStyle pointerStyle)497 void PointerDrawingManager::SetHardwareCursorPosition(int32_t displayId, int32_t physicalX, int32_t physicalY,
498     PointerStyle pointerStyle)
499 {
500 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
501     CHKPV(hardwareCursorPointerManager_);
502     if (g_isHdiRemoteDied) {
503         hardwareCursorPointerManager_->SetHdiServiceState(false);
504     }
505     hardwareCursorPointerManager_->SetTargetDevice(displayId);
506     if (hardwareCursorPointerManager_->IsSupported() && lastMouseStyle_.id != MOUSE_ICON::LOADING &&
507             lastMouseStyle_.id != MOUSE_ICON::RUNNING) {
508         if (hardwareCursorPointerManager_->SetPosition((physicalX - CalculateHardwareXOffset(ICON_TYPE(
509             mouseIcons_[MOUSE_ICON(pointerStyle.id)].alignmentWay))), (physicalY - CalculateHardwareYOffset(
510                 ICON_TYPE(mouseIcons_[MOUSE_ICON(pointerStyle.id)].alignmentWay)))) != RET_OK) {
511             MMI_HILOGE("Set hardware cursor position error");
512         }
513     }
514 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
515 }
516 
DrawPointer(int32_t displayId, int32_t physicalX, int32_t physicalY, const PointerStyle pointerStyle, Direction direction)517 void PointerDrawingManager::DrawPointer(int32_t displayId, int32_t physicalX, int32_t physicalY,
518     const PointerStyle pointerStyle, Direction direction)
519 {
520     CALL_DEBUG_ENTER;
521     MMI_HILOGD("Display:%{public}d, physicalX:%{public}d, physicalY:%{public}d, pointerStyle:%{public}d",
522         displayId, physicalX, physicalY, pointerStyle.id);
523     FixCursorPosition(physicalX, physicalY);
524     lastPhysicalX_ = physicalX;
525     lastPhysicalY_ = physicalY;
526     currentMouseStyle_ = pointerStyle;
527     currentDirection_ = direction;
528     if (pointerStyle.id == MOUSE_ICON::DEFAULT && mouseIcons_[MOUSE_ICON(pointerStyle.id)].iconPath == CursorIconPath) {
529         AdjustMouseFocus(direction, ICON_TYPE(mouseIcons_[MOUSE_ICON(MOUSE_ICON::CURSOR_CIRCLE)].alignmentWay),
530             physicalX, physicalY);
531     } else {
532         AdjustMouseFocus(direction, ICON_TYPE(mouseIcons_[MOUSE_ICON(pointerStyle.id)].alignmentWay),
533             physicalX, physicalY);
534     }
535     // Log printing only occurs when the mouse style changes
536     if (currentMouseStyle_.id != lastMouseStyle_.id) {
537         MMI_HILOGD("MagicCursor AdjustMouseFocus:%{public}d",
538             ICON_TYPE(mouseIcons_[MOUSE_ICON(pointerStyle.id)].alignmentWay));
539     }
540     if (DrawMovePointer(displayId, physicalX, physicalY, pointerStyle, direction) == RET_OK) {
541         return;
542     }
543 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
544     if (HasMagicCursor() && currentMouseStyle_.id != DEVELOPER_DEFINED_ICON) {
545         MMI_HILOGD("magicCursor DrawPointer enter CreatePointerWindow");
546         MAGIC_CURSOR->CreatePointerWindow(displayId, physicalX, physicalY, direction, surfaceNode_);
547     } else {
548         CreatePointerWindow(displayId, physicalX, physicalY, direction);
549     }
550 #else
551     CreatePointerWindow(displayId, physicalX, physicalY, direction);
552 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
553     CHKPV(surfaceNode_);
554     UpdateMouseStyle();
555     if (InitLayer(MOUSE_ICON(lastMouseStyle_.id)) != RET_OK) {
556         MMI_HILOGE("Init layer failed");
557         return;
558     }
559     UpdatePointerVisible();
560     SetHardwareCursorPosition(displayId, physicalX, physicalY, lastMouseStyle_);
561     MMI_HILOGI("Leave, display:%{public}d, physicalX:%d, physicalY:%d", displayId, physicalX, physicalY);
562 }
563 
UpdateMouseStyle()564 void PointerDrawingManager::UpdateMouseStyle()
565 {
566     CALL_DEBUG_ENTER;
567     PointerStyle curPointerStyle;
568     GetPointerStyle(pid_, GLOBAL_WINDOW_ID, curPointerStyle);
569     if (curPointerStyle.id == CURSOR_CIRCLE_STYLE) {
570         lastMouseStyle_.id = curPointerStyle.id;
571         int ret = SetPointerStyle(pid_, GLOBAL_WINDOW_ID, curPointerStyle);
572         if (ret != RET_OK) {
573             MMI_HILOGE("Set pointer style failed");
574         }
575         return;
576     }
577 }
578 
SwitchPointerStyle()579 int32_t PointerDrawingManager::SwitchPointerStyle()
580 {
581     CALL_DEBUG_ENTER;
582     int32_t size = GetPointerSize();
583     if (size < MIN_POINTER_SIZE) {
584         size = MIN_POINTER_SIZE;
585     } else if (size > MAX_POINTER_SIZE) {
586         size = MAX_POINTER_SIZE;
587     }
588     imageWidth_ = pow(INCREASE_RATIO, size - 1) * displayInfo_.dpi * GetIndependentPixels() / BASELINE_DENSITY;
589     imageHeight_ = pow(INCREASE_RATIO, size - 1) * displayInfo_.dpi * GetIndependentPixels() / BASELINE_DENSITY;
590     canvasWidth_ = (imageWidth_ / POINTER_WINDOW_INIT_SIZE + 1) * POINTER_WINDOW_INIT_SIZE;
591     canvasHeight_ = (imageHeight_ / POINTER_WINDOW_INIT_SIZE + 1) * POINTER_WINDOW_INIT_SIZE;
592 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
593     MAGIC_CURSOR->SetPointerSize(imageWidth_, imageHeight_);
594 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
595     Direction direction = DIRECTION0;
596     int32_t physicalX = lastPhysicalX_;
597     int32_t physicalY = lastPhysicalY_;
598     AdjustMouseFocus(
599         direction, ICON_TYPE(GetIconStyle(MOUSE_ICON(lastMouseStyle_.id)).alignmentWay), physicalX, physicalY);
600 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
601     if (HasMagicCursor()) {
602         MAGIC_CURSOR->EnableCursorInversion();
603         MAGIC_CURSOR->CreatePointerWindow(displayInfo_.id, physicalX, physicalY, direction, surfaceNode_);
604     } else {
605         MAGIC_CURSOR->DisableCursorInversion();
606         CreatePointerWindow(displayInfo_.id, physicalX, physicalY, direction);
607     }
608 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
609     int32_t ret = InitLayer(MOUSE_ICON(lastMouseStyle_.id));
610     if (ret != RET_OK) {
611         MMI_HILOGE("Init layer failed");
612         return ret;
613     }
614     UpdatePointerVisible();
615     SetHardwareCursorPosition(displayInfo_.id, physicalX, physicalY, lastMouseStyle_);
616     return RET_OK;
617 }
618 
CreateMagicCursorChangeObserver()619 void PointerDrawingManager::CreateMagicCursorChangeObserver()
620 {
621     // Listening enabling cursor deformation and color inversion
622     SettingObserver::UpdateFunc func = [](const std::string& key) {
623         bool statusValue = false;
624         auto ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).GetBoolValue(key, statusValue);
625         if (ret != RET_OK) {
626             MMI_HILOGE("Get value from setting date fail");
627             return;
628         }
629 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
630         MAGIC_CURSOR->UpdateMagicCursorChangeState(statusValue);
631 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
632     };
633     std::string dynamicallyKey = "smartChange";
634     sptr<SettingObserver> magicCursorChangeObserver = SettingDataShare::GetInstance(
635         MULTIMODAL_INPUT_SERVICE_ID).CreateObserver(dynamicallyKey, func);
636     ErrCode ret =
637         SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).RegisterObserver(magicCursorChangeObserver);
638     if (ret != ERR_OK) {
639 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
640         DfxHisysevent::ReportMagicCursorFault(dynamicallyKey, "Register setting observer failed");
641 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
642         MMI_HILOGE("Register magic cursor change observer failed, ret:%{public}d", ret);
643         magicCursorChangeObserver = nullptr;
644     }
645 }
646 
UpdateStyleOptions()647 void PointerDrawingManager::UpdateStyleOptions()
648 {
649     CALL_DEBUG_ENTER;
650     PointerStyle curPointerStyle;
651     WIN_MGR->GetPointerStyle(pid_, GLOBAL_WINDOW_ID, curPointerStyle);
652     curPointerStyle.options = HasMagicCursor() ? MAGIC_STYLE_OPT : MOUSE_STYLE_OPT;
653     int ret = WIN_MGR->SetPointerStyle(pid_, GLOBAL_WINDOW_ID, curPointerStyle);
654     if (ret != RET_OK) {
655         MMI_HILOGE("Set pointer style failed");
656     }
657 }
658 
InitPointerObserver()659 void PointerDrawingManager::InitPointerObserver()
660 {
661     CALL_INFO_TRACE;
662     if (hasInitObserver_) {
663         MMI_HILOGI("Settingdata observer has init");
664         return;
665     }
666 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
667     int32_t ret = CreatePointerSwitchObserver(hasMagicCursor_);
668     if (ret == RET_OK) {
669         hasInitObserver_ = true;
670         MMI_HILOGD("Create pointer switch observer success");
671     }
672 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
673 }
674 
CreatePointerSwitchObserver(isMagicCursor& item)675 int32_t PointerDrawingManager::CreatePointerSwitchObserver(isMagicCursor& item)
676 {
677     CALL_DEBUG_ENTER;
678     SettingObserver::UpdateFunc updateFunc = [this, &item](const std::string& key) {
679         bool statusValue = false;
680 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
681         statusValue = true;
682 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
683         auto ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).GetBoolValue(key, statusValue);
684         if (ret != RET_OK) {
685             MMI_HILOGE("Get value from setting date fail");
686             return;
687         }
688         bool tmp = item.isShow;
689         item.isShow = statusValue;
690         this->UpdateStyleOptions();
691         if (item.isShow != tmp) {
692 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
693             MAGIC_CURSOR->InitRenderThread([]() { IPointerDrawingManager::GetInstance()->SwitchPointerStyle(); });
694 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
695             CHKPV(surfaceNode_);
696 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
697             MMI_HILOGD("Switch pointer style");
698             int64_t nodeId = surfaceNode_->GetId();
699             if (nodeId != MAGIC_CURSOR->GetSurfaceNodeId(nodeId)) {
700                 surfaceNode_->DetachToDisplay(screenId_);
701                 Rosen::RSTransaction::FlushImplicitTransaction();
702             }
703             MAGIC_CURSOR->DetachDisplayNode();
704             this->SwitchPointerStyle();
705 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
706         }
707     };
708     sptr<SettingObserver> statusObserver =
709         SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).CreateObserver(item.name, updateFunc);
710     ErrCode ret = SettingDataShare::GetInstance(MULTIMODAL_INPUT_SERVICE_ID).RegisterObserver(statusObserver);
711     if (ret != ERR_OK) {
712 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
713         DfxHisysevent::ReportMagicCursorFault(item.name, "Register setting observer failed");
714 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
715         MMI_HILOGE("Register setting observer failed, ret:%{public}d", ret);
716         statusObserver = nullptr;
717         return RET_ERR;
718     }
719     CreateMagicCursorChangeObserver();
720     return RET_OK;
721 }
722 
HasMagicCursor()723 bool PointerDrawingManager::HasMagicCursor()
724 {
725 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
726     if (!MAGIC_CURSOR->isExistDefaultStyle) {
727         MMI_HILOGE("MagicCursor default icon file is not exist");
728         return false;
729     }
730 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
731     return hasMagicCursor_.isShow;
732 }
733 
CreateDynamicCanvas()734 void PointerDrawingManager::CreateDynamicCanvas()
735 {
736     CALL_DEBUG_ENTER;
737     OHOS::Rosen::Drawing::BitmapFormat format { OHOS::Rosen::Drawing::COLORTYPE_RGBA_8888,
738         OHOS::Rosen::Drawing::ALPHATYPE_OPAQUE };
739     if (dynamicBitmap_ == nullptr) {
740         dynamicBitmap_ = std::make_shared<OHOS::Rosen::Drawing::Bitmap>();
741     }
742     g_hardwareCanvasSize = GetCanvasSize();
743     dynamicBitmap_->Build(g_hardwareCanvasSize, g_hardwareCanvasSize, format);
744     if (dynamicCanvas_ == nullptr) {
745         dynamicCanvas_ = std::make_shared<OHOS::Rosen::Drawing::Canvas>();
746     }
747     dynamicCanvas_->Bind(*dynamicBitmap_);
748 }
749 
ParsingDynamicImage(MOUSE_ICON mouseStyle)750 int32_t PointerDrawingManager::ParsingDynamicImage(MOUSE_ICON mouseStyle)
751 {
752     CALL_DEBUG_ENTER;
753     std::shared_ptr<OHOS::Media::PixelMap> pixelmap = nullptr;
754     if (mouseStyle == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
755         MMI_HILOGD("Set mouseicon by userIcon_");
756         image_ = ExtractDrawingImage(userIcon_);
757     } else {
758         if (mouseStyle == MOUSE_ICON::RUNNING) {
759             pixelmap = DecodeImageToPixelMap(mouseIcons_[MOUSE_ICON::RUNNING_LEFT].iconPath);
760         } else {
761             pixelmap = DecodeImageToPixelMap(mouseIcons_[mouseStyle].iconPath);
762         }
763         CHKPR(pixelmap, RET_ERR);
764         if (mouseStyle == MOUSE_ICON::RUNNING_RIGHT) {
765             runningRightImage_ = ExtractDrawingImage(pixelmap);
766             CHKPR(runningRightImage_, RET_ERR);
767             return RET_OK;
768         }
769         image_ = ExtractDrawingImage(pixelmap);
770         CHKPR(image_, RET_ERR);
771     }
772     return RET_OK;
773 }
774 
775 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
DrawTraditionsCursor(MOUSE_ICON mouseStyle)776 void PointerDrawingManager::DrawTraditionsCursor(MOUSE_ICON mouseStyle)
777 {
778     PostTask([this, mouseStyle]() -> void {
779         this->DrawCursor(mouseStyle);
780     });
781 }
782 
InitVsync(MOUSE_ICON mouseStyle)783 int32_t PointerDrawingManager::InitVsync(MOUSE_ICON mouseStyle)
784 {
785     if (ParsingDynamicImage(mouseStyle) != RET_OK) {
786         MMI_HILOGE("Parsing mouseStyle fail");
787         return RET_ERR;
788     }
789     if (ParsingDynamicImage(MOUSE_ICON::RUNNING_RIGHT) != RET_OK) {
790         MMI_HILOGE("Parsing mouse icon fail");
791         return RET_ERR;
792     }
793     if (mouseStyle == MOUSE_ICON::LOADING) {
794         hasLoadingPointerStyle_ = true;
795     } else if (mouseStyle == MOUSE_ICON::RUNNING) {
796         hasHardwareCursorAnimate_ = true;
797     }
798     CreateDynamicCanvas();
799     if (g_isReStartVsync) {
800         isRenderRuning_.store(true);
801         auto rsClient = std::static_pointer_cast<Rosen::RSRenderServiceClient>(
802             Rosen::RSIRenderClient::CreateRenderServiceClient());
803         CHKPR(rsClient, RET_ERR);
804         receiver_ = rsClient->CreateVSyncReceiver(POINTER_CURSOR_RENDER_RECEIVER_NAME, handler_);
805         if (receiver_ == nullptr || receiver_->Init() != VSYNC_ERROR_OK) {
806             MMI_HILOGE("Receiver init failed");
807             return RET_ERR;
808         }
809         g_isReStartVsync = false;
810     }
811     return RequestNextVSync();
812 }
813 
RetryGetSurfaceBuffer(sptr<OHOS::SurfaceBuffer> buffer, sptr<OHOS::Surface> layer)814 bool PointerDrawingManager::RetryGetSurfaceBuffer(sptr<OHOS::SurfaceBuffer> buffer, sptr<OHOS::Surface> layer)
815 {
816     bool ret = true;
817     if (hardwareCursorPointerManager_->IsSupported()) {
818         for (size_t i = 0; i < RETRY_TIMES; i++) {
819             buffer = GetSurfaceBuffer(layer);
820             if (buffer != nullptr && buffer->GetVirAddr() != nullptr) {
821                 ret = false;
822                 break;
823             }
824         }
825     }
826     return ret;
827 }
828 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
829 
InitLayer(const MOUSE_ICON mouseStyle)830 int32_t PointerDrawingManager::InitLayer(const MOUSE_ICON mouseStyle)
831 {
832 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
833     if (HasMagicCursor() && mouseStyle != MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
834         MMI_HILOGD("magiccursor enter MAGIC_CURSOR->Initlayer");
835         return MAGIC_CURSOR->InitLayer(mouseStyle);
836     }
837 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
838 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
839     CHKPR(hardwareCursorPointerManager_, RET_ERR);
840     hasLoadingPointerStyle_ = false;
841     hasHardwareCursorAnimate_ = false;
842     if (hardwareCursorPointerManager_->IsSupported()) {
843         if ((mouseStyle == MOUSE_ICON::LOADING) || (mouseStyle == MOUSE_ICON::RUNNING)) {
844             return InitVsync(mouseStyle);
845         } else {
846             GetCanvasSize();
847             GetFocusCoordinates();
848             hardwareCanvasSize_ = g_hardwareCanvasSize;
849             // Change the drawing to asynchronous, and when obtaining the surfaceBuffer fails,
850             // repeatedly obtain the surfaceBuffer.
851             DrawTraditionsCursor(mouseStyle);
852             return RET_OK;
853         }
854     }
855 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
856     return DrawCursor(mouseStyle);
857 }
858 
DrawCursor(const MOUSE_ICON mouseStyle)859 int32_t PointerDrawingManager::DrawCursor(const MOUSE_ICON mouseStyle)
860 {
861     CALL_DEBUG_ENTER;
862     CHKPR(surfaceNode_, RET_ERR);
863     DrawLoadingPointerStyle(mouseStyle);
864     DrawRunningPointerAnimate(mouseStyle);
865     sptr<OHOS::Surface> layer = GetLayer();
866     if (layer == nullptr) {
867         MMI_HILOGE("Init layer is failed, Layer is nullptr");
868         surfaceNode_->DetachToDisplay(screenId_);
869         surfaceNode_ = nullptr;
870         Rosen::RSTransaction::FlushImplicitTransaction();
871         MMI_HILOGE("Pointer window destroy success");
872         return RET_ERR;
873     }
874     if (!isInit_) {
875         layer->SetQueueSize(QUEUE_SIZE);
876         isInit_ = true;
877     }
878     sptr<OHOS::SurfaceBuffer> buffer = GetSurfaceBuffer(layer);
879     if (buffer == nullptr || buffer->GetVirAddr() == nullptr) {
880 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
881         if (RetryGetSurfaceBuffer(buffer, layer)) {
882             return RET_OK;
883         }
884 #else
885         surfaceNode_->DetachToDisplay(screenId_);
886         surfaceNode_ = nullptr;
887         Rosen::RSTransaction::FlushImplicitTransaction();
888         MMI_HILOGE("Pointer window destroy success");
889         return RET_ERR;
890 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
891     }
892 
893     auto addr = static_cast<uint8_t *>(buffer->GetVirAddr());
894     DoDraw(addr, buffer->GetWidth(), buffer->GetHeight(), mouseStyle);
895     OHOS::BufferFlushConfig flushConfig = {
896         .damage = {
897             .w = buffer->GetWidth(),
898             .h = buffer->GetHeight(),
899         },
900     };
901     OHOS::SurfaceError ret = layer->FlushBuffer(buffer, -1, flushConfig);
902     if (ret != OHOS::SURFACE_ERROR_OK) {
903         MMI_HILOGE("Init layer failed, FlushBuffer return ret:%{public}s", SurfaceErrorStr(ret).c_str());
904         return RET_ERR;
905     }
906     MMI_HILOGD("Init layer success");
907     return RET_OK;
908 }
909 
DrawLoadingPointerStyle(const MOUSE_ICON mouseStyle)910 void PointerDrawingManager::DrawLoadingPointerStyle(const MOUSE_ICON mouseStyle)
911 {
912     CALL_DEBUG_ENTER;
913     CHKPV(surfaceNode_);
914 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
915     CHKPV(hardwareCursorPointerManager_);
916     if (hardwareCursorPointerManager_->IsSupported()) {
917         return;
918     }
919 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
920     Rosen::RSAnimationTimingProtocol protocol;
921     if (mouseStyle != MOUSE_ICON::LOADING &&
922         (mouseStyle != MOUSE_ICON::DEFAULT ||
923             mouseIcons_[mouseStyle].iconPath != (IMAGE_POINTER_DEFAULT_PATH + "Loading.svg"))) {
924         protocol.SetDuration(0);
925         Rosen::RSNode::Animate(
926             protocol,
927             Rosen::RSAnimationTimingCurve::LINEAR,
928             [this]() {
929                 if (!Rosen::SceneBoardJudgement::IsSceneBoardEnabled()) {
930                     RotateDegree(DIRECTION0);
931                     return;
932                 }
933                 RotateDegree(currentDirection_);
934             });
935         MMI_HILOGE("current pointer is not loading");
936         Rosen::RSTransaction::FlushImplicitTransaction();
937         return;
938     }
939     float ratio = imageWidth_ * 1.0 / canvasWidth_;
940     surfaceNode_->SetPivot({LOADING_CENTER_RATIO * ratio, LOADING_CENTER_RATIO * ratio});
941     protocol.SetDuration(ANIMATION_DURATION);
942     protocol.SetRepeatCount(DEFAULT_VALUE);
943 
944     // create property animation
945     Rosen::RSNode::Animate(
946         protocol,
947         Rosen::RSAnimationTimingCurve::LINEAR,
948         [this]() { surfaceNode_->SetRotation(ROTATION_ANGLE); });
949 
950     Rosen::RSTransaction::FlushImplicitTransaction();
951 }
952 
ConvertToColorSpace( Media::ColorSpace colorSpace)953 std::shared_ptr<Rosen::Drawing::ColorSpace> PointerDrawingManager::ConvertToColorSpace(
954     Media::ColorSpace colorSpace)
955 {
956     switch (colorSpace) {
957         case Media::ColorSpace::DISPLAY_P3:
958             return Rosen::Drawing::ColorSpace::CreateRGB(
959                 Rosen::Drawing::CMSTransferFuncType::SRGB, Rosen::Drawing::CMSMatrixType::DCIP3);
960         case Media::ColorSpace::LINEAR_SRGB:
961             return Rosen::Drawing::ColorSpace::CreateSRGBLinear();
962         case Media::ColorSpace::SRGB:
963             return Rosen::Drawing::ColorSpace::CreateSRGB();
964         default:
965             return Rosen::Drawing::ColorSpace::CreateSRGB();
966     }
967 }
968 
PixelFormatToColorType(Media::PixelFormat pixelFormat)969 Rosen::Drawing::ColorType PointerDrawingManager::PixelFormatToColorType(Media::PixelFormat pixelFormat)
970 {
971     switch (pixelFormat) {
972         case Media::PixelFormat::RGB_565:
973             return Rosen::Drawing::ColorType::COLORTYPE_RGB_565;
974         case Media::PixelFormat::RGBA_8888:
975             return Rosen::Drawing::ColorType::COLORTYPE_RGBA_8888;
976         case Media::PixelFormat::BGRA_8888:
977             return Rosen::Drawing::ColorType::COLORTYPE_BGRA_8888;
978         case Media::PixelFormat::ALPHA_8:
979             return Rosen::Drawing::ColorType::COLORTYPE_ALPHA_8;
980         case Media::PixelFormat::RGBA_F16:
981             return Rosen::Drawing::ColorType::COLORTYPE_RGBA_F16;
982         case Media::PixelFormat::UNKNOWN:
983         case Media::PixelFormat::ARGB_8888:
984         case Media::PixelFormat::RGB_888:
985         case Media::PixelFormat::NV21:
986         case Media::PixelFormat::NV12:
987         case Media::PixelFormat::CMYK:
988         default:
989             return Rosen::Drawing::ColorType::COLORTYPE_UNKNOWN;
990     }
991 }
992 
AlphaTypeToAlphaType(Media::AlphaType alphaType)993 Rosen::Drawing::AlphaType PointerDrawingManager::AlphaTypeToAlphaType(Media::AlphaType alphaType)
994 {
995     switch (alphaType) {
996         case Media::AlphaType::IMAGE_ALPHA_TYPE_UNKNOWN:
997             return Rosen::Drawing::AlphaType::ALPHATYPE_UNKNOWN;
998         case Media::AlphaType::IMAGE_ALPHA_TYPE_OPAQUE:
999             return Rosen::Drawing::AlphaType::ALPHATYPE_OPAQUE;
1000         case Media::AlphaType::IMAGE_ALPHA_TYPE_PREMUL:
1001             return Rosen::Drawing::AlphaType::ALPHATYPE_PREMUL;
1002         case Media::AlphaType::IMAGE_ALPHA_TYPE_UNPREMUL:
1003             return Rosen::Drawing::AlphaType::ALPHATYPE_UNPREMUL;
1004         default:
1005             return Rosen::Drawing::AlphaType::ALPHATYPE_UNKNOWN;
1006     }
1007 }
1008 
PixelMapReleaseProc(const void* , void* context)1009 static void PixelMapReleaseProc(const void* /* pixels */, void* context)
1010 {
1011     PixelMapReleaseContext* ctx = static_cast<PixelMapReleaseContext*>(context);
1012     if (ctx != nullptr) {
1013         delete ctx;
1014     }
1015 }
1016 
ExtractDrawingImage( std::shared_ptr<Media::PixelMap> pixelMap)1017 std::shared_ptr<Rosen::Drawing::Image> PointerDrawingManager::ExtractDrawingImage(
1018     std::shared_ptr<Media::PixelMap> pixelMap)
1019 {
1020     CHKPP(pixelMap);
1021     Media::ImageInfo imageInfo;
1022     pixelMap->GetImageInfo(imageInfo);
1023     Rosen::Drawing::ImageInfo drawingImageInfo { imageInfo.size.width, imageInfo.size.height,
1024         PixelFormatToColorType(imageInfo.pixelFormat),
1025         AlphaTypeToAlphaType(imageInfo.alphaType),
1026         ConvertToColorSpace(imageInfo.colorSpace) };
1027     Rosen::Drawing::Pixmap imagePixmap(drawingImageInfo,
1028         reinterpret_cast<const void*>(pixelMap->GetPixels()), pixelMap->GetRowBytes());
1029     PixelMapReleaseContext* releaseContext = new (std::nothrow) PixelMapReleaseContext(pixelMap);
1030     CHKPP(releaseContext);
1031     auto image = Rosen::Drawing::Image::MakeFromRaster(imagePixmap, PixelMapReleaseProc, releaseContext);
1032     if (image == nullptr) {
1033         MMI_HILOGE("ExtractDrawingImage image fail");
1034         delete releaseContext;
1035     }
1036     return image;
1037 }
1038 
1039 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
PostTask(Rosen::RSTaskMessage::RSTask task)1040 void PointerDrawingManager::PostTask(Rosen::RSTaskMessage::RSTask task)
1041 {
1042     CHKPV(hardwareCursorPointerManager_);
1043     if (g_isHdiRemoteDied) {
1044         hardwareCursorPointerManager_->SetHdiServiceState(false);
1045     }
1046     if (handler_ != nullptr) {
1047         handler_->PostTask(task);
1048     }
1049 }
1050 
DoHardwareCursorDraw()1051 void PointerDrawingManager::DoHardwareCursorDraw()
1052 {
1053     CHKPV(hardwareCursorPointerManager_);
1054     CHKPV(dynamicCanvas_);
1055     CHKPV(dynamicBitmap_);
1056     dynamicCanvas_->Save();
1057     dynamicCanvas_->Clear(OHOS::Rosen::Drawing::Color::COLOR_TRANSPARENT);
1058     FOCUS_COORDINATES(FOCUS_COORDINATES_, CHANGE) = GetFocusCoordinates();
1059     CALCULATE_CANVAS_SIZE(CALCULATE_CANVAS_SIZE_, CHANGE) = GetCanvasSize();
1060     if (hardwareCursorPointerManager_->IsSupported() && hasLoadingPointerStyle_) {
1061         dynamicCanvas_->Rotate(DYNAMIC_ROTATION_ANGLE * currentFrame_, FOCUS_COORDINATES_CHANGE,
1062             FOCUS_COORDINATES_CHANGE);
1063         currentFrame_++;
1064         if (currentFrame_ == frameCount_) {
1065             currentFrame_ = 0;
1066         }
1067     }
1068     DrawDynamicImage(*dynamicCanvas_, MOUSE_ICON(lastMouseStyle_.id));
1069     if (hardwareCursorPointerManager_->IsSupported() && hasHardwareCursorAnimate_) {
1070         dynamicCanvas_->Rotate(DYNAMIC_ROTATION_ANGLE * currentFrame_, (FOCUS_COORDINATES_CHANGE +
1071             (imageWidth_ * RUNNING_X_RATIO)), (FOCUS_COORDINATES_CHANGE + (imageHeight_ * RUNNING_Y_RATIO)));
1072         DrawDynamicImage(*dynamicCanvas_, MOUSE_ICON::RUNNING_RIGHT);
1073         currentFrame_++;
1074         if (currentFrame_ == frameCount_) {
1075             currentFrame_ = 0;
1076         }
1077     }
1078     dynamicCanvas_->Restore();
1079     static constexpr uint32_t stride = 4;
1080     uint32_t addrSize = buffer_->GetWidth() * buffer_->GetHeight() * stride;
1081     CHKPV(addr_);
1082     errno_t ret = memcpy_s(*addr_, addrSize, dynamicBitmap_->GetPixels(), addrSize);
1083     if (ret != EOK) {
1084         MMI_HILOGE("Memcpy data is error, ret:%{public}d", ret);
1085     }
1086 }
1087 
FlushBuffer()1088 int32_t PointerDrawingManager::FlushBuffer()
1089 {
1090     CHKPR(buffer_, RET_ERR);
1091     CHKPR(layer_, RET_ERR);
1092     OHOS::BufferFlushConfig flushConfig = {
1093         .damage = {
1094             .w = buffer_->GetWidth(),
1095             .h = buffer_->GetHeight(),
1096         },
1097     };
1098     OHOS::SurfaceError ret = layer_->FlushBuffer(buffer_, DEFAULT_VALUE, flushConfig);
1099     if (ret != OHOS::SURFACE_ERROR_OK) {
1100         MMI_HILOGE("Init layer failed, FlushBuffer return ret:%{public}s", SurfaceErrorStr(ret).c_str());
1101     }
1102     return ret;
1103 }
1104 
GetSurfaceInformation()1105 int32_t PointerDrawingManager::GetSurfaceInformation()
1106 {
1107     CHKPR(surfaceNode_, RET_ERR);
1108     if (currentMouseStyle_.id != MOUSE_ICON::RUNNING && currentMouseStyle_.id != MOUSE_ICON::LOADING) {
1109         MMI_HILOGE("Current mouse style is not equal to last mouse style");
1110         return RET_ERR;
1111     }
1112     layer_ = GetLayer();
1113     CHKPR(layer_, RET_ERR);
1114     buffer_ = GetSurfaceBuffer(layer_);
1115     if (buffer_ == nullptr || buffer_->GetVirAddr() == nullptr) {
1116         MMI_HILOGE("Init layer is failed, buffer or virAddr is nullptr");
1117         return RET_ERR;
1118     }
1119     addr_ = std::make_shared<uint8_t *>(static_cast<uint8_t *>(buffer_->GetVirAddr()));
1120     CHKPR(addr_, RET_ERR);
1121     return RET_OK;
1122 }
1123 
OnVsync(uint64_t timestamp)1124 void PointerDrawingManager::OnVsync(uint64_t timestamp)
1125 {
1126     if (currentMouseStyle_.id != MOUSE_ICON::RUNNING && currentMouseStyle_.id != MOUSE_ICON::LOADING) {
1127         MMI_HILOGE("Current mouse style is not equal to last mouse style");
1128         return;
1129     }
1130     PostTask([this]() -> void {
1131         if (currentMouseStyle_.id != MOUSE_ICON::RUNNING && currentMouseStyle_.id != MOUSE_ICON::LOADING) {
1132             MMI_HILOGE("Current post task mouse style is not equal to last mouse style");
1133             return;
1134         }
1135         if (GetSurfaceInformation() != RET_OK) {
1136             MMI_HILOGE("OnVsync Get surface information fail");
1137             return;
1138         }
1139         DoHardwareCursorDraw();
1140         FlushBuffer();
1141         UpdatePointerVisible();
1142         mouseIconUpdate_ = false;
1143         if (!SetDynamicHardWareCursorLocation(lastPhysicalX_, lastPhysicalY_, MOUSE_ICON(lastMouseStyle_.id))) {
1144             MMI_HILOGE("OnVsync set dynamic hardware cursor location error");
1145             return;
1146         }
1147     });
1148     RequestNextVSync();
1149 }
1150 
RequestNextVSync()1151 int32_t PointerDrawingManager::RequestNextVSync()
1152 {
1153     if (handler_ != nullptr) {
1154         Rosen::VSyncReceiver::FrameCallback fcb = {
1155             .userData_ = this,
1156             .callback_ = [this] (uint64_t timestamp, void*) {
1157                 return this->OnVsync(timestamp);
1158             },
1159         };
1160         if (receiver_ != nullptr) {
1161             receiver_->RequestNextVSync(fcb);
1162             return RET_OK;
1163         }
1164     }
1165     return RET_ERR;
1166 }
1167 
RenderThreadLoop()1168 void PointerDrawingManager::RenderThreadLoop()
1169 {
1170     isRenderRuning_.store(true);
1171     runner_ = AppExecFwk::EventRunner::Create(false);
1172     CHKPV(runner_);
1173     handler_ = std::make_shared<AppExecFwk::EventHandler>(runner_);
1174     CHKPV(handler_);
1175     auto rsClient = std::static_pointer_cast<Rosen::RSRenderServiceClient>(
1176         Rosen::RSIRenderClient::CreateRenderServiceClient());
1177     CHKPV(rsClient);
1178     receiver_ = rsClient->CreateVSyncReceiver(POINTER_CURSOR_RENDER_RECEIVER_NAME, handler_);
1179     if (receiver_ == nullptr || receiver_->Init() != VSYNC_ERROR_OK) {
1180         MMI_HILOGE("Receiver init failed");
1181         return;
1182     }
1183     if (runner_ != nullptr) {
1184         MMI_HILOGI("Runner is run");
1185         runner_->Run();
1186     }
1187 }
1188 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1189 
DrawRunningPointerAnimate(const MOUSE_ICON mouseStyle)1190 void PointerDrawingManager::DrawRunningPointerAnimate(const MOUSE_ICON mouseStyle)
1191 {
1192     CALL_DEBUG_ENTER;
1193 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1194     CHKPV(hardwareCursorPointerManager_);
1195     if (hardwareCursorPointerManager_->IsSupported()) {
1196         return;
1197     }
1198 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1199     CHKPV(surfaceNode_);
1200     CHKPV(canvasNode_);
1201     if (mouseStyle != MOUSE_ICON::RUNNING && (mouseStyle != MOUSE_ICON::DEFAULT ||
1202             mouseIcons_[mouseStyle].iconPath != (IMAGE_POINTER_DEFAULT_PATH + "Loading_Left.svg"))) {
1203         if (canvasNode_ != nullptr) {
1204             Rosen::RSAnimationTimingProtocol protocol;
1205             protocol.SetDuration(0);
1206             Rosen::RSNode::Animate(
1207                 protocol,
1208                 Rosen::RSAnimationTimingCurve::LINEAR,
1209                 [this]() { canvasNode_->SetRotation(0); });
1210             Rosen::RSTransaction::FlushImplicitTransaction();
1211             canvasNode_->SetVisible(false);
1212         }
1213         MMI_HILOGE("current pointer is not running");
1214         return;
1215     }
1216     canvasNode_->SetVisible(true);
1217     float ratio = imageWidth_ * 1.0 / canvasWidth_;
1218     canvasNode_->SetPivot({RUNNING_X_RATIO * ratio, RUNNING_Y_RATIO * ratio});
1219     std::shared_ptr<OHOS::Media::PixelMap> pixelmap =
1220         DecodeImageToPixelMap(mouseIcons_[MOUSE_ICON::RUNNING_RIGHT].iconPath);
1221     CHKPV(pixelmap);
1222     MMI_HILOGD("Set mouseicon to OHOS system");
1223 
1224 #ifndef USE_ROSEN_DRAWING
1225     auto canvas = static_cast<Rosen::RSRecordingCanvas *>(canvasNode_->BeginRecording(imageWidth_, imageHeight_));
1226     canvas->DrawPixelMap(pixelmap, 0, 0, SkSamplingOptions(), nullptr);
1227 #else
1228     Rosen::Drawing::Brush brush;
1229     Rosen::Drawing::Rect src = Rosen::Drawing::Rect(0, 0, pixelmap->GetWidth(), pixelmap->GetHeight());
1230     Rosen::Drawing::Rect dst = Rosen::Drawing::Rect(src);
1231     auto canvas =
1232         static_cast<Rosen::ExtendRecordingCanvas *>(canvasNode_->BeginRecording(imageWidth_, imageHeight_));
1233     canvas->AttachBrush(brush);
1234     canvas->DrawPixelMapRect(pixelmap, src, dst, Rosen::Drawing::SamplingOptions());
1235     canvas->DetachBrush();
1236 #endif // USE_ROSEN_DRAWING
1237 
1238     canvasNode_->FinishRecording();
1239 
1240     Rosen::RSAnimationTimingProtocol protocol;
1241     protocol.SetDuration(ANIMATION_DURATION);
1242     protocol.SetRepeatCount(DEFAULT_VALUE);
1243 
1244     // create property animation
1245     Rosen::RSNode::Animate(
1246         protocol,
1247         Rosen::RSAnimationTimingCurve::LINEAR,
1248         [this]() { canvasNode_->SetRotation(ROTATION_ANGLE); });
1249 
1250     Rosen::RSTransaction::FlushImplicitTransaction();
1251 }
1252 
AdjustMouseFocus(Direction direction, ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)1253 void PointerDrawingManager::AdjustMouseFocus(Direction direction, ICON_TYPE iconType,
1254     int32_t &physicalX, int32_t &physicalY)
1255 {
1256     CALL_DEBUG_ENTER;
1257     switch (direction) {
1258         case DIRECTION0: {
1259             AdjustMouseFocusByDirection0(iconType, physicalX, physicalY);
1260             break;
1261         }
1262         case DIRECTION90: {
1263             AdjustMouseFocusByDirection90(iconType, physicalX, physicalY);
1264             break;
1265         }
1266         case DIRECTION180: {
1267             AdjustMouseFocusByDirection180(iconType, physicalX, physicalY);
1268             break;
1269         }
1270         case DIRECTION270: {
1271             AdjustMouseFocusByDirection270(iconType, physicalX, physicalY);
1272             break;
1273         }
1274         default: {
1275             MMI_HILOGW("direction is invalid,direction:%{public}d", direction);
1276             break;
1277         }
1278     }
1279 }
1280 
AdjustMouseFocusByDirection0(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)1281 void PointerDrawingManager::AdjustMouseFocusByDirection0(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)
1282 {
1283     CALL_DEBUG_ENTER;
1284     int32_t height = imageHeight_;
1285     int32_t width = imageWidth_;
1286 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1287     CHKPV(hardwareCursorPointerManager_);
1288     if (hardwareCursorPointerManager_->IsSupported() &&
1289         currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1290         height = cursorHeight_;
1291         width = cursorWidth_;
1292     }
1293 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1294     switch (iconType) {
1295         case ANGLE_SW: {
1296             physicalY -= height;
1297             break;
1298         }
1299         case ANGLE_CENTER: {
1300             physicalX -= width / CALCULATE_MIDDLE;
1301             physicalY -= height / CALCULATE_MIDDLE;
1302             break;
1303         }
1304         case ANGLE_NW_RIGHT: {
1305             physicalX -= MOUSE_ICON_BAIS;
1306             [[fallthrough]];
1307         }
1308         case ANGLE_NW: {
1309             if (userIcon_ != nullptr && currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1310                 physicalX -= userIconHotSpotX_;
1311                 physicalY -= userIconHotSpotY_;
1312             }
1313             break;
1314         }
1315         default: {
1316             MMI_HILOGW("No need adjust mouse focus,iconType:%{public}d", iconType);
1317             break;
1318         }
1319     }
1320 }
1321 
AdjustMouseFocusByDirection90(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)1322 void PointerDrawingManager::AdjustMouseFocusByDirection90(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)
1323 {
1324     CALL_DEBUG_ENTER;
1325     int32_t height = imageHeight_;
1326     int32_t width = imageWidth_;
1327 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1328     CHKPV(hardwareCursorPointerManager_);
1329     if (hardwareCursorPointerManager_->IsSupported() &&
1330         currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1331         height = cursorHeight_;
1332         width = cursorWidth_;
1333     }
1334 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1335     switch (iconType) {
1336         case ANGLE_SW: {
1337             physicalY += height;
1338             break;
1339         }
1340         case ANGLE_CENTER: {
1341             physicalX -= width / CALCULATE_MIDDLE;
1342             physicalY += height / CALCULATE_MIDDLE;
1343             break;
1344         }
1345         case ANGLE_NW_RIGHT: {
1346             physicalX -= MOUSE_ICON_BAIS;
1347             [[fallthrough]];
1348         }
1349         case ANGLE_NW: {
1350             if (userIcon_ != nullptr && currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1351                 physicalX -= userIconHotSpotX_;
1352                 physicalY += userIconHotSpotY_;
1353             }
1354             break;
1355         }
1356         default: {
1357             MMI_HILOGW("No need adjust mouse focus,iconType:%{public}d", iconType);
1358             break;
1359         }
1360     }
1361 }
1362 
AdjustMouseFocusByDirection180(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)1363 void PointerDrawingManager::AdjustMouseFocusByDirection180(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)
1364 {
1365     CALL_DEBUG_ENTER;
1366     int32_t height = imageHeight_;
1367     int32_t width = imageWidth_;
1368 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1369     CHKPV(hardwareCursorPointerManager_);
1370     if (hardwareCursorPointerManager_->IsSupported() &&
1371         currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1372         height = cursorHeight_;
1373         width = cursorWidth_;
1374     }
1375 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1376     switch (iconType) {
1377         case ANGLE_SW: {
1378             physicalY += height;
1379             break;
1380         }
1381         case ANGLE_CENTER: {
1382             physicalX += width / CALCULATE_MIDDLE;
1383             physicalY += height / CALCULATE_MIDDLE;
1384             break;
1385         }
1386         case ANGLE_NW_RIGHT: {
1387             physicalX += MOUSE_ICON_BAIS;
1388             [[fallthrough]];
1389         }
1390         case ANGLE_NW: {
1391             if (userIcon_ != nullptr && currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1392                 physicalX += userIconHotSpotX_;
1393                 physicalY += userIconHotSpotY_;
1394             }
1395             break;
1396         }
1397         default: {
1398             MMI_HILOGW("No need adjust mouse focus,iconType:%{public}d", iconType);
1399             break;
1400         }
1401     }
1402 }
1403 
AdjustMouseFocusByDirection270(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)1404 void PointerDrawingManager::AdjustMouseFocusByDirection270(ICON_TYPE iconType, int32_t &physicalX, int32_t &physicalY)
1405 {
1406     CALL_DEBUG_ENTER;
1407     int32_t height = imageHeight_;
1408     int32_t width = imageWidth_;
1409 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1410     CHKPV(hardwareCursorPointerManager_);
1411     if (hardwareCursorPointerManager_->IsSupported() &&
1412         currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1413         height = cursorHeight_;
1414         width = cursorWidth_;
1415     }
1416 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1417     switch (iconType) {
1418         case ANGLE_SW: {
1419             physicalY -= height;
1420             break;
1421         }
1422         case ANGLE_CENTER: {
1423             physicalX += width / CALCULATE_MIDDLE;
1424             physicalY -= height / CALCULATE_MIDDLE;
1425             break;
1426         }
1427         case ANGLE_NW_RIGHT: {
1428             physicalX += MOUSE_ICON_BAIS;
1429             [[fallthrough]];
1430         }
1431         case ANGLE_NW: {
1432             if (userIcon_ != nullptr && currentMouseStyle_.id == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1433                 physicalX += userIconHotSpotX_;
1434                 physicalY -= userIconHotSpotY_;
1435             }
1436             break;
1437         }
1438         default: {
1439             MMI_HILOGW("No need adjust mouse focus,iconType:%{public}d", iconType);
1440             break;
1441         }
1442     }
1443 }
1444 
SetMouseDisplayState(bool state)1445 void PointerDrawingManager::SetMouseDisplayState(bool state)
1446 {
1447     CALL_DEBUG_ENTER;
1448     if (mouseDisplayState_ != state) {
1449         mouseDisplayState_ = state;
1450         if (mouseDisplayState_) {
1451             InitLayer(MOUSE_ICON(lastMouseStyle_.id));
1452         }
1453         MMI_HILOGI("state:%{public}s", state ? "true" : "false");
1454         UpdatePointerVisible();
1455     }
1456 }
1457 
GetMouseDisplayState() const1458 bool PointerDrawingManager::GetMouseDisplayState() const
1459 {
1460     return mouseDisplayState_;
1461 }
1462 
IsWindowRotation()1463 bool PointerDrawingManager::IsWindowRotation()
1464 {
1465     MMI_HILOGD("ROTATE_POLICY: %{public}d, FOLDABLE_DEVICE_POLICY:%{public}s",
1466         ROTATE_POLICY, FOLDABLE_DEVICE_POLICY.c_str());
1467     return (ROTATE_POLICY == WINDOW_ROTATE ||
1468         (ROTATE_POLICY == FOLDABLE_DEVICE &&
1469         ((displayInfo_.displayMode == DisplayMode::MAIN &&
1470         FOLDABLE_DEVICE_POLICY[0] == ROTATE_WINDOW_ROTATE) ||
1471         (displayInfo_.displayMode == DisplayMode::FULL &&
1472         FOLDABLE_DEVICE_POLICY[FOLDABLE_DEVICE] == ROTATE_WINDOW_ROTATE))));
1473 }
1474 
FixCursorPosition(int32_t &physicalX, int32_t &physicalY)1475 void PointerDrawingManager::FixCursorPosition(int32_t &physicalX, int32_t &physicalY)
1476 {
1477     if (physicalX < 0) {
1478         physicalX = 0;
1479     }
1480 
1481     if (physicalY < 0) {
1482         physicalY = 0;
1483     }
1484     const int32_t cursorUnit = 16;
1485     if (IsWindowRotation()) {
1486         if (displayInfo_.direction == DIRECTION0 || displayInfo_.direction == DIRECTION180) {
1487             if (physicalX > (displayInfo_.width - imageWidth_ / cursorUnit)) {
1488                 physicalX = displayInfo_.width - imageWidth_ / cursorUnit;
1489             }
1490             if (physicalY > (displayInfo_.height - imageHeight_ / cursorUnit)) {
1491                 physicalY = displayInfo_.height - imageHeight_ / cursorUnit;
1492             }
1493         } else {
1494             if (physicalX > (displayInfo_.height - imageHeight_ / cursorUnit)) {
1495                 physicalX = displayInfo_.height - imageHeight_ / cursorUnit;
1496             }
1497             if (physicalY > (displayInfo_.width - imageWidth_ / cursorUnit)) {
1498                 physicalY = displayInfo_.width - imageWidth_ / cursorUnit;
1499             }
1500         }
1501     } else {
1502         if (physicalX > (displayInfo_.width - imageWidth_ / cursorUnit)) {
1503             physicalX = displayInfo_.width - imageWidth_ / cursorUnit;
1504         }
1505         if (physicalY > (displayInfo_.height - imageHeight_ / cursorUnit)) {
1506             physicalY = displayInfo_.height - imageHeight_ / cursorUnit;
1507         }
1508     }
1509 }
1510 
AttachToDisplay()1511 void PointerDrawingManager::AttachToDisplay()
1512 {
1513     CALL_DEBUG_ENTER;
1514     CHKPV(surfaceNode_);
1515     if (IsSingleDisplayFoldDevice() && (WIN_MGR->GetDisplayMode() == DisplayMode::MAIN)
1516         && (screenId_ == FOLD_SCREEN_ID_FULL)) {
1517         screenId_ = FOLD_SCREEN_ID_MAIN;
1518     }
1519     MMI_HILOGI("screenId_: %{public}" PRIu64"", screenId_);
1520     surfaceNode_->AttachToDisplay(screenId_);
1521 }
1522 
CreateCanvasNode()1523 void PointerDrawingManager::CreateCanvasNode()
1524 {
1525 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1526     CHKPV(hardwareCursorPointerManager_);
1527     CHKPV(surfaceNode_);
1528     if (!hardwareCursorPointerManager_->IsSupported()) {
1529         canvasNode_ = Rosen::RSCanvasNode::Create();
1530         CHKPV(canvasNode_);
1531         canvasNode_->SetBounds(0, 0, canvasWidth_, canvasHeight_);
1532         canvasNode_->SetFrame(0, 0, canvasWidth_, canvasHeight_);
1533 #ifndef USE_ROSEN_DRAWING
1534         canvasNode_->SetBackgroundColor(SK_ColorTRANSPARENT);
1535 #else
1536         canvasNode_->SetBackgroundColor(Rosen::Drawing::Color::COLOR_TRANSPARENT);
1537 #endif // USE_ROSEN_DRAWING
1538         canvasNode_->SetCornerRadius(1);
1539         canvasNode_->SetPositionZ(Rosen::RSSurfaceNode::POINTER_WINDOW_POSITION_Z);
1540         canvasNode_->SetRotation(0);
1541         surfaceNode_->AddChild(canvasNode_, DEFAULT_VALUE);
1542     }
1543 #else
1544     canvasNode_ = Rosen::RSCanvasNode::Create();
1545     CHKPV(canvasNode_);
1546     canvasNode_->SetBounds(0, 0, canvasWidth_, canvasHeight_);
1547     canvasNode_->SetFrame(0, 0, canvasWidth_, canvasHeight_);
1548 #ifndef USE_ROSEN_DRAWING
1549     canvasNode_->SetBackgroundColor(SK_ColorTRANSPARENT);
1550 #else
1551     canvasNode_->SetBackgroundColor(Rosen::Drawing::Color::COLOR_TRANSPARENT);
1552 #endif // USE_ROSEN_DRAWING
1553     canvasNode_->SetCornerRadius(1);
1554     canvasNode_->SetPositionZ(Rosen::RSSurfaceNode::POINTER_WINDOW_POSITION_Z);
1555     canvasNode_->SetRotation(0);
1556     surfaceNode_->AddChild(canvasNode_, DEFAULT_VALUE);
1557 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1558 }
1559 
CreatePointerWindow(int32_t displayId, int32_t physicalX, int32_t physicalY, Direction direction)1560 void PointerDrawingManager::CreatePointerWindow(int32_t displayId, int32_t physicalX, int32_t physicalY,
1561     Direction direction)
1562 {
1563     CALL_DEBUG_ENTER;
1564     CALL_INFO_TRACE;
1565     Rosen::RSSurfaceNodeConfig surfaceNodeConfig;
1566     surfaceNodeConfig.SurfaceNodeName = "pointer window";
1567     Rosen::RSSurfaceNodeType surfaceNodeType = Rosen::RSSurfaceNodeType::SELF_DRAWING_WINDOW_NODE;
1568     surfaceNode_ = Rosen::RSSurfaceNode::Create(surfaceNodeConfig, surfaceNodeType);
1569     CHKPV(surfaceNode_);
1570     surfaceNode_->SetPositionZ(Rosen::RSSurfaceNode::POINTER_WINDOW_POSITION_Z);
1571 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1572     CHKPV(hardwareCursorPointerManager_);
1573     hardwareCursorPointerManager_->SetTargetDevice(displayId);
1574     if (g_isHdiRemoteDied) {
1575         hardwareCursorPointerManager_->SetHdiServiceState(false);
1576     }
1577     if (hardwareCursorPointerManager_->IsSupported()) {
1578         surfaceNode_->SetFrameGravity(Rosen::Gravity::TOP_LEFT);
1579         g_isHdiRemoteDied = false;
1580         CALCULATE_CANVAS_SIZE(CALCULATE_CANVAS_SIZE_, CHANGE) = GetCanvasSize();
1581         surfaceNode_->SetBounds(
1582             (physicalX - CalculateHardwareXOffset(ICON_TYPE(mouseIcons_[MOUSE_ICON(
1583                 lastMouseStyle_.id)].alignmentWay))),
1584             (physicalY - CalculateHardwareYOffset(ICON_TYPE(mouseIcons_[MOUSE_ICON(
1585                 lastMouseStyle_.id)].alignmentWay))),
1586             CALCULATE_CANVAS_SIZE_CHANGE,
1587             CALCULATE_CANVAS_SIZE_CHANGE);
1588     } else {
1589         surfaceNode_->SetFrameGravity(Rosen::Gravity::RESIZE_ASPECT_FILL);
1590         surfaceNode_->SetBounds(physicalX, physicalY, canvasWidth_, canvasHeight_);
1591     }
1592 #else
1593     surfaceNode_->SetFrameGravity(Rosen::Gravity::RESIZE_ASPECT_FILL);
1594     surfaceNode_->SetBounds(physicalX, physicalY, canvasWidth_, canvasHeight_);
1595 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1596 #ifndef USE_ROSEN_DRAWING
1597     surfaceNode_->SetBackgroundColor(SK_ColorTRANSPARENT);
1598 #else
1599     surfaceNode_->SetBackgroundColor(Rosen::Drawing::Color::COLOR_TRANSPARENT);
1600 #endif
1601 
1602     screenId_ = static_cast<uint64_t>(displayId);
1603     std::cout << "ScreenId: " << screenId_ << std::endl;
1604     AttachToDisplay();
1605     lastDisplayId_ = displayId;
1606     RotateDegree(direction);
1607     lastDirection_ = direction;
1608     CreateCanvasNode();
1609     Rosen::RSTransaction::FlushImplicitTransaction();
1610 }
1611 
GetLayer()1612 sptr<OHOS::Surface> PointerDrawingManager::GetLayer()
1613 {
1614     CALL_DEBUG_ENTER;
1615     CHKPP(surfaceNode_);
1616     return surfaceNode_->GetSurface();
1617 }
1618 
GetSurfaceBuffer(sptr<OHOS::Surface> layer) const1619 sptr<OHOS::SurfaceBuffer> PointerDrawingManager::GetSurfaceBuffer(sptr<OHOS::Surface> layer) const
1620 {
1621     CALL_DEBUG_ENTER;
1622     sptr<OHOS::SurfaceBuffer> buffer;
1623     int32_t releaseFence = -1;
1624     int32_t width = 0;
1625     int32_t height = 0;
1626 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1627     CHKPP(hardwareCursorPointerManager_);
1628     if (g_isHdiRemoteDied) {
1629         hardwareCursorPointerManager_->SetHdiServiceState(false);
1630     }
1631     if (hardwareCursorPointerManager_->IsSupported()) {
1632         CALCULATE_CANVAS_SIZE(CALCULATE_CANVAS_SIZE_, CHANGE) = GetCanvasSize();
1633         auto canvasSize = static_cast<int32_t>(CALCULATE_CANVAS_SIZE_CHANGE);
1634         width = canvasSize;
1635         height = canvasSize;
1636     } else {
1637         width = canvasWidth_;
1638         height = canvasHeight_;
1639     }
1640 #else
1641     width = canvasWidth_;
1642     height = canvasHeight_;
1643 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1644     OHOS::BufferRequestConfig config = {
1645         .width = width,
1646         .height = height,
1647         .strideAlignment = 0x8,
1648         .format = GRAPHIC_PIXEL_FMT_RGBA_8888,
1649         .usage = BUFFER_USAGE_CPU_READ | BUFFER_USAGE_CPU_WRITE | BUFFER_USAGE_MEM_DMA,
1650         .timeout = 150,
1651     };
1652 
1653     OHOS::SurfaceError ret = layer->RequestBuffer(buffer, releaseFence, config);
1654     if (ret != OHOS::SURFACE_ERROR_OK) {
1655         MMI_HILOGE("Request buffer ret:%{public}s", SurfaceErrorStr(ret).c_str());
1656         return nullptr;
1657     }
1658 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1659     if (hardwareCursorPointerManager_->IsSupported()) {
1660         sptr<OHOS::SyncFence> tempFence = new OHOS::SyncFence(releaseFence);
1661         if (tempFence != nullptr && (tempFence->Wait(SYNC_FENCE_WAIT_TIME) < 0)) {
1662             MMI_HILOGE("Failed to create surface, this buffer is not available");
1663         }
1664     }
1665 #else
1666     close(releaseFence);
1667 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1668     return buffer;
1669 }
1670 
DrawDynamicImage(OHOS::Rosen::Drawing::Canvas &canvas, MOUSE_ICON mouseStyle)1671 void PointerDrawingManager::DrawDynamicImage(OHOS::Rosen::Drawing::Canvas &canvas, MOUSE_ICON mouseStyle)
1672 {
1673     CALL_DEBUG_ENTER;
1674     OHOS::Rosen::Drawing::Pen pen;
1675     pen.SetAntiAlias(true);
1676     pen.SetColor(OHOS::Rosen::Drawing::Color::COLOR_BLUE);
1677     OHOS::Rosen::Drawing::scalar penWidth = 1;
1678     pen.SetWidth(penWidth);
1679     canvas.AttachPen(pen);
1680     CHKPV(image_);
1681     OHOS::Rosen::Drawing::Brush brush;
1682     brush.SetColor(Rosen::Drawing::Color::COLOR_TRANSPARENT);
1683     canvas.DrawBackground(brush);
1684     ICON_TYPE iconType = ICON_TYPE::ANGLE_NW;
1685     if (mouseStyle == MOUSE_ICON::LOADING) {
1686         iconType = ICON_TYPE::ANGLE_CENTER;
1687     } else {
1688         iconType = ICON_TYPE::ANGLE_NW;
1689     }
1690     float physicalXOffset = CalculateHardwareXOffset(iconType);
1691     float physicalYOffset = CalculateHardwareYOffset(iconType);
1692     if (mouseStyle == MOUSE_ICON::RUNNING_RIGHT) {
1693         CHKPV(runningRightImage_);
1694         canvas.DrawImage(*runningRightImage_, physicalXOffset, physicalYOffset, Rosen::Drawing::SamplingOptions());
1695     } else {
1696         canvas.DrawImage(*image_, physicalXOffset, physicalYOffset, Rosen::Drawing::SamplingOptions());
1697     }
1698 }
1699 
DrawImage(OHOS::Rosen::Drawing::Canvas &canvas, MOUSE_ICON mouseStyle)1700 void PointerDrawingManager::DrawImage(OHOS::Rosen::Drawing::Canvas &canvas, MOUSE_ICON mouseStyle)
1701 {
1702     MMI_HILOGI("Draw mouse icon of style(%{public}d)", static_cast<int32_t>(mouseStyle));
1703     OHOS::Rosen::Drawing::Pen pen;
1704     pen.SetAntiAlias(true);
1705     pen.SetColor(OHOS::Rosen::Drawing::Color::COLOR_BLUE);
1706     OHOS::Rosen::Drawing::scalar penWidth = 1;
1707     pen.SetWidth(penWidth);
1708     canvas.AttachPen(pen);
1709     std::shared_ptr<Rosen::Drawing::Image> image = nullptr;
1710     std::shared_ptr<OHOS::Media::PixelMap> pixelmap = nullptr;
1711     if (mouseStyle == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1712         MMI_HILOGD("Set mouseicon by userIcon_");
1713         image = ExtractDrawingImage(userIcon_);
1714 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
1715         SetPixelMap(userIcon_);
1716 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
1717     } else {
1718         if (mouseStyle == MOUSE_ICON::RUNNING) {
1719             pixelmap = DecodeImageToPixelMap(mouseIcons_[MOUSE_ICON::RUNNING_LEFT].iconPath);
1720         } else {
1721             pixelmap = DecodeImageToPixelMap(mouseIcons_[mouseStyle].iconPath);
1722         }
1723         CHKPV(pixelmap);
1724         image = ExtractDrawingImage(pixelmap);
1725 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
1726         if ((mouseStyle == MOUSE_ICON::DEFAULT) || (mouseStyle == MOUSE_ICON::CURSOR_CIRCLE)) {
1727             SetPixelMap(pixelmap);
1728         }
1729 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
1730     }
1731     CHKPV(image);
1732     OHOS::Rosen::Drawing::Brush brush;
1733     brush.SetColor(Rosen::Drawing::Color::COLOR_TRANSPARENT);
1734     canvas.DrawBackground(brush);
1735 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1736     CHKPV(hardwareCursorPointerManager_);
1737     if (hardwareCursorPointerManager_->IsSupported()) {
1738         float physicalXOffset = CalculateHardwareXOffset(ICON_TYPE(mouseIcons_[MOUSE_ICON(
1739             mouseStyle)].alignmentWay));
1740         float physicalYOffset = CalculateHardwareYOffset(ICON_TYPE(mouseIcons_[MOUSE_ICON(
1741             mouseStyle)].alignmentWay));
1742         canvas.DrawImage(*image, physicalXOffset, physicalYOffset, Rosen::Drawing::SamplingOptions());
1743     } else {
1744         canvas.DrawImage(*image, IMAGE_PIXEL, IMAGE_PIXEL, Rosen::Drawing::SamplingOptions());
1745     }
1746 #else
1747     canvas.DrawImage(*image, IMAGE_PIXEL, IMAGE_PIXEL, Rosen::Drawing::SamplingOptions());
1748 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
1749     MMI_HILOGD("Canvas draw image, success");
1750 }
1751 
1752 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
SetPixelMap(std::shared_ptr<OHOS::Media::PixelMap> pixelMap)1753 void PointerDrawingManager::SetPixelMap(std::shared_ptr<OHOS::Media::PixelMap> pixelMap)
1754 {
1755     MMI_HILOGI("Set pointer snapshot");
1756     pixelMap_ = pixelMap;
1757 }
1758 
GetPointerSnapshot(void *pixelMapPtr)1759 int32_t PointerDrawingManager::GetPointerSnapshot(void *pixelMapPtr)
1760 {
1761     CALL_DEBUG_ENTER;
1762     std::shared_ptr<Media::PixelMap> *newPixelMapPtr = static_cast<std::shared_ptr<Media::PixelMap> *>(pixelMapPtr);
1763     MMI_HILOGI("Get pointer snapshot");
1764     *newPixelMapPtr = pixelMap_;
1765     if (HasMagicCursor()) {
1766         MMI_HILOGE("magic pixelmap");
1767         *newPixelMapPtr = MAGIC_CURSOR->GetPixelMap();
1768     }
1769     CHKPR(*newPixelMapPtr, ERROR_NULL_POINTER);
1770     return RET_OK;
1771 }
1772 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
1773 
DoDraw(uint8_t *addr, uint32_t width, uint32_t height, const MOUSE_ICON mouseStyle)1774 void PointerDrawingManager::DoDraw(uint8_t *addr, uint32_t width, uint32_t height, const MOUSE_ICON mouseStyle)
1775 {
1776     CALL_DEBUG_ENTER;
1777     currentFrame_ = 0;
1778     OHOS::Rosen::Drawing::Bitmap bitmap;
1779     OHOS::Rosen::Drawing::BitmapFormat format { OHOS::Rosen::Drawing::COLORTYPE_RGBA_8888,
1780         OHOS::Rosen::Drawing::ALPHATYPE_OPAQUE };
1781     bitmap.Build(width, height, format);
1782     OHOS::Rosen::Drawing::Canvas canvas;
1783     canvas.Bind(bitmap);
1784     canvas.Clear(OHOS::Rosen::Drawing::Color::COLOR_TRANSPARENT);
1785     DrawImage(canvas, mouseStyle);
1786     static constexpr uint32_t stride = 4;
1787     uint32_t addrSize = width * height * stride;
1788     errno_t ret = memcpy_s(addr, addrSize, bitmap.GetPixels(), addrSize);
1789     if (ret != EOK) {
1790         MMI_HILOGE("Memcpy data is error, ret:%{public}d", ret);
1791         return;
1792     }
1793 }
1794 
DrawPixelmap(OHOS::Rosen::Drawing::Canvas &canvas, const MOUSE_ICON mouseStyle)1795 void PointerDrawingManager::DrawPixelmap(OHOS::Rosen::Drawing::Canvas &canvas, const MOUSE_ICON mouseStyle)
1796 {
1797     CALL_DEBUG_ENTER;
1798     OHOS::Rosen::Drawing::Pen pen;
1799     pen.SetAntiAlias(true);
1800     pen.SetColor(OHOS::Rosen::Drawing::Color::COLOR_BLUE);
1801     OHOS::Rosen::Drawing::scalar penWidth = 1;
1802     pen.SetWidth(penWidth);
1803     canvas.AttachPen(pen);
1804     if (mouseStyle == MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1805         MMI_HILOGD("Set mouseicon by userIcon_");
1806         OHOS::Rosen::RSPixelMapUtil::DrawPixelMap(canvas, *userIcon_, 0, 0);
1807     } else {
1808         std::shared_ptr<OHOS::Media::PixelMap> pixelmap;
1809         if (mouseStyle == MOUSE_ICON::RUNNING) {
1810             pixelmap = DecodeImageToPixelMap(mouseIcons_[MOUSE_ICON::RUNNING_LEFT].iconPath);
1811         } else {
1812             pixelmap = DecodeImageToPixelMap(mouseIcons_[mouseStyle].iconPath);
1813         }
1814         CHKPV(pixelmap);
1815         MMI_HILOGD("Set mouseicon to OHOS system");
1816         OHOS::Rosen::RSPixelMapUtil::DrawPixelMap(canvas, *pixelmap, 0, 0);
1817     }
1818 }
1819 
SetCustomCursor(void* pixelMap, int32_t pid, int32_t windowId, int32_t focusX, int32_t focusY)1820 int32_t PointerDrawingManager::SetCustomCursor(void* pixelMap, int32_t pid, int32_t windowId, int32_t focusX,
1821     int32_t focusY)
1822 {
1823     CALL_DEBUG_ENTER;
1824     CHKPR(pixelMap, RET_ERR);
1825     if (pid == -1) {
1826         MMI_HILOGE("The pid is invalid");
1827         return RET_ERR;
1828     }
1829     if (windowId < 0) {
1830         MMI_HILOGE("The windowId is invalid, windowId:%{public}d", windowId);
1831         return RET_ERR;
1832     }
1833     if (WIN_MGR->CheckWindowIdPermissionByPid(windowId, pid) != RET_OK) {
1834         MMI_HILOGE("The windowId not in right pid");
1835         return RET_ERR;
1836     }
1837     int32_t ret = UpdateCursorProperty(pixelMap, focusX, focusY);
1838     if (ret != RET_OK) {
1839         MMI_HILOGE("UpdateCursorProperty is failed");
1840         return ret;
1841     }
1842     mouseIconUpdate_ = true;
1843     PointerStyle style;
1844     style.id = MOUSE_ICON::DEVELOPER_DEFINED_ICON;
1845     lastMouseStyle_ = style;
1846 
1847     ret = SetPointerStyle(pid, windowId, style);
1848     if (ret == RET_ERR) {
1849         MMI_HILOGE("SetPointerStyle is failed");
1850     }
1851     MMI_HILOGD("style.id:%{public}d, userIconHotSpotX_:%{public}d, userIconHotSpotY_:%{public}d",
1852         style.id, userIconHotSpotX_, userIconHotSpotY_);
1853     return ret;
1854 }
1855 
UpdateCursorProperty(void* pixelMap, const int32_t &focusX, const int32_t &focusY)1856 int32_t PointerDrawingManager::UpdateCursorProperty(void* pixelMap, const int32_t &focusX, const int32_t &focusY)
1857 {
1858     CHKPR(pixelMap, RET_ERR);
1859     Media::PixelMap* newPixelMap = static_cast<Media::PixelMap*>(pixelMap);
1860     CHKPR(newPixelMap, RET_ERR);
1861     Media::ImageInfo imageInfo;
1862     newPixelMap->GetImageInfo(imageInfo);
1863     int32_t cursorSize = GetPointerSize();
1864     cursorWidth_ =
1865         pow(INCREASE_RATIO, cursorSize - 1) * displayInfo_.dpi * GetIndependentPixels() / BASELINE_DENSITY;
1866     cursorHeight_ =
1867         pow(INCREASE_RATIO, cursorSize - 1) * displayInfo_.dpi * GetIndependentPixels() / BASELINE_DENSITY;
1868     cursorWidth_ = cursorWidth_ < MIN_CURSOR_SIZE ? MIN_CURSOR_SIZE : cursorWidth_;
1869     cursorHeight_ = cursorHeight_ < MIN_CURSOR_SIZE ? MIN_CURSOR_SIZE : cursorHeight_;
1870     float xAxis = (float)cursorWidth_ / (float)imageInfo.size.width;
1871     float yAxis = (float)cursorHeight_ / (float)imageInfo.size.height;
1872     newPixelMap->scale(xAxis, yAxis, Media::AntiAliasingOption::LOW);
1873     userIcon_.reset(newPixelMap);
1874     userIconHotSpotX_ = static_cast<int32_t>((float)focusX * xAxis);
1875     userIconHotSpotY_ = static_cast<int32_t>((float)focusY * yAxis);
1876     MMI_HILOGI("cursorWidth:%{public}d, cursorHeight:%{public}d, imageWidth:%{public}d, imageHeight:%{public}d,"
1877         "focusX:%{public}d, focuxY:%{public}d, xAxis:%{public}f, yAxis:%{public}f, userIconHotSpotX_:%{public}d,"
1878         "userIconHotSpotY_:%{public}d", cursorWidth_, cursorHeight_, imageInfo.size.width, imageInfo.size.height,
1879         focusX, focusY, xAxis, yAxis, userIconHotSpotX_, userIconHotSpotY_);
1880     return RET_OK;
1881 }
1882 
1883 int32_t PointerDrawingManager::SetMouseIcon(int32_t pid, int32_t windowId, void* pixelMap)
1884     __attribute__((no_sanitize("cfi")))
1885 {
1886     CALL_DEBUG_ENTER;
1887     if (pid == -1) {
1888         MMI_HILOGE("pid is invalid return -1");
1889         return RET_ERR;
1890     }
1891     CHKPR(pixelMap, RET_ERR);
1892     if (windowId < 0) {
1893         MMI_HILOGE("Get invalid windowId, %{public}d", windowId);
1894         return RET_ERR;
1895     }
1896     if (WIN_MGR->CheckWindowIdPermissionByPid(windowId, pid) != RET_OK) {
1897         MMI_HILOGE("windowId not in right pid");
1898         return RET_ERR;
1899     }
1900     OHOS::Media::PixelMap* pixelMapPtr = static_cast<OHOS::Media::PixelMap*>(pixelMap);
1901     userIcon_.reset(pixelMapPtr);
1902     mouseIconUpdate_ = true;
1903     PointerStyle style;
1904     style.id = MOUSE_ICON::DEVELOPER_DEFINED_ICON;
1905     int32_t ret = SetPointerStyle(pid, windowId, style);
1906     if (ret == RET_ERR) {
1907         MMI_HILOGE("SetPointerStyle return RET_ERR here");
1908     }
1909     return ret;
1910 }
1911 
1912 int32_t PointerDrawingManager::SetMouseHotSpot(int32_t pid, int32_t windowId, int32_t hotSpotX, int32_t hotSpotY)
1913 {
1914     CALL_DEBUG_ENTER;
1915     if (pid == -1) {
1916         MMI_HILOGE("pid is invalid return -1");
1917         return RET_ERR;
1918     }
1919     if (windowId < 0) {
1920         MMI_HILOGE("invalid windowId, %{public}d", windowId);
1921         return RET_ERR;
1922     }
1923     if (WIN_MGR->CheckWindowIdPermissionByPid(windowId, pid) != RET_OK) {
1924         MMI_HILOGE("windowId not in right pid");
1925         return RET_ERR;
1926     }
1927     if (hotSpotX < 0 || hotSpotY < 0 || userIcon_ == nullptr) {
1928         MMI_HILOGE("invalid value");
1929         return RET_ERR;
1930     }
1931     PointerStyle pointerStyle;
1932     WIN_MGR->GetPointerStyle(pid, windowId, pointerStyle);
1933     if (pointerStyle.id != MOUSE_ICON::DEVELOPER_DEFINED_ICON) {
1934         MMI_HILOGE("Get pointer style failed, pid %{publid}d, pointerStyle %{public}d", pid, pointerStyle.id);
1935         return RET_ERR;
1936     }
1937     userIconHotSpotX_ = hotSpotX;
1938     userIconHotSpotY_ = hotSpotY;
1939     return RET_OK;
1940 }
1941 
1942 std::shared_ptr<OHOS::Media::PixelMap> PointerDrawingManager::DecodeImageToPixelMap(const std::string &imagePath)
1943 {
1944     CALL_DEBUG_ENTER;
1945     OHOS::Media::SourceOptions opts;
1946     uint32_t ret = 0;
1947     auto imageSource = OHOS::Media::ImageSource::CreateImageSource(imagePath, opts, ret);
1948     CHKPP(imageSource);
1949     std::set<std::string> formats;
1950     ret = imageSource->GetSupportedFormats(formats);
1951     MMI_HILOGD("Get supported format ret:%{public}u", ret);
1952 
1953     OHOS::Media::DecodeOptions decodeOpts;
1954     decodeOpts.desiredSize = {
1955         .width = imageWidth_,
1956         .height = imageHeight_
1957     };
1958     int32_t pointerColor = GetPointerColor();
1959     if (tempPointerColor_ != DEFAULT_VALUE) {
1960         decodeOpts.SVGOpts.fillColor = {.isValidColor = true, .color = pointerColor};
1961         if (pointerColor == MAX_POINTER_COLOR) {
1962             decodeOpts.SVGOpts.strokeColor = {.isValidColor = true, .color = MIN_POINTER_COLOR};
1963         } else {
1964             decodeOpts.SVGOpts.strokeColor = {.isValidColor = true, .color = MAX_POINTER_COLOR};
1965         }
1966     }
1967 
1968     std::shared_ptr<OHOS::Media::PixelMap> pixelMap = imageSource->CreatePixelMap(decodeOpts, ret);
1969     CHKPL(pixelMap);
1970     return pixelMap;
1971 }
1972 
GetPreferenceKey(std::string &name)1973 void PointerDrawingManager::GetPreferenceKey(std::string &name)
1974 {
1975 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
1976     if (HasMagicCursor()) {
1977         if (name == POINTER_COLOR) {
1978             name = MAGIC_POINTER_COLOR;
1979         } else if (name == POINTER_SIZE) {
1980             name = MAGIC_POINTER_SIZE;
1981         }
1982     }
1983 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
1984 }
1985 
SetPointerColor(int32_t color)1986 int32_t PointerDrawingManager::SetPointerColor(int32_t color)
1987 {
1988     CALL_DEBUG_ENTER;
1989     if (surfaceNode_ != nullptr) {
1990         float alphaRatio = (static_cast<uint32_t>(color) >> RGB_CHANNEL_BITS_LENGTH) / MAX_ALPHA_VALUE;
1991         if (alphaRatio > 1) {
1992             MMI_HILOGW("Invalid alphaRatio:%{public}f", alphaRatio);
1993         } else {
1994             surfaceNode_->SetAlpha(1 - alphaRatio);
1995         }
1996     }
1997     MMI_HILOGI("PointerColor:%{public}x", color);
1998     // ARGB从表面看比RGB多了个A,也是一种色彩模式,是在RGB的基础上添加了Alpha(透明度)通道。
1999     // 透明度也是以0到255表示的,所以也是总共有256级,透明是0,不透明是255。
2000     // 这个color每8位代表一个通道值,分别是alpha和rgb,总共32位。
2001     color = static_cast<int32_t>(static_cast<uint32_t>(color) & static_cast<uint32_t>(MAX_POINTER_COLOR));
2002     std::string name = POINTER_COLOR;
2003     GetPreferenceKey(name);
2004     int32_t ret = PREFERENCES_MGR->SetIntValue(name, MOUSE_FILE_NAME, color);
2005     if (ret != RET_OK) {
2006         MMI_HILOGE("Set pointer color failed, color:%{public}d", color);
2007         return ret;
2008     }
2009     MMI_HILOGD("Set pointer color successfully, color:%{public}d", color);
2010 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2011     if (HasMagicCursor()) {
2012         ret = MAGIC_CURSOR->SetPointerColor(color);
2013     } else {
2014         ret = InitLayer(MOUSE_ICON(lastMouseStyle_.id));
2015     }
2016 #else
2017     ret = InitLayer(MOUSE_ICON(lastMouseStyle_.id));
2018 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2019     if (ret != RET_OK) {
2020         MMI_HILOGE("Init layer failed");
2021         return RET_ERR;
2022     }
2023     UpdatePointerVisible();
2024     SetHardwareCursorPosition(displayInfo_.id, lastPhysicalX_, lastPhysicalY_, lastMouseStyle_);
2025     return RET_OK;
2026 }
2027 
GetPointerColor()2028 int32_t PointerDrawingManager::GetPointerColor()
2029 {
2030     CALL_DEBUG_ENTER;
2031     std::string name = POINTER_COLOR;
2032     GetPreferenceKey(name);
2033     int32_t pointerColor = PREFERENCES_MGR->GetIntValue(name, DEFAULT_VALUE);
2034     tempPointerColor_ = pointerColor;
2035     if (pointerColor == DEFAULT_VALUE) {
2036         pointerColor = MIN_POINTER_COLOR;
2037     }
2038     MMI_HILOGD("Get pointer color successfully, pointerColor:%{public}d", pointerColor);
2039     return pointerColor;
2040 }
2041 
UpdateDisplayInfo(const DisplayInfo &displayInfo)2042 void PointerDrawingManager::UpdateDisplayInfo(const DisplayInfo &displayInfo)
2043 {
2044     CALL_DEBUG_ENTER;
2045 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2046     CHKPV(hardwareCursorPointerManager_);
2047     hardwareCursorPointerManager_->SetTargetDevice(displayInfo.id);
2048 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2049     hasDisplay_ = true;
2050     displayInfo_ = displayInfo;
2051     int32_t size = GetPointerSize();
2052     imageWidth_ = pow(INCREASE_RATIO, size - 1) * displayInfo.dpi * GetIndependentPixels() / BASELINE_DENSITY;
2053     imageHeight_ = pow(INCREASE_RATIO, size - 1) * displayInfo.dpi * GetIndependentPixels() / BASELINE_DENSITY;
2054     canvasWidth_ = (imageWidth_ / POINTER_WINDOW_INIT_SIZE + 1) * POINTER_WINDOW_INIT_SIZE;
2055     canvasHeight_ = (imageHeight_ / POINTER_WINDOW_INIT_SIZE + 1) * POINTER_WINDOW_INIT_SIZE;
2056 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2057     MAGIC_CURSOR->SetDisplayInfo(displayInfo);
2058 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2059 }
2060 
GetIndependentPixels()2061 int32_t PointerDrawingManager::GetIndependentPixels()
2062 {
2063     CALL_DEBUG_ENTER;
2064 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2065     if (HasMagicCursor()) {
2066         return MAGIC_INDEPENDENT_PIXELS;
2067     } else {
2068         return DEVICE_INDEPENDENT_PIXELS;
2069     }
2070 #else
2071     return DEVICE_INDEPENDENT_PIXELS;
2072 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2073 }
2074 
SetPointerSize(int32_t size)2075 int32_t PointerDrawingManager::SetPointerSize(int32_t size)
2076 {
2077     CALL_DEBUG_ENTER;
2078     if (size < MIN_POINTER_SIZE) {
2079         size = MIN_POINTER_SIZE;
2080     } else if (size > MAX_POINTER_SIZE) {
2081         size = MAX_POINTER_SIZE;
2082     }
2083     std::string name = POINTER_SIZE;
2084     GetPreferenceKey(name);
2085     int32_t ret = PREFERENCES_MGR->SetIntValue(name, MOUSE_FILE_NAME, size);
2086     if (ret != RET_OK) {
2087         MMI_HILOGE("Set pointer size failed, code:%{public}d", ret);
2088         return ret;
2089     }
2090 
2091     CHKPR(surfaceNode_, RET_OK);
2092     imageWidth_ = pow(INCREASE_RATIO, size - 1) * displayInfo_.dpi * GetIndependentPixels() / BASELINE_DENSITY;
2093     imageHeight_ = pow(INCREASE_RATIO, size - 1) * displayInfo_.dpi * GetIndependentPixels() / BASELINE_DENSITY;
2094     canvasWidth_ = (imageWidth_ / POINTER_WINDOW_INIT_SIZE + 1) * POINTER_WINDOW_INIT_SIZE;
2095     canvasHeight_ = (imageHeight_ / POINTER_WINDOW_INIT_SIZE + 1) * POINTER_WINDOW_INIT_SIZE;
2096     int32_t physicalX = lastPhysicalX_;
2097     int32_t physicalY = lastPhysicalY_;
2098 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2099     MAGIC_CURSOR->SetPointerSize(imageWidth_, imageHeight_);
2100 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2101     Direction direction = DIRECTION0;
2102     if (IsWindowRotation()) {
2103         direction = displayInfo_.direction;
2104     }
2105     auto& iconPath = GetMouseIconPath();
2106     AdjustMouseFocus(direction, ICON_TYPE(iconPath.at(MOUSE_ICON(lastMouseStyle_.id)).alignmentWay),
2107         physicalX, physicalY);
2108 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2109     if (HasMagicCursor()) {
2110         MAGIC_CURSOR->CreatePointerWindow(displayInfo_.id, physicalX, physicalY, direction, surfaceNode_);
2111     } else {
2112         CreatePointerWindow(displayInfo_.id, physicalX, physicalY, direction);
2113     }
2114 #else
2115     CreatePointerWindow(displayInfo_.id, physicalX, physicalY, direction);
2116 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2117     if (InitLayer(MOUSE_ICON(lastMouseStyle_.id)) != RET_OK) {
2118         MMI_HILOGE("Init layer failed");
2119         return RET_ERR;
2120     }
2121     UpdatePointerVisible();
2122     SetHardwareCursorPosition(displayInfo_.id, physicalX, physicalY, lastMouseStyle_);
2123     return RET_OK;
2124 }
2125 
GetPointerSize()2126 int32_t PointerDrawingManager::GetPointerSize()
2127 {
2128     CALL_DEBUG_ENTER;
2129     std::string name = POINTER_SIZE;
2130     GetPreferenceKey(name);
2131     int32_t pointerSize = PREFERENCES_MGR->GetIntValue(name, DEFAULT_POINTER_SIZE);
2132     MMI_HILOGD("Get pointer size successfully, pointerSize:%{public}d", pointerSize);
2133     return pointerSize;
2134 }
2135 
OnDisplayInfo(const DisplayGroupInfo &displayGroupInfo)2136 void PointerDrawingManager::OnDisplayInfo(const DisplayGroupInfo &displayGroupInfo)
2137 {
2138     CALL_DEBUG_ENTER;
2139     for (const auto& item : displayGroupInfo.displaysInfo) {
2140         if (item.id == displayInfo_.id) {
2141             UpdateDisplayInfo(item);
2142             DrawManager();
2143             return;
2144         }
2145     }
2146     UpdateDisplayInfo(displayGroupInfo.displaysInfo[0]);
2147     lastPhysicalX_ = displayGroupInfo.displaysInfo[0].width / CALCULATE_MIDDLE;
2148     lastPhysicalY_ = displayGroupInfo.displaysInfo[0].height / CALCULATE_MIDDLE;
2149     MouseEventHdr->OnDisplayLost(displayInfo_.id);
2150     if (surfaceNode_ != nullptr) {
2151         surfaceNode_->DetachToDisplay(screenId_);
2152 #ifndef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2153         surfaceNode_ = nullptr;
2154 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2155         Rosen::RSTransaction::FlushImplicitTransaction();
2156         MMI_HILOGD("Pointer window destroy success");
2157     }
2158     MMI_HILOGD("displayId_:%{public}d, displayWidth_:%{public}d, displayHeight_:%{public}d",
2159         displayInfo_.id, displayInfo_.width, displayInfo_.height);
2160 }
2161 
OnWindowInfo(const WinInfo &info)2162 void PointerDrawingManager::OnWindowInfo(const WinInfo &info)
2163 {
2164     CALL_DEBUG_ENTER;
2165     if (pid_ != info.windowPid) {
2166         windowId_ = info.windowId;
2167         pid_ = info.windowPid;
2168         UpdatePointerVisible();
2169     }
2170 }
2171 
UpdatePointerDevice(bool hasPointerDevice, bool isPointerVisible, bool isHotPlug)2172 void PointerDrawingManager::UpdatePointerDevice(bool hasPointerDevice, bool isPointerVisible,
2173     bool isHotPlug)
2174 {
2175     CALL_DEBUG_ENTER;
2176     MMI_HILOGD("hasPointerDevice:%{public}s, isPointerVisible:%{public}s",
2177         hasPointerDevice ? "true" : "false", isPointerVisible? "true" : "false");
2178     hasPointerDevice_ = hasPointerDevice;
2179     if (hasPointerDevice_) {
2180         bool pointerVisible = isPointerVisible;
2181         if (!isHotPlug) {
2182             pointerVisible = (pointerVisible && IsPointerVisible());
2183         }
2184         SetPointerVisible(getpid(), pointerVisible, 0, false);
2185     } else {
2186         DeletePointerVisible(getpid());
2187     }
2188     DrawManager();
2189     if (!hasPointerDevice_ && surfaceNode_ != nullptr) {
2190         MMI_HILOGD("Pointer window destroy start");
2191         surfaceNode_->DetachToDisplay(screenId_);
2192         surfaceNode_ = nullptr;
2193         Rosen::RSTransaction::FlushImplicitTransaction();
2194         MMI_HILOGD("Pointer window destroy success");
2195     }
2196 }
2197 
DrawManager()2198 void PointerDrawingManager::DrawManager()
2199 {
2200     CALL_DEBUG_ENTER;
2201 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2202     if (HasMagicCursor() && lastDrawPointerStyle_.id != currentMouseStyle_.id
2203         && (lastDrawPointerStyle_.id == DEVELOPER_DEFINED_ICON
2204         || currentMouseStyle_.id == DEVELOPER_DEFINED_ICON)) {
2205         if (surfaceNode_ != nullptr) {
2206             surfaceNode_->DetachToDisplay(screenId_);
2207             surfaceNode_ = nullptr;
2208             Rosen::RSTransaction::FlushImplicitTransaction();
2209         }
2210     }
2211 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2212     if (hasDisplay_ && hasPointerDevice_ && surfaceNode_ == nullptr) {
2213         MMI_HILOGD("Draw pointer begin");
2214         PointerStyle pointerStyle;
2215         WIN_MGR->GetPointerStyle(pid_, windowId_, pointerStyle);
2216         MMI_HILOGD("Get pid %{publid}d with pointerStyle %{public}d", pid_, pointerStyle.id);
2217         Direction direction = DIRECTION0;
2218         if (IsWindowRotation()) {
2219             direction = displayInfo_.direction;
2220         }
2221         lastDrawPointerStyle_ = pointerStyle;
2222         if (lastPhysicalX_ == -1 || lastPhysicalY_ == -1) {
2223             DrawPointer(displayInfo_.id, displayInfo_.width / CALCULATE_MIDDLE, displayInfo_.height / CALCULATE_MIDDLE,
2224                 pointerStyle, direction);
2225             MMI_HILOGD("Draw manager, mouseStyle:%{public}d, last physical is initial value", pointerStyle.id);
2226             return;
2227         }
2228         DrawPointer(displayInfo_.id, lastPhysicalX_, lastPhysicalY_, pointerStyle, direction);
2229         MMI_HILOGD("Draw manager, mouseStyle:%{public}d", pointerStyle.id);
2230         return;
2231     }
2232 }
2233 
Init()2234 bool PointerDrawingManager::Init()
2235 {
2236     CALL_DEBUG_ENTER;
2237     INPUT_DEV_MGR->Attach(shared_from_this());
2238     pidInfos_.clear();
2239     hapPidInfos_.clear();
2240     return true;
2241 }
2242 
GetInstance()2243 std::shared_ptr<IPointerDrawingManager> IPointerDrawingManager::GetInstance()
2244 {
2245     if (iPointDrawMgr_ == nullptr) {
2246         iPointDrawMgr_ = std::make_shared<PointerDrawingManager>();
2247     }
2248     return iPointDrawMgr_;
2249 }
2250 
UpdatePointerVisible()2251 void PointerDrawingManager::UpdatePointerVisible()
2252 {
2253     CALL_DEBUG_ENTER;
2254     CHKPV(surfaceNode_);
2255     if (IsPointerVisible() && mouseDisplayState_) {
2256         surfaceNode_->SetVisible(true);
2257         MMI_HILOGI("Pointer window show success, mouseDisplayState_:%{public}s",
2258             mouseDisplayState_ ? "true" : "false");
2259     } else {
2260         surfaceNode_->SetVisible(false);
2261         MMI_HILOGI("Pointer window hide success, mouseDisplayState_:%{public}s",
2262             mouseDisplayState_ ? "true" : "false");
2263     }
2264     Rosen::RSTransaction::FlushImplicitTransaction();
2265 }
2266 
IsPointerVisible()2267 bool PointerDrawingManager::IsPointerVisible()
2268 {
2269     CALL_DEBUG_ENTER;
2270     if (!pidInfos_.empty()) {
2271         auto info = pidInfos_.back();
2272         if (!info.visible) {
2273             MMI_HILOGI("High priority visible property:%{public}zu.%{public}d-visible:%{public}s",
2274                 pidInfos_.size(), info.pid, info.visible?"true":"false");
2275             return info.visible;
2276         }
2277     }
2278     if (!hapPidInfos_.empty()) {
2279         for (auto& item : hapPidInfos_) {
2280             if (item.pid == pid_) {
2281                 MMI_HILOGI("Visible pid:%{public}d-visible:%{public}s",
2282                     item.pid, item.visible ? "true" : "false");
2283                 return item.visible;
2284             }
2285         }
2286         if (!(INPUT_DEV_MGR->HasPointerDevice() || WIN_MGR->IsMouseSimulate()) || pid_ == 0) {
2287             auto info = hapPidInfos_.back();
2288             MMI_HILOGI("Only hap visible pid:%{public}d-visible:%{public}s",
2289                 info.pid, info.visible ? "true" : "false");
2290             return info.visible;
2291         }
2292     }
2293     if (pidInfos_.empty()) {
2294         MMI_HILOGD("Visible property is true");
2295         return true;
2296     }
2297     auto info = pidInfos_.back();
2298     MMI_HILOGI("Visible property:%{public}zu.%{public}d-visible:%{public}s",
2299         pidInfos_.size(), info.pid, info.visible ? "true" : "false");
2300     return info.visible;
2301 }
2302 
DeletePointerVisible(int32_t pid)2303 void PointerDrawingManager::DeletePointerVisible(int32_t pid)
2304 {
2305     CALL_DEBUG_ENTER;
2306     MMI_HILOGI("g_isRsRemoteDied:%{public}d", g_isRsRemoteDied ? 1 : 0);
2307     if (g_isRsRemoteDied && surfaceNode_ != nullptr) {
2308         g_isRsRemoteDied = false;
2309         surfaceNode_->DetachToDisplay(screenId_);
2310         surfaceNode_ = nullptr;
2311         Rosen::RSTransaction::FlushImplicitTransaction();
2312     }
2313     if (pidInfos_.empty()) {
2314         return;
2315     }
2316     auto it = pidInfos_.begin();
2317     for (; it != pidInfos_.end(); ++it) {
2318         if (it->pid == pid) {
2319             pidInfos_.erase(it);
2320             break;
2321         }
2322     }
2323     if (it != pidInfos_.end()) {
2324         if (IsPointerVisible()) {
2325             InitLayer(MOUSE_ICON(lastMouseStyle_.id));
2326         }
2327         UpdatePointerVisible();
2328     }
2329 }
2330 
GetPointerVisible(int32_t pid)2331 bool PointerDrawingManager::GetPointerVisible(int32_t pid)
2332 {
2333     bool ret = true;
2334     int32_t count = 0;
2335     for (auto it = pidInfos_.begin(); it != pidInfos_.end(); ++it) {
2336         if (it->pid == pid) {
2337             count++;
2338             ret = it->visible;
2339             break;
2340         }
2341     }
2342     if (count == 0 && !hapPidInfos_.empty()) {
2343         for (auto& item : hapPidInfos_) {
2344             if (item.pid == pid_) {
2345                 MMI_HILOGI("Visible pid:%{public}d-visible:%{public}s",
2346                     item.pid, item.visible ? "true" : "false");
2347                 count++;
2348                 ret = item.visible;
2349                 break;
2350             }
2351         }
2352     }
2353     return ret;
2354 }
2355 
OnSessionLost(int32_t pid)2356 void PointerDrawingManager::OnSessionLost(int32_t pid)
2357 {
2358     for (auto it = hapPidInfos_.begin(); it != hapPidInfos_.end(); ++it) {
2359         if (it->pid == pid) {
2360             hapPidInfos_.erase(it);
2361             break;
2362         }
2363     }
2364 }
2365 
SetPointerVisible(int32_t pid, bool visible, int32_t priority, bool isHap)2366 int32_t PointerDrawingManager::SetPointerVisible(int32_t pid, bool visible, int32_t priority, bool isHap)
2367 {
2368     MMI_HILOGI("pid:%{public}d,visible:%{public}s,priority:%{public}d,isHap:%{public}s", pid,
2369         visible ? "true" : "false", priority, isHap ? "true" : "false");
2370     if (isHap) {
2371         for (auto it = hapPidInfos_.begin(); it != hapPidInfos_.end(); ++it) {
2372             if (it->pid == pid) {
2373                 hapPidInfos_.erase(it);
2374                 break;
2375             }
2376         }
2377         PidInfo info = { .pid = pid, .visible = visible };
2378         hapPidInfos_.push_back(info);
2379         if (hapPidInfos_.size() > VISIBLE_LIST_MAX_SIZE) {
2380             hapPidInfos_.pop_front();
2381         }
2382         UpdatePointerVisible();
2383         return RET_OK;
2384     }
2385     if (WIN_MGR->GetExtraData().appended && visible && priority == 0) {
2386         MMI_HILOGE("current is drag state, can not set pointer visible");
2387         return RET_ERR;
2388     }
2389     for (auto it = pidInfos_.begin(); it != pidInfos_.end(); ++it) {
2390         if (it->pid == pid) {
2391             pidInfos_.erase(it);
2392             break;
2393         }
2394     }
2395     PidInfo info = { .pid = pid, .visible = visible };
2396     pidInfos_.push_back(info);
2397     if (pidInfos_.size() > VISIBLE_LIST_MAX_SIZE) {
2398         pidInfos_.pop_front();
2399     }
2400     UpdatePointerVisible();
2401     return RET_OK;
2402 }
2403 
SetPointerLocation(int32_t x, int32_t y)2404 void PointerDrawingManager::SetPointerLocation(int32_t x, int32_t y)
2405 {
2406     CALL_DEBUG_ENTER;
2407     FixCursorPosition(x, y);
2408     lastPhysicalX_ = x;
2409     lastPhysicalY_ = y;
2410     MMI_HILOGD("Pointer window move, x:%{public}d, y:%{public}d", lastPhysicalX_, lastPhysicalY_);
2411     CHKPV(surfaceNode_);
2412 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2413     CHKPV(hardwareCursorPointerManager_);
2414     if (g_isHdiRemoteDied) {
2415         hardwareCursorPointerManager_->SetHdiServiceState(false);
2416     }
2417     if (hardwareCursorPointerManager_->IsSupported()) {
2418         if (!SetTraditionsHardWareCursorLocation(displayId_, x, y,
2419             ICON_TYPE(mouseIcons_[MOUSE_ICON(lastMouseStyle_.id)].alignmentWay))) {
2420             MMI_HILOGE("Set hardware cursor position fail");
2421             return;
2422         }
2423     }
2424 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2425     MMI_HILOGD("Pointer window move success");
2426 }
2427 
UpdateDefaultPointerStyle(int32_t pid, int32_t windowId, PointerStyle pointerStyle, bool isUiExtension)2428 int32_t PointerDrawingManager::UpdateDefaultPointerStyle(int32_t pid, int32_t windowId, PointerStyle pointerStyle,
2429     bool isUiExtension)
2430 {
2431     if (windowId != GLOBAL_WINDOW_ID) {
2432         MMI_HILOGD("No need to change the default icon style");
2433         return RET_OK;
2434     }
2435     PointerStyle style;
2436     WIN_MGR->GetPointerStyle(pid, GLOBAL_WINDOW_ID, style, isUiExtension);
2437     if (pointerStyle.id != style.id) {
2438         auto iconPath = GetMouseIconPath();
2439         auto it = iconPath.find(MOUSE_ICON(MOUSE_ICON::DEFAULT));
2440         if (it == iconPath.end()) {
2441             MMI_HILOGE("Cannot find the default style");
2442             return RET_ERR;
2443         }
2444         std::string newIconPath;
2445         if (pointerStyle.id == MOUSE_ICON::DEFAULT) {
2446             newIconPath = DefaultIconPath;
2447         } else {
2448             newIconPath = iconPath.at(MOUSE_ICON(pointerStyle.id)).iconPath;
2449         }
2450         MMI_HILOGD("Default path has changed from %{public}s to %{public}s",
2451             it->second.iconPath.c_str(), newIconPath.c_str());
2452         UpdateIconPath(MOUSE_ICON(MOUSE_ICON::DEFAULT), newIconPath);
2453     }
2454     lastMouseStyle_ = style;
2455     return RET_OK;
2456 }
2457 
GetMouseIconPath()2458 const std::map<MOUSE_ICON, IconStyle>& PointerDrawingManager::GetMouseIconPath()
2459 {
2460     CALL_DEBUG_ENTER;
2461 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2462     if (HasMagicCursor()) {
2463         MMI_HILOGD("Magiccurosr get magic mouse map");
2464         return MAGIC_CURSOR->magicMouseIcons_;
2465     } else {
2466         MMI_HILOGD("Magiccurosr get mouse icon, HasMagicCursor is false");
2467         return mouseIcons_;
2468     }
2469 #else
2470     return mouseIcons_;
2471 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2472 }
2473 
GetIconStyle(const MOUSE_ICON mouseStyle)2474 IconStyle PointerDrawingManager::GetIconStyle(const MOUSE_ICON mouseStyle)
2475 {
2476     std::map<MOUSE_ICON, IconStyle> mouseIcons = GetMouseIcons();
2477     auto iter = mouseIcons.find(mouseStyle);
2478     if (iter == mouseIcons.end()) {
2479         MMI_HILOGE("Cannot find the mouseStyle:%{public}d", static_cast<int32_t>(mouseStyle));
2480         return IconStyle();
2481     }
2482     return iter->second;
2483 }
2484 
GetMouseIcons()2485 std::map<MOUSE_ICON, IconStyle>& PointerDrawingManager::GetMouseIcons()
2486 {
2487 #ifdef OHOS_BUILD_ENABLE_MAGICCURSOR
2488     if (HasMagicCursor()) {
2489         MMI_HILOGD("Magiccurosr get magic mouse map");
2490         return MAGIC_CURSOR->magicMouseIcons_;
2491     } else {
2492         MMI_HILOGD("Magiccurosr get mouse icon, HasMagicCursor is false");
2493         return mouseIcons_;
2494     }
2495 #else
2496     return mouseIcons_;
2497 #endif // OHOS_BUILD_ENABLE_MAGICCURSOR
2498 }
2499 
UpdateIconPath(const MOUSE_ICON mouseStyle, std::string iconPath)2500 void PointerDrawingManager::UpdateIconPath(const MOUSE_ICON mouseStyle, std::string iconPath)
2501 {
2502     auto iter = mouseIcons_.find(mouseStyle);
2503     if (iter == mouseIcons_.end()) {
2504         MMI_HILOGE("Cannot find the mouseStyle:%{public}d", static_cast<int32_t>(mouseStyle));
2505         return;
2506     }
2507     iter->second.iconPath = iconPath;
2508 }
2509 
SetPointerStylePreference(PointerStyle pointerStyle)2510 int32_t PointerDrawingManager::SetPointerStylePreference(PointerStyle pointerStyle)
2511 {
2512     CALL_DEBUG_ENTER;
2513     std::string name = "pointerStyle";
2514     int32_t ret = PREFERENCES_MGR->SetIntValue(name, MOUSE_FILE_NAME, pointerStyle.id);
2515     if (ret == RET_OK) {
2516         MMI_HILOGE("Set pointer style successfully, style:%{public}d", pointerStyle.id);
2517     }
2518     return RET_OK;
2519 }
2520 
CheckPointerStyleParam(int32_t windowId, PointerStyle pointerStyle)2521 bool PointerDrawingManager::CheckPointerStyleParam(int32_t windowId, PointerStyle pointerStyle)
2522 {
2523     CALL_DEBUG_ENTER;
2524     if (windowId < -1) {
2525         return false;
2526     }
2527     if ((pointerStyle.id < MOUSE_ICON::DEFAULT && pointerStyle.id != MOUSE_ICON::DEVELOPER_DEFINED_ICON) ||
2528         pointerStyle.id > MOUSE_ICON::RUNNING_RIGHT) {
2529         return false;
2530     }
2531     return true;
2532 }
2533 
SetPointerStyle(int32_t pid, int32_t windowId, PointerStyle pointerStyle, bool isUiExtension)2534 int32_t PointerDrawingManager::SetPointerStyle(int32_t pid, int32_t windowId, PointerStyle pointerStyle,
2535     bool isUiExtension)
2536 {
2537     CALL_DEBUG_ENTER;
2538     if (!CheckPointerStyleParam(windowId, pointerStyle)) {
2539         MMI_HILOGE("PointerStyle param is invalid");
2540         return RET_ERR;
2541     }
2542     if (windowId == GLOBAL_WINDOW_ID) {
2543         int32_t ret = SetPointerStylePreference(pointerStyle);
2544         if (ret != RET_OK) {
2545             MMI_HILOGE("Set style preference is failed, ret:%{public}d", ret);
2546             return RET_ERR;
2547         }
2548     }
2549     auto& iconPath = GetMouseIconPath();
2550     if (iconPath.find(MOUSE_ICON(pointerStyle.id)) == iconPath.end()) {
2551         MMI_HILOGE("The param pointerStyle is invalid");
2552         return RET_ERR;
2553     }
2554     if (UpdateDefaultPointerStyle(pid, windowId, pointerStyle) != RET_OK) {
2555         MMI_HILOGE("Update default pointer iconPath failed");
2556         return RET_ERR;
2557     }
2558     if (WIN_MGR->SetPointerStyle(pid, windowId, pointerStyle, isUiExtension) != RET_OK) {
2559         MMI_HILOGE("Set pointer style failed");
2560         return RET_ERR;
2561     }
2562     if (!INPUT_DEV_MGR->HasPointerDevice() && !WIN_MGR->IsMouseSimulate()) {
2563         MMI_HILOGD("The pointer device is not exist");
2564         return RET_OK;
2565     }
2566     if (!WIN_MGR->IsNeedRefreshLayer(windowId)) {
2567         MMI_HILOGD("Not need refresh layer, window type:%{public}d, pointer style:%{public}d",
2568             windowId, pointerStyle.id);
2569         return RET_OK;
2570     }
2571     if (windowId != GLOBAL_WINDOW_ID && (pointerStyle.id == MOUSE_ICON::DEFAULT &&
2572         iconPath.at(MOUSE_ICON(pointerStyle.id)).iconPath != DefaultIconPath)) {
2573         PointerStyle style;
2574         WIN_MGR->GetPointerStyle(pid, GLOBAL_WINDOW_ID, style);
2575         pointerStyle = style;
2576     }
2577     if (windowId == windowId_ || windowId == GLOBAL_WINDOW_ID) {
2578         // Draw mouse style only when the current window is the top-level window
2579         if (!WIN_MGR->SelectPointerChangeArea(windowId, lastPhysicalX_ + displayInfo_.x,
2580             lastPhysicalY_ + displayInfo_.y)) {
2581             DrawPointerStyle(pointerStyle);
2582         } else {
2583             MMI_HILOGW("skip the pointerstyle");
2584         }
2585     } else {
2586         MMI_HILOGW("set windowid:%{public}d, top windowid:%{public}d, dont draw pointer", windowId, windowId_);
2587     }
2588     MMI_HILOGI("Window id:%{public}d set pointer style:%{public}d success", windowId, pointerStyle.id);
2589     return RET_OK;
2590 }
2591 
GetPointerStyle(int32_t pid, int32_t windowId, PointerStyle &pointerStyle, bool isUiExtension)2592 int32_t PointerDrawingManager::GetPointerStyle(int32_t pid, int32_t windowId, PointerStyle &pointerStyle,
2593     bool isUiExtension)
2594 {
2595     CALL_DEBUG_ENTER;
2596     if (windowId == GLOBAL_WINDOW_ID) {
2597         std::string name = POINTER_COLOR;
2598         pointerStyle.color = PREFERENCES_MGR->GetIntValue(name, DEFAULT_VALUE);
2599         name = POINTER_SIZE;
2600         pointerStyle.size = PREFERENCES_MGR->GetIntValue(name, DEFAULT_POINTER_SIZE);
2601         name = "pointerStyle";
2602         int32_t style = PREFERENCES_MGR->GetIntValue(name, DEFAULT_POINTER_STYLE);
2603         MMI_HILOGD("Get pointer style successfully, pointerStyle:%{public}d", style);
2604         if (style == CURSOR_CIRCLE_STYLE) {
2605             pointerStyle.id = style;
2606             return RET_OK;
2607         }
2608     }
2609     WIN_MGR->GetPointerStyle(pid, windowId, pointerStyle, isUiExtension);
2610     MMI_HILOGD("Window id:%{public}d get pointer style:%{public}d success", windowId, pointerStyle.id);
2611     return RET_OK;
2612 }
2613 
ClearWindowPointerStyle(int32_t pid, int32_t windowId)2614 int32_t PointerDrawingManager::ClearWindowPointerStyle(int32_t pid, int32_t windowId)
2615 {
2616     CALL_DEBUG_ENTER;
2617     return WIN_MGR->ClearWindowPointerStyle(pid, windowId);
2618 }
2619 
DrawPointerStyle(const PointerStyle& pointerStyle)2620 void PointerDrawingManager::DrawPointerStyle(const PointerStyle& pointerStyle)
2621 {
2622     CALL_DEBUG_ENTER;
2623     bool simulate = WIN_MGR->IsMouseSimulate();
2624     if (hasDisplay_ && (hasPointerDevice_ || simulate)) {
2625         if (surfaceNode_ != nullptr) {
2626             AttachToDisplay();
2627             Rosen::RSTransaction::FlushImplicitTransaction();
2628         }
2629         Direction direction = DIRECTION0;
2630         if (IsWindowRotation()) {
2631             direction = displayInfo_.direction;
2632         }
2633         if (lastPhysicalX_ == -1 || lastPhysicalY_ == -1) {
2634             DrawPointer(displayInfo_.id, displayInfo_.width / CALCULATE_MIDDLE, displayInfo_.height / CALCULATE_MIDDLE,
2635                 pointerStyle, direction);
2636             MMI_HILOGD("Draw pointer style, mouseStyle:%{public}d", pointerStyle.id);
2637             return;
2638         }
2639 
2640         DrawPointer(displayInfo_.id, lastPhysicalX_, lastPhysicalY_, pointerStyle, direction);
2641         MMI_HILOGD("Draw pointer style, mouseStyle:%{public}d", pointerStyle.id);
2642     }
2643 }
2644 
CheckMouseIconPath()2645 void PointerDrawingManager::CheckMouseIconPath()
2646 {
2647     for (auto iter = mouseIcons_.begin(); iter != mouseIcons_.end();) {
2648         if ((ReadCursorStyleFile(iter->second.iconPath)) != RET_OK) {
2649             iter = mouseIcons_.erase(iter);
2650             continue;
2651         }
2652         ++iter;
2653     }
2654 }
2655 
EnableHardwareCursorStats(int32_t pid, bool enable)2656 int32_t PointerDrawingManager::EnableHardwareCursorStats(int32_t pid, bool enable)
2657 {
2658     CALL_DEBUG_ENTER;
2659 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2660     CHKPR(hardwareCursorPointerManager_, ERROR_NULL_POINTER);
2661     if (g_isHdiRemoteDied) {
2662         hardwareCursorPointerManager_->SetHdiServiceState(false);
2663     }
2664     if (hardwareCursorPointerManager_->IsSupported()) {
2665         if ((hardwareCursorPointerManager_->EnableStats(enable)) != RET_OK) {
2666             MMI_HILOGE("Enable stats failed");
2667             return RET_ERR;
2668         }
2669     }
2670 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2671     MMI_HILOGI("EnableHardwareCursorStats, enable:%{private}d", enable);
2672     return RET_OK;
2673 }
2674 
GetHardwareCursorStats(int32_t pid, uint32_t &frameCount, uint32_t &vsyncCount)2675 int32_t PointerDrawingManager::GetHardwareCursorStats(int32_t pid, uint32_t &frameCount, uint32_t &vsyncCount)
2676 {
2677     CALL_DEBUG_ENTER;
2678 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2679     CHKPR(hardwareCursorPointerManager_, ERROR_NULL_POINTER);
2680     if (g_isHdiRemoteDied) {
2681         hardwareCursorPointerManager_->SetHdiServiceState(false);
2682     }
2683     if (hardwareCursorPointerManager_->IsSupported()) {
2684         if ((hardwareCursorPointerManager_->GetCursorStats(frameCount, vsyncCount)) != RET_OK) {
2685             MMI_HILOGE("Query stats failed");
2686             return RET_ERR;
2687         }
2688     }
2689 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2690     MMI_HILOGI("GetHardwareCursorStats, frameCount:%{private}d, vsyncCount:%{private}d", frameCount, vsyncCount);
2691     return RET_OK;
2692 }
2693 
InitStyle()2694 void PointerDrawingManager::InitStyle()
2695 {
2696     CALL_DEBUG_ENTER;
2697     mouseIcons_ = {
2698         {DEFAULT, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Default.svg"}},
2699         {EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "East.svg"}},
2700         {WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "West.svg"}},
2701         {SOUTH, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "South.svg"}},
2702         {NORTH, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "North.svg"}},
2703         {WEST_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "West_East.svg"}},
2704         {NORTH_SOUTH, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "North_South.svg"}},
2705         {NORTH_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "North_East.svg"}},
2706         {NORTH_WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "North_West.svg"}},
2707         {SOUTH_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "South_East.svg"}},
2708         {SOUTH_WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "South_West.svg"}},
2709         {NORTH_EAST_SOUTH_WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "North_East_South_West.svg"}},
2710         {NORTH_WEST_SOUTH_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "North_West_South_East.svg"}},
2711         {CROSS, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Cross.svg"}},
2712         {CURSOR_COPY, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Copy.svg"}},
2713         {CURSOR_FORBID, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Forbid.svg"}},
2714         {COLOR_SUCKER, {ANGLE_SW, IMAGE_POINTER_DEFAULT_PATH + "Colorsucker.svg"}},
2715         {HAND_GRABBING, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Hand_Grabbing.svg"}},
2716         {HAND_OPEN, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Hand_Open.svg"}},
2717         {HAND_POINTING, {ANGLE_NW_RIGHT, IMAGE_POINTER_DEFAULT_PATH + "Hand_Pointing.svg"}},
2718         {HELP, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Help.svg"}},
2719         {CURSOR_MOVE, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Move.svg"}},
2720         {RESIZE_LEFT_RIGHT, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Resize_Left_Right.svg"}},
2721         {RESIZE_UP_DOWN, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Resize_Up_Down.svg"}},
2722         {SCREENSHOT_CHOOSE, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Screenshot_Cross.svg"}},
2723         {SCREENSHOT_CURSOR, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Screenshot_Cursor.png"}},
2724         {TEXT_CURSOR, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Text_Cursor.svg"}},
2725         {ZOOM_IN, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Zoom_In.svg"}},
2726         {ZOOM_OUT, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Zoom_Out.svg"}},
2727         {MIDDLE_BTN_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_East.svg"}},
2728         {MIDDLE_BTN_WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_West.svg"}},
2729         {MIDDLE_BTN_SOUTH, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_South.svg"}},
2730         {MIDDLE_BTN_NORTH, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_North.svg"}},
2731         {MIDDLE_BTN_NORTH_SOUTH, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_North_South.svg"}},
2732         {MIDDLE_BTN_NORTH_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_North_East.svg"}},
2733         {MIDDLE_BTN_NORTH_WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_North_West.svg"}},
2734         {MIDDLE_BTN_SOUTH_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_South_East.svg"}},
2735         {MIDDLE_BTN_SOUTH_WEST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "MID_Btn_South_West.svg"}},
2736         {MIDDLE_BTN_NORTH_SOUTH_WEST_EAST, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH +
2737             "MID_Btn_North_South_West_East.svg"}},
2738         {HORIZONTAL_TEXT_CURSOR, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Horizontal_Text_Cursor.svg"}},
2739         {CURSOR_CROSS, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Cursor_Cross.svg"}},
2740         {CURSOR_CIRCLE, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Cursor_Circle.png"}},
2741         {LOADING, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Loading.svg"}},
2742         {RUNNING, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Loading_Left.svg"}},
2743         {RUNNING_LEFT, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Loading_Left.svg"}},
2744         {RUNNING_RIGHT, {ANGLE_CENTER, IMAGE_POINTER_DEFAULT_PATH + "Loading_Right.svg"}},
2745         {DEVELOPER_DEFINED_ICON, {ANGLE_NW, IMAGE_POINTER_DEFAULT_PATH + "Default.svg"}},
2746     };
2747     CheckMouseIconPath();
2748 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2749     std::string productType = OHOS::system::GetParameter("const.build.product", "HYM");
2750     if (productType == DEVICE_TYPE_HARDEN) {
2751         renderThread_ = std::make_unique<std::thread>([this] { this->RenderThreadLoop(); });
2752     }
2753 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2754 }
2755 
RotateDegree(Direction direction)2756 void PointerDrawingManager::RotateDegree(Direction direction)
2757 {
2758     CHKPV(surfaceNode_);
2759     surfaceNode_->SetPivot(0, 0);
2760     float degree = (static_cast<int>(DIRECTION0) - static_cast<int>(direction)) * ROTATION_ANGLE90;
2761     surfaceNode_->SetRotation(degree);
2762 }
2763 
SkipPointerLayer(bool isSkip)2764 int32_t PointerDrawingManager::SkipPointerLayer(bool isSkip)
2765 {
2766     CALL_INFO_TRACE;
2767     if (surfaceNode_ != nullptr) {
2768         surfaceNode_->SetSkipLayer(isSkip);
2769     }
2770     return RET_OK;
2771 }
2772 
Dump(int32_t fd, const std::vector<std::string> &args)2773 void PointerDrawingManager::Dump(int32_t fd, const std::vector<std::string> &args)
2774 {
2775     CALL_DEBUG_ENTER;
2776     std::ostringstream oss;
2777     oss << std::endl;
2778 
2779     std::vector<std::string> displayTitles = {"ID", "X", "Y", "Width", "Height", "DPI", "Name", "Uniq",
2780                                               "Direction", "Display Direction", "Display Mode"};
2781     DisplayInfo &di = displayInfo_;
2782     std::vector<std::vector<std::string>> displayInfo = {
2783         {std::to_string(di.id), std::to_string(di.x), std::to_string(di.y), std::to_string(di.width),
2784          std::to_string(di.height), std::to_string(di.dpi), di.name, di.uniq,
2785          std::to_string(static_cast<int32_t>(di.direction)), std::to_string(static_cast<int32_t>(di.displayDirection)),
2786          std::to_string(static_cast<int32_t>(di.displayMode))}};
2787 
2788     DumpFullTable(oss, "Display Info", displayTitles, displayInfo);
2789     oss << std::endl;
2790 
2791     std::vector<std::string> titles1 = {"hasDisplay", "hasPointerDevice", "lastPhysicalX", "lastPhysicalY",
2792                                         "pid", "windowId", "imageWidth", "imageHeight", "canvasWidth", "canvasHeight"};
2793     std::vector<std::vector<std::string>> data1 = {
2794         {std::to_string(hasDisplay_), std::to_string(hasPointerDevice_), std::to_string(lastPhysicalX_),
2795          std::to_string(lastPhysicalY_), std::to_string(pid_), std::to_string(windowId_),
2796          std::to_string(imageWidth_), std::to_string(imageHeight_), std::to_string(canvasWidth_),
2797          std::to_string(canvasHeight_)}};
2798 
2799     DumpFullTable(oss, "Cursor Info", titles1, data1);
2800     oss << std::endl;
2801 
2802     std::vector<std::string> titles2 = {"mouseDisplayState", "mouseIconUpdate", "screenId", "userIconHotSpotX",
2803                                         "userIconHotSpotY", "tempPointerColor", "lastDirection", "currentDirection"};
2804     std::vector<std::vector<std::string>> data2 = {
2805         {std::to_string(mouseDisplayState_), std::to_string(mouseIconUpdate_), std::to_string(screenId_),
2806          std::to_string(userIconHotSpotX_), std::to_string(userIconHotSpotY_), std::to_string(tempPointerColor_),
2807          std::to_string(lastDirection_), std::to_string(currentDirection_)}};
2808 
2809     DumpFullTable(oss, "Cursor Info", titles2, data2);
2810     oss << std::endl;
2811 
2812     std::vector<std::string> styleTitles = {"name", "Size", "Color", "ID"};
2813     std::vector<std::vector<std::string>> styleData = {
2814         {"lastMouseStyle", std::to_string(lastMouseStyle_.size), std::to_string(lastMouseStyle_.color),
2815          std::to_string(lastMouseStyle_.id)},
2816         {"currentMouseStyle", std::to_string(currentMouseStyle_.size), std::to_string(currentMouseStyle_.color),
2817          std::to_string(currentMouseStyle_.id)}};
2818 
2819     DumpFullTable(oss, "Cursor Style Info", styleTitles, styleData);
2820     oss << std::endl;
2821 
2822     std::vector<std::string> pidTitles = {"pid", "visible"};
2823     std::vector<std::vector<std::string>> pidInfos;
2824     for (const auto &pidInfo : pidInfos_) {
2825         pidInfos.push_back({std::to_string(pidInfo.pid), pidInfo.visible ? "true" : "false"});
2826     }
2827     DumpFullTable(oss, "Visible Info", pidTitles, pidInfos);
2828     oss << std::endl;
2829 
2830     std::string dumpInfo = oss.str();
2831     dprintf(fd, dumpInfo.c_str());
2832 }
2833 
2834 #ifdef OHOS_BUILD_ENABLE_HARDWARE_CURSOR
UpdateBindDisplayId(int32_t displayId)2835 void PointerDrawingManager::UpdateBindDisplayId(int32_t displayId)
2836 {
2837     if (lastDisplayId_ != displayId) {
2838         MMI_HILOGI("Mouse traversal occurs, lastDisplayId_:%{public}d, displayId:%{public}d",
2839             lastDisplayId_, displayId);
2840         CHKPV(surfaceNode_);
2841         surfaceNode_->DetachToDisplay(screenId_);
2842         screenId_ = static_cast<uint64_t>(displayId);
2843         MMI_HILOGI("screenId_: %{public}" PRIu64, screenId_);
2844         AttachToDisplay();
2845         CHKPV(hardwareCursorPointerManager_);
2846         if (!hardwareCursorPointerManager_->IsSupported()) {
2847             DrawCursor(MOUSE_ICON(lastMouseStyle_.id));
2848         }
2849         lastDisplayId_ = displayId;
2850     }
2851 }
2852 #endif // OHOS_BUILD_ENABLE_HARDWARE_CURSOR
2853 
DrawScreenCenterPointer(const PointerStyle& pointerStyle)2854 void PointerDrawingManager::DrawScreenCenterPointer(const PointerStyle& pointerStyle)
2855 {
2856     CALL_DEBUG_ENTER;
2857     if (hasDisplay_ && hasPointerDevice_) {
2858         if (surfaceNode_ != nullptr) {
2859             AttachToDisplay();
2860             Rosen::RSTransaction::FlushImplicitTransaction();
2861         }
2862         Direction direction = DIRECTION0;
2863         if (displayInfo_.displayDirection == DIRECTION0) {
2864             direction = displayInfo_.direction;
2865         }
2866         DrawPointer(displayInfo_.id, displayInfo_.width / CALCULATE_MIDDLE, displayInfo_.height / CALCULATE_MIDDLE,
2867             pointerStyle, direction);
2868     }
2869 }
2870 } // namespace MMI
2871 } // namespace OHOS
2872