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 "processing_pen_device.h"
17
18 #undef MMI_LOG_TAG
19 #define MMI_LOG_TAG "ProcessingPenDevice"
20
21 namespace OHOS {
22 namespace MMI {
23 namespace {
24 constexpr int32_t EV_ABS_Z_DEFAULT_VALUE { 450 };
25 constexpr int32_t EV_ABS_MISC_DEFAULT_VALUE { 2114 };
26 } // namespace
27
TransformJsonDataToInputData(const DeviceItem & penEventArrays,InputEventArray & inputEventArray)28 int32_t ProcessingPenDevice::TransformJsonDataToInputData(const DeviceItem& penEventArrays,
29 InputEventArray& inputEventArray)
30 {
31 CALL_DEBUG_ENTER;
32 if (penEventArrays.events.empty()) {
33 MMI_HILOGE("Manage pen array failed, inputData is empty");
34 return RET_ERR;
35 }
36 std::vector<PenEvent> penEventArray;
37 if (AnalysisPenPadEvent(penEventArrays.events, penEventArray) == RET_ERR) {
38 MMI_HILOGE("AnalysisPenPadEvent error");
39 return RET_ERR;
40 }
41 TransformPenEventToInputEvent(penEventArray, inputEventArray);
42 return RET_OK;
43 }
44
TransformPenEventToInputEvent(const std::vector<PenEvent> & penEvents,InputEventArray & inputEventArray)45 void ProcessingPenDevice::TransformPenEventToInputEvent(const std::vector<PenEvent>& penEvents,
46 InputEventArray& inputEventArray)
47 {
48 if (penEvents.empty()) {
49 MMI_HILOGE("penEvents is empty");
50 return;
51 }
52 SetPenApproachPadEvent(penEvents.front(), inputEventArray);
53 for (const auto &item : penEvents) {
54 SetPenSlidePadEvent(item, inputEventArray);
55 }
56 SetPenLeavePadEvent(penEvents[penEvents.back()], inputEventArray);
57 }
58
SetPenApproachPadEvent(const PenEvent & penEvent,InputEventArray & inputEventArray)59 void ProcessingPenDevice::SetPenApproachPadEvent(const PenEvent& penEvent, InputEventArray& inputEventArray)
60 {
61 SetEvAbsX(inputEventArray, 0, penEvent.xPos);
62 SetEvAbsY(inputEventArray, 0, penEvent.yPos);
63 SetAbsTiltX(inputEventArray, 0, penEvent.tiltX);
64 SetAbsTiltY(inputEventArray, 0, penEvent.tiltY);
65 SetEvAbsZ(inputEventArray, 0, EV_ABS_Z_DEFAULT_VALUE);
66 SetAbsDistance(inputEventArray, 0, penEvent.distance);
67 if (penEvent.eventType == "PEN_TOUCH") {
68 SetBtnPen(inputEventArray, 0, 1);
69 } else if (penEvent.eventType == "RUBBER_TOUCH") {
70 SetBtnRubber(inputEventArray, 0, 1);
71 } else {
72 MMI_HILOGW("Unknown eventType type");
73 }
74
75 SetMscSerial(inputEventArray, 0);
76 SetAbsMisc(inputEventArray, 0, EV_ABS_MISC_DEFAULT_VALUE);
77 SetSynReport(inputEventArray);
78 }
79
SetPenSlidePadEvent(const PenEvent & penEvent,InputEventArray & inputEventArray)80 void ProcessingPenDevice::SetPenSlidePadEvent(const PenEvent& penEvent, InputEventArray& inputEventArray)
81 {
82 if (penEvent.eventType == "PEN_KEY") {
83 SetBtnStylus(inputEventArray, 0, static_cast<uint16_t>(penEvent.keyValue), penEvent.keyStatus);
84 return;
85 }
86 if (penEvent.distance == 0) {
87 SetMscSerial(inputEventArray, 0);
88 SetSynReport(inputEventArray, 0);
89 return;
90 }
91 SetEvAbsX(inputEventArray, 0, penEvent.xPos);
92 SetEvAbsY(inputEventArray, 0, penEvent.yPos);
93 static int32_t previousPressure = 0;
94 if (penEvent.pressure > 0) {
95 if (previousPressure == 0) {
96 SetAbsPressure(inputEventArray, 0, penEvent.pressure);
97 SetBtnTouch(inputEventArray, 0, 1);
98 } else if (previousPressure > 0) {
99 SetAbsPressure(inputEventArray, 0, penEvent.pressure);
100 } else {
101 MMI_HILOGW("Unknown previousPressure type");
102 }
103 } else if ((penEvent.pressure == 0) && (previousPressure > 0)) {
104 SetAbsPressure(inputEventArray, 0, penEvent.pressure);
105 SetBtnTouch(inputEventArray, 0, 0);
106 } else {
107 MMI_HILOGW("Unknown pressure type");
108 }
109 previousPressure = penEvent.pressure;
110 SetAbsDistance(inputEventArray, 0, penEvent.distance);
111 SetAbsTiltX(inputEventArray, 0, penEvent.tiltX);
112 SetAbsTiltY(inputEventArray, 0, penEvent.tiltY);
113 SetMscSerial(inputEventArray, 0);
114 SetSynReport(inputEventArray);
115 }
116
SetPenLeavePadEvent(const PenEvent & penEvent,InputEventArray & inputEventArray)117 void ProcessingPenDevice::SetPenLeavePadEvent(const PenEvent& penEvent, InputEventArray& inputEventArray)
118 {
119 SetEvAbsX(inputEventArray, 0);
120 SetEvAbsY(inputEventArray, 0);
121 SetAbsTiltX(inputEventArray, 0);
122 SetAbsTiltY(inputEventArray, 0);
123 SetEvAbsZ(inputEventArray, 0);
124 SetAbsDistance(inputEventArray, 0, 0);
125 if (penEvent.eventType == "PEN_TOUCH") {
126 SetBtnPen(inputEventArray, 0, 0);
127 } else if (penEvent.eventType == "RUBBER_TOUCH") {
128 SetBtnRubber(inputEventArray, 0, 0);
129 } else {
130 MMI_HILOGW("Unknown eventType type");
131 }
132
133 SetMscSerial(inputEventArray, 0);
134 SetAbsMisc(inputEventArray, 0, 0);
135 SetSynReport(inputEventArray);
136 }
137
AnalysisPenPadEvent(const std::vector<DeviceEvent> & inputData,std::vector<PenEvent> & penEventArray)138 int32_t ProcessingPenDevice::AnalysisPenPadEvent(const std::vector<DeviceEvent>& inputData,
139 std::vector<PenEvent>& penEventArray)
140 {
141 if (AnalysisPenApproachPadEvent(inputData[0], penEventArray) == RET_ERR) {
142 return RET_ERR;
143 }
144
145 uint64_t endEventIndex = inputData.size() - 1;
146 for (uint64_t i = 1; i < endEventIndex; i++) {
147 if (AnalysisPenSlidePadEvent(inputData[i], penEventArray) == RET_ERR) {
148 return RET_ERR;
149 }
150 }
151 if (AnalysisPenLeavePadEvent(inputData[endEventIndex], penEventArray) == RET_ERR) {
152 return RET_ERR;
153 }
154
155 return RET_OK;
156 }
157
AnalysisPenApproachPadEvent(const DeviceEvent & event,std::vector<PenEvent> & penEventArray)158 int32_t ProcessingPenDevice::AnalysisPenApproachPadEvent(const DeviceEvent& event, std::vector<PenEvent>& penEventArray)
159 {
160 if ((event.eventType != "RUBBER_TOUCH") && (event.eventType != "PEN_TOUCH")) {
161 MMI_HILOGE("Enter the correct event type in the configuration file.");
162 return RET_ERR;
163 }
164
165 PenEvent penEvent;
166 penEvent.eventType = event.eventType;
167 penEvent.distance = event.distance;
168 penEvent.yPos = event.yPos;
169 penEvent.tiltX = event.tiltX;
170 penEvent.tiltY = event.tiltY;
171 penEvent.pressure = event.pressure;
172 penEvent.xPos = event.xPos;
173 penEventArray.push_back(penEvent);
174
175 return RET_OK;
176 }
177
AnalysisPenSlidePadEvent(const DeviceEvent & event,std::vector<PenEvent> & penEventArray)178 int32_t ProcessingPenDevice::AnalysisPenSlidePadEvent(const DeviceEvent& event, std::vector<PenEvent>& penEventArray)
179 {
180 PenEvent penEvent;
181 penEvent.eventType = event.eventType;
182 if (penEvent.eventType == "PEN_KEY") {
183 penEvent.keyValue = event.keyValue;
184 penEvent.keyStatus = event.keyStatus;
185 } else if ((penEvent.eventType == "PEN_TOUCH") || (penEvent.eventType == "RUBBER_TOUCH")) {
186 penEvent.yPos = event.yPos;
187 penEvent.xPos = event.xPos;
188 penEvent.tiltY = event.tiltY;
189 penEvent.tiltX = event.tiltX;
190 penEvent.distance = event.distance;
191 penEvent.pressure = event.pressure;
192 } else {
193 MMI_HILOGW("Unknown eventType type");
194 }
195 penEventArray.push_back(penEvent);
196
197 return RET_OK;
198 }
199
AnalysisPenLeavePadEvent(const DeviceEvent & event,std::vector<PenEvent> & penEventArray)200 int32_t ProcessingPenDevice::AnalysisPenLeavePadEvent(const DeviceEvent& event, std::vector<PenEvent>& penEventArray)
201 {
202 if ((event.eventType != "RUBBER_TOUCH") && (event.eventType != "PEN_TOUCH")) {
203 MMI_HILOGE("Enter the correct event type in the configuration file.");
204 return RET_ERR;
205 }
206
207 PenEvent penEvent;
208 penEvent.eventType = event.eventType;
209 penEvent.yPos = event.yPos;
210 penEvent.tiltY = event.tiltY;
211 penEvent.xPos = event.xPos;
212 penEvent.tiltX = event.tiltX;
213 penEvent.distance = event.distance;
214 penEvent.pressure = event.pressure;
215 penEventArray.push_back(penEvent);
216
217 return RET_OK;
218 }
219 } // namespace MMI
220 } // namespace OHOS