function applyStereoToStereoPanning(l, r, panningValues, panning) { var outL, outR;
if (panning <= 0) {
outL = l + r * panningValues[0];
outR = r * panningValues[1];
} else {
outL = l * panningValues[0];
outR = r + l * panningValues[1];
}
return [outL,outR];
}
function applyMonoToStereoPanning(c, panning) {
return [c * panning[0], c * panning[1]];
}
// Test the DOM interface var context = new OfflineAudioContext(1, 1, SR); var stereoPanner = new StereoPannerNode(context);
ok(stereoPanner.pan, "The AudioParam member must exist");
is(stereoPanner.pan.value, 0.0, "Correct initial value");
is(stereoPanner.pan.defaultValue, 0.0, "Correct default value");
is(stereoPanner.channelCount, 2, "StereoPannerNode node has 2 input channels by default");
is(stereoPanner.channelCountMode, "clamped-max", "Correct channelCountMode for the StereoPannerNode");
is(stereoPanner.channelInterpretation, "speakers", "Correct channelCountInterpretation for the StereoPannerNode");
expectException(function() {
stereoPanner.channelCount = 3;
}, DOMException.NOT_SUPPORTED_ERR);
expectException(function() {
stereoPanner.channelCountMode = "max";
}, DOMException.NOT_SUPPORTED_ERR);
// A sine to be used to fill the buffers
function sine(t) {
return Math.sin(440 * 2 * Math.PI * t / context.sampleRate);
}
// A couple mono and stereo buffers: the StereoPannerNode equation is different
// if the input is mono or stereo var stereoBuffer = new AudioBuffer({ numberOfChannels: 2,
length: BUF_SIZE,
sampleRate: context.sampleRate }); var monoBuffer = new AudioBuffer({ numberOfChannels: 1,
length: BUF_SIZE,
sampleRate: context.sampleRate });
for (var i = 0; i < BUF_SIZE; ++i) {
monoBuffer.getChannelData(0)[i] =
stereoBuffer.getChannelData(0)[i] =
stereoBuffer.getChannelData(1)[i] = sine(i);
}
// Expected test vectors
function expectedBufferNoop(gain) {
gain = gain || 1.0; var expectedBuffer = new AudioBuffer({ numberOfChannels: 2,
length: BUF_SIZE,
sampleRate: SR });
for (var i = 0; i < BUF_SIZE; i++) {
expectedBuffer.getChannelData(0)[i] = gain * sine(i);
expectedBuffer.getChannelData(1)[i] = gain * sine(i);
}
return expectedBuffer;
}
function expectedBufferForStereo(panning, gain) {
gain = gain || 1.0; var expectedBuffer = new AudioBuffer({ numberOfChannels: 2,
length: BUF_SIZE,
sampleRate: SR }); var gainPanning = gainForPanningStereoToStereo(panning);
for (var i = 0; i < BUF_SIZE; i++) { var values = [ gain * sine(i), gain * sine(i) ]; var processed = applyStereoToStereoPanning(values[0], values[1], gainPanning, PANNING);
expectedBuffer.getChannelData(0)[i] = processed[0];
expectedBuffer.getChannelData(1)[i] = processed[1];
}
return expectedBuffer;
}
function expectedBufferForMono(panning, gain) {
gain = gain || 1.0; var expectedBuffer = new AudioBuffer({ numberOfChannels: 2,
length: BUF_SIZE,
sampleRate: SR }); var gainPanning = gainForPanningMonoToStereo(panning);
gainPanning[0] *= gain;
gainPanning[1] *= gain;
for (var i = 0; i < BUF_SIZE; i++) { var value = sine(i); var processed = applyMonoToStereoPanning(value, gainPanning);
expectedBuffer.getChannelData(0)[i] = processed[0];
expectedBuffer.getChannelData(1)[i] = processed[1];
}
return expectedBuffer;
}
// Actual test cases var tests = [
function monoPanningNoop(ctx, panner) { var monoSource = ctx.createBufferSource();
monoSource.connect(panner);
monoSource.buffer = monoBuffer;
monoSource.start(0);
return expectedBufferForMono(0);
},
function stereoPanningNoop(ctx, panner) { var stereoSource = ctx.createBufferSource();
stereoSource.connect(panner);
stereoSource.buffer = stereoBuffer;
stereoSource.start(0);
return expectedBufferNoop();
},
function monoPanningNoopWithGain(ctx, panner) { var monoSource = ctx.createBufferSource(); var gain = ctx.createGain();
gain.gain.value = GAIN;
monoSource.connect(gain);
gain.connect(panner);
monoSource.buffer = monoBuffer;
monoSource.start(0);
return expectedBufferForMono(0, GAIN);
},
function stereoPanningNoopWithGain(ctx, panner) { var stereoSource = ctx.createBufferSource(); var gain = ctx.createGain();
gain.gain.value = GAIN;
stereoSource.connect(gain);
gain.connect(panner);
stereoSource.buffer = stereoBuffer;
stereoSource.start(0);
return expectedBufferNoop(GAIN);
},
function stereoPanningAutomation(ctx, panner) { var stereoSource = ctx.createBufferSource();
stereoSource.connect(panner);
stereoSource.buffer = stereoBuffer;
panner.pan.setValueAtTime(0.1, 0.0);
stereoSource.start(0);
return expectedBufferForStereo(PANNING);
},
function stereoPanning(ctx, panner) { var stereoSource = ctx.createBufferSource();
stereoSource.buffer = stereoBuffer;
stereoSource.connect(panner);
panner.pan.value = 0.1;
stereoSource.start(0);
return expectedBufferForStereo(PANNING);
},
function monoPanningAutomation(ctx, panner) { var monoSource = ctx.createBufferSource();
monoSource.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.setValueAtTime(PANNING, 0.0);
monoSource.start(0);
return expectedBufferForMono(PANNING);
},
function monoPanning(ctx, panner) { var monoSource = ctx.createBufferSource();
monoSource.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.value = 0.1;
monoSource.start(0);
return expectedBufferForMono(PANNING);
},
function monoPanningWithGain(ctx, panner) { var monoSource = ctx.createBufferSource(); var gain = ctx.createGain();
gain.gain.value = GAIN;
monoSource.connect(gain);
gain.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.value = 0.1;
monoSource.start(0);
return expectedBufferForMono(PANNING, GAIN);
},
function stereoPanningWithGain(ctx, panner) { var stereoSource = ctx.createBufferSource(); var gain = ctx.createGain();
gain.gain.value = GAIN;
stereoSource.connect(gain);
gain.connect(panner);
stereoSource.buffer = stereoBuffer;
panner.pan.value = 0.1;
stereoSource.start(0);
return expectedBufferForStereo(PANNING, GAIN);
},
function monoPanningWithGainAndAutomation(ctx, panner) { var monoSource = ctx.createBufferSource(); var gain = ctx.createGain();
gain.gain.value = GAIN;
monoSource.connect(gain);
gain.connect(panner);
monoSource.buffer = monoBuffer;
panner.pan.setValueAtTime(PANNING, 0);
monoSource.start(0);
return expectedBufferForMono(PANNING, GAIN);
},
function stereoPanningWithGainAndAutomation(ctx, panner) { var stereoSource = ctx.createBufferSource(); var gain = ctx.createGain();
gain.gain.value = GAIN;
stereoSource.connect(gain);
gain.connect(panner);
stereoSource.buffer = stereoBuffer;
panner.pan.setValueAtTime(PANNING, 0);
stereoSource.start(0);
return expectedBufferForStereo(PANNING, GAIN);
},
function bug_1783181(ctx, panner) {
const length = 128;
const buffer = new AudioBuffer({ length, numberOfChannels: 2, sampleRate: ctx.sampleRate });
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.