前端实现 web获取麦克风权限 录制音频 (需求:ai对话问答)

下载插件

javascript 复制代码
npm i recordrtc

文档:https://recordrtc.org/RecordRTC.html

相关方法整理

获取设备
javascript 复制代码
getvice() {
      if (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) {
        var Mic = [];
        // 弹框获取麦克风
        navigator.mediaDevices.getUserMedia({ audio: true }).then((stream) => {
          navigator.mediaDevices.enumerateDevices().then((devices) => {
            devices.forEach((device) => {
              if (device.kind === "audioinput") {
                // 麦克风
                if (
                  device.deviceId != "default" &&
                  device.deviceId != "communications"
                ) {
                  this.Mic.push(device);//获取到的麦克风设备
                }
              }
            });
          });
          // 只是为了获取麦克风权限,获取以后立马关闭
          stream.getTracks().forEach((track) => track.stop());
          console.log(this.Mic, 22);
        });
      }
    },

开始录音

javascript 复制代码
 // 开始录音
    startRecord() {
      var that = this;
      // this.voiceStatus = true;
      // mediaDevices可提供对相机和麦克风等媒体输入设备的连接访问
      window.navigator.mediaDevices
        .getUserMedia({ audio: { deviceId: this.Mic[0].deviceId } })//设置{ audio: true}会选择电脑默认设置的麦克风设备
        .then((stream) => {
          this.stream = stream;
          this.getVoice();

          this.recorder = RecordRTC(stream, {
            type: "audio",//类型
            mimeType: "audio/wav",//音频格式
            recorderType: RecordRTC.StereoAudioRecorder,
            desiredSampRate: 16000,//频率
            numberOfAudioChannels: 2, // 单声道
            timeSlice: 1000,
            // bufferSize: 4096, // 缓存大小
            // ondataavailable: this.sendData,//有音频时的回调,一般及时传输websocket有用
            checkForInactiveTracks: true,
          });
          this.recorder.startRecording();
        })
        .catch(function (err) {
          console.log(err);
          console.log("当前浏览器不支持开启麦克风!");
          // that.voiceStatus = false;
        });
    },

停止录音

javascript 复制代码
  // 结束录音
    stopRecord() {
      // this.voiceStatus = false;
      if (this.recorder != null) {
        let recorder = this.recorder;
        // var internalRecorder = recorder.getInternalRecorder();
        // console.log("停止录音回调internalRecorder", internalRecorder);
        //停止录音
        recorder.stopRecording(() => {
          //   var BB = new Blob([recorder.getBlob()], {
          //   type: "audio/wav; codecs=opus",
          // });
          let blob = recorder.getBlob();//获取blob
          var audioURL = window.URL.createObjectURL(blob);

          // let a = document.createElement("a");
          // a.href = audioURL;
          // a.download = "测试";
          // a.click();
          // 将录音文件 以文件对象形式传给后端
          var form = new FormData();
          form.append("upfile", blob);
          console.log("form", form, blob);

          // 释放这个临时的对象url
          window.URL.revokeObjectURL(audioURL);
        });
        let stream = this.stream;
        clearInterval(this.timer1);
        RMSList = [//记录音频大小,用于音频波动样式绘制用
          0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
          0, 0, 0, 0, 0, 0, 0,
        ];
        //结束媒体
        stream.getAudioTracks().forEach((track) => track.stop());
      }
    },

获取音量大小

javascript 复制代码
 // 获取音量值大小
    getVoice() {
      const audioContext = new (window.AudioContext ||
        window.webkitAudioContext)();
      // 将麦克风的声音输入这个对象
      const mediaStreamSource = audioContext.createMediaStreamSource(
        this.stream
      );
      // 创建分析节点
      const analyserNode = audioContext.createAnalyser();
      // 连接节点
      mediaStreamSource.connect(analyserNode);
      // 可以实时听到麦克风采集的声音
      // analyserNode.connect(audioContext.destination)

      // 获取音量数据
      const dataArray = new Uint8Array(analyserNode.frequencyBinCount);

      function getVolume() {
        analyserNode.getByteFrequencyData(dataArray);
        let sum = 0;
        for (let i = 0; i < dataArray.length; i++) {
          sum += dataArray[i];
        }
        // 计算平均音量
        const averageVolume = sum / dataArray.length;
        return averageVolume;
      }

      // 每隔一段时间获取一次音量
      this.timer1 = setInterval(() => {
        const volume = getVolume();
        console.log("音量:", Math.round(volume));
        RMSList.unshift(Math.round(volume));
        RMSList.pop();
        // 在这里可以根据需要进行相应的处理
      }, 100);
    },

以上用于记录,后续补充文章,整理AI对话搭建成果

相关推荐
huuyii11 小时前
Nest 基础知识
前端
沢田纲吉11 小时前
《LLVM IR 学习手记(三):赋值表达式与错误处理的实现与解析》
前端·编程语言·llvm
sophie旭11 小时前
一道面试题,开始性能优化之旅(3)-- DNS查询+TCP(一)
前端·面试·性能优化
DogDaoDao11 小时前
DCT与DST变换原理及其在音视频编码中的应用解析
音视频·实时音视频·视频编解码·dct变换·变换编码·dst变换
PythonFun11 小时前
从零开始,用WPS和DeepSeek打造数字人科普视频
音视频·wps
IT_陈寒12 小时前
JavaScript性能优化:这7个V8引擎技巧让我的应用速度提升了50%
前端·人工智能·后端
学渣y12 小时前
nvm下载node版本,npm -v查看版本报错
前端·npm·node.js
excel12 小时前
首屏加载优化总结
前端
敲代码的嘎仔12 小时前
JavaWeb零基础学习Day1——HTML&CSS
java·开发语言·前端·css·学习·html·学习方法
Tachyon.xue14 小时前
Vue 3 项目集成 Element Plus + Tailwind CSS 详细教程
前端·css·vue.js