0
点赞
收藏
分享

微信扫一扫

语音房开发简单总结

MaxWen 2022-02-27 阅读 58

语音房开发, 这里使用的是声网和网易云信

声网提供连麦的功能,

网易云信处理消息的同步

1, 待验证

1.1 加入房间

注册好网易云信,再去注册声网的服务

        let request = NIMChatroomEnterRequest()

        // 

        NIMSDK.shared().chatroomManager.enterChatroom(request) { error, chatRoomModel, member in

            self.configAgoraRtc()

        }
        
 public func configAgoraRtc(){

        let config = AgoraRtcEngineConfig()
        //

        agorat = AgoraRtcEngineKit.sharedEngine(with: config, delegate: self)

        agorat.enableAudioVolumeIndication(400, smooth: 3, report_vad:true)

        agorat.adjustPlaybackSignalVolume(2)

        agorat.setChannelProfile(.liveBroadcasting)

        agorat.enableDeepLearningDenoise(true)

        agorat.setClientRole(.audience)

 }
    
调整为

        let request = NIMChatroomEnterRequest()

        // 

        NIMSDK.shared().chatroomManager.enterChatroom(request) { error, chatRoomModel, member in

        }
        
        
         self.configAgoraRtc()

因为,如果没网,就一起 gg 了

1.2 消息同步, 性能优化,耗电方向的角度

语音房,按职能( 权限 )的角度,一般可分为,游客和管理员

语音房,1 / 3 左右的功能,不对游客开发

所以, 房间的成员信息变更的时候,不用通知游客

游客的手机,减少了很多网络 socket 传输,减少耗电

1.2.1 网易云信的消息,一般用 P2P,和 Chatroom,

这里可使用 Team , 群组功能

成为管理员,就加入了房间对应的群组,接收关联的消息

1.3, 刚开始开发,按照一切非常顺利

公司发现啥问题,马上补

KPI 非,用户授予

可能性,那么多。进度,能不赶

1.4 常见的优化 ( 请求加速 )手段,略

加流程大法,好

弱网环境下,点击上麦,

用户头像,马上上去了,

调用声网修改角色的方法,gg

2, 功能

发消息的常见流程:

有一个基于时间的考量

用户点击,发消息,UI 上,秒发出

UI, 就是障眼法

200 ms 后,这个网络请求 pending

消息的旁边出现一个进度条

后来,请求超时了,

列表的该消息,旁边出现,

一个重试按钮,和提示语 ( 请检查网络 )

2.1 公屏消息

可以移动端,直接发消息

         let session = NIMSession(chatK, type: NIMSessionType.chatroom)

        let message = NIMMessage()

            let object = NIMCustomObject()

            object.attachment = HelloMessage()

            // 构造出具体消息并注入附件

            message.messageObject = object

        do {

             try NIMSDK.shared().chatManager.send(message, to: session)

         } catch let err {

             print(err)

        }

消息编码

class HelloMessage: NSObject, NIMCustomAttachment{


    var txt = ""
    

    func encode() -> String {

        let dict: [String: Any] = ["txt": txt,

                                "type": 6]


        var content = ""

        do {

            let data = try JSONSerialization.data(withJSONObject: dict, options: [])

            if let val = String(data: data, encoding: .utf8){

                content = val

            }

        } catch {

            print(error)

        }

        return content

    }

注册解码

NIMCustomObject.registerCustomDecoder(TheDecoder())

解码器



class TheDecoder: NSObject, NIMCustomAttachmentCoding {



    /// 消息解码 处理

    func decodeAttachment(_ content: String?) -> NIMCustomAttachment? {

        var attachment: NIMCustomAttachment?

        guard let contentData = content?.data(using: .utf8),

        let dic = try? JSONSerialization.jsonObject(with: contentData, options: .mutableContainers) as? [String:Any]

        else{ return nil }

        guard let type = dic["type"] as? Int

        else {

            return nil

        }

            switch type{

            case 6:
            
               //  见后面的 3.1

                if let model = RoomTxtModel.deserialize(from: dic){

                    attachment = HelloMessage.instance(model)

                }

            default:

                ()

            }
            return attachment
        }
        
        
}

收到消息的 NIMSDK 的回调方法

func onRecvMessages(_ messages: [NIMMessage]) {

        if let object = message.messageObject as? NIMCustomObject{

            if let tmpModel = object.attachment as? HelloMessage{
                var item = tmpModel.item

                item.id = message.messageId
                // 见 3.2

                subject.onNext([item])

            }
        }
}
2.1.1 公屏消息, 的另一种实现

用户发消息,调用后端 API.

后端调用网易云信的接口,

然后房间内所有的用户收到消息,同步公屏的内容

2.2, 上麦

本地判断成功, 秒上

用户自己的手机上, 他的头像覆盖麦位,

开声网的角色

同时,调用 API ,上传自己的麦位信息,

等待服务端云信,下方的消息,

是否有异常,需要在该麦位旁边,来一把叉

3, 三方库

3.1, HandyJSON

Swift 项目中,数据 ( 模型 ) 一般使用结构体,

NIMSDK 的附件 attachment, id 类型, 一般继承自 NSObject

需要来一个转换


class HelloMessage: NSObject, NIMCustomAttachment, JSONy{

    required override init() { }
    
  

    class func instance(_ model: RoomTxtModel) -> HelloMessage{

        if let tmp = model.toJSON(), let data = HelloMessage.deserialize(from: tmp){

            return data

        }

        else{

            return RoomTxtModel()

        }

    }

    

    var item: RoomTxtModel{

        if let tmp = toJSON(), let data = RoomTxtModel.deserialize(from: tmp){

            return data

        }

        else{

            return RoomTxtModel()

        }

    }

    

}
3.2 RxDataSources
var subject = PublishSubject<[RoomTxtModel]>()

公屏就是一个 tableView,

RoomTxtModel 对应 cell,

每一个 RoomTxtModel 的 id, 就是云信消息的 id

( 区别开,拿来就用 )

举报

相关推荐

0 条评论