1 /*
2 * Copyright (c) 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 "sensor_adapter_impl.h"
17
18 #include <cinttypes>
19 #include <securec.h>
20 #include <map>
21
22 #include "nweb_log.h"
23
24 namespace OHOS::NWeb {
25
26 std::unordered_map<int32_t, std::shared_ptr<SensorCallbackImpl>> SensorAdapterImpl::sensorCallbackMap;
27 std::mutex SensorAdapterImpl::sensorCallbackMapMutex_;
28 constexpr double NANOSECONDS_IN_SECOND = 1000000000.0;
29 constexpr double DEFAULT_SAMPLE_PERIOD = 200000000.0;
30
SensorTypeToOhosSensorType(int sensorTypeId)31 SensorTypeId SensorTypeToOhosSensorType(int sensorTypeId)
32 {
33 SensorTypeId ohosSensorTypeId = SENSOR_TYPE_ID_NONE;
34 const static std::map<int32_t, SensorTypeId> TO_OHOS_SENSOR_TYPE_MAP = {
35 {2 /* ACCELEROMETER */, SENSOR_TYPE_ID_ACCELEROMETER },
36 {3 /* LINEAR_ACCELERATION */, SENSOR_TYPE_ID_LINEAR_ACCELERATION },
37 {4 /* GRAVITY */, SENSOR_TYPE_ID_GRAVITY },
38 {5 /* GYROSCOPE */, SENSOR_TYPE_ID_GYROSCOPE },
39 {6 /* MAGNETOMETER */, SENSOR_TYPE_ID_MAGNETIC_FIELD },
40 {8 /* ABSOLUTE_ORIENTATION_EULER_ANGLES}*/, SENSOR_TYPE_ID_ORIENTATION },
41 {9 /* ABSOLUTE_ORIENTATION_QUATERNION} */, SENSOR_TYPE_ID_ROTATION_VECTOR },
42 {11 /* RELATIVE_ORIENTATION_QUATERNION} */, SENSOR_TYPE_ID_GAME_ROTATION_VECTOR }
43 };
44 auto checkIter = TO_OHOS_SENSOR_TYPE_MAP.find(sensorTypeId);
45 if (checkIter != TO_OHOS_SENSOR_TYPE_MAP.end()) {
46 ohosSensorTypeId = checkIter->second;
47 }
48 return ohosSensorTypeId;
49 }
50
SensorTypeToSensorUserName(int sensorTypeId)51 std::string SensorTypeToSensorUserName(int sensorTypeId)
52 {
53 const static std::map<int32_t, std::string> TO_OHOS_SENSOR_USER_NAME_MAP = {
54 {2 /* ACCELEROMETER */, "OhosAccelerometerService" },
55 {3 /* LINEAR_ACCELERATION */, "OhosLinearAccelerometerService" },
56 {4 /* GRAVITY */, "OhosGravityService" },
57 {5 /* GYROSCOPE */, "OhosCyroscopeService" },
58 {6 /* MAGNETOMETER */, "OhosMagnetometerService" },
59 {8 /* ABSOLUTE_ORIENTATION_EULER_ANGLES}*/, "OhosOrientationService" },
60 {9 /* ABSOLUTE_ORIENTATION_QUATERNION} */, "OhosRotationVectorService"},
61 {11 /* RELATIVE_ORIENTATION_QUATERNION} */, "OhosGameRotationVectorService" }
62 };
63 std::string userName = "OhosSensorService";
64 auto checkIter = TO_OHOS_SENSOR_USER_NAME_MAP.find(sensorTypeId);
65 if (checkIter != TO_OHOS_SENSOR_USER_NAME_MAP.end()) {
66 userName = checkIter->second;
67 }
68 return userName;
69 }
70
SensorCallbackImpl(std::shared_ptr<SensorCallbackAdapter> callbackAdapter)71 SensorCallbackImpl::SensorCallbackImpl(
72 std::shared_ptr<SensorCallbackAdapter> callbackAdapter)
73 : callbackAdapter_(callbackAdapter)
74 {}
75
UpdateOhosSensorData(double timestamp,double value1,double value2,double value3,double value4)76 void SensorCallbackImpl::UpdateOhosSensorData(double timestamp,
77 double value1, double value2, double value3, double value4)
78 {
79 if (callbackAdapter_) {
80 callbackAdapter_->UpdateOhosSensorData(timestamp, value1, value2, value3, value4);
81 }
82 }
83
IsOhosSensorSupported(int32_t sensorTypeId)84 int32_t SensorAdapterImpl::IsOhosSensorSupported(int32_t sensorTypeId)
85 {
86 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
87 if (ohosSensorTypeId != SENSOR_TYPE_ID_NONE) {
88 SensorInfo* sensorInfo = nullptr;
89 int32_t count;
90 int ret = GetAllSensors(&sensorInfo, &count);
91 if (ret != SENSOR_SUCCESS || sensorInfo == nullptr || count < 0) {
92 WVLOG_E("IsOhosSensorSupported Error, ret = %{public}d, count = %{public}d.", ret, count);
93 return SENSOR_ERROR;
94 }
95
96 for (int i = 0; i < count; i++) {
97 if (sensorInfo[i].sensorId == ohosSensorTypeId) {
98 WVLOG_I("IsOhosSensorSupported SUCCESS, sensorTypeId = %{public}d.", sensorTypeId);
99 return SENSOR_SUCCESS;
100 }
101 }
102 }
103 WVLOG_E("IsOhosSensorSupported Error, sensorTypeId = %{public}d is invalid.", sensorTypeId);
104 return SENSOR_ERROR;
105 }
106
GetOhosSensorReportingMode(int32_t sensorTypeId)107 int32_t SensorAdapterImpl::GetOhosSensorReportingMode(int32_t sensorTypeId)
108 {
109 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
110 int32_t reportingMode = -1;
111 switch (ohosSensorTypeId) {
112 case SENSOR_TYPE_ID_ACCELEROMETER:
113 case SENSOR_TYPE_ID_GRAVITY:
114 case SENSOR_TYPE_ID_LINEAR_ACCELERATION:
115 case SENSOR_TYPE_ID_GYROSCOPE:
116 case SENSOR_TYPE_ID_MAGNETIC_FIELD:
117 case SENSOR_TYPE_ID_ORIENTATION:
118 case SENSOR_TYPE_ID_ROTATION_VECTOR:
119 case SENSOR_TYPE_ID_GAME_ROTATION_VECTOR:
120 reportingMode = SENSOR_DATA_REPORT_CONTINUOUS;
121 break;
122 default:
123 break;
124 }
125 return reportingMode;
126 }
127
GetOhosSensorDefaultSupportedFrequency(int32_t sensorTypeId)128 double SensorAdapterImpl::GetOhosSensorDefaultSupportedFrequency(int32_t sensorTypeId)
129 {
130 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
131 double defaultFrequency = 0.0;
132 if (ohosSensorTypeId != SENSOR_TYPE_ID_NONE) {
133 defaultFrequency = NANOSECONDS_IN_SECOND / DEFAULT_SAMPLE_PERIOD;
134 }
135 WVLOG_I("GetOhosSensorDefaultSupportedFrequency sensorTypeId: %{public}d, defaultFrequency: %{public}f",
136 sensorTypeId, defaultFrequency);
137 return defaultFrequency;
138 }
139
GetOhosSensorMinSupportedFrequency(int32_t sensorTypeId)140 double SensorAdapterImpl::GetOhosSensorMinSupportedFrequency(int32_t sensorTypeId)
141 {
142 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
143 double minFrequency = 0.0;
144 if (ohosSensorTypeId == SENSOR_TYPE_ID_NONE) {
145 WVLOG_E("GetOhosSensorMinSupportedFrequency Error, sensorTypeId = %{public}d is invalid.", sensorTypeId);
146 return minFrequency;
147 }
148 SensorInfo* sensorInfo = nullptr;
149 int32_t count;
150 int ret = GetAllSensors(&sensorInfo, &count);
151 if (ret != SENSOR_SUCCESS || sensorInfo == nullptr || count < 0) {
152 WVLOG_E("GetOhosSensorMinSupportedFrequency Error, ret = %{public}d, count = %{public}d.", ret, count);
153 return minFrequency;
154 }
155 for (int i = 0; i < count; i++) {
156 if (sensorInfo[i].sensorId == ohosSensorTypeId) {
157 int64_t maxSamplePeriod = sensorInfo[i].maxSamplePeriod;
158 if (maxSamplePeriod > 0) {
159 minFrequency = NANOSECONDS_IN_SECOND / static_cast<double>(maxSamplePeriod);
160 }
161 break;
162 }
163 }
164 WVLOG_I("GetOhosSensorMinSupportedFrequency sensorTypeId: %{public}d, minFrequency: %{public}f",
165 sensorTypeId, minFrequency);
166 return minFrequency;
167 }
168
GetOhosSensorMaxSupportedFrequency(int32_t sensorTypeId)169 double SensorAdapterImpl::GetOhosSensorMaxSupportedFrequency(int32_t sensorTypeId)
170 {
171 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
172 double maxFrequency = 0.0;
173 if (ohosSensorTypeId == SENSOR_TYPE_ID_NONE) {
174 WVLOG_E("GetOhosSensorMaxSupportedFrequency Error, sensorTypeId = %{public}d is invalid.", sensorTypeId);
175 return maxFrequency;
176 }
177 SensorInfo* sensorInfo = nullptr;
178 int32_t count;
179 int ret = GetAllSensors(&sensorInfo, &count);
180 if (ret != SENSOR_SUCCESS || sensorInfo == nullptr || count < 0) {
181 WVLOG_E("GetOhosSensorMaxSupportedFrequency Error, ret = %{public}d, count = %{public}d.", ret, count);
182 return maxFrequency;
183 }
184 for (int i = 0; i < count; i++) {
185 if (sensorInfo[i].sensorId == ohosSensorTypeId) {
186 int64_t minSamplePeriod = sensorInfo[i].minSamplePeriod;
187 if (minSamplePeriod > 0) {
188 maxFrequency = NANOSECONDS_IN_SECOND / static_cast<double>(minSamplePeriod);
189 }
190 break;
191 }
192 }
193 WVLOG_I("GetOhosSensorMaxSupportedFrequency sensorTypeId: %{public}d, maxFrequency: %{public}f",
194 sensorTypeId, maxFrequency);
195 return maxFrequency;
196 }
197
handleAccelerometerData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)198 void SensorAdapterImpl::handleAccelerometerData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
199 SensorEvent* event)
200 {
201 if ((event == nullptr) || (callback == nullptr)) {
202 WVLOG_E("handleAccelerometerData Error.");
203 return;
204 }
205 AccelData* data = reinterpret_cast<AccelData*>(event->data);
206 if (data != nullptr) {
207 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, 0.0f);
208 }
209 }
210
handleLinearAccelerometerData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)211 void SensorAdapterImpl::handleLinearAccelerometerData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
212 SensorEvent* event)
213 {
214 if ((event == nullptr) || (callback == nullptr)) {
215 WVLOG_E("handleLinearAccelerometerData Error.");
216 return;
217 }
218 LinearAccelData* data = reinterpret_cast<LinearAccelData*>(event->data);
219 if (data != nullptr) {
220 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, 0.0f);
221 }
222 }
223
handleGravityData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)224 void SensorAdapterImpl::handleGravityData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
225 SensorEvent* event)
226 {
227 if ((event == nullptr) || (callback == nullptr)) {
228 WVLOG_E("handleGravityData Error.");
229 return;
230 }
231 GravityData* data = reinterpret_cast<GravityData*>(event->data);
232 if (data != nullptr) {
233 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, 0.0f);
234 }
235 }
236
handleCyroscopeData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)237 void SensorAdapterImpl::handleCyroscopeData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
238 SensorEvent* event)
239 {
240 if ((event == nullptr) || (callback == nullptr)) {
241 WVLOG_E("handleCyroscopeData Error.");
242 return;
243 }
244 GyroscopeData* data = reinterpret_cast<GyroscopeData*>(event->data);
245 if (data != nullptr) {
246 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, 0.0f);
247 }
248 }
249
handleMagnetometerData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)250 void SensorAdapterImpl::handleMagnetometerData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
251 SensorEvent* event)
252 {
253 if ((event == nullptr) || (callback == nullptr)) {
254 WVLOG_E("handleMagnetometerData Error.");
255 return;
256 }
257 MagneticFieldData* data = reinterpret_cast<MagneticFieldData*>(event->data);
258 if (data != nullptr) {
259 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, 0.0f);
260 }
261 }
262
handleOrientationData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)263 void SensorAdapterImpl::handleOrientationData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
264 SensorEvent* event)
265 {
266 if ((event == nullptr) || (callback == nullptr)) {
267 WVLOG_E("handleOrientationData Error.");
268 return;
269 }
270 OrientationData* data = reinterpret_cast<OrientationData*>(event->data);
271 if (data != nullptr) {
272 callback->UpdateOhosSensorData(event->timestamp, data->beta, data->gamma, data->alpha, 0.0f);
273 }
274 }
275
handleRotationVectorData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)276 void SensorAdapterImpl::handleRotationVectorData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
277 SensorEvent* event)
278 {
279 if ((event == nullptr) || (callback == nullptr)) {
280 WVLOG_E("handleRotationVectorData Error.");
281 return;
282 }
283 RotationVectorData* data = reinterpret_cast<RotationVectorData*>(event->data);
284 if (data != nullptr) {
285 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, data->w);
286 }
287 }
288
handleGameRotationVectorData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,SensorEvent * event)289 void SensorAdapterImpl::handleGameRotationVectorData(std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback,
290 SensorEvent* event)
291 {
292 if ((event == nullptr) || (callback == nullptr)) {
293 WVLOG_E("handleGameRotationVectorData Error.");
294 return;
295 }
296 GameRotationVectorData* data = reinterpret_cast<GameRotationVectorData*>(event->data);
297 if (data != nullptr) {
298 callback->UpdateOhosSensorData(event->timestamp, data->x, data->y, data->z, data->w);
299 }
300 }
301
OhosSensorCallback(SensorEvent * event)302 void SensorAdapterImpl::OhosSensorCallback(SensorEvent* event)
303 {
304 if (event == nullptr) {
305 WVLOG_E("SensorEvent Error.");
306 return;
307 }
308 std::shared_ptr<OHOS::NWeb::SensorCallbackImpl> callback = nullptr;
309 {
310 std::lock_guard<std::mutex> lock(sensorCallbackMapMutex_);
311 auto findIter = sensorCallbackMap.find(event->sensorTypeId);
312 if (findIter != sensorCallbackMap.end()) {
313 callback = findIter->second;
314 }
315 }
316 if (callback == nullptr) {
317 WVLOG_E("OhosSensorCallback Error.");
318 return;
319 }
320 switch (event->sensorTypeId) {
321 case SENSOR_TYPE_ID_ACCELEROMETER:
322 handleAccelerometerData(callback, event);
323 break;
324
325 case SENSOR_TYPE_ID_GRAVITY:
326 handleGravityData(callback, event);
327 break;
328
329 case SENSOR_TYPE_ID_LINEAR_ACCELERATION:
330 handleLinearAccelerometerData(callback, event);
331 break;
332
333 case SENSOR_TYPE_ID_GYROSCOPE:
334 handleCyroscopeData(callback, event);
335 break;
336
337 case SENSOR_TYPE_ID_MAGNETIC_FIELD:
338 handleMagnetometerData(callback, event);
339 break;
340 case SENSOR_TYPE_ID_ORIENTATION:
341 handleOrientationData(callback, event);
342 break;
343 case SENSOR_TYPE_ID_ROTATION_VECTOR:
344 handleRotationVectorData(callback, event);
345 break;
346 case SENSOR_TYPE_ID_GAME_ROTATION_VECTOR:
347 handleGameRotationVectorData(callback, event);
348 break;
349
350 default:
351 break;
352 }
353 }
354
SubscribeOhosSensor(int32_t sensorTypeId,int64_t samplingInterval)355 int32_t SensorAdapterImpl::SubscribeOhosSensor(int32_t sensorTypeId, int64_t samplingInterval)
356 {
357 WVLOG_I("SubscribeOhosSensor sensorTypeId: %{public}d, samplingInterval: %{public}" PRId64,
358 sensorTypeId, samplingInterval);
359 if (samplingInterval <= 0) {
360 WVLOG_E("SubscribeOhosSensor error, samplingInterval is invalid.");
361 return SENSOR_PARAMETER_ERROR;
362 }
363 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
364 if (ohosSensorTypeId == SENSOR_TYPE_ID_NONE) {
365 WVLOG_E("SubscribeOhosSensor error, sensorTypeId is invalid.");
366 return SENSOR_PARAMETER_ERROR;
367 }
368
369 std::string userName = SensorTypeToSensorUserName(sensorTypeId);
370 int cpyret = strcpy_s(mSensorUser.name, sizeof(mSensorUser.name), userName.c_str());
371 if (cpyret != 0) {
372 WVLOG_E("SubscribeOhosSensor error, call strcpy_s ret = %{public}d.", cpyret);
373 }
374 mSensorUser.userData = nullptr;
375 mSensorUser.callback = &OhosSensorCallback;
376 int32_t ret = SENSOR_SUCCESS;
377 ret = SubscribeSensor(ohosSensorTypeId, &mSensorUser);
378 if (ret != SENSOR_SUCCESS) {
379 WVLOG_E("SubscribeOhosSensor error, call SubscribeSensor ret = %{public}d.", ret);
380 return ret;
381 }
382 ret = SetBatch(ohosSensorTypeId, &mSensorUser, samplingInterval, samplingInterval);
383 if (ret != SENSOR_SUCCESS) {
384 WVLOG_E("SubscribeOhosSensor error, call SetBatch ret = %{public}d.", ret);
385 return ret;
386 }
387 ret = ActivateSensor(ohosSensorTypeId, &mSensorUser);
388 if (ret != SENSOR_SUCCESS) {
389 WVLOG_E("SubscribeOhosSensor error, call ActivateSensor ret = %{public}d.", ret);
390 return ret;
391 }
392 ret = SetMode(ohosSensorTypeId, &mSensorUser, SENSOR_REALTIME_MODE);
393 if (ret != SENSOR_SUCCESS) {
394 WVLOG_E("SubscribeOhosSensor error, call SetMode ret = %{public}d.", ret);
395 return ret;
396 }
397 return SENSOR_SUCCESS;
398 }
399
RegistOhosSensorCallback(int32_t sensorTypeId,std::shared_ptr<SensorCallbackAdapter> callbackAdapter)400 int32_t SensorAdapterImpl::RegistOhosSensorCallback(int32_t sensorTypeId,
401 std::shared_ptr<SensorCallbackAdapter> callbackAdapter)
402 {
403 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
404 if (ohosSensorTypeId != SENSOR_TYPE_ID_NONE) {
405 auto callback = std::make_shared<SensorCallbackImpl>(callbackAdapter);
406 std::lock_guard<std::mutex> lock(sensorCallbackMapMutex_);
407 sensorCallbackMap[ohosSensorTypeId] = callback;
408 return SENSOR_SUCCESS;
409 }
410 WVLOG_E("RegistOhosSensorCallback error, sensorTypeId is invalid.");
411 return SENSOR_PARAMETER_ERROR;
412 }
413
UnsubscribeOhosSensor(int32_t sensorTypeId)414 int32_t SensorAdapterImpl::UnsubscribeOhosSensor(int32_t sensorTypeId)
415 {
416 WVLOG_I("UnsubscribeOhosSensor sensorTypeId: %{public}d.", sensorTypeId);
417 int32_t ohosSensorTypeId = SensorTypeToOhosSensorType(sensorTypeId);
418 if (ohosSensorTypeId != SENSOR_TYPE_ID_NONE) {
419 int32_t ret = DeactivateSensor(ohosSensorTypeId, &mSensorUser);
420 if (ret != SENSOR_SUCCESS) {
421 WVLOG_E("UnsubscribeOhosSensor error, call DeactivateSensor ret = %{public}d.", ret);
422 return ret;
423 }
424 ret = UnsubscribeSensor(ohosSensorTypeId, &mSensorUser);
425 if (ret != SENSOR_SUCCESS) {
426 WVLOG_E("UnsubscribeOhosSensor error, call UnsubscribeSensor ret = %{public}d.", ret);
427 return ret;
428 }
429 std::lock_guard<std::mutex> lock(sensorCallbackMapMutex_);
430 sensorCallbackMap.erase(ohosSensorTypeId);
431 return SENSOR_SUCCESS;
432 }
433 WVLOG_E("UnsubscribeOhosSensor error, sensorTypeId is invalid.");
434 return SENSOR_PARAMETER_ERROR;
435 }
436 } // namespace OHOS::NWeb