• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# Vibrator
2
3## Overview
4
5### Function
6
7The vibrator driver model is developed based on OpenHarmony Hardware Driver Foundation (HDF) to facilitate vibrator driver development. The vibrator driver model shields the interaction between the device driver and the system, and provides unified and stable driver interface capabilities for the hardware service layer. It also provides open interfaces and interface parsing capabilities for developing vibrator drivers and deploying vibrators in different OSs.<br> The figure below shows the vibrator driver model.
8
9**Figure 1** Vibrator driver model
10
11![Vibrator driver model](figures/vibrator_driver_model.png)
12
13### Basic Concepts
14
15Vibrators can be classified into the following types based on vibration mechanism:
16
17- Rotor vibrator
18
19  The rotor vibrator uses magnetic field caused by current to drive the rotor to rotate and produce vibration. Rotor vibrators include ordinary rotor vibrators and coin rotor vibrators. The rotor vibrators cannot start or stop quickly or implement multiple vibration modes. However, they have small footprint and are cost-efficient.
20
21- Linear vibrator
22
23  The linear vibrator drives the spring mass for linear movement and produce vibration. Linear vibrators include longitudinal and transverse linear vibrators. The linear vibrators start and stop quickly, produce different vibration inductions, and have good sense of direction.
24
25The system calls the vibrator driver APIs to control the vibration of the device. There are two vibration modes:
26
27- One-shot vibration
28
29  The vibrator vibrates once for a given duration.
30
31- Periodic vibration
32
33  The vibrator vibrates at preset intervals. For example, if **haptic.clock.timer** is set to **[600, 600, 200, 600]**, the vibrator waits for 600 ms, vibrates for 600 ms, waits for 200 ms, and vibrates for 600 ms.
34
35### Working Principles
36
37The figure below shows how a vibrator driver is loaded.
38
39**Figure 2** How a vibrator driver works
40
41![How vibrator driver works](figures/vibrator_working.png)
42
43The following describes how a vibrator module driver loads and starts on a Hi3516DV300 that runs the standard system.
44
451. The Device Manager reads the vibrator management configuration from the **device_info.hcs** file.
462. The HDF Configuration Source (HCS) Parser parses the vibrator management configuration and loads the vibrator abstract driver.
473. The Device Manager reads the Vibrator data configuration from the **linear_vibrator_config.hcs** file.
484. The HCS Parser parses the vibrator data configuration and loads the haptic driver.
495. The Vibrator Proxy obtains the vibrator HDI service instance and sends it to the Vibrator Stub over Inter-Process Communication (IPC).
506. The Vibrator Stub processes IPC-related service logic and calls the Light Controller after parameter deserialization.
517. The Vibrator Controller implements the HDI APIs and calls the Vibrator abstract driver APIs over IPC.
528. The haptic driver starts a thread to parse the vibrator haptic module.
539. The haptic driver calls **Start()** in the vibrator abstract driver.
5410. The vibrator abstract driver calls **Start()** in the vibrator differentiated driver to control the vibrator device to vibrate with a given effect.
55
56## Development Guidelines
57
58### When to Use
59
60You can set different vibration effects as needed, for example, customizing vibration effects with different intensities and durations for buttons on the device, and customizing one-shot or periodic vibration effects with different intensities and durations for alarm clocks and incoming calls.
61
62### Available APIs
63
64The vibrator driver model supports static HCS and dynamic parameter configuration. The vibrator hardware service calls **StartOnce()** to trigger continuous vibration and calls **Start()** to trigger vibration with a specified effect. The following table describes the APIs provided by the vibrator driver model for the hardware service layer.
65
66**Table 1** APIs of the vibrator driver model
67
68| API                                 | Description                                          |
69| -------------------------------------- | ------------------------------------------------ |
70| int32_t (*StartOnce)([in] uint32_t duration)                        | Triggers a one-short vibration with a given duration.<br>**duration** specifies the duration of the one-short vibration.      |
71| int32_t (*Start)([in] const char *effectType)                        | Triggers periodic vibrations with a preset effect. <br>**effectType** indicates the pointer to the preset effect type.    |
72| int32_t (*Stop)([in] enum VibratorMode mode)                         | Stops vibration. <br>**mode** indicates the vibration mode, which can be one-short or periodic vibration.                            |
73| int32_t (*EnableVibratorModulation)(uint32_t duration, int32_t intensity, int32_t frequency) | Triggers a vibration with the given duration, frequency, and intensity.<br>**duration** indicates the duration of the vibration.<br>**intensity** indicates the vibration amplitude.<br>**frequency** indicates the vibrator frequency in the vibration period.|
74| int32_t (*GetVibratorInfo)([out] struct VibratorInfo **vibratorInfo) | Obtains information about all vibrators whose amplitude and frequency can be set in the system. <br>**vibratorInfo** indicates the pointer to the vibrator information obtained.|
75
76### How to Develop
77
78The vibrator driver model provides APIs for the upper-layer hardware service to trigger a one-shot vibration with a given duration, trigger vibration with a given effect, and stop vibration. This model implements functionalities such as cross-OS porting and device-specific configurations. The development procedure is as follows:
79
801. Develop the vibrator abstract driver based on the driver entry. Specifically, implement the **Bind**, **Init**, **Release**, and **Dispatch** functions, configure resources, and parse the HCS.
81
82   - Call **HDF_INIT** to register the driver entry with the HDF. The HDF calls **Bind** and then **Init** to load the driver. If **Init** fails to be called, the HDF calls **Release** to release the driver resources and exit the vibrator driver model. The vibrator driver model uses the HCS as the configuration source code. For details about HCS fields, see [Configuration Management](driver-hdf-manage.md). The driver entry function is defined as follows:
83
84     ```c
85     /* Register the entry structure object of the vibrator abstract driver. */
86     struct HdfDriverEntry g_vibratorDriverEntry = {
87         .moduleVersion = 1,               // Vibrator module version.
88         .moduleName = "HDF_VIBRATOR",     // Vibrator module name, which must be the same as moduleName in the device_info.hcs file.
89         .Bind = BindVibratorDriver,       // Bind function for the vibrator driver.
90         .Init = InitVibratorDriver,       // Ini function for the vibrator driver.
91         .Release = ReleaseVibratorDriver, // Release function for the vibrator driver.
92     };
93     /* Call HDF_INIT to register the driver entry with the HDF. */
94     HDF_INIT(g_vibratorDriverEntry);
95     ```
96
97   - Develop the vibrator abstract driver. Specifically, implement the **Bind**, **Init**, **Release**, and **Dispatch** functions.
98
99     ```c
100     /* External service published by the vibrator driver. */
101     static int32_t DispatchVibrator(struct HdfDeviceIoClient *client,
102         int32_t cmd, struct HdfSBuf *data, struct HdfSBuf *reply)
103     {
104         int32_t loop;
105
106         for (loop = 0; loop < sizeof(g_vibratorCmdHandle) / sizeof(g_vibratorCmdHandle[0]); ++loop) {
107             if ((cmd == g_vibratorCmdHandle[loop].cmd) && (g_vibratorCmdHandle[loop].func != NULL)) {
108                 return g_vibratorCmdHandle[loop].func(data, reply);
109             }
110         }
111
112         return HDF_SUCCESS;
113     }
114
115     /* Bind the external service provided by the vibrator driver to the HDF. */
116     int32_t BindVibratorDriver(struct HdfDeviceObject *device)
117     {
118         struct VibratorDriverData *drvData = NULL;
119         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(device, HDF_FAILURE);
120
121         drvData = (struct VibratorDriverData *)OsalMemCalloc(sizeof(*drvData));
122         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData, HDF_ERR_MALLOC_FAIL);
123
124         drvData->ioService.Dispatch = DispatchVibrator;
125         drvData->device = device;
126         device->service = &drvData->ioService;
127         g_vibratorDrvData = drvData;
128
129         return HDF_SUCCESS;
130     }
131
132     /* Entry function for vibrator driver initialization. */
133     int32_t InitVibratorDriver(struct HdfDeviceObject *device)
134     {
135         struct VibratorDriverData *drvData = NULL;
136
137         drvData->mode = VIBRATOR_MODE_BUTT;
138         drvData->state = VIBRATOR_STATE_IDLE;
139         ......
140         if (CreateVibratorHaptic(device) != HDF_SUCCESS) {
141             HDF_LOGE("%s: init workQueue failed!", __func__);
142             return HDF_FAILURE;
143         }
144
145         return HDF_SUCCESS;
146     }
147
148     /* Release the resources allocated during vibrator driver initialization. */
149     void ReleaseVibratorDriver(struct HdfDeviceObject *device)
150     {
151         struct VibratorDriverData *drvData = NULL;
152         ......
153         (void)DestroyVibratorHaptic();
154         (void)OsalMutexDestroy(&drvData->mutex);
155         (void)OsalMemFree(drvData);
156         g_vibratorDrvData = NULL;
157     }
158     ```
159
160   - During system startup, the HDF configuration management loads the vibrator abstract driver based on the device information HCS and publishes the vibrator driver interfaces.
161
162     ```c
163     /* Device information HCS. */
164     vibrator :: host {
165         hostName = "vibrator_host";
166         device_vibrator :: device {
167             device0 :: deviceNode {
168                 policy = 2;                              // Policy for the driver to publish services.
169                 priority = 100;                          // Priority (0–200) for starting the vibrator driver. A larger value indicates a lower priority. The recommended value is 100. If the priorities are the same, the device loading sequence is not ensured.
170                 preload = 0;                             // The value 0 means to load the driver by default during the startup of the system. The value 2 means the opposite.
171                 permission = 0664;                       // Permission for the device node created.
172                 moduleName = "HDF_VIBRATOR";             // Vibrator driver name. It must be the same as moduleName in the driver entry structure.
173                 serviceName = "hdf_misc_vibrator";       // Service published by the vibrator driver. The service name must be unique.
174                 deviceMatchAttr = "hdf_vibrator_driver"; // Keyword matching the private data of the driver. The value must be the same as that of match_attr in the private data configuration table of the driver.
175            }
176        }
177     }
178     ```
179
1802. Create a vibrator haptic model and parse the haptic HCS.
181
182   - Create a vibrator haptic model.
183
184     ```c
185     /* Create a vibrator haptic model, allocate resources, and parse the haptic HCS. */
186     int32_t CreateVibratorHaptic(struct HdfDeviceObject *device)
187     {
188         struct VibratorHapticData *hapticData = NULL;
189         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(device, HDF_FAILURE);
190
191         hapticData = (struct VibratorHapticData *)OsalMemCalloc(sizeof(*hapticData));
192         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(hapticData, HDF_ERR_MALLOC_FAIL);
193         g_vibratorHapticData = hapticData;
194         hapticData->supportHaptic = false;
195
196         if (OsalMutexInit(&hapticData->mutex) != HDF_SUCCESS) {
197             HDF_LOGE("%s: failed to init mutex", __func__);
198             goto EXIT;
199         }
200
201         DListHeadInit(&hapticData->effectSeqHead);
202
203         /* Parse the haptic HCS. */
204         if (ParserVibratorHapticConfig(device->property) != HDF_SUCCESS) {
205             HDF_LOGE("%s: parser haptic config failed!", __func__);
206             goto EXIT;
207         }
208
209         return HDF_SUCCESS;
210     EXIT:
211         OsalMemFree(hapticData);
212         return HDF_FAILURE;
213     }
214     ```
215
216   - The vibrator haptic model uses the HCS. For details about the HCS fields, see [Configuration Management](driver-hdf-manage.md).
217
218     ```c
219     /* Vibrator data configuration template (vibrator_config.hcs). */
220     root {
221         vibratorConfig {
222             boardConfig {
223                 match_attr = "hdf_vibrator_driver"; // The value must be the same as that of match_attr in the vibrator device configuration file.
224                 vibratorAttr {
225                     /* The value 0 means a rotor vibrator, and 1 means a linear vibrator. */
226                     deviceType = 1;                 // Device type.
227                     upportPreset = 1;               // Supported preset type.
228                 }
229                 vibratorHapticConfig {
230                     haptic_clock_timer {
231                         effectName = "haptic.clock.timer";
232                         type = 1;                   //  The value 0 indicates the built-in mode, and 1 indicates the time sequence.
233                         seq = [600, 600, 200, 600]; // Time sequence.
234                     }
235                     haptic_default_effect {
236                         effectName = "haptic.default.effect";
237                         type = 0;
238                         seq = [0, 3, 800, 1];
239                     }
240                 }
241             }
242         }
243     }
244     ```
245
2463. Implement the APIs for obtaining vibrator information, triggering and stopping a vibration, and creating and destroying a timer based on the vibration mode.
247
248   The vibrator hardware service calls **StartOnce** to start a one-shot vibration with a given duration and calls **StartEffect** to start vibration with a specified effect.
249
250   ```c
251   /* Trigger a one-short vibration with a given duration. */
252   static int32_t StartOnce(struct HdfSBuf *data, struct HdfSBuf *reply)
253   {
254       uint32_t duration;
255       int32_t ret;
256       struct VibratorEffectCfg config;
257       struct VibratorDriverData *drvData = GetVibratorDrvData();
258       (void)reply;
259       ......
260       config.cfgMode = VIBRATOR_MODE_ONCE;
261       config.duration = duration;
262       config.effect = NULL;
263       /* Create a timer based on the vibration effect. */
264       ret = StartHaptic(&config);
265       if (ret != HDF_SUCCESS) {
266           HDF_LOGE("%s: start haptic failed!", __func__);
267           return ret;
268       }
269
270       return HDF_SUCCESS;
271   }
272
273   /* Trigger a vibration with a given effect. */
274   static int32_t StartEffect(struct HdfSBuf *data, struct HdfSBuf *reply)
275   {
276       int32_t ret;
277       const char *effect = NULL;
278       struct VibratorEffectCfg config;
279       struct VibratorDriverData *drvData = GetVibratorDrvData();
280       (void)reply;
281       ......
282       config.cfgMode = VIBRATOR_MODE_PRESET;
283       config.duration = 0;
284       config.effect = effect;
285
286       ret = StartHaptic(&config);
287       if (ret != HDF_SUCCESS) {
288           HDF_LOGE("%s: start haptic failed!", __func__);
289           return ret;
290       }
291
292       return HDF_SUCCESS;
293   }
294
295   /* Stop vibration based on the specified vibration mode. */
296   static int32_t Stop(struct HdfSBuf *data, struct HdfSBuf *reply)
297   {
298       int32_t ret;
299       int32_t mode;
300       struct VibratorDriverData *drvData = GetVibratorDrvData();
301       (void)reply;
302       ......
303       /* Stop vibration and destroy the timer. */
304       ret = StopHaptic();
305       if (ret != HDF_SUCCESS) {
306           HDF_LOGE("%s: stop haptic failed!", __func__);
307           return ret;
308       }
309
310       (void)OsalMutexLock(&drvData->mutex);
311       drvData->mode = VIBRATOR_MODE_BUTT;
312       (void)OsalMutexUnlock(&drvData->mutex);
313
314       return HDF_SUCCESS;
315   }
316
317   /* Trigger vibration with the given duration, frequency, and intensity. */
318   static int32_t EnableModulationParameter(struct HdfSBuf *data, struct HdfSBuf *reply)
319   {
320       (void)reply;
321       struct VibratorEffectCfg config;
322       struct VibratorDriverData *drvData;
323       uint32_t duration;
324       int32_t intensity;
325       int32_t frequency;
326       int32_t ret;
327       .....
328       (void)OsalMutexLock(&drvData->mutex);
329       drvData->mode = VIBRATOR_MODE_ONCE;
330       (void)OsalMutexUnlock(&drvData->mutex);
331       /* Set the vibration intensity and frequency. */
332       ret = drvData->ops.SetParameter(intensity, frequency);
333       if (ret != HDF_SUCCESS) {
334           HDF_LOGE("%s: set parameter failed", __func__);
335           return HDF_FAILURE;
336       }
337
338       config.cfgMode = VIBRATOR_MODE_ONCE;
339       config.duration = duration;
340       config.effect = NULL;
341
342       ret = StartHaptic(&config);
343       if (ret != HDF_SUCCESS) {
344           HDF_LOGE("%s: start haptic failed", __func__);
345           return HDF_FAILURE;
346       }
347
348       return HDF_SUCCESS;
349   }
350
351   /* Obtain vibrator information, including whether the intensity and frequency can be set and the intensity and frequency range. */
352   static int32_t GetVibratorInfo(struct HdfSBuf *data, struct HdfSBuf *reply)
353   {
354       (void)data;
355       struct VibratorDriverData *drvData;
356
357       drvData = GetVibratorDrvData();
358       CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData, HDF_ERR_INVALID_PARAM);
359       CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(reply, HDF_ERR_INVALID_PARAM);
360
361       if (!HdfSbufWriteBuffer(reply, &drvData->vibratorInfo, sizeof(drvData->vibratorInfo))) {
362           HDF_LOGE("%s: write sbuf failed", __func__);
363           return HDF_FAILURE;
364       }
365
366       return HDF_SUCCESS;
367   }
368   ```
369
3704. Implement the interfaces for the vibrator chipset driver.
371
372   - Register the vibrator chipset driver interfaces when the vibrator chipset driver is initialized successfully.
373
374     ```c
375     /* Register the vibrator chipset driver interfaces. */
376     int32_t RegisterVibrator(struct VibratorOps *ops)
377     {
378         struct VibratorDriverData *drvData = GetVibratorDrvData();
379
380         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(ops, HDF_FAILURE);
381         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData, HDF_FAILURE);
382
383         (void)OsalMutexLock(&drvData->mutex);
384         drvData->ops.Start = ops->Start;
385         drvData->ops.StartEffect = ops->StartEffect;
386         drvData->ops.Stop = ops->Stop;
387         drvData->ops.SetParameter = ops->SetParameter;
388         (void)OsalMutexUnlock(&drvData->mutex);
389
390         return HDF_SUCCESS;
391     }
392
393     /* Register vibrator information. */
394     int32_t RegisterVibratorInfo(struct VibratorInfo *vibratorInfo)
395     {
396         struct VibratorDriverData *drvData = GetVibratorDrvData();
397
398         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(vibratorInfo, HDF_FAILURE);
399         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData, HDF_FAILURE);
400
401         (void)OsalMutexLock(&drvData->mutex);
402         if (memcpy_s(&drvData->vibratorInfo, sizeof(drvData->vibratorInfo), vibratorInfo, sizeof(*vibratorInfo)) != EOK) {
403             HDF_LOGE("%s: Memcpy vibrator config failed", __func__);
404             return HDF_FAILURE;
405         }
406         (void)OsalMutexUnlock(&drvData->mutex);
407
408         return HDF_SUCCESS;
409     }
410     ```
411
412
413
414   - The vibrator driver model provides vibrator chipset driver interfaces. Implement these interfaces as follows:
415
416     ```c
417     /* Stop vibration based on the specified vibration mode. */
418     static int32_t StopModulationParameter()
419     {
420         uint8_t value[DRV2605L_VALUE_BUTT];
421         struct Drv2605lDriverData *drvData = NULL;
422         drvData = GetDrv2605lDrvData();
423
424         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData, HDF_FAILURE);
425         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData->drv2605lCfgData, HDF_FAILURE);
426
427         value[DRV2605L_ADDR_INDEX] = (uint8_t)DRV2605_REG_MODE;
428         value[DRV2605L_VALUE_INDEX] = (uint8_t)DRV2605_MODE_STANDBY;
429         if (WriteDrv2605l(&drvData->drv2605lCfgData->vibratorBus.i2cCfg, value, sizeof(value)) != HDF_SUCCESS) {
430             HDF_LOGE("%s: i2c addr [%0X] write failed", __func__, value[DRV2605L_ADDR_INDEX]);
431             return HDF_FAILURE;
432         }
433
434         value[DRV2605L_ADDR_INDEX] = (uint8_t)DRV2605_REG_RTPIN;
435         value[DRV2605L_VALUE_INDEX] = (uint8_t)&drvData->drv2605lCfgData->vibratorAttr.defaultIntensity;
436         if (WriteDrv2605l(&drvData->drv2605lCfgData->vibratorBus.i2cCfg, value, sizeof(value)) != HDF_SUCCESS) {
437             HDF_LOGE("%s: i2c addr [%0X] write failed", __func__, value[DRV2605L_ADDR_INDEX]);
438         }
439
440         value[DRV2605L_ADDR_INDEX] = (uint8_t)DRV2605_REG_LRARESON;
441         value[DRV2605L_VALUE_INDEX] = (uint8_t)&drvData->drv2605lCfgData->vibratorAttr.defaultFrequency;
442         if (WriteDrv2605l(&drvData->drv2605lCfgData->vibratorBus.i2cCfg, value, sizeof(value)) != HDF_SUCCESS) {
443             HDF_LOGE("%s: i2c addr [%0X] write failed", __func__, value[DRV2605L_ADDR_INDEX]);
444         }
445
446         return HDF_SUCCESS;
447     }
448
449     /* Set the vibration intensity and frequency. */
450     static void SetModulationParameter(int32_t intensity, int32_t frequency)
451     {
452         uint8_t value[DRV2605L_VALUE_BUTT];
453         struct Drv2605lDriverData *drvData = NULL;
454         drvData = GetDrv2605lDrvData();
455
456         CHECK_VIBRATOR_NULL_PTR_RETURN_VALUE(drvData, HDF_FAILURE);
457
458         if (intensity != 0) {
459             value[DRV2605L_ADDR_INDEX] = (uint8_t)DRV2605_REG_RTPIN;
460             value[DRV2605L_VALUE_INDEX] = (uint8_t)INTENSITY_MAPPING_VALUE(intensity);
461             if (WriteDrv2605l(&drvData->drv2605lCfgData->vibratorBus.i2cCfg, value, sizeof(value)) != HDF_SUCCESS) {
462                 HDF_LOGE("%s: i2c addr [%0X] write failed", __func__, value[DRV2605L_ADDR_INDEX]);
463                 return;
464             }
465         } else {
466             HDF_LOGD("%s: the setting of intensity 0 is not supported and \
467                 will be set as the system default intensity", __func__);
468         }
469
470         if (frequency != 0) {
471             value[DRV2605L_ADDR_INDEX] = (uint8_t)DRV2605_REG_LRARESON;
472             value[DRV2605L_VALUE_INDEX] = (uint8_t)FREQUENCY_MAPPING_VALUE(frequency);
473             if (WriteDrv2605l(&drvData->drv2605lCfgData->vibratorBus.i2cCfg, value, sizeof(value)) != HDF_SUCCESS) {
474                 HDF_LOGE("%s: i2c addr [%0X] write failed", __func__, value[DRV2605L_ADDR_INDEX]);
475                 return;
476             }
477         } else {
478             HDF_LOGD("%s: the setting of frequency 0 is not supported and \
479                 will be set as the system default frequency", __func__);
480         }
481     }
482     ```
483
484### Verification
485
486After the driver is developed, develop test cases in the vibrator unit test to verify the basic functionalities of the driver. Use your own platform as the test environment.
487
488```c++
489/* Initialize the vibrator interface instance before executing test cases. */
490void HdfVibratorTest::SetUpTestCase()
491{
492    g_vibratorDev = NewVibratorInterfaceInstance();
493}
494/* Release test case resources. */
495void HdfVibratorTest::TearDownTestCase()
496{
497    if(g_vibratorDev != nullptr){
498        FreeVibratorInterfaceInstance();
499        g_vibratorDev = nullptr;
500    }
501}
502
503/* Verify one-short vibration. */
504HWTEST_F(HdfVibratorTest, PerformOneShotVibratorDuration_001, TestSize.Level1)
505{
506    ASSERT_NE(nullptr, g_vibratorDev);
507
508    int32_t startRet = g_vibratorDev->StartOnce(g_duration);
509    EXPECT_EQ(startRet, HDF_SUCCESS);
510
511    OsalMSleep(g_sleepTime1);
512
513    int32_t endRet = g_vibratorDev->Stop(VIBRATOR_MODE_ONCE);
514    EXPECT_EQ(endRet, HDF_SUCCESS);
515}
516/* Verify vibration with the preset effect. */
517HWTEST_F(HdfVibratorTest, ExecuteVibratorEffect_002, TestSize.Level1)
518{
519    ASSERT_NE(nullptr, g_vibratorDev);
520
521    int32_t startRet = g_vibratorDev->Start(g_builtIn);
522    EXPECT_EQ(startRet, HDF_SUCCESS);
523
524    OsalMSleep(g_sleepTime1);
525
526    int32_t endRet = g_vibratorDev->Stop(VIBRATOR_MODE_PRESET);
527    EXPECT_EQ(endRet, HDF_SUCCESS);
528}
529/* Obtain vibrator information, including whether the intensity and frequency can be set and the intensity and frequency range. */
530HWTEST_F(HdfVibratorTest, GetVibratorInfo_001, TestSize.Level1)
531{
532    ASSERT_NE(nullptr, g_vibratorDev);
533
534    int32_t startRet = g_vibratorDev->GetVibratorInfo(&g_vibratorInfo);
535    EXPECT_EQ(startRet, HDF_SUCCESS);
536    EXPECT_NE(g_vibratorInfo, nullptr);
537
538    printf("intensity = %d, intensityMaxValue = %d, intensityMinValue = %d\n\t",
539    g_vibratorInfo->isSupportIntensity, g_vibratorInfo->intensityMaxValue, g_vibratorInfo->intensityMinValue);
540    printf("frequency = %d, frequencyMaxValue = %d, frequencyMinValue = %d\n\t",
541    g_vibratorInfo->isSupportFrequency, g_vibratorInfo->frequencyMaxValue, g_vibratorInfo->frequencyMinValue);
542}
543/* Trigger vibration with the given duration, frequency, and intensity. */
544HWTEST_F(HdfVibratorTest, EnableVibratorModulation_001, TestSize.Level1)
545{
546    int32_t startRet;
547    ASSERT_NE(nullptr, g_vibratorDev);
548    EXPECT_GT(g_duration, 0);
549
550    if ((g_vibratorInfo->isSupportIntensity == 1) || (g_vibratorInfo->isSupportFrequency == 1)) {
551        EXPECT_GE(g_intensity1, g_vibratorInfo->intensityMinValue);
552        EXPECT_LE(g_intensity1, g_vibratorInfo->intensityMaxValue);
553        EXPECT_GE(g_frequency1, g_vibratorInfo->frequencyMinValue);
554        EXPECT_LE(g_frequency1, g_vibratorInfo->frequencyMaxValue);
555
556        startRet = g_vibratorDev->EnableVibratorModulation(g_duration, g_intensity1, g_frequency1);
557        EXPECT_EQ(startRet, HDF_SUCCESS);
558        OsalMSleep(g_sleepTime1);
559        startRet = g_vibratorDev->Stop(VIBRATOR_MODE_ONCE);
560        EXPECT_EQ(startRet, HDF_SUCCESS);
561    }
562}
563```
564