создание узла audioWorklet с 4 каналами? - PullRequest
0 голосов
/ 12 сентября 2018

Я работаю над проигрывателем модов, который представляет собой аудиофайл с 4 различными дорожками (каналами) с использованием webaudio / audioWorkletNode.

Я правильно понял, используя 2-канальный (стерео) аудио узел:

  • каналы (треки) 0 и 3 микшируются в левый канал
  • каналы (треки) 1 и 2 смешаны в правый канал

Проблема в том, что я хотел бы проанализировать и показать отображение формы сигнала для каждой из дорожек (поэтому должно быть 4 разных анализатора).

У меня была идея создать audioWorkletNode с outputChannelCount, установленным в [4], подключить анализатор к каждому из четырех каналов узла и затем использовать channelMerger для микширования его в 2 стереоканала.

Итак, я использовал следующий код, ожидая, что он создаст узел с 4 каналами:

let node = new AudioWorkletNode (context, 'processor', {outputChannelCount: [4]});

Но параметр outputChannelCount, похоже, игнорируется. Независимо от того, что я указываю, в конце концов он настроен на 2 канала.

Есть ли способ сделать это по-другому, или я должен сам провести анализ, используя свой собственный анализатор?

1 Ответ

0 голосов
/ 12 сентября 2018

Я наконец нашел способ смешать все четыре канала и передать каждый канал в свой собственный анализатор, выполнив следующее:

this.context.audioWorklet.addModule(`js/${soundProcessor}`).then(() => 
{
    this.splitter = this.context.createChannelSplitter(4);
    // Use 4 inputs that will be used to send each track's data to a separate analyser
    // NOTE: what should we do if we support more channels (and different mod formats)?
    this.workletNode = new AudioWorkletNode(this.context, 'mod-processor', {
            outputChannelCount: [1, 1, 1, 1],
            numberOfInputs: 0,
            numberOfOutputs: 4
    });

    this.workletNode.port.onmessage = this.handleMessage.bind(this);
    this.postMessage({
        message: 'init',
        mixingRate: this.mixingRate
    });
    this.workletNode.port.start();

    // create four analysers and connect each worklet's input to one
    this.analysers = new Array();

    for (let i = 0; i < 4; ++i) {
        const analyser = this.context.createAnalyser();
        analyser.fftSize = 256;// Math.pow(2, 11);
        analyser.minDecibels = -90;
        analyser.maxDecibels = -10;
        analyser.smoothingTimeConstant = 0.65;
        this.workletNode.connect(analyser, i, 0);
        this.analysers.push(analyser);
    }

    this.merger = this.context.createChannelMerger(4);

    // merge the channel 0+3 in left channel, 1+2 in right channel
    this.workletNode.connect(this.merger, 0, 0);
    this.workletNode.connect(this.merger, 1, 1);
    this.workletNode.connect(this.merger, 2, 1);
    this.workletNode.connect(this.merger, 3, 0);
     this.merger.connect(this.context.destination);
});

Я в основном создаю новый узел с 4 выходами и использую выходы как канал,Для создания стерео выхода я могу использовать слияние каналов.И вуаля!

Полный исходный код приложения можно найти здесь: https://warpdesign.github.io/modplayer-js/

...