Skip to main content
useThunderPhone Hook 让您能够完全掌控用户界面,同时由 ThunderPhone 管理语音会话、音频路由和连接状态。当您需要完全自定义的 UI——包括自己的按钮、布局、动画和品牌风格——同时希望 ThunderPhone 在底层处理一切时,请使用它。

何时使用无头 Hook

预构建的 ThunderPhoneWidget 组件可满足大多数使用场景,但在您需要以下功能时,应使用无头 Hook:
  • 与您的应用设计系统匹配的完全自定义通话 UI
  • 由实时音频电平驱动的音频响应式可视化效果(波形、光球、脉冲指示器)
  • 自定义通话流程,例如通话前表单、通话后问卷,或与语音并列的内嵌聊天
  • 集成到现有组件库中(Material UI、Chakra、Radix 等)

安装

由于您需要提供自己的 UI,无头 Hook 要求导入 @thunderphone/widget/style.css。不过,您仍必须安装相同的 @thunderphone/widget 包。

基本用法

**您必须在组件树中的某处渲染 phone.audio。**它是一个不可见的 React 元素,用于管理底层音频连接。如果省略它,将不会播放音频,且会话无法正常工作。

选项

通过 UseThunderPhoneOptions 将以下选项传递给 useThunderPhone
此 Hook 为无头 Hook:它接受 ThunderPhoneWidget 的外观属性(themeprimaryColortitlepositionclassName)。传入这些属性会导致 TypeScript 错误——界面呈现完全由您构建。

返回值

该 Hook 返回一个 UseThunderPhoneReturn 对象:

音频响应式 UI

audioLevelRef ref 可为您提供帧率级别的音频音量,而不会触发 React 重新渲染,因此非常适合驱动流畅的波形可视化、脉冲光球或任何与对话关联的动画。该音量反映语音智能体声音和访客麦克风中音量较高的一方。

波形示例

脉冲光球示例

说话状态指示器示例

对于会随音量变化的 React 渲染 UI——例如基于阈值的“说话中”徽章——请按固定间隔读取 audioLevelRef.current,并将结果存储在状态中:
始终从 audioLevelRef.current 读取音量。返回对象上的 audioLevel 数值已弃用且始终为 0——任何基于它构建的逻辑都会在无提示的情况下读取到零。

状态机

state 属性遵循以下生命周期:

示例

使用静音控制

使用铃声

在连接期间播放响铃声,以模拟电话呼叫:
铃声会在 connecting 状态期间循环播放,并在智能体接通时淡出。传入 true 可使用内置默认铃声,或传入 URL 字符串以使用您自己的音频文件。

使用事件回调

完全自定义 UI


提示

phone.audio 元素不可见,但必不可少。将其放在 JSX 中的任意位置——它不会渲染可见的 DOM,但会在内部管理 WebRTC 音频连接。
connecting 状态可能持续 1-3 秒。在此状态期间禁用通话按钮,以防止重复连接尝试。
当状态为 error 时,向用户显示 phone.error,并保持通话按钮可用。该 Hook 不会自行离开 error 状态——再次调用 connect() 会发起新的尝试并清除之前的错误。
onConnectonDisconnectonError 回调非常适合用于分析、日志记录,或触发其他应用逻辑,而无需轮询状态。
audioLevelRef 是唯一的实时音频级别来源。对于波形等流畅动画,请在 requestAnimationFrame 中读取 audioLevelRef.current(读取 ref 不会导致重新渲染);或者按固定间隔采样并将结果存储在状态中,以用于由 React 渲染的 UI。audioLevel 数值已弃用,且始终为 0——请勿基于它构建逻辑。