OLD | NEW |
| (Empty) |
1 <!doctype html> | |
2 <html> | |
3 <head> | |
4 <script src="../resources/js-test.js"></script> | |
5 <script src="resources/compatibility.js"></script> | |
6 <script src="resources/audit-util.js"></script> | |
7 <script src="resources/audio-testing.js"></script> | |
8 <title>Test Multiple Calls to getFloatFrequencyData</title> | |
9 </head> | |
10 | |
11 <body> | |
12 <script> | |
13 description("Test AnalyserNode getFloatFrequencyData and getByteFrequencyD
ata"); | |
14 window.jsTestIsAsync = true; | |
15 | |
16 var sampleRate = 48000; | |
17 // Render enough data to run the test. | |
18 var renderFrames = 2*1024; | |
19 var renderDuration = renderFrames / sampleRate; | |
20 | |
21 var audit = Audit.createTaskRunner(); | |
22 | |
23 audit.defineTask("test", function (done) { | |
24 | |
25 var context = new OfflineAudioContext(1, renderFrames, sampleRate); | |
26 | |
27 // Use sawtooth oscillator as the source because it has quite a bit of h
armonic content. | |
28 // Otherwise, the type doesn't really matter. | |
29 var osc = context.createOscillator(); | |
30 osc.type = "sawtooth"; | |
31 | |
32 // Create an analyser with 256-point FFT. The FFT size doesn't really m
atter much. | |
33 var analyser = context.createAnalyser(); | |
34 analyser.fftSize = 256; | |
35 | |
36 osc.connect(analyser); | |
37 analyser.connect(context.destination); | |
38 | |
39 var success = true; | |
40 | |
41 // Suspend after getting a full analyser frame. (Not really necessary, b
ut it's nice that | |
42 // the frame doesn't include any initial zeroes. | |
43 var suspendFrame = analyser.fftSize; | |
44 context.suspend(suspendFrame / sampleRate).then(function () { | |
45 // Test successive calls to getFloatFrequencyData in the same renderin
g quantum. | |
46 var f1 = new Float32Array(analyser.frequencyBinCount); | |
47 var f2 = new Float32Array(analyser.frequencyBinCount); | |
48 | |
49 analyser.getFloatFrequencyData(f1); | |
50 analyser.getFloatFrequencyData(f2); | |
51 | |
52 success = Should("Second call to getFloatFrequencyData", f2, { | |
53 precision: 5 | |
54 }).beEqualToArray(f1) && success; | |
55 }).then(context.resume.bind(context)); | |
56 | |
57 suspendFrame += 128; | |
58 context.suspend(suspendFrame / sampleRate).then(function () { | |
59 // Test successive calls to getByteFrequencyData in the same rendering
quantum. | |
60 var f1 = new Uint8Array(analyser.frequencyBinCount); | |
61 var f2 = new Uint8Array(analyser.frequencyBinCount); | |
62 | |
63 analyser.getByteFrequencyData(f1); | |
64 analyser.getByteFrequencyData(f2); | |
65 | |
66 success = Should("Second call to getByteFrequencyData", f2) | |
67 .beEqualToArray(f1) && success; | |
68 }).then(context.resume.bind(context)); | |
69 | |
70 suspendFrame += 128; | |
71 context.suspend(suspendFrame / sampleRate).then(function () { | |
72 // Test calls to getFloatFrequencyData followed by getByteFrequencyDat
a. The float data, | |
73 // when converted to byte values should be identical to the result fro
m | |
74 // getByteFrequencyData. | |
75 var f1 = new Float32Array(analyser.frequencyBinCount); | |
76 var f2 = new Uint8Array(analyser.frequencyBinCount); | |
77 | |
78 analyser.getFloatFrequencyData(f1); | |
79 analyser.getByteFrequencyData(f2); | |
80 | |
81 var byteValuesFromFloat = convertFloatToByte(f1, analyser.minDecibels,
analyser.maxDecibels); | |
82 success = Should("Output of getByteFrequencyData after getFloatFrequen
cyData", | |
83 byteValuesFromFloat) | |
84 .beEqualToArray(f2) && success; | |
85 }).then(context.resume.bind(context)); | |
86 | |
87 suspendFrame += 128; | |
88 context.suspend(suspendFrame / sampleRate).then(function () { | |
89 // Test calls to getByteFrequencyData followed by getFloatFrequencyDat
a. The float data, | |
90 // when converted to byte values should be identical to the result fro
m | |
91 // getByteFrequencyData. | |
92 var f1 = new Uint8Array(analyser.frequencyBinCount); | |
93 var f2 = new Float32Array(analyser.frequencyBinCount); | |
94 | |
95 analyser.getByteFrequencyData(f1); | |
96 analyser.getFloatFrequencyData(f2); | |
97 | |
98 var byteValuesFromFloat = convertFloatToByte(f2, analyser.minDecibels,
analyser.maxDecibels); | |
99 success = Should( | |
100 "Output of getFloatFrequenycData (converted to byte) after getByte
FrequencyData", | |
101 f1) | |
102 .beEqualToArray(byteValuesFromFloat) && success; | |
103 }).then(context.resume.bind(context)); | |
104 | |
105 osc.start(); | |
106 context.startRendering().then(done); | |
107 }); | |
108 | |
109 audit.defineTask("finish", function (done) { | |
110 finishJSTest(); | |
111 done(); | |
112 }); | |
113 | |
114 audit.runTasks(); | |
115 | |
116 // Convert the float frequency data (in dB), |floatFreqData|, to byte valu
es using the dB | |
117 // limits |minDecibels| and |maxDecibels|. The new byte array is returned
. | |
118 function convertFloatToByte(floatFreqData, minDecibels, maxDecibels) { | |
119 var scale = 255 / (maxDecibels - minDecibels); | |
120 | |
121 return floatFreqData.map(function (x) { | |
122 var value = Math.floor(scale * (x - minDecibels)); | |
123 return Math.min(255, Math.max(0, value)); | |
124 }); | |
125 } | |
126 </script> | |
127 </body> | |
128 </html> | |
OLD | NEW |