Files
zyt/admin/GROUP_VIDEO_CALL.md
T
2026-03-04 15:32:30 +08:00

5.1 KiB

群组视频通话功能说明

功能概述

在诊断列表页面新增了群组视频通话功能,支持三方视频通话(医助、患者、当前登录用户)。

实现原理

由于腾讯云 TUICallKit 的 groupCall 方法需要预先创建的 IM 群组,本实现采用了以下策略:

  1. 当前登录用户作为发起者
  2. 先发起与患者的一对一通话
  3. 当患者接听后,自动邀请医助加入通话
  4. 这样可以实现三方视频通话,无需预先创建 IM 群组

参与顺序:当前登录用户(发起者)→ 患者 → 医助

使用方法

1. 一对一视频通话

点击"视频通话"按钮,发起与患者的一对一视频通话。

  • 参与者:当前登录用户、患者

2. 群组视频通话

点击"群通话"按钮,发起三方群组视频通话。

  • 参与者:医助、患者、当前登录用户
  • 前提条件:该诊单必须已指派医助

技术实现

前端修改

1. 诊断列表页面 (admin/src/views/tcm/diagnosis/index.vue)

新增 handleGroupVideoCall 方法:

// 群组视频通话(三方通话)
const handleGroupVideoCall = (row: any) => {
    if (!row.patient_id) {
        feedback.msgWarning('患者信息不完整')
        return
    }
    
    if (!row.assistant_id) {
        feedback.msgWarning('该诊单未指派医助,无法发起群组通话')
        return
    }
    
    // 群组通话参与者顺序:当前登录用户(发起者)、患者、医助
    const userIds = [
        `patient_${row.patient_id}`,  // 先邀请患者
        `doctor_${row.assistant_id}`  // 再邀请医助
    ]
    
    videoCallRef.value?.open({
        diagnosisId: row.id,
        patientId: row.patient_id,
        patientName: row.patient_name,
        assistantId: row.assistant_id,
        userIds: userIds,
        isGroup: true
    })
}

2. 视频通话组件 (admin/src/components/video-call/index.vue)

更新 CallInfo 接口:

interface CallInfo {
    diagnosisId: number
    patientId: number
    patientName: string
    userId?: string          // 一对一通话时使用
    assistantId?: number     // 群组通话时的医助ID
    userIds?: string[]       // 群组通话时的用户ID列表
    isGroup: boolean         // 是否为群组通话
}

更新 startCall 方法,支持多人通话:

if (callInfo.value.isGroup && callInfo.value.userIds && callInfo.value.userIds.length > 0) {
    // 多人通话 - 先邀请第一个用户建立通话
    await TUICallKitServer.call({
        userID: callInfo.value.userIds[0],
        type: TUICallType.VIDEO_CALL
    })
    
    // 在通话接通后,通过 handleStatusChange 回调自动邀请其他用户
} else {
    // 一对一通话
    await TUICallKitServer.call({
        userID: callInfo.value.userId || '',
        type: TUICallType.VIDEO_CALL
    })
}

新增 inviteOtherUsers 方法,在通话接通后邀请其他用户:

const inviteOtherUsers = async () => {
    if (!callInfo.value.userIds || callInfo.value.userIds.length <= 1) {
        return
    }
    
    // 从第二个用户开始邀请
    for (let i = 1; i < callInfo.value.userIds.length; i++) {
        await TUICallKitServer.call({
            userID: callInfo.value.userIds[i],
            type: TUICallType.VIDEO_CALL
        })
        
        // 等待一下再邀请下一个
        await new Promise(resolve => setTimeout(resolve, 500))
    }
}

handleStatusChange 中监听通话接通事件:

// 通话接通
if (newStatus === STATUS.CALLING_C2C_VIDEO || newStatus === STATUS.CALLING_GROUP_VIDEO) {
    callConnected.value = true
    
    // 如果是多人通话且还有其他用户需要邀请
    if (callInfo.value.isGroup && callInfo.value.userIds && callInfo.value.userIds.length > 1) {
        inviteOtherUsers()
    }
}

用户ID格式

  • 医助:doctor_{assistant_id}
  • 患者:patient_{patient_id}
  • 当前登录用户:由后端返回的 userId 决定

通话流程

一对一视频通话

  1. 点击"视频通话"按钮
  2. 系统发起与患者的通话邀请
  3. 患者接听后开始通话

群组视频通话

  1. 点击"群通话"按钮
  2. 系统检查是否已指派医助
  3. 先向患者发起通话邀请
  4. 患者接听后,系统自动邀请医助加入
  5. 医助接听后,三方通话建立完成

参与顺序:当前登录用户(发起者)→ 患者 → 医助

注意事项

  1. 多人通话需要诊单已指派医助,否则会提示错误
  2. 多人通话采用"先建立通话,再邀请加入"的方式,避免了创建 IM 群组的复杂性
  3. 第一个用户必须接听后,才会邀请其他用户
  4. 当前登录用户作为发起者会自动加入通话,无需在 userIds 中添加
  5. 需要确保后端 getCallSignature 接口支持多人通话的签名生成
  6. 所有参与者都需要在腾讯云 IM 中注册并在线才能接收到通话邀请
  7. 邀请其他用户时会有短暂延迟(500ms),避免请求过快

权限控制

  • 一对一视频通话:tcm.diagnosis/video-call
  • 群组视频通话:tcm.diagnosis/video-group