振动执行器入门

设计 Android 设备上的触觉效果之前,了解振动执行器的运作方式会有所帮助。

Illustration of the components of a Haptic LRA

最常见的振动执行器是线性谐振执行器 (LRA)。每个 LRA 都由一个压在磁性活动质量上的音圈组成,该质量连接到弹簧上。施加到音圈上的交流电压会产生电磁力,导致质量移动。弹簧提供使质量返回其起始位置的恢复力。质量的来回运动导致 LRA 振动。它们具有谐振频率,在该频率下输出最大。

在两个不同频率下施加相同的输入电压时,振动输出幅度可能不同。频率离 LRA 的谐振频率越远,其振动幅度越低。

LRA 在设备中的一个常见功能是模拟无响应玻璃表面上的按钮点击感觉。它有助于使用户交互感觉更自然。当应用于虚拟键盘上的打字时,点击反馈可以提高打字速度并减少错误。清晰明了的点击反馈信号的持续时间通常小于 10 到 20 毫秒。实现良好的点击需要了解设备中使用的 LRA。这就是为什么依赖预制波形可以为点击提供最佳反馈的原因。每当需要点击反馈时,都可以使用平台提供的常量。

设备中可实现的触觉效果取决于振动执行器及其驱动程序。包含过驱动和主动制动功能的触觉驱动程序可以减少 LRA 的上升时间和振铃,从而实现更灵敏、更清晰的振动。为了说明,让我们看看自定义波形图案在通用设备上的行为。

Kotlin

val timings: LongArray = longArrayOf(50, 50, 50, 50, 50, 100, 350, 250)
val amplitudes: IntArray = intArrayOf(77, 79, 84, 99, 143, 255, 0, 255)
val repeatIndex = -1 // Do not repeat.

vibrator.vibrate(VibrationEffect.createWaveform(timings, amplitudes, repeatIndex))

Java

long[] timings = new long[] { 50, 50, 50, 50, 50, 100, 350, 250 };
int[] amplitudes = new int[] { 77, 79, 84, 99, 143, 255, 0, 255 };
int repeatIndex = -1 // Do not repeat.

vibrator.vibrate(VibrationEffect.createWaveform(timings, amplitudes, repeatIndex));

下图显示了上面显示的代码片段对应的波形。

Plot of step function input waveform

相应的加速度如下所示

Plot of actual measured waveform, showing more organic transitions between levels

请注意,每当图案的幅度发生阶跃变化时(例如,在 0ms、150ms、200ms、250ms、700ms),加速度都会逐渐增加,而不是突然增加。在每个幅度阶跃变化处也存在过冲,并且当输入幅度突然下降到 0 时,可见的“振铃”持续至少 50ms。

可以通过逐渐增加和减小幅度来改进这种触觉模式,以避免过冲并减少振铃时间。以下是修改版波形和加速度图。

Kotlin

val timings: LongArray = longArrayOf(
    25, 25, 50, 25, 25, 25, 25, 25, 25, 25, 75, 25, 25,
    300, 25, 25, 150, 25, 25, 25
)
val amplitudes: IntArray = intArrayOf(
    38, 77, 79, 84, 92, 99, 121, 143, 180, 217, 255, 170, 85,
    0, 85, 170, 255, 170, 85, 0
)
val repeatIndex = -1 // Do not repeat.

vibrator.vibrate(VibrationEffect.createWaveform(timings, amplitudes, repeatIndex))

Java

long[] timings = new long[] {
        25, 25, 50, 25, 25, 25, 25, 25, 25, 25, 75, 25, 25,
        300, 25, 25, 150, 25, 25, 25
    };
int[] amplitudes = new int[] {
        38, 77, 79, 84, 92, 99, 121, 143, 180, 217, 255, 170, 85,
        0, 85, 170, 255, 170, 85, 0
    };
int repeatIndex = -1; // Do not repeat.

vibrator.vibrate(VibrationEffect.createWaveform(timings, amplitudes, repeatIndex));

Plot of input waveform with additional steps

Plot of measured waveform, showing smoother transitions

因此,在 Android 设备上创建触觉效果不仅仅是提供频率和幅度值。如果没有完全访问振动执行器和驱动程序的工程规范,从头开始设计触觉效果并非易事。Android API 提供了允许您执行以下操作的常量

  • 执行清晰的效果和基本元素

  • 将它们连接起来以组合新的触觉效果。

这些预定义的触觉常量和基本元素可以大大加快您的工作速度,同时确保高质量的触觉效果。