为什么某些.wav文件无法在Firefox中解码 [英] Why certain .wav files cannot be decoded in Firefox

查看:1610
本文介绍了为什么某些.wav文件无法在Firefox中解码的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个网页,由于某些原因解码波形文件。 Chrome和Safari似乎工作正常。 Firefox偶尔无法解码文件,并给出错误:传递给decodeAudioData的缓冲区包含无法成功解码的无效内容。我已经创建了一个 jsfiddle ,说明了这个问题:

  var audioCtx = new(window.AudioContext || window.webkitAudioContext)(); 
var source;
函数getData(){
source = audioCtx.createBufferSource();
request = new XMLHttpRequest();
request.open('GET','https://mpclubtest.s3.amazonaws.com/Malice_Bass.wav',true);
request.responseType ='arraybuffer';
request.onload = function(){
var audioData = request.response;
audioCtx.decodeAudioData(audioData,function(buffer){
source.buffer = buffer;
source.connect(audioCtx.destination);
},
function e){音频数据解码出错+ e.err});
}
request.send();
}
getData();
source.start(0);

任何人都可以告诉我问题是什么,是否有办法避开?很多谢谢。
$ b $ p 编辑
由于Michael Chaney能够实现的巨大贡献,一些JavaScript处理波,以便它可以在Firefox中播放。代码修剪16字节的fmt块的任何部分。代码位于: jfiddle

  var audioCtx = new(window.AudioContext || window.webkitAudioContext)(); 
var source;
函数getData(){
source = audioCtx.createBufferSource();
request = new XMLHttpRequest();
request.open('GET','https://mpclubtest.s3.amazonaws.com/Malice_Bass.wav',true);
request.responseType ='arraybuffer';
request.onload = function(){
var audioData = request.response;
var dv = new DataView(audioData);
var junk = 0;
var position = 12;
do {
var header = String.fromCharCode.apply(null,Uint8Array(audioData,position,4));
var length = dv.getUint32(position + 4,true);
if(header.trim()==='fmt'){
junk = junk + length - 16;
}
position = position + 8 + length;
} while(position< audioData.byteLength);
var productArray = new Uint8Array(audioData.byteLength - junk);
productArray.set(new Uint8Array(audioData,0,12));
var newPosition = 12;
position = 12;
var fmt_length_spot;
do {
var header = String.fromCharCode.apply(null,Uint8Array(audioData,position,4));
var length = dv.getUint32(position + 4,true);
if(header.trim()==='fmt'){
productArray.set(new Uint8Array(audioData,position,24),newPosition);
fmt_length_spot = newPosition + 4;
newPosition = newPosition + 24;

else {
productArray.set(new Uint8Array(audioData,position,length + 8),newPosition);
newPosition = newPosition + 8 + length;
}
position = position + 8 + length;
} while(position< audioData.byteLength);
audioData = productArray.buffer;
dv = new DataView(audioData);
dv.setUint32(4,audioData.byteLength - 8,true);
dv.setUint32(fmt_length_spot,16,true);
audioCtx.decodeAudioData(audioData,function(buffer){
source.buffer = buffer;
source.connect(audioCtx.destination);
},
function e){音频数据解码出错+ e.err});
}
request.send();
}
getData();
source.start(0);

谢谢Michael。

解决方案

它可能是文件开头的JUNK块。你可以通过sox来运行它,以清除不必要的块:

  sox Malice_Bass.wav Malice_Bass_simple.wav 

以下是我的个人解析器对文件所说的内容:

<$ p $
原始码:Pro Tools
原始码(R) - 波形(36467192字节)
JUNK(92)
bext(602)
Ref:jicj!dad1ofaaaGk
起源日期:2014-09-09
起始时间:20:46:43
时间参考最低价:0
时间参考最高价:
BWF版本:0
SMPTE UMID字节数: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 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 0 0 0 0
编码历史:
fmt(40)
格式标签:1
频道:2
每秒采样数:48000
每秒平均字节数:192000
块对齐:4
每个样本的位数:16
minf(16)
elm1(214)
data(36466048)
regn(92)
umid(24)

当我使用sox进行清理时,Firefox停止抱怨,但仍然没有不玩。我确认它加载的文件,但似乎并没有玩。


I have a web page which decodes wave files for certain reasons. Chrome and Safari seem to work fine. Firefox occasionally is unable to decode the file and gives the error: "The buffer passed to decodeAudioData contains invalid content which cannot be decoded successfully." I have created a jsfiddle which illustrates the issue:

var audioCtx = new (window.AudioContext || window.webkitAudioContext)();
var source;
function getData() {
  source = audioCtx.createBufferSource();
  request = new XMLHttpRequest();
  request.open('GET', 'https://mpclubtest.s3.amazonaws.com/Malice_Bass.wav', true);
  request.responseType = 'arraybuffer';
  request.onload = function() {
    var audioData = request.response;
    audioCtx.decodeAudioData(audioData, function(buffer) {
        source.buffer = buffer;
        source.connect(audioCtx.destination);
      },
      function(e){"Error with decoding audio data" + e.err});
  }
  request.send();
}
getData();
source.start(0);

Can anyone tell me what the issue is and if there is any way to circumvent? Many Thanks.

EDIT Thanks to the substantial contributions of Michael Chaney I was able to implement some javascript which processes the wave so that it can be played in Firefox. The code trims any part of the "fmt" chunk over 16 bytes. Code located at: jfiddle

var audioCtx = new (window.AudioContext || window.webkitAudioContext)();
var source;
function getData() {
  source = audioCtx.createBufferSource();
  request = new XMLHttpRequest();
  request.open('GET', 'https://mpclubtest.s3.amazonaws.com/Malice_Bass.wav', true);
  request.responseType = 'arraybuffer';
  request.onload = function() {
      var audioData = request.response;
      var dv = new DataView(audioData);
      var junk = 0;
      var position = 12;
      do {
          var header = String.fromCharCode.apply(null, Uint8Array(audioData, position, 4));
          var length = dv.getUint32(position + 4, true);
          if (header.trim() === 'fmt') {
              junk = junk + length - 16;
          }
          position = position + 8 + length;
      }while(position < audioData.byteLength);
      var productArray = new Uint8Array(audioData.byteLength - junk);
      productArray.set(new Uint8Array(audioData, 0, 12));
      var newPosition = 12;
      position = 12;
      var fmt_length_spot;
      do {
          var header = String.fromCharCode.apply(null, Uint8Array(audioData, position, 4));
          var length = dv.getUint32(position + 4, true);
          if (header.trim() === 'fmt') {
              productArray.set(new Uint8Array(audioData, position, 24), newPosition);
              fmt_length_spot = newPosition + 4;
              newPosition = newPosition + 24;
          }
          else {
              productArray.set(new Uint8Array(audioData, position, length + 8), newPosition);
              newPosition = newPosition + 8 + length;
          }
          position = position + 8 + length;
      }while(position < audioData.byteLength);
      audioData = productArray.buffer;
      dv = new DataView(audioData);
      dv.setUint32(4, audioData.byteLength - 8, true);
      dv.setUint32(fmt_length_spot, 16, true);
      audioCtx.decodeAudioData(audioData, function(buffer) {
          source.buffer = buffer;
          source.connect(audioCtx.destination);
        },
        function(e){"Error with decoding audio data" + e.err});
    }
    request.send();
}
getData();
source.start(0);

Thanks Michael.

解决方案

It might be the JUNK chunk at the start of the file. You can run it through sox to clean out extraneous chunks like this:

sox Malice_Bass.wav Malice_Bass_simple.wav

Here's what my personal parser says about the file:

RIFF - WAVE (36467192 bytes)
   JUNK (92)
   bext (602)
         Description:       
         Originator:        Pro Tools
         Originator Ref:    jicj!dad1ofaaaGk
         Origination Date:  2014-09-09
         Origination Time:  20:46:43
         Time Ref Low:      0
         Time Ref High:     0
         BWF Version:       0
         SMPTE UMID Bytes:  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 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 0 0 0 0
         Coding History:    
   fmt (40)
         Format Tag:        1
         Channels:          2
         Samples per sec:   48000
         Avg bytes per sec: 192000
         Block align:       4
         Bits per sample:   16
   minf (16)
   elm1 (214)
   data (36466048)
   regn (92)
   umid (24)

When I clean it up using sox Firefox quits complaining about it but still doesn't play it. I confirmed that it loads the file but doesn't seem to play it.

这篇关于为什么某些.wav文件无法在Firefox中解码的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆