使用websocket实现发送语音信息

1,406 阅读1分钟

| 效果

2chart.gif

| 实现思路

1.利用浏览器的navigator.mediaDevices.getUserMedia进行录音
2.将录音数据传输给websocket广播给其他人
3.渲染录音

navigator.mediaDevices.getUserMedia返回的是一个promise对象

| Talk is cheap. Show me the code

客户端
利用浏览器的navigator.mediaDevices.getUserMedia进行录音
Touch开始时

    if (!this.audioMediaPromise) {
      const constraints = { audio: true, video: false };
      this.audioMediaPromise =
        navigator?.mediaDevices?.getUserMedia(constraints);
    }
    
    this.audioMediaPromise.then(stream => {
      this.recorder = new MediaRecorder(stream);
      this.recorder.start(); // 开始录音

      const self = this;
      this.recorder.ondataavailable = function (event) {
        console.log(event.data, '声音数据'); // Blob
        if (event.data.size === 0) return;

        // 发送websocket请求
        const params: any = {
          msg: '语音文件',
          sendId: getUserId(),
          date: dayjs().format('YYYY-MM-DD HH:mm:ss'),
          type: chatSendTypeEnum.World,
          username: '用户' + getUserId(),
          recordData: event.data, // 录音文件
          duration: String(self.recorderTime)
        };

        SocketTest.socket.emit('sendMessage', params);
        self.recorderTime = 0;
      };
    });

    this.audioMediaPromise.catch(function (error) {
      console.log(error);
    });

touch结束后

  /**
   * 语音录制长按松开
   * @returns
   */
  onRecorderTouchEnd() {
    console.log('录音结束');
    clearInterval(this.recorderTimer);
    if (!this.recorder) {
      return;
    }

    this.recorder.stop();
  }

服务端
将语音数据广播给客户端

socket.on('sendMessage', data => {
    // 广播给所有用户
    if (data.type === chatSendTypeEnum.World) {
      io.emit('receiveMessage', data);
    }
  });

客户端
获取到声音数据,通过audio标签播放

    SocketTest.socket.on('receiveMessage', data => {
      if (data.type === chatSendTypeEnum.World) {
        console.log('世界频道信息接收', data);
        const blob = new Blob([data.recordData]);
        const audioUrl = URL.createObjectURL(blob);
        
        if (!this.audioElem) {
          this.audioElem = document.createElement('audio');
        } else {
          this.audioElem.pause();
        }
         
        this.audioElem.src = audioUrl;
        this.audioElem.play();
      }
    });

| 参考资料

# MediaDevices.getUserMedia() - Web API 接口参考| MDN
# Socket.IO