Intro
This time, I play my own voice with Web Audio API.
Environments
- Node.js ver.16.7.0
- TypeScript ver.4.3.5
- Webpack ver.5.42.0
- ts-loader ver.9.2.3",
- webpack-cli ver.4.7.2
Basic usage
To control the audio data, first create an "AudioContext".
Each operation such as audio setting and volume up / down is expressed as "AudioNode".
From input to output, I connect all the "AudioNode".
Use mic
This time, I use microphone.
To do this, I get devices with "getUserMedia".
main.page.ts
export async function init(): Promise<void> {
// Get audio(microphone)
const medias = await navigator.mediaDevices.getUserMedia({
video: false,
audio: true,
});
const audioContext = new AudioContext();
const audioSourceNode = audioContext.createMediaStreamSource(medias);
// By default, use speaker of the computer as output
audioSourceNode
.connect(audioContext.destination);
}
Add effects
I can connect effects.
main.page.ts
export async function init(): Promise<void> {
...
audioContext = new AudioContext();
const audioSourceNode = audioContext.createMediaStreamSource(medias);
// volume up
const gain = audioContext.createGain();
gain.gain.value = 2.0;
// delay the sound
const delay = new DelayNode(audioContext);
delay.delayTime.value = 1;
// output only right channel
const panner = new StereoPannerNode(audioContext, { pan: 1 });
audioSourceNode
.connect(gain)
.connect(delay)
.connect(panner)
.connect(audioContext.destination);
}
gain
delay
panner
Update effect values
After connecting, I can update the effect's values.
Next time, I will try more effects.
Split and merge channels
Split channels
I can split channels to left and right with "createChannelSplitter".
main.page.ts
export async function init(): Promise<void> {
...
// volume up
const gain = audioContext.createGain();
gain.gain.value = 2.0;
// delay the sound
const delay = new DelayNode(audioContext);
delay.delayTime.value = 1;
// output only right channel
const panner = new StereoPannerNode(audioContext, { pan: 1});
const splitter = audioContext.createChannelSplitter(2);
audioSourceNode.connect(splitter);
splitter.connect(gain, 1);
splitter.connect(delay, 1);
// No any effects...
splitter.connect(panner, 1);
splitter.connect(audioContext.destination);
}
Because the audio source becomes mono by "ChannelSplitterNode", I can't pan again.
So "StereoPannerNode" in the sample code doesn't work.
Merge sources
After splitting, I can merge them with "ChannelMergerNode".
main.page.ts
export async function init(): Promise<void> {
...
// volume up
const gain = audioContext.createGain();
gain.gain.value = 2.0;
// delay the sound
const delay = new DelayNode(audioContext);
delay.delayTime.value = 0.1;
const splitter = audioContext.createChannelSplitter(2);
audioSourceNode.connect(splitter);
splitter.connect(gain, 1);
splitter.connect(delay, 1);
const merger = audioContext.createChannelMerger(2);
gain.connect(merger, 0, 1);
delay.connect(merger, 0, 1);
splitter.connect(merger, 1, 0);
merger.connect(audioContext.destination);
}
Top comments (0)