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

Side by Side Diff: tools/perf/page_sets/webrtc_cases/audio.js

Issue 2761163003: Use local pages for webrtc telemetry tests. (Closed)
Patch Set: Exclude all of webrtc_cases in PRESUBMIT.py and add a comment explaining it is because these are te… Created 3 years, 8 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 /*
2 * Copyright 2017 The Chromium Authors. All rights reserved.
3 * Use of this source code is governed by a BSD-style license that can be
4 * found in the LICENSE file.
5 */
6
7 'use strict';
8
9 var audio2 = document.querySelector('audio#audio2');
10 var callButton = document.querySelector('button#callButton');
11 var hangupButton = document.querySelector('button#hangupButton');
12 var codecSelector = document.querySelector('select#codec');
13 hangupButton.disabled = true;
14 callButton.onclick = call;
15 hangupButton.onclick = hangup;
16
17 var pc1;
18 var pc2;
19 var localStream;
20
21 var bitrateGraph;
22 var bitrateSeries;
23
24 var packetGraph;
25 var packetSeries;
26
27 var lastResult;
28
29 var offerOptions = {
30 offerToReceiveAudio: 1,
31 offerToReceiveVideo: 0,
32 voiceActivityDetection: false
33 };
34
35 function gotStream(stream) {
36 hangupButton.disabled = false;
37 trace('Received local stream');
38 localStream = stream;
39 var audioTracks = localStream.getAudioTracks();
40 if (audioTracks.length > 0) {
41 trace('Using Audio device: ' + audioTracks[0].label);
42 }
43 pc1.addStream(localStream);
44 trace('Adding Local Stream to peer connection');
45
46 pc1.createOffer(
47 offerOptions
48 ).then(
49 gotDescription1,
50 onCreateSessionDescriptionError
51 );
52
53 bitrateSeries = new TimelineDataSeries();
54 bitrateGraph = new TimelineGraphView('bitrateGraph', 'bitrateCanvas');
55 bitrateGraph.updateEndDate();
56
57 packetSeries = new TimelineDataSeries();
58 packetGraph = new TimelineGraphView('packetGraph', 'packetCanvas');
59 packetGraph.updateEndDate();
60 }
61
62 function onCreateSessionDescriptionError(error) {
63 trace('Failed to create session description: ' + error.toString());
64 }
65
66 function call() {
67 callButton.disabled = true;
68 codecSelector.disabled = true;
69 trace('Starting call');
70 var servers = null;
71 var pcConstraints = {
72 'optional': []
73 };
74 pc1 = new RTCPeerConnection(servers, pcConstraints);
75 trace('Created local peer connection object pc1');
76 pc1.onicecandidate = function(e) {
77 onIceCandidate(pc1, e);
78 };
79 pc2 = new RTCPeerConnection(servers, pcConstraints);
80 trace('Created remote peer connection object pc2');
81 pc2.onicecandidate = function(e) {
82 onIceCandidate(pc2, e);
83 };
84 pc2.onaddstream = gotRemoteStream;
85 trace('Requesting local stream');
86 navigator.mediaDevices.getUserMedia({
87 audio: true,
88 video: false
89 })
90 .then(gotStream)
91 .catch(function(e) {
92 alert('getUserMedia() error: ' + e.name);
93 });
94 }
95
96 function gotDescription1(desc) {
97 trace('Offer from pc1 \n' + desc.sdp);
98 pc1.setLocalDescription(desc).then(
99 function() {
100 desc.sdp = forceChosenAudioCodec(desc.sdp);
101 pc2.setRemoteDescription(desc).then(
102 function() {
103 pc2.createAnswer().then(
104 gotDescription2,
105 onCreateSessionDescriptionError
106 );
107 },
108 onSetSessionDescriptionError
109 );
110 },
111 onSetSessionDescriptionError
112 );
113 }
114
115 function gotDescription2(desc) {
116 trace('Answer from pc2 \n' + desc.sdp);
117 pc2.setLocalDescription(desc).then(
118 function() {
119 desc.sdp = forceChosenAudioCodec(desc.sdp);
120 pc1.setRemoteDescription(desc).then(
121 function() {
122 },
123 onSetSessionDescriptionError
124 );
125 },
126 onSetSessionDescriptionError
127 );
128 }
129
130 function hangup() {
131 trace('Ending call');
132 localStream.getTracks().forEach(function(track) {
133 track.stop();
134 });
135 pc1.close();
136 pc2.close();
137 pc1 = null;
138 pc2 = null;
139 hangupButton.disabled = true;
140 callButton.disabled = false;
141 codecSelector.disabled = false;
142 }
143
144 function gotRemoteStream(e) {
145 audio2.srcObject = e.stream;
146 trace('Received remote stream');
147 }
148
149 function getOtherPc(pc) {
150 return (pc === pc1) ? pc2 : pc1;
151 }
152
153 function getName(pc) {
154 return (pc === pc1) ? 'pc1' : 'pc2';
155 }
156
157 function onIceCandidate(pc, event) {
158 getOtherPc(pc).addIceCandidate(event.candidate)
159 .then(
160 function() {
161 onAddIceCandidateSuccess(pc);
162 },
163 function(err) {
164 onAddIceCandidateError(pc, err);
165 }
166 );
167 trace(getName(pc) + ' ICE candidate: \n' + (event.candidate ?
168 event.candidate.candidate : '(null)'));
169 }
170
171 function onAddIceCandidateSuccess() {
172 trace('AddIceCandidate success.');
173 }
174
175 function onAddIceCandidateError(error) {
176 trace('Failed to add ICE Candidate: ' + error.toString());
177 }
178
179 function onSetSessionDescriptionError(error) {
180 trace('Failed to set session description: ' + error.toString());
181 }
182
183 function forceChosenAudioCodec(sdp) {
184 return maybePreferCodec(sdp, 'audio', 'send', codecSelector.value);
185 }
186
187 // Copied from AppRTC's sdputils.js:
188
189 // Sets |codec| as the default |type| codec if it's present.
190 // The format of |codec| is 'NAME/RATE', e.g. 'opus/48000'.
191 function maybePreferCodec(sdp, type, dir, codec) {
192 var str = type + ' ' + dir + ' codec';
193 if (codec === '') {
194 trace('No preference on ' + str + '.');
195 return sdp;
196 }
197
198 trace('Prefer ' + str + ': ' + codec);
199
200 var sdpLines = sdp.split('\r\n');
201
202 // Search for m line.
203 var mLineIndex = findLine(sdpLines, 'm=', type);
204 if (mLineIndex === null) {
205 return sdp;
206 }
207
208 // If the codec is available, set it as the default in m line.
209 var codecIndex = findLine(sdpLines, 'a=rtpmap', codec);
210 console.log('codecIndex', codecIndex);
211 if (codecIndex) {
212 var payload = getCodecPayloadType(sdpLines[codecIndex]);
213 if (payload) {
214 sdpLines[mLineIndex] = setDefaultCodec(sdpLines[mLineIndex], payload);
215 }
216 }
217
218 sdp = sdpLines.join('\r\n');
219 return sdp;
220 }
221
222 // Find the line in sdpLines that starts with |prefix|, and, if specified,
223 // contains |substr| (case-insensitive search).
224 function findLine(sdpLines, prefix, substr) {
225 return findLineInRange(sdpLines, 0, -1, prefix, substr);
226 }
227
228 // Find the line in sdpLines[startLine...endLine - 1] that starts with |prefix|
229 // and, if specified, contains |substr| (case-insensitive search).
230 function findLineInRange(sdpLines, startLine, endLine, prefix, substr) {
231 var realEndLine = endLine !== -1 ? endLine : sdpLines.length;
232 for (var i = startLine; i < realEndLine; ++i) {
233 if (sdpLines[i].indexOf(prefix) === 0) {
234 if (!substr ||
235 sdpLines[i].toLowerCase().indexOf(substr.toLowerCase()) !== -1) {
236 return i;
237 }
238 }
239 }
240 return null;
241 }
242
243 // Gets the codec payload type from an a=rtpmap:X line.
244 function getCodecPayloadType(sdpLine) {
245 var pattern = new RegExp('a=rtpmap:(\\d+) \\w+\\/\\d+');
246 var result = sdpLine.match(pattern);
247 return (result && result.length === 2) ? result[1] : null;
248 }
249
250 // Returns a new m= line with the specified codec as the first one.
251 function setDefaultCodec(mLine, payload) {
252 var elements = mLine.split(' ');
253
254 // Just copy the first three parameters; codec order starts on fourth.
255 var newLine = elements.slice(0, 3);
256
257 // Put target payload first and copy in the rest.
258 newLine.push(payload);
259 for (var i = 3; i < elements.length; i++) {
260 if (elements[i] !== payload) {
261 newLine.push(elements[i]);
262 }
263 }
264 return newLine.join(' ');
265 }
266
267 // query getStats every second
268 window.setInterval(function() {
269 if (!window.pc1) {
270 return;
271 }
272 window.pc1.getStats(null).then(function(res) {
273 res.forEach(function(report) {
274 var bytes;
275 var packets;
276 var now = report.timestamp;
277 if ((report.type === 'outboundrtp') ||
278 (report.type === 'outbound-rtp') ||
279 (report.type === 'ssrc' && report.bytesSent)) {
280 bytes = report.bytesSent;
281 packets = report.packetsSent;
282 if (lastResult && lastResult.get(report.id)) {
283 // calculate bitrate
284 var bitrate = 8 * (bytes - lastResult.get(report.id).bytesSent) /
285 (now - lastResult.get(report.id).timestamp);
286
287 // append to chart
288 bitrateSeries.addPoint(now, bitrate);
289 bitrateGraph.setDataSeries([bitrateSeries]);
290 bitrateGraph.updateEndDate();
291
292 // calculate number of packets and append to chart
293 packetSeries.addPoint(now, packets -
294 lastResult.get(report.id).packetsSent);
295 packetGraph.setDataSeries([packetSeries]);
296 packetGraph.updateEndDate();
297 }
298 }
299 });
300 lastResult = res;
301 });
302 }, 1000);
OLDNEW
« no previous file with comments | « tools/perf/page_sets/webrtc_cases/audio.html ('k') | tools/perf/page_sets/webrtc_cases/canvas-capture.html » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698