Advertisement
Guest User

webrtc_android_kakopappa

a guest
Mar 9th, 2015
356
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 12.12 KB | None | 0 0
  1. package fr.pchab.AndroidRTC;
  2.  
  3. import java.util.HashMap;
  4. import java.util.LinkedList;
  5.  
  6. import org.json.JSONArray;
  7. import org.json.JSONException;
  8. import org.json.JSONObject;
  9. import org.webrtc.DataChannel;
  10. import org.webrtc.IceCandidate;
  11. import org.webrtc.MediaConstraints;
  12. import org.webrtc.MediaStream;
  13. import org.webrtc.PeerConnection;
  14. import org.webrtc.PeerConnectionFactory;
  15. import org.webrtc.SdpObserver;
  16. import org.webrtc.SessionDescription;
  17. import org.webrtc.VideoCapturer;
  18.  
  19. import android.content.Context;
  20. import android.media.AudioManager;
  21. import android.os.Handler;
  22. import android.util.Log;
  23.  
  24. import com.koushikdutta.async.http.socketio.Acknowledge;
  25. import com.koushikdutta.async.http.socketio.ConnectCallback;
  26. import com.koushikdutta.async.http.socketio.EventCallback;
  27. import com.koushikdutta.async.http.socketio.SocketIOClient;
  28.  
  29. class WebRtcClient {
  30. private final static int MAX_PEER = 2;
  31. private boolean[] endPoints = new boolean[MAX_PEER];
  32. private PeerConnectionFactory factory;
  33. private HashMap<String, Peer> peers = new HashMap<String, Peer>();
  34. private LinkedList<PeerConnection.IceServer> iceServers = new LinkedList<PeerConnection.IceServer>();
  35. private MediaConstraints pcConstraints = new MediaConstraints();
  36. private MediaStream lMS;
  37. private RTCListener mListener;
  38. private SocketIOClient client;
  39. private final MessageHandler messageHandler = new MessageHandler();
  40. private final static String TAG = WebRtcClient.class.getCanonicalName();
  41.  
  42. public interface RTCListener{
  43. void onCallReady(String callId);
  44.  
  45. void onStatusChanged(String newStatus);
  46.  
  47. void onLocalStream(MediaStream localStream);
  48.  
  49. void onAddRemoteStream(MediaStream remoteStream, int endPoint);
  50.  
  51. void onRemoveRemoteStream(MediaStream remoteStream, int endPoint);
  52. }
  53.  
  54. private interface Command{
  55. void execute(String peerId, JSONObject payload) throws JSONException;
  56. }
  57.  
  58. private class CreateOfferCommand implements Command{
  59. public void execute(String peerId, JSONObject payload) throws JSONException {
  60. Log.d(TAG,"CreateOfferCommand");
  61. Peer peer = peers.get(peerId);
  62. peer.pc.createOffer(peer, pcConstraints);
  63. }
  64. }
  65.  
  66. private class CreateAnswerCommand implements Command{
  67. public void execute(String peerId, JSONObject payload) throws JSONException {
  68. Log.d(TAG,"CreateAnswerCommand");
  69. Peer peer = peers.get(peerId);
  70. SessionDescription sdp = new SessionDescription(
  71. SessionDescription.Type.fromCanonicalForm(payload.getString("type")),
  72. payload.getString("sdp")
  73. );
  74. peer.pc.setRemoteDescription(peer, sdp);
  75. peer.pc.createAnswer(peer, pcConstraints);
  76. }
  77. }
  78.  
  79. private class SetRemoteSDPCommand implements Command{
  80. public void execute(String peerId, JSONObject payload) throws JSONException {
  81. Log.d(TAG,"SetRemoteSDPCommand");
  82. Peer peer = peers.get(peerId);
  83. SessionDescription sdp = new SessionDescription(
  84. SessionDescription.Type.fromCanonicalForm(payload.getString("type")),
  85. payload.getString("sdp")
  86. );
  87. peer.pc.setRemoteDescription(peer, sdp);
  88. }
  89. }
  90.  
  91. private class AddIceCandidateCommand implements Command{
  92. public void execute(String peerId, JSONObject payload) throws JSONException {
  93. Log.d(TAG,"AddIceCandidateCommand");
  94. PeerConnection pc = peers.get(peerId).pc;
  95. if (pc.getRemoteDescription() != null) {
  96. IceCandidate candidate = new IceCandidate(
  97. payload.getString("id"),
  98. payload.getInt("label"),
  99. payload.getString("candidate")
  100. );
  101. pc.addIceCandidate(candidate);
  102. }
  103. }
  104. }
  105.  
  106. public void sendMessage(String to, String type, JSONObject payload) throws JSONException {
  107. JSONObject message = new JSONObject();
  108. message.put("to", to);
  109. message.put("type", type);
  110. message.put("payload", payload);
  111. client.emit("message", new JSONArray().put(message));
  112. }
  113.  
  114. private class MessageHandler implements EventCallback {
  115. private HashMap<String, Command> commandMap;
  116.  
  117. public MessageHandler() {
  118. this.commandMap = new HashMap<String, Command>();
  119. commandMap.put("init", new CreateOfferCommand());
  120. commandMap.put("offer", new CreateAnswerCommand());
  121. commandMap.put("answer", new SetRemoteSDPCommand());
  122. commandMap.put("candidate", new AddIceCandidateCommand());
  123. }
  124.  
  125. @Override
  126. public void onEvent(String s, JSONArray jsonArray, Acknowledge acknowledge) {
  127. try {
  128. Log.d(TAG,"MessageHandler.onEvent() "+ (s == null ? "nil" : s));
  129. if(s.equals("id")) {
  130. mListener.onCallReady(jsonArray.getString(0));
  131. } else {
  132. JSONObject json = jsonArray.getJSONObject(0);
  133. String from = json.getString("from");
  134. String type = json.getString("type");
  135. JSONObject payload = null;
  136. if(!type.equals("init")) {
  137. payload = json.getJSONObject("payload");
  138. }
  139.  
  140. // if peer is unknown, try to add him
  141. if(!peers.containsKey(from)) {
  142. // if MAX_PEER is reach, ignore the call
  143. int endPoint = findEndPoint();
  144. if(endPoint != MAX_PEER) {
  145. addPeer(from, endPoint);
  146.  
  147. commandMap.get(type).execute(from, payload);
  148. }
  149. } else {
  150. commandMap.get(type).execute(from, payload);
  151. }
  152. }
  153. } catch (JSONException e) {
  154. e.printStackTrace();
  155. }
  156. }
  157. }
  158.  
  159. private class Peer implements SdpObserver, PeerConnection.Observer{
  160. private PeerConnection pc;
  161. private String id;
  162. private int endPoint;
  163.  
  164. @Override
  165. public void onCreateSuccess(final SessionDescription sdp) {
  166. try {
  167. JSONObject payload = new JSONObject();
  168. payload.put("type", sdp.type.canonicalForm());
  169. payload.put("sdp", sdp.description);
  170. sendMessage(id, sdp.type.canonicalForm(), payload);
  171. pc.setLocalDescription(Peer.this, sdp);
  172. } catch (JSONException e) {
  173. e.printStackTrace();
  174. }
  175. }
  176.  
  177. @Override
  178. public void onSetSuccess() {}
  179.  
  180. @Override
  181. public void onCreateFailure(String s) {}
  182.  
  183. @Override
  184. public void onSetFailure(String s) {}
  185.  
  186. @Override
  187. public void onSignalingChange(PeerConnection.SignalingState signalingState) {}
  188.  
  189. @Override
  190. public void onIceConnectionChange(PeerConnection.IceConnectionState iceConnectionState) {
  191. if(iceConnectionState == PeerConnection.IceConnectionState.DISCONNECTED) {
  192. removePeer(id);
  193. mListener.onStatusChanged("DISCONNECTED");
  194. }
  195. }
  196.  
  197. @Override
  198. public void onIceGatheringChange(PeerConnection.IceGatheringState iceGatheringState) {}
  199.  
  200. @Override
  201. public void onIceCandidate(final IceCandidate candidate) {
  202. try {
  203. JSONObject payload = new JSONObject();
  204. payload.put("label", candidate.sdpMLineIndex);
  205. payload.put("id", candidate.sdpMid);
  206. payload.put("candidate", candidate.sdp);
  207. sendMessage(id, "candidate", payload);
  208. } catch (JSONException e) {
  209. e.printStackTrace();
  210. }
  211. }
  212.  
  213. @Override
  214. public void onError() {}
  215.  
  216. @Override
  217. public void onAddStream(MediaStream mediaStream) {
  218. Log.d(TAG,"onAddStream "+mediaStream.label());
  219.  
  220. // remote streams are displayed from 1 to MAX_PEER (0 is localStream)
  221. mListener.onAddRemoteStream(mediaStream, endPoint+1);
  222. }
  223.  
  224. @Override
  225. public void onRemoveStream(MediaStream mediaStream) {
  226. mListener.onRemoveRemoteStream(mediaStream, endPoint);
  227.  
  228. removePeer(id);
  229. }
  230.  
  231. @Override
  232. public void onDataChannel(DataChannel dataChannel) {}
  233.  
  234. public Peer(String id, int endPoint) {
  235. Log.d(TAG,"new Peer: "+id + " " + endPoint);
  236. this.pc = factory.createPeerConnection(iceServers, pcConstraints, this);
  237. this.id = id;
  238. this.endPoint = endPoint;
  239.  
  240. pc.addStream(lMS, new MediaConstraints());
  241.  
  242. mListener.onStatusChanged("CONNECTING");
  243. }
  244. }
  245.  
  246. public WebRtcClient(RTCListener listener, String host, Context context) {
  247. mListener = listener;
  248. factory = new PeerConnectionFactory();
  249.  
  250. SocketIOClient.connect(host, new ConnectCallback() {
  251.  
  252. @Override
  253. public void onConnectCompleted(Exception ex, SocketIOClient socket) {
  254. if (ex != null) {
  255. Log.e(TAG,"WebRtcClient connect failed: "+ex.getMessage());
  256. return;
  257. }
  258. Log.d(TAG,"WebRtcClient connected.");
  259. client = socket;
  260.  
  261. // specify which events you are interested in receiving
  262. client.addListener("id", messageHandler);
  263. client.addListener("message", messageHandler);
  264. }
  265. }, new Handler());
  266.  
  267. iceServers.add(new PeerConnection.IceServer("stun:23.21.150.121"));
  268. iceServers.add(new PeerConnection.IceServer("stun:stun.l.google.com:19302"));
  269.  
  270. AudioManager audioManager =
  271. ((AudioManager) context.getSystemService(Context.AUDIO_SERVICE));
  272. audioManager.setMode(audioManager.isWiredHeadsetOn() ?
  273. AudioManager.MODE_IN_CALL : AudioManager.MODE_IN_COMMUNICATION);
  274. audioManager.setSpeakerphoneOn(!audioManager.isWiredHeadsetOn());
  275.  
  276.  
  277. pcConstraints.mandatory.add(new MediaConstraints.KeyValuePair("OfferToReceiveAudio", "true"));
  278. pcConstraints.mandatory.add(new MediaConstraints.KeyValuePair("OfferToReceiveVideo", "false"));
  279. }
  280.  
  281. /* public void setCamera(String cameraFacing, String height, String width){
  282. //MediaConstraints videoConstraints = new MediaConstraints();
  283. //videoConstraints.mandatory.add(new MediaConstraints.KeyValuePair("maxHeight", height));
  284. //videoConstraints.mandatory.add(new MediaConstraints.KeyValuePair("maxWidth", width));
  285.  
  286. //VideoSource videoSource = factory.createVideoSource(getVideoCapturer(cameraFacing), videoConstraints);
  287. lMS = factory.createLocalMediaStream("ARDAMS");
  288. //lMS.addTrack(factory.createVideoTrack("ARDAMSv0", videoSource));
  289. lMS.addTrack(factory.createAudioTrack("ARDAMSa0"));
  290.  
  291.  
  292. mListener.onLocalStream(lMS);
  293. }*/
  294.  
  295. public void setAudio() {
  296. lMS = factory.createLocalMediaStream("ARDAMS");
  297. lMS.addTrack(factory.createAudioTrack("ARDAMSa0"));
  298.  
  299. mListener.onLocalStream(lMS);
  300. }
  301.  
  302. private int findEndPoint() {
  303. for(int i = 0; i < MAX_PEER; i++) {
  304. if(!endPoints[i]) return i;
  305. }
  306. return MAX_PEER;
  307. }
  308.  
  309. public void start(String name, boolean privacy){
  310. try {
  311. JSONObject message = new JSONObject();
  312. message.put("name", name);
  313. client.emit("readyToStream", new JSONArray().put(message));
  314. } catch (JSONException e) {
  315. e.printStackTrace();
  316. }
  317. }
  318.  
  319. /*
  320. Cycle through likely device names for the camera and return the first
  321. capturer that works, or crash if none do.
  322. */
  323. private VideoCapturer getVideoCapturer(String cameraFacing) {
  324. int[] cameraIndex = { 0, 1 };
  325. int[] cameraOrientation = { 0, 90, 180, 270 };
  326. for (int index : cameraIndex) {
  327. for (int orientation : cameraOrientation) {
  328. String name = "Camera " + index + ", Facing " + cameraFacing +
  329. ", Orientation " + orientation;
  330. VideoCapturer capturer = VideoCapturer.create(name);
  331. if (capturer != null) {
  332. return capturer;
  333. }
  334. }
  335. }
  336. throw new RuntimeException("Failed to open capturer");
  337. }
  338.  
  339. private void addPeer(String id, int endPoint) {
  340. Peer peer = new Peer(id, endPoint);
  341. peers.put(id, peer);
  342.  
  343. endPoints[endPoint] = true;
  344. }
  345.  
  346. private void removePeer(String id) {
  347. Peer peer = peers.get(id);
  348. peer.pc.close();
  349. peer.pc.dispose();
  350. peers.remove(peer.id);
  351.  
  352. endPoints[peer.endPoint] = false;
  353. }
  354. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement