实现智能调度合唱

更新时间: 2022/11/04 10:02:17

网易云信 K 歌场景会根据合唱双方的网络和设备情况,自动选择采用 NTP 实时合唱或串行合唱。

功能原理

RTC 服务器计算主唱和合唱者的网络延时均满足如下要求,且连接了有线耳机时,自动选择 NTP 实时合唱方案,否则采用串行合唱方案:

  • 主唱的采集播放延时 + 主唱上报的 RTT(Round-Trip Time) + 合唱者上报的 RTT < 特定阈值
  • 合唱者的采集播放延时 + 主唱上报的 RTT + 合唱者上报的 RTT < 特定阈值
  • 如果主唱或合唱者任意一方的网络延时不满足要求,则采用串行合唱方案。
  • 因蓝牙耳机会有较大延时,所以 NTP 实时合唱方案要求主唱和合唱者连接有线耳机。

实现方法

获取采集播放延时

不同的 Android 设备类型,底层设置的缓存 buffer 大小不同,导致采集和播放的时延会有所不同,请业务自行实现相关逻辑或联系网易云信技术支持工程师。

获取上报的 RTT

通过NERoomRtcStatsListener监听器可以获取当前房间内RTC的统计信息,并计算 rtt:

NERoomService roomService = NERoomKit.getInstance().getService(NERoomService.class);
NERoomContext roomContext = roomService.getRoomContext(roomUuid);
if (roomContext != null) {
    roomContext.addRtcStatsListener(new NERoomRtcStatsListener() {
        // 其他回调方法
        // ...

        @Override
        public void onRtcStats(@NonNull NERoomRtcStats stats) {
            long downRtt = stats.getDownRtt();
            long upRtt = stats.getUpRtt();

            if(downRtt > 0 && upRtt > 0) {
                this.rtt = convertRtt(downRtt + upRtt) / 2;
            } else if(downRtt == 0 && upRtt > 0) {
                this.rtt = convertRtt(upRtt);
            } else if(downRtt > 0 && upRtt == 0) {
                this.rtt = convertRtt(downRtt);
            }
        }
    });
}

private long convertRtt(long originRtt) {
    // 这里算法的原理是:originRtt代表用户手机到rtc边缘节点一个来回的时间。除以2得到单向的时间。合唱双方连接的边缘节点,典型情况会经过1到3个中心节点,
    // 取中间值2个,每个节点之间的单向时间估计为10ms,得到总共节点之间耗时30ms,两个人评分,每人加15ms。
    return (originRtt / 2) + 15;
}

获取是否连接了有线耳机

    private boolean isWiredHeadsetConnected() {
        Context context = null;
        AudioManager audioManager = (AudioManager)context.getSystemService(Context.AUDIO_SERVICE);
        return audioManager.isWiredHeadsetOn();
    }
此文档是否对你有帮助?
有帮助
去反馈
  • 功能原理
  • 实现方法
  • 获取采集播放延时
  • 获取上报的 RTT
  • 获取是否连接了有线耳机