function init() {
	console.log('Connecting to signaling server');
	signalingSocket = io(SIGNALING_SERVER);
	signalingSocket = io();

	signalingSocket.on('connect', function() {
		console.log('Connected to signaling server');
		if (localMediaStream) joinChannel(ROOM_ID, {});
		else
			setup_local_media(function() {
				// Join the channel once user gives access to microphone & webcam
				joinChannel(ROOM_ID, {});
			});
	});
	signalingSocket.on('disconnect', function() {
		for (peer_id in peerMediaElements) {
			document.body.removeChild(peerMediaElements[peer_id].parentNode);
			resizeVideos();
		}
		for (peer_id in peers) {
			peers[peer_id].close();
		}

		peers = {};
		peerMediaElements = {};
	});

	function joinChannel(channel, userdata) {
		signalingSocket.emit('join', { channel: channel, userdata: userdata });
	}
	signalingSocket.on('addPeer', function(config) {
		var peer_id = config.peer_id;
		if (peer_id in peers) return;
		peerConnection = new RTCPeerConnection({ iceServers: ICE_SERVERS }, { optional: [{ DtlsSrtpKeyAgreement: true }] } // this will no longer be needed by chrome eventually (supposedly), but is necessary for now to get firefox to talk to chrome
		);
		peers[peer_id] = peerConnection;

		peerConnection.onicecandidate = function(event) {
			if (event.candidate) {
				signalingSocket.emit('relayICECandidate', {
					peer_id: peer_id,
					ice_candidate: {
						sdpMLineIndex: event.candidate.sdpMLineIndex,
						candidate: event.candidate.candidate
					}
				});
			}
		};
		peerConnection.onaddstream = function(event) {
			const videoWrap = document.createElement('div');
			videoWrap.className = 'video';
			const remoteMedia = document.createElement('video');
			videoWrap.appendChild(remoteMedia);
			remoteMedia.setAttribute('playsinline', true);
			remoteMedia.mediaGroup = 'remotevideo';
			remoteMedia.autoplay = true;
			remoteMedia.controls = false;
			peerMediaElements[peer_id] = remoteMedia;
			document.body.appendChild(videoWrap);
			document.getElementById('message').style.display = 'none';

			attachMediaStream(remoteMedia, event.stream);
			resizeVideos();
		};

		/* Add our local stream */
		peerConnection.addStream(localMediaStream);

		if (config.should_create_offer) {
			peerConnection.createOffer(
				function(local_description) {
					peerConnection.setLocalDescription(
						local_description,
						function() {
							signalingSocket.emit('relaySessionDescription', {
								peer_id: peer_id,
								session_description: local_description
							});
						},
						function(err) {
							console.log(err);
							alert('Offer setLocalDescription failed!');
						}
					);
				},
				function(error) {
					console.log('Error sending offer: ', error);
				}
			);
		}
	});

	signalingSocket.on('sessionDescription', function(config) {
		var peer_id = config.peer_id;
		var peer = peers[peer_id];
		var remote_description = config.session_description;

		var desc = new RTCSessionDescription(remote_description);
		var stuff = peer.setRemoteDescription(
			desc,
			function() {
				if (remote_description.type == 'offer') {
					peer.createAnswer(
						function(local_description) {
							peer.setLocalDescription(
								local_description,
								function() {
									signalingSocket.emit('relaySessionDescription', {
										peer_id: peer_id,
										session_description: local_description
									});
								},
								function(err) {
									console.log(err);
									alert('Answer setLocalDescription failed!');
								}
							);
						},
						function(error) {
							console.log('Error creating answer: ', error);
						}
					);
				}
			},
			function(error) {
				console.log('setRemoteDescription error: ', error);
			}
		);
	});

	signalingSocket.on('iceCandidate', function(config) {
		var peer = peers[config.peer_id];
		var ice_candidate = config.ice_candidate;
		peer.addIceCandidate(new RTCIceCandidate(ice_candidate));
	});
	signalingSocket.on('removePeer', function(config) {
		var peer_id = config.peer_id;
		if (peer_id in peerMediaElements) {
			document.body.removeChild(peerMediaElements[peer_id].parentNode);
			resizeVideos();
		}
		if (peer_id in peers) {
			peers[peer_id].close();
		}

		delete peers[peer_id];
		delete peerMediaElements[config.peer_id];
	});
	// document.getElementById('roomurl').value = appURL() + '/' + getRoomName();
}
/* keep track of our <video> tags, indexed by peer_id */
keep track of our  tags, indexed by peer_id
keep track of our tags indexed by peer_id
function init() {
	console.log('Connecting to signaling server');
	signalingSocket = io(SIGNALING_SERVER);
	signalingSocket = io();
	signalingSocket.on('connect', function() {
		console.log('Connected to signaling server');
		if (localMediaStream) joinChannel(ROOM_ID, {});
		else
			setup_local_media(function() {
				joinChannel(ROOM_ID, {});
			});
	});
	signalingSocket.on('disconnect', function() {
		for (peer_id in peerMediaElements) {
			document.body.removeChild(peerMediaElements[peer_id].parentNode);
			resizeVideos();
		}
		for (peer_id in peers) {
			peers[peer_id].close();
		}
		peers = {};
		peerMediaElements = {};
	});
	function joinChannel(channel, userdata) {
		signalingSocket.emit('join', { channel: channel, userdata: userdata });
	}
	signalingSocket.on('addPeer', function(config) {
		var peer_id = config.peer_id;
		if (peer_id in peers) return;
		peerConnection = new RTCPeerConnection({ iceServers: ICE_SERVERS }, { optional: [{ DtlsSrtpKeyAgreement: true }] } 
		);
		peers[peer_id] = peerConnection;
		peerConnection.onicecandidate = function(event) {
			if (event.candidate) {
				signalingSocket.emit('relayICECandidate', {
					peer_id: peer_id,
					ice_candidate: {
						sdpMLineIndex: event.candidate.sdpMLineIndex,
						candidate: event.candidate.candidate
					}
				});
			}
		};
		peerConnection.onaddstream = function(event) {
			const videoWrap = document.createElement('div');
			videoWrap.className = 'video';
			const remoteMedia = document.createElement('video');
			videoWrap.appendChild(remoteMedia);
			remoteMedia.setAttribute('playsinline', true);
			remoteMedia.mediaGroup = 'remotevideo';
			remoteMedia.autoplay = true;
			remoteMedia.controls = false;
			peerMediaElements[peer_id] = remoteMedia;
			document.body.appendChild(videoWrap);
			document.getElementById('message').style.display = 'none';
			attachMediaStream(remoteMedia, event.stream);
			resizeVideos();
		};
		peerConnection.addStream(localMediaStream);
		if (config.should_create_offer) {
			peerConnection.createOffer(
				function(local_description) {
					peerConnection.setLocalDescription(
						local_description,
						function() {
							signalingSocket.emit('relaySessionDescription', {
								peer_id: peer_id,
								session_description: local_description
							});
						},
						function(err) {
							console.log(err);
							alert('Offer setLocalDescription failed!');
						}
					);
				},
				function(error) {
					console.log('Error sending offer: ', error);
				}
			);
		}
	});
	signalingSocket.on('sessionDescription', function(config) {
		var peer_id = config.peer_id;
		var peer = peers[peer_id];
		var remote_description = config.session_description;
		var desc = new RTCSessionDescription(remote_description);
		var stuff = peer.setRemoteDescription(
			desc,
			function() {
				if (remote_description.type == 'offer') {
					peer.createAnswer(
						function(local_description) {
							peer.setLocalDescription(
								local_description,
								function() {
									signalingSocket.emit('relaySessionDescription', {
										peer_id: peer_id,
										session_description: local_description
									});
								},
								function(err) {
									console.log(err);
									alert('Answer setLocalDescription failed!');
								}
							);
						},
						function(error) {
							console.log('Error creating answer: ', error);
						}
					);
				}
			},
			function(error) {
				console.log('setRemoteDescription error: ', error);
			}
		);
	});
	signalingSocket.on('iceCandidate', function(config) {
		var peer = peers[config.peer_id];
		var ice_candidate = config.ice_candidate;
		peer.addIceCandidate(new RTCIceCandidate(ice_candidate));
	});
	signalingSocket.on('removePeer', function(config) {
		var peer_id = config.peer_id;
		if (peer_id in peerMediaElements) {
			document.body.removeChild(peerMediaElements[peer_id].parentNode);
			resizeVideos();
		}
		if (peer_id in peers) {
			peers[peer_id].close();
		}
		delete peers[peer_id];
		delete peerMediaElements[config.peer_id];
	});
}
function init ( ) { console . log ( 'Connecting to signaling server' ) ; signalingSocket = io ( SIGNALING_SERVER ) ; signalingSocket = io ( ) ; signalingSocket . on ( 'connect' , function ( ) { console . log ( 'Connected to signaling server' ) ; if ( localMediaStream ) joinChannel ( ROOM_ID , { } ) ; else setup_local_media ( function ( ) { joinChannel ( ROOM_ID , { } ) ; } ) ; } ) ; signalingSocket . on ( 'disconnect' , function ( ) { for ( peer_id in peerMediaElements ) { document . body . removeChild ( peerMediaElements [ peer_id ] . parentNode ) ; resizeVideos ( ) ; } for ( peer_id in peers ) { peers [ peer_id ] . close ( ) ; } peers = { } ; peerMediaElements = { } ; } ) ; function joinChannel ( channel , userdata ) { signalingSocket . emit ( 'join' , { channel : channel , userdata : userdata } ) ; } signalingSocket . on ( 'addPeer' , function ( config ) { var peer_id = config . peer_id ; if ( peer_id in peers ) return ; peerConnection = new RTCPeerConnection ( { iceServers : ICE_SERVERS } , { optional : [ { DtlsSrtpKeyAgreement : true } ] } ) ; peers [ peer_id ] = peerConnection ; peerConnection . onicecandidate = function ( event ) { if ( event . candidate ) { signalingSocket . emit ( 'relayICECandidate' , { peer_id : peer_id , ice_candidate : { sdpMLineIndex : event . candidate . sdpMLineIndex , candidate : event . candidate . candidate } } ) ; } } ; peerConnection . onaddstream = function ( event ) { const videoWrap = document . createElement ( 'div' ) ; videoWrap . className = 'video' ; const remoteMedia = document . createElement ( 'video' ) ; videoWrap . appendChild ( remoteMedia ) ; remoteMedia . setAttribute ( 'playsinline' , true ) ; remoteMedia . mediaGroup = 'remotevideo' ; remoteMedia . autoplay = true ; remoteMedia . controls = false ; peerMediaElements [ peer_id ] = remoteMedia ; document . body . appendChild ( videoWrap ) ; document . getElementById ( 'message' ) . style . display = 'none' ; attachMediaStream ( remoteMedia , event . stream ) ; resizeVideos ( ) ; } ; peerConnection . addStream ( localMediaStream ) ; if ( config . should_create_offer ) { peerConnection . createOffer ( function ( local_description ) { peerConnection . setLocalDescription ( local_description , function ( ) { signalingSocket . emit ( 'relaySessionDescription' , { peer_id : peer_id , session_description : local_description } ) ; } , function ( err ) { console . log ( err ) ; alert ( 'Offer setLocalDescription failed!' ) ; } ) ; } , function ( error ) { console . log ( 'Error sending offer: ' , error ) ; } ) ; } } ) ; signalingSocket . on ( 'sessionDescription' , function ( config ) { var peer_id = config . peer_id ; var peer = peers [ peer_id ] ; var remote_description = config . session_description ; var desc = new RTCSessionDescription ( remote_description ) ; var stuff = peer . setRemoteDescription ( desc , function ( ) { if ( remote_description . type == 'offer' ) { peer . createAnswer ( function ( local_description ) { peer . setLocalDescription ( local_description , function ( ) { signalingSocket . emit ( 'relaySessionDescription' , { peer_id : peer_id , session_description : local_description } ) ; } , function ( err ) { console . log ( err ) ; alert ( 'Answer setLocalDescription failed!' ) ; } ) ; } , function ( error ) { console . log ( 'Error creating answer: ' , error ) ; } ) ; } } , function ( error ) { console . log ( 'setRemoteDescription error: ' , error ) ; } ) ; } ) ; signalingSocket . on ( 'iceCandidate' , function ( config ) { var peer = peers [ config . peer_id ] ; var ice_candidate = config . ice_candidate ; peer . addIceCandidate ( new RTCIceCandidate ( ice_candidate ) ) ; } ) ; signalingSocket . on ( 'removePeer' , function ( config ) { var peer_id = config . peer_id ; if ( peer_id in peerMediaElements ) { document . body . removeChild ( peerMediaElements [ peer_id ] . parentNode ) ; resizeVideos ( ) ; } if ( peer_id in peers ) { peers [ peer_id ] . close ( ) ; } delete peers [ peer_id ] ; delete peerMediaElements [ config . peer_id ] ; } ) ; }
keep track of our <video> tags, indexed by peer_id
keep track of our <video > tags indexed by peer_id
// Join the channel once user gives access to microphone & webcam // this will no longer be needed by chrome eventually (supposedly), but is necessary for now to get firefox to talk to chrome /* Add our local stream */ // document.getElementById('roomurl').value = appURL() + '/' + getRoomName();