blob: cf0eed50b94429e08dce28c667e6a69b82f7b1a1 [file] [log] [blame]
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001/*
kjellanderb24317b2016-02-10 07:54:43 -08002 * Copyright 2013 The WebRTC project authors. All Rights Reserved.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00003 *
kjellanderb24317b2016-02-10 07:54:43 -08004 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree.
henrike@webrtc.org28e20752013-07-10 00:45:36 +00009 */
10
henrike@webrtc.org28e20752013-07-10 00:45:36 +000011package org.webrtc;
12
Magnus Jedvert6062f372017-11-16 16:53:12 +010013import java.util.ArrayList;
Sami Kalliomäki3e189a62017-11-24 11:13:39 +010014import java.util.Collections;
henrike@webrtc.org28e20752013-07-10 00:45:36 +000015import java.util.List;
16
17/**
18 * Java-land version of the PeerConnection APIs; wraps the C++ API
19 * http://www.webrtc.org/reference/native-apis, which in turn is inspired by the
20 * JS APIs: http://dev.w3.org/2011/webrtc/editor/webrtc.html and
21 * http://www.w3.org/TR/mediacapture-streams/
22 */
Magnus Jedvert84d8ae52017-12-20 15:12:10 +010023@JNINamespace("webrtc::jni")
henrike@webrtc.org28e20752013-07-10 00:45:36 +000024public class PeerConnection {
henrike@webrtc.org28e20752013-07-10 00:45:36 +000025 /** Tracks PeerConnectionInterface::IceGatheringState */
Magnus Jedvertba700f62017-12-04 13:43:27 +010026 public enum IceGatheringState {
27 NEW,
28 GATHERING,
29 COMPLETE;
30
31 @CalledByNative("IceGatheringState")
32 static IceGatheringState fromNativeIndex(int nativeIndex) {
33 return values()[nativeIndex];
34 }
35 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +000036
37 /** Tracks PeerConnectionInterface::IceConnectionState */
38 public enum IceConnectionState {
sakalb6760f92016-09-29 04:12:44 -070039 NEW,
40 CHECKING,
41 CONNECTED,
42 COMPLETED,
43 FAILED,
44 DISCONNECTED,
Magnus Jedvertba700f62017-12-04 13:43:27 +010045 CLOSED;
46
47 @CalledByNative("IceConnectionState")
48 static IceConnectionState fromNativeIndex(int nativeIndex) {
49 return values()[nativeIndex];
50 }
sakalb6760f92016-09-29 04:12:44 -070051 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +000052
hnsl04833622017-01-09 08:35:45 -080053 /** Tracks PeerConnectionInterface::TlsCertPolicy */
54 public enum TlsCertPolicy {
55 TLS_CERT_POLICY_SECURE,
56 TLS_CERT_POLICY_INSECURE_NO_CHECK,
57 }
58
henrike@webrtc.org28e20752013-07-10 00:45:36 +000059 /** Tracks PeerConnectionInterface::SignalingState */
60 public enum SignalingState {
sakalb6760f92016-09-29 04:12:44 -070061 STABLE,
62 HAVE_LOCAL_OFFER,
63 HAVE_LOCAL_PRANSWER,
64 HAVE_REMOTE_OFFER,
65 HAVE_REMOTE_PRANSWER,
Magnus Jedvertba700f62017-12-04 13:43:27 +010066 CLOSED;
67
68 @CalledByNative("SignalingState")
69 static SignalingState fromNativeIndex(int nativeIndex) {
70 return values()[nativeIndex];
71 }
sakalb6760f92016-09-29 04:12:44 -070072 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +000073
74 /** Java version of PeerConnectionObserver. */
75 public static interface Observer {
76 /** Triggered when the SignalingState changes. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010077 @CalledByNative("Observer") void onSignalingChange(SignalingState newState);
henrike@webrtc.org28e20752013-07-10 00:45:36 +000078
79 /** Triggered when the IceConnectionState changes. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010080 @CalledByNative("Observer") void onIceConnectionChange(IceConnectionState newState);
henrike@webrtc.org28e20752013-07-10 00:45:36 +000081
Peter Thatcher54360512015-07-08 11:08:35 -070082 /** Triggered when the ICE connection receiving status changes. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010083 @CalledByNative("Observer") void onIceConnectionReceivingChange(boolean receiving);
Peter Thatcher54360512015-07-08 11:08:35 -070084
henrike@webrtc.org28e20752013-07-10 00:45:36 +000085 /** Triggered when the IceGatheringState changes. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010086 @CalledByNative("Observer") void onIceGatheringChange(IceGatheringState newState);
henrike@webrtc.org28e20752013-07-10 00:45:36 +000087
88 /** Triggered when a new ICE candidate has been found. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010089 @CalledByNative("Observer") void onIceCandidate(IceCandidate candidate);
henrike@webrtc.org28e20752013-07-10 00:45:36 +000090
Honghai Zhang7fb69db2016-03-14 11:59:18 -070091 /** Triggered when some ICE candidates have been removed. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010092 @CalledByNative("Observer") void onIceCandidatesRemoved(IceCandidate[] candidates);
Honghai Zhang7fb69db2016-03-14 11:59:18 -070093
henrike@webrtc.org28e20752013-07-10 00:45:36 +000094 /** Triggered when media is received on a new stream from remote peer. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010095 @CalledByNative("Observer") void onAddStream(MediaStream stream);
henrike@webrtc.org28e20752013-07-10 00:45:36 +000096
97 /** Triggered when a remote peer close a stream. */
Magnus Jedvertba700f62017-12-04 13:43:27 +010098 @CalledByNative("Observer") void onRemoveStream(MediaStream stream);
henrike@webrtc.org723d6832013-07-12 16:04:50 +000099
100 /** Triggered when a remote peer opens a DataChannel. */
Magnus Jedvertba700f62017-12-04 13:43:27 +0100101 @CalledByNative("Observer") void onDataChannel(DataChannel dataChannel);
fischman@webrtc.orgd7568a02014-01-13 22:04:12 +0000102
103 /** Triggered when renegotiation is necessary. */
Magnus Jedvertba700f62017-12-04 13:43:27 +0100104 @CalledByNative("Observer") void onRenegotiationNeeded();
zhihuangdcccda72016-12-21 14:08:03 -0800105
106 /**
107 * Triggered when a new track is signaled by the remote peer, as a result of
108 * setRemoteDescription.
109 */
Magnus Jedvertba700f62017-12-04 13:43:27 +0100110 @CalledByNative("Observer") void onAddTrack(RtpReceiver receiver, MediaStream[] mediaStreams);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000111 }
112
113 /** Java version of PeerConnectionInterface.IceServer. */
114 public static class IceServer {
Emad Omaradab1d2d2017-06-16 15:43:11 -0700115 // List of URIs associated with this server. Valid formats are described
116 // in RFC7064 and RFC7065, and more may be added in the future. The "host"
117 // part of the URI may contain either an IP address or a hostname.
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700118 @Deprecated public final String uri;
119 public final List<String> urls;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000120 public final String username;
121 public final String password;
hnsl04833622017-01-09 08:35:45 -0800122 public final TlsCertPolicy tlsCertPolicy;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000123
Emad Omaradab1d2d2017-06-16 15:43:11 -0700124 // If the URIs in |urls| only contain IP addresses, this field can be used
125 // to indicate the hostname, which may be necessary for TLS (using the SNI
126 // extension). If |urls| itself contains the hostname, this isn't
127 // necessary.
128 public final String hostname;
129
Diogo Real1dca9d52017-08-29 12:18:32 -0700130 // List of protocols to be used in the TLS ALPN extension.
131 public final List<String> tlsAlpnProtocols;
132
Diogo Real7bd1f1b2017-09-08 12:50:41 -0700133 // List of elliptic curves to be used in the TLS elliptic curves extension.
134 // Only curve names supported by OpenSSL should be used (eg. "P-256","X25519").
135 public final List<String> tlsEllipticCurves;
136
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000137 /** Convenience constructor for STUN servers. */
Diogo Real05ea2b32017-08-31 00:12:58 -0700138 @Deprecated
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000139 public IceServer(String uri) {
140 this(uri, "", "");
141 }
142
Diogo Real05ea2b32017-08-31 00:12:58 -0700143 @Deprecated
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000144 public IceServer(String uri, String username, String password) {
hnsl04833622017-01-09 08:35:45 -0800145 this(uri, username, password, TlsCertPolicy.TLS_CERT_POLICY_SECURE);
146 }
147
Diogo Real05ea2b32017-08-31 00:12:58 -0700148 @Deprecated
hnsl04833622017-01-09 08:35:45 -0800149 public IceServer(String uri, String username, String password, TlsCertPolicy tlsCertPolicy) {
Emad Omaradab1d2d2017-06-16 15:43:11 -0700150 this(uri, username, password, tlsCertPolicy, "");
151 }
152
Diogo Real05ea2b32017-08-31 00:12:58 -0700153 @Deprecated
Emad Omaradab1d2d2017-06-16 15:43:11 -0700154 public IceServer(String uri, String username, String password, TlsCertPolicy tlsCertPolicy,
155 String hostname) {
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700156 this(uri, Collections.singletonList(uri), username, password, tlsCertPolicy, hostname, null,
157 null);
Diogo Real1dca9d52017-08-29 12:18:32 -0700158 }
159
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700160 private IceServer(String uri, List<String> urls, String username, String password,
161 TlsCertPolicy tlsCertPolicy, String hostname, List<String> tlsAlpnProtocols,
162 List<String> tlsEllipticCurves) {
163 if (uri == null || urls == null || urls.isEmpty()) {
164 throw new IllegalArgumentException("uri == null || urls == null || urls.isEmpty()");
165 }
166 for (String it : urls) {
167 if (it == null) {
168 throw new IllegalArgumentException("urls element is null: " + urls);
169 }
170 }
171 if (username == null) {
172 throw new IllegalArgumentException("username == null");
173 }
174 if (password == null) {
175 throw new IllegalArgumentException("password == null");
176 }
177 if (hostname == null) {
178 throw new IllegalArgumentException("hostname == null");
179 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000180 this.uri = uri;
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700181 this.urls = urls;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000182 this.username = username;
183 this.password = password;
hnsl04833622017-01-09 08:35:45 -0800184 this.tlsCertPolicy = tlsCertPolicy;
Emad Omaradab1d2d2017-06-16 15:43:11 -0700185 this.hostname = hostname;
Diogo Real1dca9d52017-08-29 12:18:32 -0700186 this.tlsAlpnProtocols = tlsAlpnProtocols;
Diogo Real7bd1f1b2017-09-08 12:50:41 -0700187 this.tlsEllipticCurves = tlsEllipticCurves;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000188 }
189
Sami Kalliomäkibde473e2017-10-30 13:34:41 +0100190 @Override
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000191 public String toString() {
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700192 return urls + " [" + username + ":" + password + "] [" + tlsCertPolicy + "] [" + hostname
Diogo Real7bd1f1b2017-09-08 12:50:41 -0700193 + "] [" + tlsAlpnProtocols + "] [" + tlsEllipticCurves + "]";
Diogo Real1dca9d52017-08-29 12:18:32 -0700194 }
195
196 public static Builder builder(String uri) {
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700197 return new Builder(Collections.singletonList(uri));
198 }
199
200 public static Builder builder(List<String> urls) {
201 return new Builder(urls);
Diogo Real1dca9d52017-08-29 12:18:32 -0700202 }
203
204 public static class Builder {
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700205 private final List<String> urls;
Diogo Real1dca9d52017-08-29 12:18:32 -0700206 private String username = "";
207 private String password = "";
208 private TlsCertPolicy tlsCertPolicy = TlsCertPolicy.TLS_CERT_POLICY_SECURE;
209 private String hostname = "";
210 private List<String> tlsAlpnProtocols;
Diogo Real7bd1f1b2017-09-08 12:50:41 -0700211 private List<String> tlsEllipticCurves;
Diogo Real1dca9d52017-08-29 12:18:32 -0700212
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700213 private Builder(List<String> urls) {
214 if (urls == null || urls.isEmpty()) {
215 throw new IllegalArgumentException("urls == null || urls.isEmpty(): " + urls);
216 }
217 this.urls = urls;
Diogo Real1dca9d52017-08-29 12:18:32 -0700218 }
219
220 public Builder setUsername(String username) {
221 this.username = username;
222 return this;
223 }
224
225 public Builder setPassword(String password) {
226 this.password = password;
227 return this;
228 }
229
230 public Builder setTlsCertPolicy(TlsCertPolicy tlsCertPolicy) {
231 this.tlsCertPolicy = tlsCertPolicy;
232 return this;
233 }
234
235 public Builder setHostname(String hostname) {
236 this.hostname = hostname;
237 return this;
238 }
239
240 public Builder setTlsAlpnProtocols(List<String> tlsAlpnProtocols) {
241 this.tlsAlpnProtocols = tlsAlpnProtocols;
242 return this;
243 }
244
Diogo Real7bd1f1b2017-09-08 12:50:41 -0700245 public Builder setTlsEllipticCurves(List<String> tlsEllipticCurves) {
246 this.tlsEllipticCurves = tlsEllipticCurves;
247 return this;
248 }
249
Diogo Real1dca9d52017-08-29 12:18:32 -0700250 public IceServer createIceServer() {
korniltsev.anatoly0ea03102017-09-11 06:41:38 -0700251 return new IceServer(urls.get(0), urls, username, password, tlsCertPolicy, hostname,
252 tlsAlpnProtocols, tlsEllipticCurves);
Diogo Real1dca9d52017-08-29 12:18:32 -0700253 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000254 }
Magnus Jedvert9060eb12017-12-12 12:52:54 +0100255
256 @CalledByNative("IceServer")
257 List<String> getUrls() {
258 return urls;
259 }
260
261 @CalledByNative("IceServer")
262 String getUsername() {
263 return username;
264 }
265
266 @CalledByNative("IceServer")
267 String getPassword() {
268 return password;
269 }
270
271 @CalledByNative("IceServer")
272 TlsCertPolicy getTlsCertPolicy() {
273 return tlsCertPolicy;
274 }
275
276 @CalledByNative("IceServer")
277 String getHostname() {
278 return hostname;
279 }
280
281 @CalledByNative("IceServer")
282 List<String> getTlsAlpnProtocols() {
283 return tlsAlpnProtocols;
284 }
285
286 @CalledByNative("IceServer")
287 List<String> getTlsEllipticCurves() {
288 return tlsEllipticCurves;
289 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000290 }
291
Jiayang Liucac1b382015-04-30 12:35:24 -0700292 /** Java version of PeerConnectionInterface.IceTransportsType */
sakalb6760f92016-09-29 04:12:44 -0700293 public enum IceTransportsType { NONE, RELAY, NOHOST, ALL }
Jiayang Liucac1b382015-04-30 12:35:24 -0700294
295 /** Java version of PeerConnectionInterface.BundlePolicy */
sakalb6760f92016-09-29 04:12:44 -0700296 public enum BundlePolicy { BALANCED, MAXBUNDLE, MAXCOMPAT }
Jiayang Liucac1b382015-04-30 12:35:24 -0700297
Peter Thatcheraf55ccc2015-05-21 07:48:41 -0700298 /** Java version of PeerConnectionInterface.RtcpMuxPolicy */
sakalb6760f92016-09-29 04:12:44 -0700299 public enum RtcpMuxPolicy { NEGOTIATE, REQUIRE }
glaznev97579a42015-09-01 11:31:27 -0700300
Peter Thatcheraf55ccc2015-05-21 07:48:41 -0700301 /** Java version of PeerConnectionInterface.TcpCandidatePolicy */
sakalb6760f92016-09-29 04:12:44 -0700302 public enum TcpCandidatePolicy { ENABLED, DISABLED }
Jiayang Liucac1b382015-04-30 12:35:24 -0700303
honghaiz60347052016-05-31 18:29:12 -0700304 /** Java version of PeerConnectionInterface.CandidateNetworkPolicy */
sakalb6760f92016-09-29 04:12:44 -0700305 public enum CandidateNetworkPolicy { ALL, LOW_COST }
honghaiz60347052016-05-31 18:29:12 -0700306
Qingsi Wang9a5c6f82018-02-01 10:38:40 -0800307 // Keep in sync with webrtc/rtc_base/network_constants.h.
308 public enum AdapterType {
309 UNKNOWN,
310 ETHERNET,
311 WIFI,
312 CELLULAR,
313 VPN,
314 LOOPBACK,
315 }
316
glaznev97579a42015-09-01 11:31:27 -0700317 /** Java version of rtc::KeyType */
sakalb6760f92016-09-29 04:12:44 -0700318 public enum KeyType { RSA, ECDSA }
glaznev97579a42015-09-01 11:31:27 -0700319
honghaiz1f429e32015-09-28 07:57:34 -0700320 /** Java version of PeerConnectionInterface.ContinualGatheringPolicy */
sakalb6760f92016-09-29 04:12:44 -0700321 public enum ContinualGatheringPolicy { GATHER_ONCE, GATHER_CONTINUALLY }
honghaiz1f429e32015-09-28 07:57:34 -0700322
Steve Antond960a0c2017-07-17 12:33:07 -0700323 /** Java version of rtc::IntervalRange */
324 public static class IntervalRange {
325 private final int min;
326 private final int max;
327
328 public IntervalRange(int min, int max) {
329 this.min = min;
330 this.max = max;
331 }
332
Magnus Jedvert9060eb12017-12-12 12:52:54 +0100333 @CalledByNative("IntervalRange")
Steve Antond960a0c2017-07-17 12:33:07 -0700334 public int getMin() {
335 return min;
336 }
337
Magnus Jedvert9060eb12017-12-12 12:52:54 +0100338 @CalledByNative("IntervalRange")
Steve Antond960a0c2017-07-17 12:33:07 -0700339 public int getMax() {
340 return max;
341 }
342 }
343
Seth Hampsonc384e142018-03-06 15:47:10 -0800344 /**
345 * Java version of webrtc::SdpSemantics.
346 *
347 * Configure the SDP semantics used by this PeerConnection. Note that the
348 * WebRTC 1.0 specification requires UNIFIED_PLAN semantics. The
349 * RtpTransceiver API is only available with UNIFIED_PLAN semantics.
350 *
351 * <p>PLAN_B will cause PeerConnection to create offers and answers with at
352 * most one audio and one video m= section with multiple RtpSenders and
353 * RtpReceivers specified as multiple a=ssrc lines within the section. This
354 * will also cause PeerConnection to ignore all but the first m= section of
355 * the same media type.
356 *
357 * <p>UNIFIED_PLAN will cause PeerConnection to create offers and answers with
358 * multiple m= sections where each m= section maps to one RtpSender and one
359 * RtpReceiver (an RtpTransceiver), either both audio or both video. This
360 * will also cause PeerConnection to ignore all but the first a=ssrc lines
361 * that form a Plan B stream.
362 *
363 * <p>For users who wish to send multiple audio/video streams and need to stay
364 * interoperable with legacy WebRTC implementations, specify PLAN_B.
365 *
366 * <p>For users who wish to send multiple audio/video streams and/or wish to
367 * use the new RtpTransceiver API, specify UNIFIED_PLAN.
368 */
369 public enum SdpSemantics { PLAN_B, UNIFIED_PLAN }
370
Jiayang Liucac1b382015-04-30 12:35:24 -0700371 /** Java version of PeerConnectionInterface.RTCConfiguration */
Qingsi Wangdb53f8e2018-02-20 14:45:49 -0800372 // TODO(qingsi): Resolve the naming inconsistency of fields with/without units.
Jiayang Liucac1b382015-04-30 12:35:24 -0700373 public static class RTCConfiguration {
374 public IceTransportsType iceTransportsType;
375 public List<IceServer> iceServers;
376 public BundlePolicy bundlePolicy;
Peter Thatcheraf55ccc2015-05-21 07:48:41 -0700377 public RtcpMuxPolicy rtcpMuxPolicy;
Jiayang Liucac1b382015-04-30 12:35:24 -0700378 public TcpCandidatePolicy tcpCandidatePolicy;
honghaiz60347052016-05-31 18:29:12 -0700379 public CandidateNetworkPolicy candidateNetworkPolicy;
Henrik Lundin64dad832015-05-11 12:44:23 +0200380 public int audioJitterBufferMaxPackets;
Henrik Lundin5263b3c2015-06-01 10:29:41 +0200381 public boolean audioJitterBufferFastAccelerate;
honghaiz4edc39c2015-09-01 09:53:56 -0700382 public int iceConnectionReceivingTimeout;
Honghai Zhang381b4212015-12-04 12:24:03 -0800383 public int iceBackupCandidatePairPingInterval;
glaznev97579a42015-09-01 11:31:27 -0700384 public KeyType keyType;
honghaiz1f429e32015-09-28 07:57:34 -0700385 public ContinualGatheringPolicy continualGatheringPolicy;
deadbeefbe0c96f2016-05-18 16:20:14 -0700386 public int iceCandidatePoolSize;
Honghai Zhangd78ecf72016-07-01 14:40:40 -0700387 public boolean pruneTurnPorts;
Taylor Brandstettere9851112016-07-01 11:11:13 -0700388 public boolean presumeWritableWhenFullyRelayed;
Qingsi Wange6826d22018-03-08 14:55:14 -0800389 // The following fields define intervals in milliseconds at which ICE
390 // connectivity checks are sent.
391 //
392 // We consider ICE is "strongly connected" for an agent when there is at
393 // least one candidate pair that currently succeeds in connectivity check
394 // from its direction i.e. sending a ping and receives a ping response, AND
395 // all candidate pairs have sent a minimum number of pings for connectivity
396 // (this number is implementation-specific). Otherwise, ICE is considered in
397 // "weak connectivity".
398 //
399 // Note that the above notion of strong and weak connectivity is not defined
400 // in RFC 5245, and they apply to our current ICE implementation only.
401 //
402 // 1) iceCheckIntervalStrongConnectivityMs defines the interval applied to
403 // ALL candidate pairs when ICE is strongly connected,
404 // 2) iceCheckIntervalWeakConnectivityMs defines the counterpart for ALL
405 // pairs when ICE is weakly connected, and
406 // 3) iceCheckMinInterval defines the minimal interval (equivalently the
407 // maximum rate) that overrides the above two intervals when either of them
408 // is less.
409 public Integer iceCheckIntervalStrongConnectivityMs;
410 public Integer iceCheckIntervalWeakConnectivityMs;
skvlad51072462017-02-02 11:50:14 -0800411 public Integer iceCheckMinInterval;
Qingsi Wang22e623a2018-03-13 10:53:57 -0700412 // The time period in milliseconds for which a candidate pair must wait for response to
413 // connectivitiy checks before it becomes unwritable.
414 public Integer iceUnwritableTimeMs;
415 // The minimum number of connectivity checks that a candidate pair must sent without receiving
416 // response before it becomes unwritable.
417 public Integer iceUnwritableMinChecks;
Qingsi Wangdb53f8e2018-02-20 14:45:49 -0800418 // The interval in milliseconds at which STUN candidates will resend STUN binding requests
419 // to keep NAT bindings open.
420 // The default value in the implementation is used if this field is null.
421 public Integer stunCandidateKeepaliveIntervalMs;
zhihuangb09b3f92017-03-07 14:40:51 -0800422 public boolean disableIPv6OnWifi;
deadbeef28e29192017-07-27 09:14:38 -0700423 // By default, PeerConnection will use a limited number of IPv6 network
424 // interfaces, in order to avoid too many ICE candidate pairs being created
425 // and delaying ICE completion.
426 //
427 // Can be set to Integer.MAX_VALUE to effectively disable the limit.
428 public int maxIPv6Networks;
Steve Antond960a0c2017-07-17 12:33:07 -0700429 public IntervalRange iceRegatherIntervalRange;
Jiayang Liucac1b382015-04-30 12:35:24 -0700430
Sami Kalliomäkie8b26cd2017-12-19 12:51:53 +0100431 // These values will be overridden by MediaStream constraints if deprecated constraints-based
432 // create peerconnection interface is used.
433 public boolean disableIpv6;
434 public boolean enableDscp;
435 public boolean enableCpuOveruseDetection;
436 public boolean enableRtpDataChannel;
437 public boolean suspendBelowMinBitrate;
438 public Integer screencastMinBitrate;
439 public Boolean combinedAudioVideoBwe;
440 public Boolean enableDtlsSrtp;
Qingsi Wang9a5c6f82018-02-01 10:38:40 -0800441 // Use "Unknown" to represent no preference of adapter types, not the
442 // preference of adapters of unknown types.
443 public AdapterType networkPreference;
Seth Hampsonc384e142018-03-06 15:47:10 -0800444 public SdpSemantics sdpSemantics;
Sami Kalliomäkie8b26cd2017-12-19 12:51:53 +0100445
Jonas Orelandbdcee282017-10-10 14:01:40 +0200446 // This is an optional wrapper for the C++ webrtc::TurnCustomizer.
447 public TurnCustomizer turnCustomizer;
448
deadbeef28e29192017-07-27 09:14:38 -0700449 // TODO(deadbeef): Instead of duplicating the defaults here, we should do
450 // something to pick up the defaults from C++. The Objective-C equivalent
451 // of RTCConfiguration does that.
Jiayang Liucac1b382015-04-30 12:35:24 -0700452 public RTCConfiguration(List<IceServer> iceServers) {
453 iceTransportsType = IceTransportsType.ALL;
454 bundlePolicy = BundlePolicy.BALANCED;
zhihuang4dfb8ce2016-11-23 10:30:12 -0800455 rtcpMuxPolicy = RtcpMuxPolicy.REQUIRE;
Jiayang Liucac1b382015-04-30 12:35:24 -0700456 tcpCandidatePolicy = TcpCandidatePolicy.ENABLED;
Sami Kalliomäki9828beb2017-10-26 16:21:22 +0200457 candidateNetworkPolicy = CandidateNetworkPolicy.ALL;
Jiayang Liucac1b382015-04-30 12:35:24 -0700458 this.iceServers = iceServers;
Henrik Lundin64dad832015-05-11 12:44:23 +0200459 audioJitterBufferMaxPackets = 50;
Henrik Lundin5263b3c2015-06-01 10:29:41 +0200460 audioJitterBufferFastAccelerate = false;
honghaiz4edc39c2015-09-01 09:53:56 -0700461 iceConnectionReceivingTimeout = -1;
Honghai Zhang381b4212015-12-04 12:24:03 -0800462 iceBackupCandidatePairPingInterval = -1;
glaznev97579a42015-09-01 11:31:27 -0700463 keyType = KeyType.ECDSA;
honghaiz1f429e32015-09-28 07:57:34 -0700464 continualGatheringPolicy = ContinualGatheringPolicy.GATHER_ONCE;
deadbeefbe0c96f2016-05-18 16:20:14 -0700465 iceCandidatePoolSize = 0;
Honghai Zhangd78ecf72016-07-01 14:40:40 -0700466 pruneTurnPorts = false;
Taylor Brandstettere9851112016-07-01 11:11:13 -0700467 presumeWritableWhenFullyRelayed = false;
Qingsi Wange6826d22018-03-08 14:55:14 -0800468 iceCheckIntervalStrongConnectivityMs = null;
469 iceCheckIntervalWeakConnectivityMs = null;
skvlad51072462017-02-02 11:50:14 -0800470 iceCheckMinInterval = null;
Qingsi Wang22e623a2018-03-13 10:53:57 -0700471 iceUnwritableTimeMs = null;
472 iceUnwritableMinChecks = null;
Qingsi Wangdb53f8e2018-02-20 14:45:49 -0800473 stunCandidateKeepaliveIntervalMs = null;
zhihuangb09b3f92017-03-07 14:40:51 -0800474 disableIPv6OnWifi = false;
deadbeef28e29192017-07-27 09:14:38 -0700475 maxIPv6Networks = 5;
Steve Antond960a0c2017-07-17 12:33:07 -0700476 iceRegatherIntervalRange = null;
Sami Kalliomäkie8b26cd2017-12-19 12:51:53 +0100477 disableIpv6 = false;
478 enableDscp = false;
479 enableCpuOveruseDetection = true;
480 enableRtpDataChannel = false;
481 suspendBelowMinBitrate = false;
482 screencastMinBitrate = null;
483 combinedAudioVideoBwe = null;
484 enableDtlsSrtp = null;
Qingsi Wang9a5c6f82018-02-01 10:38:40 -0800485 networkPreference = AdapterType.UNKNOWN;
Seth Hampsonc384e142018-03-06 15:47:10 -0800486 sdpSemantics = SdpSemantics.PLAN_B;
Jiayang Liucac1b382015-04-30 12:35:24 -0700487 }
Magnus Jedvert9060eb12017-12-12 12:52:54 +0100488
489 @CalledByNative("RTCConfiguration")
490 IceTransportsType getIceTransportsType() {
491 return iceTransportsType;
492 }
493
494 @CalledByNative("RTCConfiguration")
495 List<IceServer> getIceServers() {
496 return iceServers;
497 }
498
499 @CalledByNative("RTCConfiguration")
500 BundlePolicy getBundlePolicy() {
501 return bundlePolicy;
502 }
503
504 @CalledByNative("RTCConfiguration")
505 RtcpMuxPolicy getRtcpMuxPolicy() {
506 return rtcpMuxPolicy;
507 }
508
509 @CalledByNative("RTCConfiguration")
510 TcpCandidatePolicy getTcpCandidatePolicy() {
511 return tcpCandidatePolicy;
512 }
513
514 @CalledByNative("RTCConfiguration")
515 CandidateNetworkPolicy getCandidateNetworkPolicy() {
516 return candidateNetworkPolicy;
517 }
518
519 @CalledByNative("RTCConfiguration")
520 int getAudioJitterBufferMaxPackets() {
521 return audioJitterBufferMaxPackets;
522 }
523
524 @CalledByNative("RTCConfiguration")
525 boolean getAudioJitterBufferFastAccelerate() {
526 return audioJitterBufferFastAccelerate;
527 }
528
529 @CalledByNative("RTCConfiguration")
530 int getIceConnectionReceivingTimeout() {
531 return iceConnectionReceivingTimeout;
532 }
533
534 @CalledByNative("RTCConfiguration")
535 int getIceBackupCandidatePairPingInterval() {
536 return iceBackupCandidatePairPingInterval;
537 }
538
539 @CalledByNative("RTCConfiguration")
540 KeyType getKeyType() {
541 return keyType;
542 }
543
544 @CalledByNative("RTCConfiguration")
545 ContinualGatheringPolicy getContinualGatheringPolicy() {
546 return continualGatheringPolicy;
547 }
548
549 @CalledByNative("RTCConfiguration")
550 int getIceCandidatePoolSize() {
551 return iceCandidatePoolSize;
552 }
553
554 @CalledByNative("RTCConfiguration")
555 boolean getPruneTurnPorts() {
556 return pruneTurnPorts;
557 }
558
559 @CalledByNative("RTCConfiguration")
560 boolean getPresumeWritableWhenFullyRelayed() {
561 return presumeWritableWhenFullyRelayed;
562 }
563
564 @CalledByNative("RTCConfiguration")
Qingsi Wange6826d22018-03-08 14:55:14 -0800565 Integer getIceCheckIntervalStrongConnectivity() {
566 return iceCheckIntervalStrongConnectivityMs;
567 }
568
569 @CalledByNative("RTCConfiguration")
570 Integer getIceCheckIntervalWeakConnectivity() {
571 return iceCheckIntervalWeakConnectivityMs;
572 }
573
574 @CalledByNative("RTCConfiguration")
Magnus Jedvert9060eb12017-12-12 12:52:54 +0100575 Integer getIceCheckMinInterval() {
576 return iceCheckMinInterval;
577 }
578
579 @CalledByNative("RTCConfiguration")
Qingsi Wang22e623a2018-03-13 10:53:57 -0700580 Integer getIceUnwritableTimeout() {
581 return iceUnwritableTimeMs;
582 }
583
584 @CalledByNative("RTCConfiguration")
585 Integer getIceUnwritableMinChecks() {
586 return iceUnwritableMinChecks;
587 }
588
589 @CalledByNative("RTCConfiguration")
Qingsi Wangdb53f8e2018-02-20 14:45:49 -0800590 Integer getStunCandidateKeepaliveInterval() {
591 return stunCandidateKeepaliveIntervalMs;
592 }
593
594 @CalledByNative("RTCConfiguration")
Magnus Jedvert9060eb12017-12-12 12:52:54 +0100595 boolean getDisableIPv6OnWifi() {
596 return disableIPv6OnWifi;
597 }
598
599 @CalledByNative("RTCConfiguration")
600 int getMaxIPv6Networks() {
601 return maxIPv6Networks;
602 }
603
604 @CalledByNative("RTCConfiguration")
605 IntervalRange getIceRegatherIntervalRange() {
606 return iceRegatherIntervalRange;
607 }
608
609 @CalledByNative("RTCConfiguration")
610 TurnCustomizer getTurnCustomizer() {
611 return turnCustomizer;
612 }
Sami Kalliomäkie8b26cd2017-12-19 12:51:53 +0100613
614 @CalledByNative("RTCConfiguration")
615 boolean getDisableIpv6() {
616 return disableIpv6;
617 }
618
619 @CalledByNative("RTCConfiguration")
620 boolean getEnableDscp() {
621 return enableDscp;
622 }
623
624 @CalledByNative("RTCConfiguration")
625 boolean getEnableCpuOveruseDetection() {
626 return enableCpuOveruseDetection;
627 }
628
629 @CalledByNative("RTCConfiguration")
630 boolean getEnableRtpDataChannel() {
631 return enableRtpDataChannel;
632 }
633
634 @CalledByNative("RTCConfiguration")
635 boolean getSuspendBelowMinBitrate() {
636 return suspendBelowMinBitrate;
637 }
638
639 @CalledByNative("RTCConfiguration")
640 Integer getScreencastMinBitrate() {
641 return screencastMinBitrate;
642 }
643
644 @CalledByNative("RTCConfiguration")
645 Boolean getCombinedAudioVideoBwe() {
646 return combinedAudioVideoBwe;
647 }
648
649 @CalledByNative("RTCConfiguration")
650 Boolean getEnableDtlsSrtp() {
651 return enableDtlsSrtp;
652 }
Qingsi Wang9a5c6f82018-02-01 10:38:40 -0800653
654 @CalledByNative("RTCConfiguration")
655 AdapterType getNetworkPreference() {
656 return networkPreference;
657 }
Seth Hampsonc384e142018-03-06 15:47:10 -0800658
659 @CalledByNative("RTCConfiguration")
660 SdpSemantics getSdpSemantics() {
661 return sdpSemantics;
662 }
Jiayang Liucac1b382015-04-30 12:35:24 -0700663 };
664
Magnus Jedvert6062f372017-11-16 16:53:12 +0100665 private final List<MediaStream> localStreams = new ArrayList<>();
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000666 private final long nativePeerConnection;
Magnus Jedvert6062f372017-11-16 16:53:12 +0100667 private List<RtpSender> senders = new ArrayList<>();
668 private List<RtpReceiver> receivers = new ArrayList<>();
Seth Hampsonc384e142018-03-06 15:47:10 -0800669 private List<RtpTransceiver> transceivers = new ArrayList<>();
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000670
Sami Kalliomäki1ece1ed2017-12-20 11:59:22 +0100671 /**
672 * Wraps a PeerConnection created by the factory. Can be used by clients that want to implement
673 * their PeerConnection creation in JNI.
674 */
675 public PeerConnection(NativePeerConnectionFactory factory) {
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +0100676 this(factory.createNativePeerConnection());
Sami Kalliomäki1ece1ed2017-12-20 11:59:22 +0100677 }
678
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +0100679 PeerConnection(long nativePeerConnection) {
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000680 this.nativePeerConnection = nativePeerConnection;
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000681 }
682
683 // JsepInterface.
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100684 public SessionDescription getLocalDescription() {
685 return nativeGetLocalDescription();
686 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000687
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100688 public SessionDescription getRemoteDescription() {
689 return nativeGetRemoteDescription();
690 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000691
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100692 public DataChannel createDataChannel(String label, DataChannel.Init init) {
693 return nativeCreateDataChannel(label, init);
694 }
henrike@webrtc.org723d6832013-07-12 16:04:50 +0000695
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100696 public void createOffer(SdpObserver observer, MediaConstraints constraints) {
697 nativeCreateOffer(observer, constraints);
698 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000699
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100700 public void createAnswer(SdpObserver observer, MediaConstraints constraints) {
701 nativeCreateAnswer(observer, constraints);
702 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000703
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100704 public void setLocalDescription(SdpObserver observer, SessionDescription sdp) {
705 nativeSetLocalDescription(observer, sdp);
706 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000707
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100708 public void setRemoteDescription(SdpObserver observer, SessionDescription sdp) {
709 nativeSetRemoteDescription(observer, sdp);
710 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000711
Seth Hampsonc384e142018-03-06 15:47:10 -0800712 /**
713 * Enables/disables playout of received audio streams. Enabled by default.
714 *
715 * Note that even if playout is enabled, streams will only be played out if
716 * the appropriate SDP is also applied. The main purpose of this API is to
717 * be able to control the exact time when audio playout starts.
718 */
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100719 public void setAudioPlayout(boolean playout) {
720 nativeSetAudioPlayout(playout);
721 }
henrika5f6bf242017-11-01 11:06:56 +0100722
Seth Hampsonc384e142018-03-06 15:47:10 -0800723 /**
724 * Enables/disables recording of transmitted audio streams. Enabled by default.
725 *
726 * Note that even if recording is enabled, streams will only be recorded if
727 * the appropriate SDP is also applied. The main purpose of this API is to
728 * be able to control the exact time when audio recording starts.
729 */
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100730 public void setAudioRecording(boolean recording) {
731 nativeSetAudioRecording(recording);
732 }
henrika5f6bf242017-11-01 11:06:56 +0100733
deadbeef5d0b6d82017-01-09 16:05:28 -0800734 public boolean setConfiguration(RTCConfiguration config) {
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +0100735 return nativeSetConfiguration(config);
deadbeef5d0b6d82017-01-09 16:05:28 -0800736 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000737
738 public boolean addIceCandidate(IceCandidate candidate) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100739 return nativeAddIceCandidate(candidate.sdpMid, candidate.sdpMLineIndex, candidate.sdp);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000740 }
741
Honghai Zhang7fb69db2016-03-14 11:59:18 -0700742 public boolean removeIceCandidates(final IceCandidate[] candidates) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100743 return nativeRemoveIceCandidates(candidates);
Honghai Zhang7fb69db2016-03-14 11:59:18 -0700744 }
745
Seth Hampsonc384e142018-03-06 15:47:10 -0800746 /**
747 * Adds a new MediaStream to be sent on this peer connection.
748 * Note: This method is not supported with SdpSemantics.UNIFIED_PLAN. Please
749 * use addTrack instead.
750 */
perkj@webrtc.orgc2dd5ee2014-11-04 11:31:29 +0000751 public boolean addStream(MediaStream stream) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100752 boolean ret = nativeAddLocalStream(stream.nativeStream);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000753 if (!ret) {
754 return false;
755 }
756 localStreams.add(stream);
757 return true;
758 }
759
Seth Hampsonc384e142018-03-06 15:47:10 -0800760 /**
761 * Removes the given media stream from this peer connection.
762 * This method is not supported with SdpSemantics.UNIFIED_PLAN. Please use
763 * removeTrack instead.
764 */
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000765 public void removeStream(MediaStream stream) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100766 nativeRemoveLocalStream(stream.nativeStream);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000767 localStreams.remove(stream);
768 }
769
deadbeef7a246882017-08-09 08:40:10 -0700770 /**
771 * Creates an RtpSender without a track.
Seth Hampsonc384e142018-03-06 15:47:10 -0800772 *
773 * <p>This method allows an application to cause the PeerConnection to negotiate
deadbeef7a246882017-08-09 08:40:10 -0700774 * sending/receiving a specific media type, but without having a track to
775 * send yet.
Seth Hampsonc384e142018-03-06 15:47:10 -0800776 *
777 * <p>When the application does want to begin sending a track, it can call
deadbeef7a246882017-08-09 08:40:10 -0700778 * RtpSender.setTrack, which doesn't require any additional SDP negotiation.
Seth Hampsonc384e142018-03-06 15:47:10 -0800779 *
780 * <p>Example use:
deadbeef7a246882017-08-09 08:40:10 -0700781 * <pre>
782 * {@code
783 * audioSender = pc.createSender("audio", "stream1");
784 * videoSender = pc.createSender("video", "stream1");
785 * // Do normal SDP offer/answer, which will kick off ICE/DTLS and negotiate
786 * // media parameters....
787 * // Later, when the endpoint is ready to actually begin sending:
788 * audioSender.setTrack(audioTrack, false);
789 * videoSender.setTrack(videoTrack, false);
790 * }
791 * </pre>
Seth Hampsonc384e142018-03-06 15:47:10 -0800792 * <p>Note: This corresponds most closely to "addTransceiver" in the official
deadbeef7a246882017-08-09 08:40:10 -0700793 * WebRTC API, in that it creates a sender without a track. It was
794 * implemented before addTransceiver because it provides useful
795 * functionality, and properly implementing transceivers would have required
796 * a great deal more work.
797 *
Seth Hampsonc384e142018-03-06 15:47:10 -0800798 * <p>Note: This is only available with SdpSemantics.PLAN_B specified. Please use
799 * addTransceiver instead.
800 *
deadbeef7a246882017-08-09 08:40:10 -0700801 * @param kind Corresponds to MediaStreamTrack kinds (must be "audio" or
802 * "video").
803 * @param stream_id The ID of the MediaStream that this sender's track will
804 * be associated with when SDP is applied to the remote
805 * PeerConnection. If createSender is used to create an
806 * audio and video sender that should be synchronized, they
807 * should use the same stream ID.
808 * @return A new RtpSender object if successful, or null otherwise.
809 */
deadbeefbd7d8f72015-12-18 16:58:44 -0800810 public RtpSender createSender(String kind, String stream_id) {
Seth Hampsonc384e142018-03-06 15:47:10 -0800811 RtpSender newSender = nativeCreateSender(kind, stream_id);
812 if (newSender != null) {
813 senders.add(newSender);
deadbeefee524f72015-12-02 11:27:40 -0800814 }
Seth Hampsonc384e142018-03-06 15:47:10 -0800815 return newSender;
deadbeefee524f72015-12-02 11:27:40 -0800816 }
817
Seth Hampsonc384e142018-03-06 15:47:10 -0800818 /**
819 * Gets all RtpSenders associated with this peer connection.
820 * Note that calling getSenders will dispose of the senders previously
821 * returned.
822 */
deadbeef4139c0f2015-10-06 12:29:25 -0700823 public List<RtpSender> getSenders() {
824 for (RtpSender sender : senders) {
825 sender.dispose();
826 }
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100827 senders = nativeGetSenders();
deadbeef4139c0f2015-10-06 12:29:25 -0700828 return Collections.unmodifiableList(senders);
829 }
830
Seth Hampsonc384e142018-03-06 15:47:10 -0800831 /**
832 * Gets all RtpReceivers associated with this peer connection.
833 * Note that calling getReceivers will dispose of the receivers previously
834 * returned.
835 */
deadbeef4139c0f2015-10-06 12:29:25 -0700836 public List<RtpReceiver> getReceivers() {
837 for (RtpReceiver receiver : receivers) {
838 receiver.dispose();
839 }
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100840 receivers = nativeGetReceivers();
deadbeef4139c0f2015-10-06 12:29:25 -0700841 return Collections.unmodifiableList(receivers);
842 }
843
Seth Hampsonc384e142018-03-06 15:47:10 -0800844 /**
845 * Gets all RtpTransceivers associated with this peer connection.
846 * Note that calling getTransceivers will dispose of the transceivers previously
847 * returned.
848 * Note: This is only available with SdpSemantics.UNIFIED_PLAN specified.
849 */
850 public List<RtpTransceiver> getTransceivers() {
851 for (RtpTransceiver transceiver : transceivers) {
852 transceiver.dispose();
853 }
854 transceivers = nativeGetTransceivers();
855 return Collections.unmodifiableList(transceivers);
856 }
857
858 /**
859 * Adds a new media stream track to be sent on this peer connection, and returns
860 * the newly created RtpSender. If streamIds are specified, the RtpSender will
861 * be associated with the streams specified in the streamIds list.
862 *
863 * @throws IllegalStateException if an error accors in C++ addTrack.
864 * An error can occur if:
865 * - A sender already exists for the track.
866 * - The peer connection is closed.
867 */
868 public RtpSender addTrack(MediaStreamTrack track) {
869 return addTrack(track, Collections.emptyList());
870 }
871
872 public RtpSender addTrack(MediaStreamTrack track, List<String> streamIds) {
873 if (track == null || streamIds == null) {
874 throw new NullPointerException("No MediaStreamTrack specified in addTrack.");
875 }
876 RtpSender newSender = nativeAddTrack(track.nativeTrack, streamIds);
877 if (newSender == null) {
878 throw new IllegalStateException("C++ addTrack failed.");
879 }
880 senders.add(newSender);
881 return newSender;
882 }
883
884 /**
885 * Stops sending media from sender. The sender will still appear in getSenders. Future
886 * calls to createOffer will mark the m section for the corresponding transceiver as
887 * receive only or inactive, as defined in JSEP. Returns true on success.
888 */
889 public boolean removeTrack(RtpSender sender) {
890 if (sender == null) {
891 throw new NullPointerException("No RtpSender specified for removeTrack.");
892 }
893 return nativeRemoveTrack(sender.nativeRtpSender);
894 }
895
896 /**
897 * Creates a new RtpTransceiver and adds it to the set of transceivers. Adding a
898 * transceiver will cause future calls to CreateOffer to add a media description
899 * for the corresponding transceiver.
900 *
901 * <p>The initial value of |mid| in the returned transceiver is null. Setting a
902 * new session description may change it to a non-null value.
903 *
904 * <p>https://w3c.github.io/webrtc-pc/#dom-rtcpeerconnection-addtransceiver
905 *
906 * <p>If a MediaStreamTrack is specified then a transceiver will be added with a
907 * sender set to transmit the given track. The kind
908 * of the transceiver (and sender/receiver) will be derived from the kind of
909 * the track.
910 *
911 * <p>If MediaType is specified then a transceiver will be added based upon that type.
912 * This can be either MEDIA_TYPE_AUDIO or MEDIA_TYPE_VIDEO.
913 *
914 * <p>Optionally, an RtpTransceiverInit structure can be specified to configure
915 * the transceiver from construction. If not specified, the transceiver will
916 * default to having a direction of kSendRecv and not be part of any streams.
917 *
918 * <p>Note: These methods are only available with SdpSemantics.UNIFIED_PLAN specified.
919 * @throws IllegalStateException if an error accors in C++ addTransceiver
920 */
921 public RtpTransceiver addTransceiver(MediaStreamTrack track) {
922 return addTransceiver(track, new RtpTransceiver.RtpTransceiverInit());
923 }
924
925 public RtpTransceiver addTransceiver(
926 MediaStreamTrack track, RtpTransceiver.RtpTransceiverInit init) {
927 if (track == null) {
928 throw new NullPointerException("No MediaStreamTrack specified for addTransceiver.");
929 }
930 if (init == null) {
931 init = new RtpTransceiver.RtpTransceiverInit();
932 }
933 RtpTransceiver newTransceiver = nativeAddTransceiverWithTrack(track.nativeTrack, init);
934 if (newTransceiver == null) {
935 throw new IllegalStateException("C++ addTransceiver failed.");
936 }
937 transceivers.add(newTransceiver);
938 return newTransceiver;
939 }
940
941 public RtpTransceiver addTransceiver(MediaStreamTrack.MediaType mediaType) {
942 return addTransceiver(mediaType, new RtpTransceiver.RtpTransceiverInit());
943 }
944
945 public RtpTransceiver addTransceiver(
946 MediaStreamTrack.MediaType mediaType, RtpTransceiver.RtpTransceiverInit init) {
947 if (mediaType == null) {
948 throw new NullPointerException("No MediaType specified for addTransceiver.");
949 }
950 if (init == null) {
951 init = new RtpTransceiver.RtpTransceiverInit();
952 }
953 RtpTransceiver newTransceiver = nativeAddTransceiverOfType(mediaType, init);
954 if (newTransceiver == null) {
955 throw new IllegalStateException("C++ addTransceiver failed.");
956 }
957 transceivers.add(newTransceiver);
958 return newTransceiver;
959 }
960
deadbeef82215872017-04-18 10:27:51 -0700961 // Older, non-standard implementation of getStats.
962 @Deprecated
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000963 public boolean getStats(StatsObserver observer, MediaStreamTrack track) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100964 return nativeOldGetStats(observer, (track == null) ? 0 : track.nativeTrack);
deadbeef82215872017-04-18 10:27:51 -0700965 }
966
Seth Hampsonc384e142018-03-06 15:47:10 -0800967 /**
968 * Gets stats using the new stats collection API, see webrtc/api/stats/. These
969 * will replace old stats collection API when the new API has matured enough.
970 */
deadbeef82215872017-04-18 10:27:51 -0700971 public void getStats(RTCStatsCollectorCallback callback) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100972 nativeNewGetStats(callback);
henrike@webrtc.org28e20752013-07-10 00:45:36 +0000973 }
974
Seth Hampsonc384e142018-03-06 15:47:10 -0800975 /**
976 * Limits the bandwidth allocated for all RTP streams sent by this
977 * PeerConnection. Pass null to leave a value unchanged.
978 */
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100979 public boolean setBitrate(Integer min, Integer current, Integer max) {
980 return nativeSetBitrate(min, current, max);
981 }
zsteind89b0bc2017-08-03 11:11:40 -0700982
Seth Hampsonc384e142018-03-06 15:47:10 -0800983 /**
984 * Starts recording an RTC event log.
985 *
986 * Ownership of the file is transfered to the native code. If an RTC event
987 * log is already being recorded, it will be stopped and a new one will start
988 * using the provided file. Logging will continue until the stopRtcEventLog
989 * function is called. The max_size_bytes argument is ignored, it is added
990 * for future use.
991 */
ivoc0c6f0f62016-07-06 04:34:23 -0700992 public boolean startRtcEventLog(int file_descriptor, int max_size_bytes) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +0100993 return nativeStartRtcEventLog(file_descriptor, max_size_bytes);
ivoc14d5dbe2016-07-04 07:06:55 -0700994 }
995
Seth Hampsonc384e142018-03-06 15:47:10 -0800996 /**
997 * Stops recording an RTC event log. If no RTC event log is currently being
998 * recorded, this call will have no effect.
999 */
ivoc14d5dbe2016-07-04 07:06:55 -07001000 public void stopRtcEventLog() {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001001 nativeStopRtcEventLog();
ivoc14d5dbe2016-07-04 07:06:55 -07001002 }
1003
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001004 // TODO(fischman): add support for DTMF-related methods once that API
1005 // stabilizes.
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001006 public SignalingState signalingState() {
1007 return nativeSignalingState();
1008 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001009
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001010 public IceConnectionState iceConnectionState() {
1011 return nativeIceConnectionState();
1012 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001013
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001014 public IceGatheringState iceGatheringState() {
1015 return nativeIceGatheringState();
1016 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001017
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001018 public void close() {
1019 nativeClose();
1020 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001021
deadbeef43697f62017-09-12 10:52:14 -07001022 /**
1023 * Free native resources associated with this PeerConnection instance.
Seth Hampsonc384e142018-03-06 15:47:10 -08001024 *
deadbeef43697f62017-09-12 10:52:14 -07001025 * This method removes a reference count from the C++ PeerConnection object,
1026 * which should result in it being destroyed. It also calls equivalent
1027 * "dispose" methods on the Java objects attached to this PeerConnection
1028 * (streams, senders, receivers), such that their associated C++ objects
1029 * will also be destroyed.
Seth Hampsonc384e142018-03-06 15:47:10 -08001030 *
1031 * <p>Note that this method cannot be safely called from an observer callback
deadbeef43697f62017-09-12 10:52:14 -07001032 * (PeerConnection.Observer, DataChannel.Observer, etc.). If you want to, for
1033 * example, destroy the PeerConnection after an "ICE failed" callback, you
1034 * must do this asynchronously (in other words, unwind the stack first). See
1035 * <a href="https://bugs.chromium.org/p/webrtc/issues/detail?id=3721">bug
1036 * 3721</a> for more details.
1037 */
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001038 public void dispose() {
1039 close();
1040 for (MediaStream stream : localStreams) {
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001041 nativeRemoveLocalStream(stream.nativeStream);
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001042 stream.dispose();
1043 }
1044 localStreams.clear();
deadbeef4139c0f2015-10-06 12:29:25 -07001045 for (RtpSender sender : senders) {
1046 sender.dispose();
1047 }
1048 senders.clear();
1049 for (RtpReceiver receiver : receivers) {
1050 receiver.dispose();
1051 }
Seth Hampsonc384e142018-03-06 15:47:10 -08001052 for (RtpTransceiver transceiver : transceivers) {
1053 transceiver.dispose();
1054 }
1055 transceivers.clear();
deadbeef4139c0f2015-10-06 12:29:25 -07001056 receivers.clear();
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +01001057 nativeFreeOwnedPeerConnection(nativePeerConnection);
1058 }
1059
1060 /** Returns a pointer to the native webrtc::PeerConnectionInterface. */
1061 public long getNativePeerConnection() {
1062 return nativeGetNativePeerConnection();
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001063 }
1064
Magnus Jedvert9060eb12017-12-12 12:52:54 +01001065 @CalledByNative
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +01001066 long getNativeOwnedPeerConnection() {
Magnus Jedvert9060eb12017-12-12 12:52:54 +01001067 return nativePeerConnection;
1068 }
1069
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001070 public static long createNativePeerConnectionObserver(Observer observer) {
1071 return nativeCreatePeerConnectionObserver(observer);
1072 }
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001073
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +01001074 private native long nativeGetNativePeerConnection();
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001075 private native SessionDescription nativeGetLocalDescription();
1076 private native SessionDescription nativeGetRemoteDescription();
1077 private native DataChannel nativeCreateDataChannel(String label, DataChannel.Init init);
1078 private native void nativeCreateOffer(SdpObserver observer, MediaConstraints constraints);
1079 private native void nativeCreateAnswer(SdpObserver observer, MediaConstraints constraints);
1080 private native void nativeSetLocalDescription(SdpObserver observer, SessionDescription sdp);
1081 private native void nativeSetRemoteDescription(SdpObserver observer, SessionDescription sdp);
1082 private native void nativeSetAudioPlayout(boolean playout);
1083 private native void nativeSetAudioRecording(boolean recording);
1084 private native boolean nativeSetBitrate(Integer min, Integer current, Integer max);
1085 private native SignalingState nativeSignalingState();
1086 private native IceConnectionState nativeIceConnectionState();
1087 private native IceGatheringState nativeIceGatheringState();
1088 private native void nativeClose();
1089 private static native long nativeCreatePeerConnectionObserver(Observer observer);
Sami Kalliomäkice5c19a2018-01-15 09:28:34 +01001090 private static native void nativeFreeOwnedPeerConnection(long ownedPeerConnection);
1091 private native boolean nativeSetConfiguration(RTCConfiguration config);
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001092 private native boolean nativeAddIceCandidate(
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001093 String sdpMid, int sdpMLineIndex, String iceCandidateSdp);
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001094 private native boolean nativeRemoveIceCandidates(final IceCandidate[] candidates);
1095 private native boolean nativeAddLocalStream(long stream);
1096 private native void nativeRemoveLocalStream(long stream);
1097 private native boolean nativeOldGetStats(StatsObserver observer, long nativeTrack);
1098 private native void nativeNewGetStats(RTCStatsCollectorCallback callback);
1099 private native RtpSender nativeCreateSender(String kind, String stream_id);
1100 private native List<RtpSender> nativeGetSenders();
1101 private native List<RtpReceiver> nativeGetReceivers();
Seth Hampsonc384e142018-03-06 15:47:10 -08001102 private native List<RtpTransceiver> nativeGetTransceivers();
1103 private native RtpSender nativeAddTrack(long track, List<String> streamIds);
1104 private native boolean nativeRemoveTrack(long sender);
1105 private native RtpTransceiver nativeAddTransceiverWithTrack(
1106 long track, RtpTransceiver.RtpTransceiverInit init);
1107 private native RtpTransceiver nativeAddTransceiverOfType(
1108 MediaStreamTrack.MediaType mediaType, RtpTransceiver.RtpTransceiverInit init);
Magnus Jedvert84d8ae52017-12-20 15:12:10 +01001109 private native boolean nativeStartRtcEventLog(int file_descriptor, int max_size_bytes);
1110 private native void nativeStopRtcEventLog();
henrike@webrtc.org28e20752013-07-10 00:45:36 +00001111}