腾讯tts获取文件blob推流解析

方案1,获取推流拼接到数据,播放时将 Blob 转换为 URL,把audioUrl赋值给

 ws.onmessage((res) => {
    // console.log('onmessage res.data',res.data)
    if (typeof res.data == "object") {
    blobs.value.push(res.data);
  	const newBolb = new Blob([...blobs.value], { type: "audio/mp3" });
    // 将 Blob 转换为 URL
   	audioUrl.value = URL.createObjectURL(newBolb);
   }
    // console.log('onmessage audioUrl.value',audioUrl.value)
  });
<audio  ref="audioPlayer" controls>
   <source :src="audioUrl" type="audio/mpeg" autoplay />
   Your browser does not support the audio element.
</audio>

方案2 边获取推流边解析

let mediaSource = new MediaSource();
let sourceBuffer;
let queue = [];
let isUpdating = false;

const audioPlayer = document.getElementById('audioPlayer'); // Assume you have an <audio> element with this id
audioPlayer.src = URL.createObjectURL(mediaSource);

const appendBuffer = (blob) => {
  const reader = new FileReader();
  reader.onload = () => {
    const arrayBuffer = reader.result;
    queue.push(arrayBuffer);
    processQueue();
  };
  reader.readAsArrayBuffer(blob);
};

const processQueue = () => {
  if (queue.length > 0 && !isUpdating && sourceBuffer && !audioPlayer.error) {
    const buffer = queue.shift();
    isUpdating = true;
    sourceBuffer.appendBuffer(buffer);
  }
};

const onSourceOpen = () => {
  if (!sourceBuffer) {
    sourceBuffer = mediaSource.addSourceBuffer('audio/mpeg');
    sourceBuffer.mode = 'sequence'; // Ensure the buffer is appended in sequence
    sourceBuffer.addEventListener('updateend', () => {
      isUpdating = false;
      processQueue(); // Continue processing the queue after each update
    });
  }
};

mediaSource.addEventListener('sourceopen', onSourceOpen);

ws.onmessage = (res) => {
  if (typeof res.data === 'object') {
    appendBuffer(res.data);
  }
};

这段代码旨在通过WebSocket实时接收音频流,并使用MediaSourceSourceBuffer将其解析并播放。以下是代码的详细解析:

1. 变量定义与初始化

let mediaSource = new MediaSource();
let sourceBuffer;
let queue = [];
let isUpdating = false;
  • mediaSource: 创建一个MediaSource对象,用于管理媒体数据源。
  • sourceBuffer: 用于存储音频数据的SourceBuffer对象,稍后会初始化。
  • queue: 队列,用于暂存从WebSocket接收到的音频数据,以防止在SourceBuffer忙碌时丢失数据。
  • isUpdating: 布尔标志,用于指示SourceBuffer是否正在更新。如果正在更新,则不会添加新的数据。

2. 音频播放器初始化

const audioPlayer = document.getElementById('audioPlayer'); 
audioPlayer.src = URL.createObjectURL(mediaSource);
  • 获取页面中的音频播放器元素(假设ID为audioPlayer),并将MediaSource对象与之关联。

3. 数据追加函数 appendBuffer

const appendBuffer = (blob) => {
  const reader = new FileReader();
  reader.onload = () => {
    const arrayBuffer = reader.result;
    queue.push(arrayBuffer);
    processQueue();
  };
  reader.readAsArrayBuffer(blob);
};
  • appendBuffer函数接收一个blob对象,即通过WebSocket接收到的音频数据。
  • 使用FileReaderblob对象转换为ArrayBuffer,然后将其加入queue队列中。
  • processQueue函数在转换完成后被调用,用于处理队列中的数据。

4. 处理队列中的数据 processQueue

const processQueue = () => {
  if (queue.length > 0 && !isUpdating && sourceBuffer && !audioPlayer.error) {
    const buffer = queue.shift();
    isUpdating = true;
    sourceBuffer.appendBuffer(buffer);
  }
};
  • processQueue函数检查queue队列中是否有数据,并确保SourceBuffer没有在更新(即isUpdatingfalse)。
  • 如果满足条件,则从队列中取出第一个数据并将其添加到SourceBuffer中,同时将isUpdating标志设置为true,以防止在更新期间追加新的数据。

5. SourceBuffer的初始化与事件处理

const onSourceOpen = () => {
  if (!sourceBuffer) {
    sourceBuffer = mediaSource.addSourceBuffer('audio/mpeg');
    sourceBuffer.mode = 'sequence';
    sourceBuffer.addEventListener('updateend', () => {
      isUpdating = false;
      processQueue();
    });
  }
};

mediaSource.addEventListener('sourceopen', onSourceOpen);
  • mediaSource打开时,onSourceOpen函数被调用。
  • 如果sourceBuffer还未初始化,则创建一个新的SourceBuffer,并将mode设置为'sequence',以确保数据按顺序追加。
  • sourceBuffer添加updateend事件监听器,当更新完成后,将isUpdating标志重置为false,然后继续处理队列中的下一个数据。

6. WebSocket消息处理

ws.onmessage = (res) => {
  if (typeof res.data === 'object') {
    appendBuffer(res.data);
  }
};
  • 当WebSocket接收到消息时,如果消息的数据类型是object(即二进制数据),则调用appendBuffer函数将其处理并追加到队列中。

总结

该代码通过引入队列和isUpdating标志来有效地管理音频流的实时处理,确保数据能按顺序、无缝地追加到SourceBuffer中,并在更新完成后继续处理未处理的数据,避免了数据丢失或播放中断的情况。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

给钱,谢谢!

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值