3 * Copyright 2013, Google Inc.
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
8 * 1. Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright notice,
11 * this list of conditions and the following disclaimer in the documentation
12 * and/or other materials provided with the distribution.
13 * 3. The name of the author may not be used to endorse or promote products
14 * derived from this software without specific prior written permission.
16 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
18 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
19 * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
22 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
23 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
24 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
25 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 import java.util.LinkedList;
32 import java.util.List;
35 * Java-land version of the PeerConnection APIs; wraps the C++ API
36 * http://www.webrtc.org/reference/native-apis, which in turn is inspired by the
37 * JS APIs: http://dev.w3.org/2011/webrtc/editor/webrtc.html and
38 * http://www.w3.org/TR/mediacapture-streams/
40 public class PeerConnection {
42 System.loadLibrary("jingle_peerconnection_so");
45 /** Tracks PeerConnectionInterface::IceGatheringState */
46 public enum IceGatheringState { NEW, GATHERING, COMPLETE };
49 /** Tracks PeerConnectionInterface::IceConnectionState */
50 public enum IceConnectionState {
51 NEW, CHECKING, CONNECTED, COMPLETED, FAILED, DISCONNECTED, CLOSED
54 /** Tracks PeerConnectionInterface::SignalingState */
55 public enum SignalingState {
56 STABLE, HAVE_LOCAL_OFFER, HAVE_LOCAL_PRANSWER, HAVE_REMOTE_OFFER,
57 HAVE_REMOTE_PRANSWER, CLOSED
60 /** Java version of PeerConnectionObserver. */
61 public static interface Observer {
62 /** Triggered when the SignalingState changes. */
63 public void onSignalingChange(SignalingState newState);
65 /** Triggered when the IceConnectionState changes. */
66 public void onIceConnectionChange(IceConnectionState newState);
68 /** Triggered when the IceGatheringState changes. */
69 public void onIceGatheringChange(IceGatheringState newState);
71 /** Triggered when a new ICE candidate has been found. */
72 public void onIceCandidate(IceCandidate candidate);
74 /** Triggered when media is received on a new stream from remote peer. */
75 public void onAddStream(MediaStream stream);
77 /** Triggered when a remote peer close a stream. */
78 public void onRemoveStream(MediaStream stream);
80 /** Triggered when a remote peer opens a DataChannel. */
81 public void onDataChannel(DataChannel dataChannel);
83 /** Triggered when renegotiation is necessary. */
84 public void onRenegotiationNeeded();
87 /** Java version of PeerConnectionInterface.IceServer. */
88 public static class IceServer {
89 public final String uri;
90 public final String username;
91 public final String password;
93 /** Convenience constructor for STUN servers. */
94 public IceServer(String uri) {
98 public IceServer(String uri, String username, String password) {
100 this.username = username;
101 this.password = password;
104 public String toString() {
105 return uri + "[" + username + ":" + password + "]";
109 private final List<MediaStream> localStreams;
110 private final long nativePeerConnection;
111 private final long nativeObserver;
113 PeerConnection(long nativePeerConnection, long nativeObserver) {
114 this.nativePeerConnection = nativePeerConnection;
115 this.nativeObserver = nativeObserver;
116 localStreams = new LinkedList<MediaStream>();
120 public native SessionDescription getLocalDescription();
122 public native SessionDescription getRemoteDescription();
124 public native DataChannel createDataChannel(
125 String label, DataChannel.Init init);
127 public native void createOffer(
128 SdpObserver observer, MediaConstraints constraints);
130 public native void createAnswer(
131 SdpObserver observer, MediaConstraints constraints);
133 public native void setLocalDescription(
134 SdpObserver observer, SessionDescription sdp);
136 public native void setRemoteDescription(
137 SdpObserver observer, SessionDescription sdp);
139 public native boolean updateIce(
140 List<IceServer> iceServers, MediaConstraints constraints);
142 public boolean addIceCandidate(IceCandidate candidate) {
143 return nativeAddIceCandidate(
144 candidate.sdpMid, candidate.sdpMLineIndex, candidate.sdp);
147 public boolean addStream(MediaStream stream) {
148 boolean ret = nativeAddLocalStream(stream.nativeStream);
152 localStreams.add(stream);
156 public void removeStream(MediaStream stream) {
157 nativeRemoveLocalStream(stream.nativeStream);
158 localStreams.remove(stream);
161 public boolean getStats(StatsObserver observer, MediaStreamTrack track) {
162 return nativeGetStats(observer, (track == null) ? 0 : track.nativeTrack);
165 // TODO(fischman): add support for DTMF-related methods once that API
167 public native SignalingState signalingState();
169 public native IceConnectionState iceConnectionState();
171 public native IceGatheringState iceGatheringState();
173 public native void close();
175 public void dispose() {
177 for (MediaStream stream : localStreams) {
178 nativeRemoveLocalStream(stream.nativeStream);
181 localStreams.clear();
182 freePeerConnection(nativePeerConnection);
183 freeObserver(nativeObserver);
186 private static native void freePeerConnection(long nativePeerConnection);
188 private static native void freeObserver(long nativeObserver);
190 private native boolean nativeAddIceCandidate(
191 String sdpMid, int sdpMLineIndex, String iceCandidateSdp);
193 private native boolean nativeAddLocalStream(long nativeStream);
195 private native void nativeRemoveLocalStream(long nativeStream);
197 private native boolean nativeGetStats(
198 StatsObserver observer, long nativeTrack);