功能描述
在直播观看场景中,同一路内容通常会提供多个清晰度档位,例如 1080p、720p、480p。当用户网络状况、设备性能或业务诉求发生变化时,您可能需要在不同档位之间切换,以在清晰度和流畅度之间取得更好的平衡。
TRTC Web SDK 提供实验接口 switchPlaybackQuality,用于在多路播放流之间切换清晰度。SDK 内部会负责处理切换过程中的播放衔接和主流音频同步。
本文将介绍直播播放多分辨率切换的接入方式,以及推荐的最佳实践。
适用场景
switchPlaybackQuality 适合以下场景:
- 直播观众端多清晰度观看:同一路直播内容提供多个分辨率档位,观众可以手动选择画质。
- 移动端弱网播放:当带宽下降、丢包升高或画面卡顿时,自动切换到更低档位,优先保证可播放性。
该方案更适合单路直播播放场景。如果您是多人通话或宫格视频场景,建议优先参考 开启大小流功能。
前提条件
使用该能力前,请确保:
- 同一路直播内容已经准备好多档清晰度流,每个档位都能通过唯一的
userId(以及可选的streamType)进行区分。 - 已经完成 trtc.enterRoom() 进房。
- 观众端已经通过 trtc.startRemoteVideo() 播放了
streamList中的某一路流。 streamList[].bitrate填写的是各档位的实际码率(单位:kbps),用于排序及自动切换判断。
接口说明
通过 callExperimentalAPI 调用:
await trtc.callExperimentalAPI('switchPlaybackQuality', options);
interface PlaybackQualityStream {
name: string;
userId: string;
streamType?: TRTCStreamType;
bitrate: number;
}
interface ResolutionConfig {
userId: string;
streamType: TRTCStreamType;
name: string;
}
interface SwitchPlaybackQualityOptions {
quality?: string;
streamList?: PlaybackQualityStream[];
onSwitched?: (from: ResolutionConfig, to: ResolutionConfig) => void;
}
参数说明
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
quality |
string | 否 | 目标档位名称。必须与 streamList[].name 精确匹配。传入 auto 表示开启自动切换模式;不传则仅缓存 streamList。 |
streamList |
array | 否 | 清晰度档位列表。不传则复用上一次缓存的列表。 |
streamList[].name |
string | 是 | 档位名称,例如 1080p、720p。 |
streamList[].userId |
string | 是 | 该档位对应的播放流 userId。 |
streamList[].streamType |
TRTCStreamType | 否 | 流类型,默认主流。 |
streamList[].bitrate |
number | 是 | 码率,单位 kbps。自动模式会按码率从高到低排序。 |
onSwitched |
function | 否 | 切换成功回调,返回切换前后的档位信息。 |
手动切换模式
1. 准备档位列表
建议您在业务层维护一份清晰度列表,例如:
const streamList = [
{ name: '1080p', userId: 'anchor_1080p', bitrate: 2000 },
{ name: '720p', userId: 'anchor_720p', bitrate: 1000 },
{ name: '480p', userId: 'anchor_480p', bitrate: 500 },
];
2. 进房后缓存 streamList
首次调用时,如果只传 streamList 而不传 quality,SDK 只会缓存档位信息,不会立即切换。
await trtc.callExperimentalAPI('switchPlaybackQuality', {
streamList,
});
3. 播放当前默认档位
请先通过 trtc.startRemoteVideo() 播放其中一路。当前正在播放的流必须存在于 streamList 中。
await trtc.startRemoteVideo({
userId: 'anchor_720p',
streamType: TRTC.TYPE.STREAM_TYPE_MAIN,
view: document.getElementById('live-player'),
});
4. 用户切换目标清晰度
当用户在 UI 上选择新的档位时,调用 switchPlaybackQuality 即可:
await trtc.callExperimentalAPI('switchPlaybackQuality', {
quality: '1080p',
onSwitched(from, to) {
console.log(`playback quality switched: ${from.name} -> ${to.name}`);
},
});
5. 切换过程说明
默认情况下,SDK 在执行 switchPlaybackQuality 时,会优先保障当前正在播放的档位继续渲染,并在后台异步拉起目标档位的新视频流。只有当新档位拉流并进入可播放状态后,SDK 才会停止旧的视频流并完成切换。
这意味着:
- 调用切换接口后,旧画面不会立刻消失;
- 业务层通常不需要在调用瞬间立即展示全屏 loading;
- 更推荐在
onSwitched回调中更新“当前清晰度”UI 状态,而不是在调用切换时就主动清空旧画面。
6. 完整示例
const streamList = [
{ name: '1080p', userId: 'anchor_1080p', bitrate: 2000 },
{ name: '720p', userId: 'anchor_720p', bitrate: 1000 },
{ name: '480p', userId: 'anchor_480p', bitrate: 500 },
];
await trtc.enterRoom({
sdkAppId: 1400000000,
userId: 'audience_123',
userSig: 'xxx',
roomId: 12345,
scene: 'live',
role: 'audience',
});
await trtc.callExperimentalAPI('switchPlaybackQuality', { streamList });
await trtc.startRemoteVideo({
userId: 'anchor_720p',
streamType: TRTC.TYPE.STREAM_TYPE_MAIN,
view: document.getElementById('live-player'),
});
// 用户点击“高清”按钮时
await trtc.callExperimentalAPI('switchPlaybackQuality', {
quality: '1080p',
onSwitched(from, to) {
console.log(`switch success: ${from.name} -> ${to.name}`);
},
});
自动切换模式
如果您希望 SDK 根据当前播放状态自动在不同档位之间切换,可以传入 quality: 'auto' 开启自动模式。
开启方式
const streamList = [
{ name: '1080p', userId: 'anchor_1080p', bitrate: 2000 },
{ name: '720p', userId: 'anchor_720p', bitrate: 1000 },
{ name: '480p', userId: 'anchor_480p', bitrate: 500 },
];
await trtc.callExperimentalAPI('switchPlaybackQuality', { streamList });
await trtc.startRemoteVideo({
userId: 'anchor_720p',
streamType: TRTC.TYPE.STREAM_TYPE_MAIN,
view: document.getElementById('live-player'),
});
await trtc.callExperimentalAPI('switchPlaybackQuality', {
quality: 'auto',
onSwitched(from, to) {
console.log(`auto switch: ${from.name} -> ${to.name}`);
},
});
默认策略说明
自动模式下,SDK 会根据 streamList[].bitrate 从高到低排序,并结合当前网络和播放状态决定是否切换。
下切条件
满足以下任一条件时,SDK 会尝试切换到更低档位:
- 弱网且帧率低:下行丢包率较高,同时当前解码帧率较低。
- 渲染卡顿明显:检测到较长时间的画面渲染卡顿。
默认阈值如下:
| 指标 | 默认值 |
|---|---|
| 下行丢包率阈值 | 20% |
| 解码帧率阈值 | 5fps |
| 渲染卡顿时长阈值 | 1500ms |
上切条件
当网络恢复到较好状态后,SDK 会在满足以下条件时尝试切回更高档位:
- 下行丢包率持续保持在较低水平;
- 距离上一次下切已经超过冷却时间;
- 当前会话内上切失败次数未达到限制。
默认阈值如下:
| 指标 | 默认值 |
|---|---|
| 良好丢包率阈值 | 15% |
| 上切冷却时间 | 120s |
| 最大连续上切失败次数 | 3 |
解码失败兜底
如果当前正在播放的档位发生视频解码失败,SDK 会自动回退到更低档位,并记录本次会话中设备可稳定播放的最高档位,避免后续反复上切失败。
如果您在自动模式下再次调用
switchPlaybackQuality并传入具体档位,例如quality: '720p',SDK 会退出自动模式并按手动切换处理。
与大小流方案的区别
switchPlaybackQuality 和“大小流”都能实现清晰度切换,但适用场景不同:
| 方案 | 适用场景 | 特点 |
|---|---|---|
| 大小流 | 多人通话、宫格视频、同一 userId 下切大流/小流 |
适合 RTC 多路订阅优化 |
switchPlaybackQuality |
单路直播播放、多档分辨率切换 | 适合直播观众端手动/自动切换画质 |
如果您的业务是“一个主播、多档清晰度、观众只播放其中一路”,更建议使用 switchPlaybackQuality。
最佳实践建议
如果您需要同时兼顾默认体验、弱网适配和用户自主选择,推荐采用以下接入方式:
- 首次播放默认中档:例如优先播放
720p,兼顾首屏体验和兼容性。 - 移动端默认开启自动模式:让 SDK 在弱网或渲染卡顿时自动降档。
- 用户手动选择时切为指定档位:一旦用户手动选择
1080p/720p/480p,就调用一次具体quality,覆盖自动模式。 - 使用
onSwitched同步 UI 状态:在切换成功后更新当前档位按钮、提示文案或埋点数据。
常见问题
1. 调用后没有发生切换,应该怎么排查?
您可以优先检查以下几点:
- 是否已经先调用过一次
switchPlaybackQuality({ streamList })缓存档位列表; - 当前正在播放的流是否存在于
streamList中; quality是否与streamList[].name精确匹配;- 目标档位是否与当前播放档位相同。
3. 自动模式为什么没有触发上切?
自动上切不仅依赖网络恢复,还会受到冷却时间、历史上切失败次数以及当前设备能力上限的影响。如果设备在更高档位上发生过解码失败,SDK 会降低后续自动上切的最高目标档位。
4. 手动切换时,音频需要业务层自己切吗?
在主流切换场景下,SDK 会同步处理音频切换,业务层通常不需要额外再做一次音频切换。
5. 自动模式和手动模式可以混用吗?
可以。推荐做法是默认开启自动模式;当用户明确选择某个档位时,再调用一次具体 quality 切为手动模式。