整体模型
SMeeting Swift SDK 的对象模型很集中:SMeeting:唯一对外类,登录、会议管理、进出会议、媒体控制、主持人操作都在它上面RoomInfo:当前会议的房间级状态(标题、全体禁音禁画、锁定、共享状态等)MeetingUserInfo:会中某个成员的状态(昵称、角色、麦克风、摄像头、共享)SMeetingDelegate:所有会议事件的回调入口SMeetingRemoteVideoView/SRTCVideoView:画面渲染入口
会议层与 RTC 层的术语差异
SMeeting 建立在 SRTC 之上,两层的名词不通用,混用会让你在读接口时反复卡壳:
在 SMeeting 的接口里你只会看到
enterRoom / exitRoom / createRoom 这类会议语义的命名。
会议生命周期
一次完整的接入按下面的顺序展开:
判断当前是否在会议中,用
meeting.isInRoom。
会议 ID 与房间号
两个标识经常同时出现,含义不同:MeetingEnterReq 里 meetingId 与 roomNo 二选一填写即可。
会议类型与会议模式
创建会议时有两个正交的维度:MeetingType:.instant即时会议 /.appointment预约会议。预约会议需要额外填planTime(秒级时间戳)和planDur(分钟)MeetingMode:.normal普通、.mix合成、.voice语音会议、.training培训、.subMeeting分会场
AttendType 控制,密码入会要同时填 password,仅邀请入会要同时填 conferee。
会中状态:RoomInfo 与 MeetingUserInfo
进入会议后,SDK 会持续维护一份会中状态快照,随时可读:SMeetingDelegate 事件通知你,你在事件回调里重新读一次即可,不要缓存过期的成员对象。
MeetingUserInfo 里几个高频字段:
角色与权限
判断自己是否有管控权限,读自己的
MeetingUserInfo.role:
admin 前缀的接口只有主持人 / 联席主持人调用才会成功,普通成员调用会收到服务端返回的权限错误。
轨道描述 TrackDesc
会议里的每一路媒体流都有一个固定的描述,用来在订阅远端画面时定位目标:
成员当前发布了哪些轨道,可以读
MeetingUserInfo.trackDescs。
媒体控制的命名规则
- 开启侧叫
requestOpenMic/requestOpenCamera/requestShare—— 带request是因为这些动作要先向会议申请(受全体静音、全体禁画、禁共享等房间策略约束),再在本地起流 - 关闭侧叫
closeMic/closeCamera/stopShare—— 直接停止本地流,没有申请环节,不会抛错
byAdmin: true 和 adminUid,SDK 会走「确认主持人请求」的分支而不是「主动申请」。
视频渲染入口
细节见 视频渲染。
音频的订阅语义
远端音频与远端视频的处理方式不同:- 音频:进入会议后自动订阅,不需要你逐个成员去订阅。听筒 / 外放开关走
toggleRemoteAudioMute(_:),它只切播放,不动订阅关系 - 视频:按需订阅。大会场里如果把所有人的视频都订阅了,带宽和解码开销都不可控,所以要由你决定当前布局里哪几路需要拉流
事件体系
所有会议事件都通过SMeetingDelegate 上报,注册方式:
delegates是弱引用多播,可以注册多个观察者;SDK 不会因为注册而延长你的对象生命周期- 协议里所有方法都提供了默认空实现,只实现关心的事件即可
- 事件回调统一在主线程派发,可以直接更新 UI
@MainActor 类型(例如 SwiftUI 的 ObservableObject),协议方法需要声明为 nonisolated,再在里面回到主 actor 上下文:
会议外消息(IM)
enableIm() 会建立一条独立于会议的消息通道,用于在没有进入会议时接收呼叫、会议提醒等通知。它与会中的聊天消息是两套东西:会中聊天走 sendRoomChatMessage,只在会议内有效。
见 会议外消息。
底层 RTC 能力
当会议层的高层接口不足以满足需求时(例如需要 SRTC 才有的原始帧处理、自定义编码参数),可以通过meeting.srtc 访问底层实例。
请始终使用 meeting.srtc,不要自行另建一个 SRTC 实例:会议与底层共享同一个实例,另起一个会导致状态分裂、消息通道重复、设备被抢占。