test_sequentialBufferSourceWithResampling.html (2435B)
1 <!DOCTYPE html> 2 <title>Test seamless playback of a series of resampled buffers</title> 3 <script src="/resources/testharness.js"></script> 4 <script src="/resources/testharnessreport.js"></script> 5 <script> 6 // Permitting some accumulation of rounding to int16_t. 7 // 64/2^15 would be only just small enough to detect off-by-one-subsample 8 // scheduling errors with the frequencies here. 9 const EPSILON = 4.0 / Math.pow(2, 15); 10 // Offsets test for rounding to nearest rather than up or down. 11 const OFFSETS = [EPSILON, 1.0 - EPSILON]; 12 // The ratio of resampling is 147:160, so 256 start points is enough to cover 13 // every fractional offset. 14 const LENGTH = 256; 15 16 function do_test(context_rate, buffer_rate, start_offset) { 17 18 var context = 19 new OfflineAudioContext(2, LENGTH, context_rate); 20 21 var merger = context.createChannelMerger(context.destination.channelCount); 22 merger.connect(context.destination); 23 24 // Create an audio signal that will be repeated 25 var repeating_signal = context.createBuffer(1, 1, buffer_rate); 26 repeating_signal.getChannelData(0)[0] = 0.5; 27 28 // Schedule a series of nodes to repeat the signal. 29 for (var i = 0; i < LENGTH; ++i) { 30 var source = context.createBufferSource(); 31 source.buffer = repeating_signal; 32 source.connect(merger, 0, 0); 33 source.start((i + start_offset) / buffer_rate); 34 } 35 36 // A single long signal should produce the same result. 37 var long_signal = context.createBuffer(1, LENGTH, buffer_rate); 38 var c = long_signal.getChannelData(0); 39 for (var i = 0; i < c.length; ++i) { 40 c[i] = 0.5; 41 } 42 43 var source = context.createBufferSource(); 44 source.buffer = long_signal; 45 source.connect(merger, 0, 1); 46 source.start(start_offset / buffer_rate); 47 48 return context.startRendering(). 49 then((buffer) => { 50 let series_output = buffer.getChannelData(0); 51 let expected = buffer.getChannelData(1); 52 53 for (var i = 0; i < buffer.length; ++i) { 54 assert_approx_equals(series_output[i], expected[i], EPSILON, 55 "series output at " + i); 56 } 57 }); 58 } 59 60 function start_tests(context_rate, buffer_rate) { 61 OFFSETS.forEach((start_offset) => { 62 promise_test(() => do_test(context_rate, buffer_rate, start_offset), 63 "" + context_rate + " context, " 64 + buffer_rate + " buffer, " 65 + start_offset + " start"); 66 }); 67 } 68 69 start_tests(48000, 44100); 70 start_tests(44100, 48000); 71 72 </script>