javascript - 使用 chrome 进行 OfflineAudioContext FFT 分析

标签 javascript html google-chrome chromium web-audio-api

我正在尝试构建一个波形发生器,以获取音频文件幅度值并在 javascript 中尽快(比实时更快)将它们显示到 Canvas 上。所以我使用 OfflineAudioContext/webkitOfflineAudioContext ,加载文件并开始分析。 波形将填充宽 Canvas 。

我在 processor.onaudioprocess 函数中分析缓冲区。 (我想这就是它的工作方式?)

它在 firefox 中运行良好,但我在 chrome 中遇到了一个问题:它似乎“跳过”了很多分析以尽快完成它的工作并且只返回几个坐标(大约 16)。

这是 jsfiddle: http://jsfiddle.net/bestiole/95EBf/

// create the audio context
if (! window.OfflineAudioContext) {
    if (! window.webkitOfflineAudioContext) {
        $('#output').append('failed : no audiocontext found, change browser');
    }
    window.OfflineAudioContext = window.webkitOfflineAudioContext;
}
//var context = new AudioContext();
var length = 15241583;
var samplerate = 44100;
var fftSamples = 2048;
var waveformWidth = 1920;

var context = new OfflineAudioContext(1,length,samplerate);
var source;
var splitter;
var analyser;
var processor;
var i=0;
var average;
var max;
var coord;

processor = context.createScriptProcessor(fftSamples, 1, 1);
processor.connect(context.destination);

analyser = context.createAnalyser();
analyser.smoothingTimeConstant = 0;
analyser.fftSize = fftSamples;

source = context.createBufferSource();
splitter = context.createChannelSplitter();
source.connect(splitter);
splitter.connect(analyser,0,0);

analyser.connect(processor);

context.oncomplete = function(){
    $('#output').append('<br />complete');
}

var request = new XMLHttpRequest();
request.open('GET', "http://www.mindthepressure.org/bounce.ogg", true);
request.responseType = 'arraybuffer';
request.onload = function(){
    $('#output').append('loaded ! ');
    context.decodeAudioData(request.response, function(buffer) {
        $('#output').append('starting analysis<br />');
        processor.onaudioprocess = function(e){
            var data =  new Uint8Array(analyser.frequencyBinCount);
            analyser.getByteFrequencyData(data);
            average = getAverageVolume(data);
            max = Math.max.apply(Math, data);
            coord = Math.min(average*2,255);
            coord = Math.round((max+coord)/2);
            ctx.fillStyle=gradient;
            ctx.fillRect(i,255-coord,1,255);
            console.log(i+' -> '+coord);
            i++;
        }
        source.buffer = buffer;
        source.start(0);
        context.startRendering();
    }, onError);
}
request.send();

function onError(e) {
    $('#output').append('error, check the console');
    console.log(e);
}

function getAverageVolume(array) {
    var values = 0;
    var average;
    var length = array.length;
    for (var k = 0; k < length; k++) {
        values += array[k];
    }
    average = values / length;
    return average;
}

(这是另一个版本,强制波形适合 1920 像素宽并为感兴趣的人生成波形数据:http://jsfiddle.net/bestiole/E3rSx/)

我真的不明白,chrome 怎么不处理音频文件的每个部分?

感谢您的帮助!

最佳答案

Chrome 在离线模式下的脚本处理器中存在一个错误。

关于javascript - 使用 chrome 进行 OfflineAudioContext FFT 分析,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21011701/

相关文章:

javascript - 是否有调试 jQuery 事件处理程序的工具/技术?

Laravel dd() 函数不再显示在 Google Chrome 网络选项卡中如何修复?

html - Webkit(Safari/Chrome)在 float 元素上呈现百分比不准确的边距

javascript - 我如何分析 JS 中 setTimeout 函数的存在

javascript - Github 如何隐藏垃圾邮件机器人的电子邮件

html - 如何让代码文本覆盖和图像响应?

javascript - 滚动到手机上的特定元素不起作用

带有音频和粒子的 Javascript 开源手机游戏引擎?

javascript - 将 Highcharts 与 Rails 6 结合使用

javascript - 将 PHP 数组传递给字符串变量内的 Javascript(HTML 注入(inject))