Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(512)

Side by Side Diff: third_party/WebKit/LayoutTests/webaudio/resources/mixing-rules.js

Issue 1773973002: Complete the implementation of up/down-mixing rules for AudioNode (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Initial Patch Created 4 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Utilities for mixing rule testing.
2 // http://webaudio.github.io/web-audio-api/#channel-up-mixing-and-down-mixing
3
4
5 /**
6 * Create an n-channel buffer, with all sample data zero except for a shifted
7 * impulse. The impulse position depends on the channel index. For example, for
8 * a 4-channel buffer:
9 * channel 0: 1 0 0 0 0 0 0 0
10 * channel 1: 0 1 0 0 0 0 0 0
11 * channel 2: 0 0 1 0 0 0 0 0
12 * channel 3: 0 0 0 1 0 0 0 0
13 * @param {Number} numberOfChannels Number of channels of test buffer.
Raymond Toy 2016/03/08 18:04:06 If you're going to document the code this way, don
hongchan 2016/03/08 23:53:34 Done.
14 * @return {AudioBuffer}
15 */
16 function createShiftedImpulseBuffer(context, numberOfChannels, frameLength) {
17 var shiftedImpulseBuffer = context.createBuffer(numberOfChannels, frameLengt h, context.sampleRate);
18 for (var channel = 0; channel < numberOfChannels; ++channel) {
19 var data = shiftedImpulseBuffer.getChannelData(channel);
20 data[channel] = 1;
21 }
22
23 return shiftedImpulseBuffer;
24 }
25
26 /**
27 * Stringify AudioBuffer content with options.
Raymond Toy 2016/03/08 18:04:07 Not obvious how you want to stringify the AudioBuf
hongchan 2016/03/08 23:53:35 Done.
28 * @param {AudioBuffer} audioBuffer AudioBuffer object to stringify.
Raymond Toy 2016/03/08 18:04:07 The other parameters/outputs have the description
hongchan 2016/03/08 23:53:34 Done.
29 * @param {Number} frameLength Length to print.
30 * @param {Number} frameOffset Offset frames to print.
Raymond Toy 2016/03/08 18:04:07 This description of frameOffset doesn't really say
hongchan 2016/03/08 23:53:34 Done.
31 * @return {String} Assembled string for printing.
32 */
33 function stringifyBuffer(audioBuffer, frameLength, frameOffset) {
34 frameOffset = (frameOffset || 0);
35
36 var stringifiedBuffer = '';
37 for (var channel = 0; channel < audioBuffer.numberOfChannels; ++channel) {
38 var channelData = audioBuffer.getChannelData(channel);
39 for (var i = 0; i < frameLength; ++i)
40 stringifiedBuffer += channelData[i + frameOffset] + ' ';
41 stringifiedBuffer += '\n';
42 }
43
44 return stringifiedBuffer;
45 }
46
47 /**
48 * Computer number of channels from the connection.
Raymond Toy 2016/03/08 18:04:06 Typo: "Computer" -> "Compute"
hongchan 2016/03/08 23:53:35 Done.
49 * @param {String} connections A string specifies the connection. The
50 * string "128" means 3 connections, having
Raymond Toy 2016/03/08 18:04:06 Description doesn't line up with the rest of the d
hongchan 2016/03/08 23:53:34 Done.
51 * 1, 2, and 8 channels respectively.
52 * @param {Number} channelCount Channel count.
53 * @param {String} channelCountMode Channel count mode.
54 * @return {Number} A computed number of channels.
Raymond Toy 2016/03/08 18:04:06 A link to the spec would be nice. I can never reme
hongchan 2016/03/08 23:53:35 URL is at the top of this file, and I don't think
Raymond Toy 2016/03/08 23:56:54 That link is for the mixing rules. This function
hongchan 2016/03/09 19:34:24 It does not have a separate section, but a definit
55 */
56 function computeNumberOfChannels(connections, channelCount, channelCountMode) {
57 if (channelCountMode == "explicit")
58 return channelCount;
59
60 // Must have at least one channel.
61 var computedNumberOfChannels = 1;
62
63 // Compute "computedNumberOfChannels" based on all the connections.
64 for (var i = 0; i < connections.length; ++i) {
65 var connectionNumberOfChannels = parseInt(connections[i]);
66 computedNumberOfChannels = Math.max(computedNumberOfChannels, connectionNumb erOfChannels);
67 }
68
69 if (channelCountMode == "clamped-max")
70 computedNumberOfChannels = Math.min(computedNumberOfChannels, channelCount);
71
72 return computedNumberOfChannels;
73 }
74
75 /**
76 * Apply up/down-mixing rules based on 'speaker' interpretation.
77 * @param {AudioBuffer} source Source audio buffer.
78 * @param {AudioBuffer} destination Destination audio buffer.
79 */
80 function speakersSum(source, destination) {
81 if (source.length != destination.length)
82 throw "[mixing-rules.js] speakerSum(): buffer lengths mismatch";
Raymond Toy 2016/03/08 18:04:06 Since you know the lengths, print them out in the
hongchan 2016/03/08 23:53:35 Done.
83
84 if (source.numberOfChannels === destination.numberOfChannels) {
85 for (var channel = 0; channel < destination.numberOfChannels; ++channel) {
86 var sourceChannel = source.getChannelData(channel);
87 var destinationChannel = destination.getChannelData(channel);
88 for (var i = 0; i < destinationChannel.length; i++)
89 destinationChannel[i] += sourceChannel[i];
90 }
91
92 return;
93 }
94
95 if (source.numberOfChannels < destination.numberOfChannels)
Raymond Toy 2016/03/08 18:04:07 I find this style confusing. I think it's clearer
hongchan 2016/03/08 23:53:34 Done.
96 processUpMix(source, destination);
97 else
98 processDownMix(source, destination);
99 }
100
101 /**
102 * Discrete channel interpretation mixing.
103 * @param {AudioBuffer} source Source audio buffer.
104 * @param {AudioBuffer} destination Destination audio buffer.
Raymond Toy 2016/03/08 18:04:07 Since nothing is returned, I suggest saying that t
hongchan 2016/03/08 23:53:34 Done.
105 */
106 function discreteSum(source, destination) {
107 if (source.length != destination.length)
108 throw "[mixing-rules.js] discreteSum(): buffer lengths mismatch";
Raymond Toy 2016/03/08 18:04:06 Give lengths in message.
hongchan 2016/03/08 23:53:35 Done.
109
110 var numberOfChannels = source.numberOfChannels < destination.numberOfChannels
111 ? source.numberOfChannels
112 : destination.numberOfChannels;
Raymond Toy 2016/03/08 18:04:07 numberOfChannels = Math.min(source.numberOfChannel
hongchan 2016/03/08 23:53:34 Done. I was following the original test code - but
113
114 for (var channel = 0; channel < numberOfChannels; ++channel) {
115 var sourceChannel = source.getChannelData(channel);
116 var destinationChannel = destination.getChannelData(channel);
117 for (var i = 0; i < destinationChannel.length; i++)
118 destinationChannel[i] += sourceChannel[i];
119 }
120 }
121
122 /**
123 * Process up-mix.
124 * @param {AudioBuffer} source Source audio buffer.
125 * @param {AudioBuffer} destination Destination audio buffer.
Raymond Toy 2016/03/08 18:04:07 Say that the destination is modified.
hongchan 2016/03/08 23:53:35 Done.
126 */
127 function processUpMix(source, destination) {
128 var numberOfSourceChannels = source.numberOfChannels;
129 var numberOfDestinationChannels = destination.numberOfChannels;
130 var i, length = destination.length;
131
132 // Up-mixing: 1 -> 2, 1 -> 4
133 // output.L = input
134 // output.R = input
135 // output.SL = 0 (in the case of 1 -> 4)
136 // output.SR = 0 (in the case of 1 -> 4)
Raymond Toy 2016/03/08 18:04:06 Make comment notation match code notation more clo
hongchan 2016/03/08 23:53:35 Done.
137 if ((numberOfSourceChannels === 1 && numberOfDestinationChannels === 2) ||
138 (numberOfSourceChannels === 1 && numberOfDestinationChannels === 4)) {
139 var sourceChannel = source.getChannelData(0);
140 var destinationChannel0 = destination.getChannelData(0);
141 var destinationChannel1 = destination.getChannelData(1);
142 for (i = 0; i < length; i++) {
143 destinationChannel0[i] += sourceChannel[i];
Raymond Toy 2016/03/08 18:04:06 This doesn't match the comment. You're summing the
hongchan 2016/03/08 23:53:34 Done.
144 destinationChannel1[i] += sourceChannel[i];
145 }
146
147 return;
148 }
149
150 // Up-mixing: 1 -> 5.1
151 // output.L = 0
152 // output.R = 0
153 // output.C = input
154 // output.LFE = 0
155 // output.SL = 0
156 // output.SR = 0
157 if (numberOfSourceChannels == 1 && numberOfDestinationChannels == 6) {
158 var sourceChannel = source.getChannelData(0);
159 var destinationChannel2 = destination.getChannelData(2);
160 for (i = 0; i < length; i++)
161 destinationChannel2[i] += sourceChannel[i];
Raymond Toy 2016/03/08 18:04:06 Again, this doesn't match the comment. Update com
hongchan 2016/03/08 23:53:34 Done.
162
163 return;
164 }
165
166 // Up-mixing: 2 -> 4, 2 -> 5.1
167 // output.L = input.L
168 // output.R = input.R
169 // output.C = 0 (in the case of 2 -> 5.1)
170 // output.LFE = 0 (in the case of 2 -> 5.1)
171 // output.SL = 0
172 // output.SR = 0
173 if ((numberOfSourceChannels === 2 && numberOfDestinationChannels === 4) ||
174 (numberOfSourceChannels === 2 && numberOfDestinationChannels === 6)) {
175 var sourceChannel0 = source.getChannelData(0);
176 var sourceChannel1 = source.getChannelData(1);
177 var destinationChannel0 = destination.getChannelData(0);
178 var destinationChannel1 = destination.getChannelData(1);
179 for (i = 0; i < length; i++) {
180 destinationChannel0[i] += sourceChannel0[i];
181 destinationChannel1[i] += sourceChannel1[i];
Raymond Toy 2016/03/08 18:04:07 Again, this doesn't match the comment. Update com
hongchan 2016/03/08 23:53:35 Done.
182 }
183
184 return;
185 }
186
187 // Up-mixing: 4 -> 5.1
188 // output.L = input.L
189 // output.R = input.R
190 // output.C = 0
191 // output.LFE = 0
192 // output.SL = input.SL
193 // output.SR = input.SR
194 if (numberOfSourceChannels === 4 && numberOfDestinationChannels === 6) {
195 var sourceChannel0 = source.getChannelData(0);
196 var sourceChannel1 = source.getChannelData(1);
197 var sourceChannel2 = source.getChannelData(2);
198 var sourceChannel3 = source.getChannelData(3);
199 var destinationChannel0 = destination.getChannelData(0);
200 var destinationChannel1 = destination.getChannelData(1);
201 var destinationChannel4 = destination.getChannelData(4);
202 var destinationChannel5 = destination.getChannelData(5);
203 for (i = 0; i < length; i++) {
204 destinationChannel0[i] += sourceChannel0[i];
205 destinationChannel1[i] += sourceChannel1[i];
206 destinationChannel4[i] += sourceChannel2[i];
207 destinationChannel5[i] += sourceChannel3[i];
208 }
209
210 return;
211 }
212
213 // All other cases, fall back to the discrete sum.
214 discreteSum(source, destination);
215 }
216
217 /**
218 * Process down-mix from source to destination by summing into the existing data .
219 * @param {AudioBuffer} source Source audio buffer.
220 * @param {AudioBuffer} destination Destination audio buffer.
221 */
222 function processDownMix(source, destination) {
223 var numberOfSourceChannels = source.numberOfChannels;
224 var numberOfDestinationChannels = destination.numberOfChannels;
225 var i, length = destination.length;
226
227 // Down-mixing: 2 -> 1
228 // output = 0.5 * (input.L + input.R)
229 if (numberOfSourceChannels === 2 && numberOfDestinationChannels === 1) {
230 var sourceChannel0 = source.getChannelData(0);
231 var sourceChannel1 = source.getChannelData(1);
232 var destinationChannel0 = destination.getChannelData(0);
233 for (i = 0; i < length; i++)
234 destinationChannel0[i] += 0.5 * (sourceChannel0[i] + sourceChannel1[i]);
Raymond Toy 2016/03/08 18:04:07 Again, this doesn't match the comment. Update com
hongchan 2016/03/08 23:53:35 Done.
235
236 return;
237 }
238
239 // Down-mixing: 4 -> 1
240 // output = 0.25 * (input.L + input.R + input.SL + input.SR)
241 if (numberOfSourceChannels === 4 && numberOfDestinationChannels === 1) {
242 var sourceChannel0 = source.getChannelData(0);
243 var sourceChannel1 = source.getChannelData(1);
244 var sourceChannel2 = source.getChannelData(2);
245 var sourceChannel3 = source.getChannelData(3);
246 var destinationChannel0 = destination.getChannelData(0);
247 for (i = 0; i < length; i++) {
248 destinationChannel0[i] += 0.25 * (sourceChannel0[i] + sourceChannel1[i]
Raymond Toy 2016/03/08 18:04:07 Again, this doesn't match the comment. Update com
hongchan 2016/03/08 23:53:35 Done.
249 + sourceChannel2[i] + sourceChannel3[i]);
250 }
251
252 return;
253 }
254
255 // Down-mixing: 5.1 -> 1
256 // output = sqrt(1/2) * (input.L + input.R) + input.C
257 // + 0.5 * (input.SL + input.SR)
258 if (numberOfSourceChannels === 6 && numberOfDestinationChannels === 1) {
259 var sourceChannel0 = source.getChannelData(0);
260 var sourceChannel1 = source.getChannelData(1);
261 var sourceChannel2 = source.getChannelData(2);
262 var sourceChannel4 = source.getChannelData(4);
263 var sourceChannel5 = source.getChannelData(5);
264 var destinationChannel0 = destination.getChannelData(0);
265 var scaleSqrtHalf = Math.sqrt(0.5);
266 for (i = 0; i < length; i++) {
267 destinationChannel0[i] +=
Raymond Toy 2016/03/08 18:04:07 This doesn't match the comment. Update comment or
hongchan 2016/03/08 23:53:34 Done.
268 scaleSqrtHalf * (sourceChannel0[i] + sourceChannel1[i])
269 + sourceChannel2[i] + 0.5 * (sourceChannel4[i] + sourceChannel5[i]);
270 }
271
272 return;
273 }
274
275 // Down-mixing: 4 -> 2
276 // output.L = 0.5 * (input.L + input.SL)
277 // output.R = 0.5 * (input.R + input.SR)
278 if (numberOfSourceChannels == 4 && numberOfDestinationChannels == 2) {
279 var sourceChannel0 = source.getChannelData(0);
Raymond Toy 2016/03/08 18:04:07 Probably want to say how sourceChannel<n> is assig
hongchan 2016/03/08 23:53:34 Done.
280 var sourceChannel1 = source.getChannelData(1);
281 var sourceChannel2 = source.getChannelData(2);
282 var sourceChannel3 = source.getChannelData(3);
283 var destinationChannel0 = destination.getChannelData(0);
284 var destinationChannel1 = destination.getChannelData(1);
285 for (i = 0; i < length; i++) {
286 destinationChannel0[i] += 0.5 * (sourceChannel0[i] + sourceChannel2[i]);
287 destinationChannel1[i] += 0.5 * (sourceChannel1[i] + sourceChannel3[i]);
Raymond Toy 2016/03/08 18:04:07 This doesn't match the comment. Update comment or
hongchan 2016/03/08 23:53:35 Done.
288 }
289
290 return;
291 }
292
293 // Down-mixing: 5.1 -> 2
294 // output.L = input.L + sqrt(1/2) * (input.C + input.SL)
295 // output.R = input.R + sqrt(1/2) * (input.C + input.SR)
296 if (numberOfSourceChannels == 6 && numberOfDestinationChannels == 2) {
297 var sourceChannel0 = source.getChannelData(0);
298 var sourceChannel1 = source.getChannelData(1);
299 var sourceChannel2 = source.getChannelData(2);
300 var sourceChannel4 = source.getChannelData(4);
301 var sourceChannel5 = source.getChannelData(5);
302 var destinationChannel0 = destination.getChannelData(0);
303 var destinationChannel1 = destination.getChannelData(1);
304 var scaleSqrtHalf = Math.sqrt(0.5);
305 for (i = 0; i < length; i++) {
306 destinationChannel0[i] += sourceChannel0[i]
307 + scaleSqrtHalf * (sourceChannel2[i] + sourceChannel4[i]);
308 destinationChannel1[i] += sourceChannel1[i]
309 + scaleSqrtHalf * (sourceChannel2[i] + sourceChannel5[i]);
310 }
311
312 return;
313 }
314
315 // Down-mixing: 5.1 -> 4
316 // output.L = input.L + sqrt(1/2) * input.C
317 // output.R = input.R + sqrt(1/2) * input.C
318 // output.SL = input.SL
319 // output.SR = input.SR
320 if (numberOfSourceChannels === 6 && numberOfDestinationChannels === 4) {
321 var sourceChannel0 = source.getChannelData(0);
322 var sourceChannel1 = source.getChannelData(1);
323 var sourceChannel2 = source.getChannelData(2);
324 var sourceChannel4 = source.getChannelData(4);
325 var sourceChannel5 = source.getChannelData(5);
326 var destinationChannel0 = destination.getChannelData(0);
327 var destinationChannel1 = destination.getChannelData(1);
328 var destinationChannel2 = destination.getChannelData(2);
329 var destinationChannel3 = destination.getChannelData(3);
330 var scaleSqrtHalf = Math.sqrt(0.5);
331 for (i = 0; i < length; i++) {
332 destinationChannel0[i] += sourceChannel0[i] + scaleSqrtHalf * sourceChanne l2[i];
333 destinationChannel1[i] += sourceChannel1[i] + scaleSqrtHalf * sourceChanne l2[i];
334 destinationChannel2[i] += sourceChannel4[i];
335 destinationChannel3[i] += sourceChannel5[i];
336 }
337
338 return;
339 }
340
341 // All other cases, fall back to the discrete sum.
342 discreteSum(source, destination);
343 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698