| // META: global=window,dedicatedworker |
| |
| test(() => { |
| for (const [formatFrom, formatTo] of [ |
| ['f32', 'f32'], |
| ['f32', 'f32-planar'], |
| ['f32-planar', 'f32-planar'], |
| ['f32-planar', 'f32'], |
| ]) { |
| const data = new AudioData({ |
| format: formatFrom, |
| sampleRate: 48000, |
| numberOfChannels: 1, |
| numberOfFrames: 5, |
| data: new Float32Array([1, 2, 3, 4, 5]), |
| timestamp: 0, |
| }); |
| const output = new Float32Array(5); |
| data.copyTo(output.subarray(1, 4), { |
| planeIndex: 0, |
| frameOffset: 1, |
| frameCount: 3, |
| format: formatTo, |
| }); |
| data.close(); |
| assert_array_equals(output, [0, 2, 3, 4, 0], `only 3 middle elements are copied in ${formatFrom}->${formatTo} copy`); |
| } |
| }, 'Test that AudioData.copyTo copies frameCount amount of mono frames from frameOffset'); |
| |
| test(() => { |
| const data = new AudioData({ |
| format: 'f32-planar', |
| sampleRate: 48000, |
| numberOfChannels: 2, |
| numberOfFrames: 5, |
| data: new Float32Array([ |
| 1, 2, 3, 4, 5, // left channel |
| 6, 7, 8, 9, 10, // right channel |
| ]), |
| timestamp: 0, |
| }); |
| const output = new Float32Array(10); |
| data.copyTo(output.subarray(1, 4), { |
| planeIndex: 0, |
| frameOffset: 1, |
| frameCount: 3, |
| }); |
| data.copyTo(output.subarray(data.numberOfFrames + 1, data.numberOfFrames + 4), { |
| planeIndex: 1, |
| frameOffset: 1, |
| frameCount: 3, |
| }); |
| data.close(); |
| assert_array_equals(output, [ |
| 0, 2, 3, 4, 0, // left channel |
| 0, 7, 8, 9, 0, // right channel |
| ], 'only 3 middle elements are copied in both channels'); |
| }, 'Test that AudioData.copyTo copies frameCount amount of stereo frames from frameOffset'); |
| |
| test(() => { |
| const data = new AudioData({ |
| format: 'f32', |
| sampleRate: 48000, |
| numberOfChannels: 2, |
| numberOfFrames: 5, |
| data: new Float32Array([ |
| 1, 6, |
| 2, 7, |
| 3, 8, |
| 4, 9, |
| 5, 10, |
| ]), |
| timestamp: 0, |
| }); |
| const output = new Float32Array(data.numberOfFrames * data.numberOfChannels); |
| data.copyTo(output.subarray(2, 8), { |
| planeIndex: 0, |
| frameOffset: 1, |
| frameCount: 3, |
| format: 'f32', |
| }); |
| data.close(); |
| assert_array_equals(output, [ |
| 0, 0, |
| 2, 7, |
| 3, 8, |
| 4, 9, |
| 0, 0, |
| ], 'only 3 middle elements are copied'); |
| }, 'Test that AudioData.copyTo copies frameCount amount of interleaved stereo frames from frameOffset'); |
| |
| // Per the "Compute Copy Element Count" algorithm step 7 |
| // (https://www.w3.org/TR/webcodecs/#compute-copy-element-count): |
| // "If options.frameOffset is greater than or equal to frameCount, throw a RangeError." |
| test(() => { |
| const data = new AudioData({ |
| format: 'f32', |
| sampleRate: 48000, |
| numberOfChannels: 1, |
| numberOfFrames: 5, |
| data: new Float32Array([1, 2, 3, 4, 5]), |
| timestamp: 0, |
| }); |
| const output = new Float32Array(5); |
| assert_throws_js(RangeError, () => { |
| data.copyTo(output, { planeIndex: 0, frameOffset: 5 }); |
| }, 'frameOffset == numberOfFrames must throw RangeError'); |
| assert_throws_js(RangeError, () => { |
| data.copyTo(output, { planeIndex: 0, frameOffset: 6 }); |
| }, 'frameOffset > numberOfFrames must throw RangeError'); |
| data.close(); |
| }, 'AudioData.copyTo throws RangeError when frameOffset >= frameCount'); |