vcs-controller/ui/static/gstwebrtc-api-2-0-0.js.map
2024-08-01 02:42:30 +00:00

1 line
No EOL
315 KiB
Text
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

{"version":3,"file":"gstwebrtc-api-2.0.0.min.js","mappings":"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","sources":["webpack://gstwebrtc-api/./node_modules/sdp/sdp.js","webpack://gstwebrtc-api/webpack/bootstrap","webpack://gstwebrtc-api/webpack/runtime/compat get default export","webpack://gstwebrtc-api/webpack/runtime/define property getters","webpack://gstwebrtc-api/webpack/runtime/hasOwnProperty shorthand","webpack://gstwebrtc-api/webpack/runtime/make namespace object","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/utils.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/chrome/getusermedia.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/chrome/getdisplaymedia.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/chrome/chrome_shim.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/firefox/getusermedia.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/firefox/getdisplaymedia.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/firefox/firefox_shim.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/safari/safari_shim.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/common_shim.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/adapter_factory.js","webpack://gstwebrtc-api/./node_modules/webrtc-adapter/src/js/adapter_core.js","webpack://gstwebrtc-api/./src/config.js","webpack://gstwebrtc-api/./src/session-state.js","webpack://gstwebrtc-api/./src/webrtc-session.js","webpack://gstwebrtc-api/./src/keysyms.js","webpack://gstwebrtc-api/./src/remote-controller.js","webpack://gstwebrtc-api/./src/consumer-session.js","webpack://gstwebrtc-api/./src/producer-session.js","webpack://gstwebrtc-api/./src/com-channel.js","webpack://gstwebrtc-api/./src/gstwebrtc-api.js","webpack://gstwebrtc-api/./src/index.js"],"sourcesContent":["/* eslint-env node */\n'use strict';\n\n// SDP helpers.\nconst SDPUtils = {};\n\n// Generate an alphanumeric identifier for cname or mids.\n// TODO: use UUIDs instead? https://gist.github.com/jed/982883\nSDPUtils.generateIdentifier = function() {\n return Math.random().toString(36).substring(2, 12);\n};\n\n// The RTCP CNAME used by all peerconnections from the same JS.\nSDPUtils.localCName = SDPUtils.generateIdentifier();\n\n// Splits SDP into lines, dealing with both CRLF and LF.\nSDPUtils.splitLines = function(blob) {\n return blob.trim().split('\\n').map(line => line.trim());\n};\n// Splits SDP into sessionpart and mediasections. Ensures CRLF.\nSDPUtils.splitSections = function(blob) {\n const parts = blob.split('\\nm=');\n return parts.map((part, index) => (index > 0 ?\n 'm=' + part : part).trim() + '\\r\\n');\n};\n\n// Returns the session description.\nSDPUtils.getDescription = function(blob) {\n const sections = SDPUtils.splitSections(blob);\n return sections && sections[0];\n};\n\n// Returns the individual media sections.\nSDPUtils.getMediaSections = function(blob) {\n const sections = SDPUtils.splitSections(blob);\n sections.shift();\n return sections;\n};\n\n// Returns lines that start with a certain prefix.\nSDPUtils.matchPrefix = function(blob, prefix) {\n return SDPUtils.splitLines(blob).filter(line => line.indexOf(prefix) === 0);\n};\n\n// Parses an ICE candidate line. Sample input:\n// candidate:702786350 2 udp 41819902 8.8.8.8 60769 typ relay raddr 8.8.8.8\n// rport 55996\"\n// Input can be prefixed with a=.\nSDPUtils.parseCandidate = function(line) {\n let parts;\n // Parse both variants.\n if (line.indexOf('a=candidate:') === 0) {\n parts = line.substring(12).split(' ');\n } else {\n parts = line.substring(10).split(' ');\n }\n\n const candidate = {\n foundation: parts[0],\n component: {1: 'rtp', 2: 'rtcp'}[parts[1]] || parts[1],\n protocol: parts[2].toLowerCase(),\n priority: parseInt(parts[3], 10),\n ip: parts[4],\n address: parts[4], // address is an alias for ip.\n port: parseInt(parts[5], 10),\n // skip parts[6] == 'typ'\n type: parts[7],\n };\n\n for (let i = 8; i < parts.length; i += 2) {\n switch (parts[i]) {\n case 'raddr':\n candidate.relatedAddress = parts[i + 1];\n break;\n case 'rport':\n candidate.relatedPort = parseInt(parts[i + 1], 10);\n break;\n case 'tcptype':\n candidate.tcpType = parts[i + 1];\n break;\n case 'ufrag':\n candidate.ufrag = parts[i + 1]; // for backward compatibility.\n candidate.usernameFragment = parts[i + 1];\n break;\n default: // extension handling, in particular ufrag. Don't overwrite.\n if (candidate[parts[i]] === undefined) {\n candidate[parts[i]] = parts[i + 1];\n }\n break;\n }\n }\n return candidate;\n};\n\n// Translates a candidate object into SDP candidate attribute.\n// This does not include the a= prefix!\nSDPUtils.writeCandidate = function(candidate) {\n const sdp = [];\n sdp.push(candidate.foundation);\n\n const component = candidate.component;\n if (component === 'rtp') {\n sdp.push(1);\n } else if (component === 'rtcp') {\n sdp.push(2);\n } else {\n sdp.push(component);\n }\n sdp.push(candidate.protocol.toUpperCase());\n sdp.push(candidate.priority);\n sdp.push(candidate.address || candidate.ip);\n sdp.push(candidate.port);\n\n const type = candidate.type;\n sdp.push('typ');\n sdp.push(type);\n if (type !== 'host' && candidate.relatedAddress &&\n candidate.relatedPort) {\n sdp.push('raddr');\n sdp.push(candidate.relatedAddress);\n sdp.push('rport');\n sdp.push(candidate.relatedPort);\n }\n if (candidate.tcpType && candidate.protocol.toLowerCase() === 'tcp') {\n sdp.push('tcptype');\n sdp.push(candidate.tcpType);\n }\n if (candidate.usernameFragment || candidate.ufrag) {\n sdp.push('ufrag');\n sdp.push(candidate.usernameFragment || candidate.ufrag);\n }\n return 'candidate:' + sdp.join(' ');\n};\n\n// Parses an ice-options line, returns an array of option tags.\n// Sample input:\n// a=ice-options:foo bar\nSDPUtils.parseIceOptions = function(line) {\n return line.substring(14).split(' ');\n};\n\n// Parses a rtpmap line, returns RTCRtpCoddecParameters. Sample input:\n// a=rtpmap:111 opus/48000/2\nSDPUtils.parseRtpMap = function(line) {\n let parts = line.substring(9).split(' ');\n const parsed = {\n payloadType: parseInt(parts.shift(), 10), // was: id\n };\n\n parts = parts[0].split('/');\n\n parsed.name = parts[0];\n parsed.clockRate = parseInt(parts[1], 10); // was: clockrate\n parsed.channels = parts.length === 3 ? parseInt(parts[2], 10) : 1;\n // legacy alias, got renamed back to channels in ORTC.\n parsed.numChannels = parsed.channels;\n return parsed;\n};\n\n// Generates a rtpmap line from RTCRtpCodecCapability or\n// RTCRtpCodecParameters.\nSDPUtils.writeRtpMap = function(codec) {\n let pt = codec.payloadType;\n if (codec.preferredPayloadType !== undefined) {\n pt = codec.preferredPayloadType;\n }\n const channels = codec.channels || codec.numChannels || 1;\n return 'a=rtpmap:' + pt + ' ' + codec.name + '/' + codec.clockRate +\n (channels !== 1 ? '/' + channels : '') + '\\r\\n';\n};\n\n// Parses a extmap line (headerextension from RFC 5285). Sample input:\n// a=extmap:2 urn:ietf:params:rtp-hdrext:toffset\n// a=extmap:2/sendonly urn:ietf:params:rtp-hdrext:toffset\nSDPUtils.parseExtmap = function(line) {\n const parts = line.substring(9).split(' ');\n return {\n id: parseInt(parts[0], 10),\n direction: parts[0].indexOf('/') > 0 ? parts[0].split('/')[1] : 'sendrecv',\n uri: parts[1],\n attributes: parts.slice(2).join(' '),\n };\n};\n\n// Generates an extmap line from RTCRtpHeaderExtensionParameters or\n// RTCRtpHeaderExtension.\nSDPUtils.writeExtmap = function(headerExtension) {\n return 'a=extmap:' + (headerExtension.id || headerExtension.preferredId) +\n (headerExtension.direction && headerExtension.direction !== 'sendrecv'\n ? '/' + headerExtension.direction\n : '') +\n ' ' + headerExtension.uri +\n (headerExtension.attributes ? ' ' + headerExtension.attributes : '') +\n '\\r\\n';\n};\n\n// Parses a fmtp line, returns dictionary. Sample input:\n// a=fmtp:96 vbr=on;cng=on\n// Also deals with vbr=on; cng=on\nSDPUtils.parseFmtp = function(line) {\n const parsed = {};\n let kv;\n const parts = line.substring(line.indexOf(' ') + 1).split(';');\n for (let j = 0; j < parts.length; j++) {\n kv = parts[j].trim().split('=');\n parsed[kv[0].trim()] = kv[1];\n }\n return parsed;\n};\n\n// Generates a fmtp line from RTCRtpCodecCapability or RTCRtpCodecParameters.\nSDPUtils.writeFmtp = function(codec) {\n let line = '';\n let pt = codec.payloadType;\n if (codec.preferredPayloadType !== undefined) {\n pt = codec.preferredPayloadType;\n }\n if (codec.parameters && Object.keys(codec.parameters).length) {\n const params = [];\n Object.keys(codec.parameters).forEach(param => {\n if (codec.parameters[param] !== undefined) {\n params.push(param + '=' + codec.parameters[param]);\n } else {\n params.push(param);\n }\n });\n line += 'a=fmtp:' + pt + ' ' + params.join(';') + '\\r\\n';\n }\n return line;\n};\n\n// Parses a rtcp-fb line, returns RTCPRtcpFeedback object. Sample input:\n// a=rtcp-fb:98 nack rpsi\nSDPUtils.parseRtcpFb = function(line) {\n const parts = line.substring(line.indexOf(' ') + 1).split(' ');\n return {\n type: parts.shift(),\n parameter: parts.join(' '),\n };\n};\n\n// Generate a=rtcp-fb lines from RTCRtpCodecCapability or RTCRtpCodecParameters.\nSDPUtils.writeRtcpFb = function(codec) {\n let lines = '';\n let pt = codec.payloadType;\n if (codec.preferredPayloadType !== undefined) {\n pt = codec.preferredPayloadType;\n }\n if (codec.rtcpFeedback && codec.rtcpFeedback.length) {\n // FIXME: special handling for trr-int?\n codec.rtcpFeedback.forEach(fb => {\n lines += 'a=rtcp-fb:' + pt + ' ' + fb.type +\n (fb.parameter && fb.parameter.length ? ' ' + fb.parameter : '') +\n '\\r\\n';\n });\n }\n return lines;\n};\n\n// Parses a RFC 5576 ssrc media attribute. Sample input:\n// a=ssrc:3735928559 cname:something\nSDPUtils.parseSsrcMedia = function(line) {\n const sp = line.indexOf(' ');\n const parts = {\n ssrc: parseInt(line.substring(7, sp), 10),\n };\n const colon = line.indexOf(':', sp);\n if (colon > -1) {\n parts.attribute = line.substring(sp + 1, colon);\n parts.value = line.substring(colon + 1);\n } else {\n parts.attribute = line.substring(sp + 1);\n }\n return parts;\n};\n\n// Parse a ssrc-group line (see RFC 5576). Sample input:\n// a=ssrc-group:semantics 12 34\nSDPUtils.parseSsrcGroup = function(line) {\n const parts = line.substring(13).split(' ');\n return {\n semantics: parts.shift(),\n ssrcs: parts.map(ssrc => parseInt(ssrc, 10)),\n };\n};\n\n// Extracts the MID (RFC 5888) from a media section.\n// Returns the MID or undefined if no mid line was found.\nSDPUtils.getMid = function(mediaSection) {\n const mid = SDPUtils.matchPrefix(mediaSection, 'a=mid:')[0];\n if (mid) {\n return mid.substring(6);\n }\n};\n\n// Parses a fingerprint line for DTLS-SRTP.\nSDPUtils.parseFingerprint = function(line) {\n const parts = line.substring(14).split(' ');\n return {\n algorithm: parts[0].toLowerCase(), // algorithm is case-sensitive in Edge.\n value: parts[1].toUpperCase(), // the definition is upper-case in RFC 4572.\n };\n};\n\n// Extracts DTLS parameters from SDP media section or sessionpart.\n// FIXME: for consistency with other functions this should only\n// get the fingerprint line as input. See also getIceParameters.\nSDPUtils.getDtlsParameters = function(mediaSection, sessionpart) {\n const lines = SDPUtils.matchPrefix(mediaSection + sessionpart,\n 'a=fingerprint:');\n // Note: a=setup line is ignored since we use the 'auto' role in Edge.\n return {\n role: 'auto',\n fingerprints: lines.map(SDPUtils.parseFingerprint),\n };\n};\n\n// Serializes DTLS parameters to SDP.\nSDPUtils.writeDtlsParameters = function(params, setupType) {\n let sdp = 'a=setup:' + setupType + '\\r\\n';\n params.fingerprints.forEach(fp => {\n sdp += 'a=fingerprint:' + fp.algorithm + ' ' + fp.value + '\\r\\n';\n });\n return sdp;\n};\n\n// Parses a=crypto lines into\n// https://rawgit.com/aboba/edgertc/master/msortc-rs4.html#dictionary-rtcsrtpsdesparameters-members\nSDPUtils.parseCryptoLine = function(line) {\n const parts = line.substring(9).split(' ');\n return {\n tag: parseInt(parts[0], 10),\n cryptoSuite: parts[1],\n keyParams: parts[2],\n sessionParams: parts.slice(3),\n };\n};\n\nSDPUtils.writeCryptoLine = function(parameters) {\n return 'a=crypto:' + parameters.tag + ' ' +\n parameters.cryptoSuite + ' ' +\n (typeof parameters.keyParams === 'object'\n ? SDPUtils.writeCryptoKeyParams(parameters.keyParams)\n : parameters.keyParams) +\n (parameters.sessionParams ? ' ' + parameters.sessionParams.join(' ') : '') +\n '\\r\\n';\n};\n\n// Parses the crypto key parameters into\n// https://rawgit.com/aboba/edgertc/master/msortc-rs4.html#rtcsrtpkeyparam*\nSDPUtils.parseCryptoKeyParams = function(keyParams) {\n if (keyParams.indexOf('inline:') !== 0) {\n return null;\n }\n const parts = keyParams.substring(7).split('|');\n return {\n keyMethod: 'inline',\n keySalt: parts[0],\n lifeTime: parts[1],\n mkiValue: parts[2] ? parts[2].split(':')[0] : undefined,\n mkiLength: parts[2] ? parts[2].split(':')[1] : undefined,\n };\n};\n\nSDPUtils.writeCryptoKeyParams = function(keyParams) {\n return keyParams.keyMethod + ':'\n + keyParams.keySalt +\n (keyParams.lifeTime ? '|' + keyParams.lifeTime : '') +\n (keyParams.mkiValue && keyParams.mkiLength\n ? '|' + keyParams.mkiValue + ':' + keyParams.mkiLength\n : '');\n};\n\n// Extracts all SDES parameters.\nSDPUtils.getCryptoParameters = function(mediaSection, sessionpart) {\n const lines = SDPUtils.matchPrefix(mediaSection + sessionpart,\n 'a=crypto:');\n return lines.map(SDPUtils.parseCryptoLine);\n};\n\n// Parses ICE information from SDP media section or sessionpart.\n// FIXME: for consistency with other functions this should only\n// get the ice-ufrag and ice-pwd lines as input.\nSDPUtils.getIceParameters = function(mediaSection, sessionpart) {\n const ufrag = SDPUtils.matchPrefix(mediaSection + sessionpart,\n 'a=ice-ufrag:')[0];\n const pwd = SDPUtils.matchPrefix(mediaSection + sessionpart,\n 'a=ice-pwd:')[0];\n if (!(ufrag && pwd)) {\n return null;\n }\n return {\n usernameFragment: ufrag.substring(12),\n password: pwd.substring(10),\n };\n};\n\n// Serializes ICE parameters to SDP.\nSDPUtils.writeIceParameters = function(params) {\n let sdp = 'a=ice-ufrag:' + params.usernameFragment + '\\r\\n' +\n 'a=ice-pwd:' + params.password + '\\r\\n';\n if (params.iceLite) {\n sdp += 'a=ice-lite\\r\\n';\n }\n return sdp;\n};\n\n// Parses the SDP media section and returns RTCRtpParameters.\nSDPUtils.parseRtpParameters = function(mediaSection) {\n const description = {\n codecs: [],\n headerExtensions: [],\n fecMechanisms: [],\n rtcp: [],\n };\n const lines = SDPUtils.splitLines(mediaSection);\n const mline = lines[0].split(' ');\n description.profile = mline[2];\n for (let i = 3; i < mline.length; i++) { // find all codecs from mline[3..]\n const pt = mline[i];\n const rtpmapline = SDPUtils.matchPrefix(\n mediaSection, 'a=rtpmap:' + pt + ' ')[0];\n if (rtpmapline) {\n const codec = SDPUtils.parseRtpMap(rtpmapline);\n const fmtps = SDPUtils.matchPrefix(\n mediaSection, 'a=fmtp:' + pt + ' ');\n // Only the first a=fmtp:<pt> is considered.\n codec.parameters = fmtps.length ? SDPUtils.parseFmtp(fmtps[0]) : {};\n codec.rtcpFeedback = SDPUtils.matchPrefix(\n mediaSection, 'a=rtcp-fb:' + pt + ' ')\n .map(SDPUtils.parseRtcpFb);\n description.codecs.push(codec);\n // parse FEC mechanisms from rtpmap lines.\n switch (codec.name.toUpperCase()) {\n case 'RED':\n case 'ULPFEC':\n description.fecMechanisms.push(codec.name.toUpperCase());\n break;\n default: // only RED and ULPFEC are recognized as FEC mechanisms.\n break;\n }\n }\n }\n SDPUtils.matchPrefix(mediaSection, 'a=extmap:').forEach(line => {\n description.headerExtensions.push(SDPUtils.parseExtmap(line));\n });\n const wildcardRtcpFb = SDPUtils.matchPrefix(mediaSection, 'a=rtcp-fb:* ')\n .map(SDPUtils.parseRtcpFb);\n description.codecs.forEach(codec => {\n wildcardRtcpFb.forEach(fb=> {\n const duplicate = codec.rtcpFeedback.find(existingFeedback => {\n return existingFeedback.type === fb.type &&\n existingFeedback.parameter === fb.parameter;\n });\n if (!duplicate) {\n codec.rtcpFeedback.push(fb);\n }\n });\n });\n // FIXME: parse rtcp.\n return description;\n};\n\n// Generates parts of the SDP media section describing the capabilities /\n// parameters.\nSDPUtils.writeRtpDescription = function(kind, caps) {\n let sdp = '';\n\n // Build the mline.\n sdp += 'm=' + kind + ' ';\n sdp += caps.codecs.length > 0 ? '9' : '0'; // reject if no codecs.\n sdp += ' ' + (caps.profile || 'UDP/TLS/RTP/SAVPF') + ' ';\n sdp += caps.codecs.map(codec => {\n if (codec.preferredPayloadType !== undefined) {\n return codec.preferredPayloadType;\n }\n return codec.payloadType;\n }).join(' ') + '\\r\\n';\n\n sdp += 'c=IN IP4 0.0.0.0\\r\\n';\n sdp += 'a=rtcp:9 IN IP4 0.0.0.0\\r\\n';\n\n // Add a=rtpmap lines for each codec. Also fmtp and rtcp-fb.\n caps.codecs.forEach(codec => {\n sdp += SDPUtils.writeRtpMap(codec);\n sdp += SDPUtils.writeFmtp(codec);\n sdp += SDPUtils.writeRtcpFb(codec);\n });\n let maxptime = 0;\n caps.codecs.forEach(codec => {\n if (codec.maxptime > maxptime) {\n maxptime = codec.maxptime;\n }\n });\n if (maxptime > 0) {\n sdp += 'a=maxptime:' + maxptime + '\\r\\n';\n }\n\n if (caps.headerExtensions) {\n caps.headerExtensions.forEach(extension => {\n sdp += SDPUtils.writeExtmap(extension);\n });\n }\n // FIXME: write fecMechanisms.\n return sdp;\n};\n\n// Parses the SDP media section and returns an array of\n// RTCRtpEncodingParameters.\nSDPUtils.parseRtpEncodingParameters = function(mediaSection) {\n const encodingParameters = [];\n const description = SDPUtils.parseRtpParameters(mediaSection);\n const hasRed = description.fecMechanisms.indexOf('RED') !== -1;\n const hasUlpfec = description.fecMechanisms.indexOf('ULPFEC') !== -1;\n\n // filter a=ssrc:... cname:, ignore PlanB-msid\n const ssrcs = SDPUtils.matchPrefix(mediaSection, 'a=ssrc:')\n .map(line => SDPUtils.parseSsrcMedia(line))\n .filter(parts => parts.attribute === 'cname');\n const primarySsrc = ssrcs.length > 0 && ssrcs[0].ssrc;\n let secondarySsrc;\n\n const flows = SDPUtils.matchPrefix(mediaSection, 'a=ssrc-group:FID')\n .map(line => {\n const parts = line.substring(17).split(' ');\n return parts.map(part => parseInt(part, 10));\n });\n if (flows.length > 0 && flows[0].length > 1 && flows[0][0] === primarySsrc) {\n secondarySsrc = flows[0][1];\n }\n\n description.codecs.forEach(codec => {\n if (codec.name.toUpperCase() === 'RTX' && codec.parameters.apt) {\n let encParam = {\n ssrc: primarySsrc,\n codecPayloadType: parseInt(codec.parameters.apt, 10),\n };\n if (primarySsrc && secondarySsrc) {\n encParam.rtx = {ssrc: secondarySsrc};\n }\n encodingParameters.push(encParam);\n if (hasRed) {\n encParam = JSON.parse(JSON.stringify(encParam));\n encParam.fec = {\n ssrc: primarySsrc,\n mechanism: hasUlpfec ? 'red+ulpfec' : 'red',\n };\n encodingParameters.push(encParam);\n }\n }\n });\n if (encodingParameters.length === 0 && primarySsrc) {\n encodingParameters.push({\n ssrc: primarySsrc,\n });\n }\n\n // we support both b=AS and b=TIAS but interpret AS as TIAS.\n let bandwidth = SDPUtils.matchPrefix(mediaSection, 'b=');\n if (bandwidth.length) {\n if (bandwidth[0].indexOf('b=TIAS:') === 0) {\n bandwidth = parseInt(bandwidth[0].substring(7), 10);\n } else if (bandwidth[0].indexOf('b=AS:') === 0) {\n // use formula from JSEP to convert b=AS to TIAS value.\n bandwidth = parseInt(bandwidth[0].substring(5), 10) * 1000 * 0.95\n - (50 * 40 * 8);\n } else {\n bandwidth = undefined;\n }\n encodingParameters.forEach(params => {\n params.maxBitrate = bandwidth;\n });\n }\n return encodingParameters;\n};\n\n// parses http://draft.ortc.org/#rtcrtcpparameters*\nSDPUtils.parseRtcpParameters = function(mediaSection) {\n const rtcpParameters = {};\n\n // Gets the first SSRC. Note that with RTX there might be multiple\n // SSRCs.\n const remoteSsrc = SDPUtils.matchPrefix(mediaSection, 'a=ssrc:')\n .map(line => SDPUtils.parseSsrcMedia(line))\n .filter(obj => obj.attribute === 'cname')[0];\n if (remoteSsrc) {\n rtcpParameters.cname = remoteSsrc.value;\n rtcpParameters.ssrc = remoteSsrc.ssrc;\n }\n\n // Edge uses the compound attribute instead of reducedSize\n // compound is !reducedSize\n const rsize = SDPUtils.matchPrefix(mediaSection, 'a=rtcp-rsize');\n rtcpParameters.reducedSize = rsize.length > 0;\n rtcpParameters.compound = rsize.length === 0;\n\n // parses the rtcp-mux attrіbute.\n // Note that Edge does not support unmuxed RTCP.\n const mux = SDPUtils.matchPrefix(mediaSection, 'a=rtcp-mux');\n rtcpParameters.mux = mux.length > 0;\n\n return rtcpParameters;\n};\n\nSDPUtils.writeRtcpParameters = function(rtcpParameters) {\n let sdp = '';\n if (rtcpParameters.reducedSize) {\n sdp += 'a=rtcp-rsize\\r\\n';\n }\n if (rtcpParameters.mux) {\n sdp += 'a=rtcp-mux\\r\\n';\n }\n if (rtcpParameters.ssrc !== undefined && rtcpParameters.cname) {\n sdp += 'a=ssrc:' + rtcpParameters.ssrc +\n ' cname:' + rtcpParameters.cname + '\\r\\n';\n }\n return sdp;\n};\n\n\n// parses either a=msid: or a=ssrc:... msid lines and returns\n// the id of the MediaStream and MediaStreamTrack.\nSDPUtils.parseMsid = function(mediaSection) {\n let parts;\n const spec = SDPUtils.matchPrefix(mediaSection, 'a=msid:');\n if (spec.length === 1) {\n parts = spec[0].substring(7).split(' ');\n return {stream: parts[0], track: parts[1]};\n }\n const planB = SDPUtils.matchPrefix(mediaSection, 'a=ssrc:')\n .map(line => SDPUtils.parseSsrcMedia(line))\n .filter(msidParts => msidParts.attribute === 'msid');\n if (planB.length > 0) {\n parts = planB[0].value.split(' ');\n return {stream: parts[0], track: parts[1]};\n }\n};\n\n// SCTP\n// parses draft-ietf-mmusic-sctp-sdp-26 first and falls back\n// to draft-ietf-mmusic-sctp-sdp-05\nSDPUtils.parseSctpDescription = function(mediaSection) {\n const mline = SDPUtils.parseMLine(mediaSection);\n const maxSizeLine = SDPUtils.matchPrefix(mediaSection, 'a=max-message-size:');\n let maxMessageSize;\n if (maxSizeLine.length > 0) {\n maxMessageSize = parseInt(maxSizeLine[0].substring(19), 10);\n }\n if (isNaN(maxMessageSize)) {\n maxMessageSize = 65536;\n }\n const sctpPort = SDPUtils.matchPrefix(mediaSection, 'a=sctp-port:');\n if (sctpPort.length > 0) {\n return {\n port: parseInt(sctpPort[0].substring(12), 10),\n protocol: mline.fmt,\n maxMessageSize,\n };\n }\n const sctpMapLines = SDPUtils.matchPrefix(mediaSection, 'a=sctpmap:');\n if (sctpMapLines.length > 0) {\n const parts = sctpMapLines[0]\n .substring(10)\n .split(' ');\n return {\n port: parseInt(parts[0], 10),\n protocol: parts[1],\n maxMessageSize,\n };\n }\n};\n\n// SCTP\n// outputs the draft-ietf-mmusic-sctp-sdp-26 version that all browsers\n// support by now receiving in this format, unless we originally parsed\n// as the draft-ietf-mmusic-sctp-sdp-05 format (indicated by the m-line\n// protocol of DTLS/SCTP -- without UDP/ or TCP/)\nSDPUtils.writeSctpDescription = function(media, sctp) {\n let output = [];\n if (media.protocol !== 'DTLS/SCTP') {\n output = [\n 'm=' + media.kind + ' 9 ' + media.protocol + ' ' + sctp.protocol + '\\r\\n',\n 'c=IN IP4 0.0.0.0\\r\\n',\n 'a=sctp-port:' + sctp.port + '\\r\\n',\n ];\n } else {\n output = [\n 'm=' + media.kind + ' 9 ' + media.protocol + ' ' + sctp.port + '\\r\\n',\n 'c=IN IP4 0.0.0.0\\r\\n',\n 'a=sctpmap:' + sctp.port + ' ' + sctp.protocol + ' 65535\\r\\n',\n ];\n }\n if (sctp.maxMessageSize !== undefined) {\n output.push('a=max-message-size:' + sctp.maxMessageSize + '\\r\\n');\n }\n return output.join('');\n};\n\n// Generate a session ID for SDP.\n// https://tools.ietf.org/html/draft-ietf-rtcweb-jsep-20#section-5.2.1\n// recommends using a cryptographically random +ve 64-bit value\n// but right now this should be acceptable and within the right range\nSDPUtils.generateSessionId = function() {\n return Math.random().toString().substr(2, 22);\n};\n\n// Write boiler plate for start of SDP\n// sessId argument is optional - if not supplied it will\n// be generated randomly\n// sessVersion is optional and defaults to 2\n// sessUser is optional and defaults to 'thisisadapterortc'\nSDPUtils.writeSessionBoilerplate = function(sessId, sessVer, sessUser) {\n let sessionId;\n const version = sessVer !== undefined ? sessVer : 2;\n if (sessId) {\n sessionId = sessId;\n } else {\n sessionId = SDPUtils.generateSessionId();\n }\n const user = sessUser || 'thisisadapterortc';\n // FIXME: sess-id should be an NTP timestamp.\n return 'v=0\\r\\n' +\n 'o=' + user + ' ' + sessionId + ' ' + version +\n ' IN IP4 127.0.0.1\\r\\n' +\n 's=-\\r\\n' +\n 't=0 0\\r\\n';\n};\n\n// Gets the direction from the mediaSection or the sessionpart.\nSDPUtils.getDirection = function(mediaSection, sessionpart) {\n // Look for sendrecv, sendonly, recvonly, inactive, default to sendrecv.\n const lines = SDPUtils.splitLines(mediaSection);\n for (let i = 0; i < lines.length; i++) {\n switch (lines[i]) {\n case 'a=sendrecv':\n case 'a=sendonly':\n case 'a=recvonly':\n case 'a=inactive':\n return lines[i].substring(2);\n default:\n // FIXME: What should happen here?\n }\n }\n if (sessionpart) {\n return SDPUtils.getDirection(sessionpart);\n }\n return 'sendrecv';\n};\n\nSDPUtils.getKind = function(mediaSection) {\n const lines = SDPUtils.splitLines(mediaSection);\n const mline = lines[0].split(' ');\n return mline[0].substring(2);\n};\n\nSDPUtils.isRejected = function(mediaSection) {\n return mediaSection.split(' ', 2)[1] === '0';\n};\n\nSDPUtils.parseMLine = function(mediaSection) {\n const lines = SDPUtils.splitLines(mediaSection);\n const parts = lines[0].substring(2).split(' ');\n return {\n kind: parts[0],\n port: parseInt(parts[1], 10),\n protocol: parts[2],\n fmt: parts.slice(3).join(' '),\n };\n};\n\nSDPUtils.parseOLine = function(mediaSection) {\n const line = SDPUtils.matchPrefix(mediaSection, 'o=')[0];\n const parts = line.substring(2).split(' ');\n return {\n username: parts[0],\n sessionId: parts[1],\n sessionVersion: parseInt(parts[2], 10),\n netType: parts[3],\n addressType: parts[4],\n address: parts[5],\n };\n};\n\n// a very naive interpretation of a valid SDP.\nSDPUtils.isValidSDP = function(blob) {\n if (typeof blob !== 'string' || blob.length === 0) {\n return false;\n }\n const lines = SDPUtils.splitLines(blob);\n for (let i = 0; i < lines.length; i++) {\n if (lines[i].length < 2 || lines[i].charAt(1) !== '=') {\n return false;\n }\n // TODO: check the modifier a bit more.\n }\n return true;\n};\n\n// Expose public methods.\nif (typeof module === 'object') {\n module.exports = SDPUtils;\n}\n","// The module cache\nvar __webpack_module_cache__ = {};\n\n// The require function\nfunction __webpack_require__(moduleId) {\n\t// Check if module is in cache\n\tvar cachedModule = __webpack_module_cache__[moduleId];\n\tif (cachedModule !== undefined) {\n\t\treturn cachedModule.exports;\n\t}\n\t// Create a new module (and put it into the cache)\n\tvar module = __webpack_module_cache__[moduleId] = {\n\t\t// no module.id needed\n\t\t// no module.loaded needed\n\t\texports: {}\n\t};\n\n\t// Execute the module function\n\t__webpack_modules__[moduleId](module, module.exports, __webpack_require__);\n\n\t// Return the exports of the module\n\treturn module.exports;\n}\n\n","// getDefaultExport function for compatibility with non-harmony modules\n__webpack_require__.n = (module) => {\n\tvar getter = module && module.__esModule ?\n\t\t() => (module['default']) :\n\t\t() => (module);\n\t__webpack_require__.d(getter, { a: getter });\n\treturn getter;\n};","// define getter functions for harmony exports\n__webpack_require__.d = (exports, definition) => {\n\tfor(var key in definition) {\n\t\tif(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {\n\t\t\tObject.defineProperty(exports, key, { enumerable: true, get: definition[key] });\n\t\t}\n\t}\n};","__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))","// define __esModule on exports\n__webpack_require__.r = (exports) => {\n\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n\t}\n\tObject.defineProperty(exports, '__esModule', { value: true });\n};","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\n\nlet logDisabled_ = true;\nlet deprecationWarnings_ = true;\n\n/**\n * Extract browser version out of the provided user agent string.\n *\n * @param {!string} uastring userAgent string.\n * @param {!string} expr Regular expression used as match criteria.\n * @param {!number} pos position in the version string to be returned.\n * @return {!number} browser version.\n */\nexport function extractVersion(uastring, expr, pos) {\n const match = uastring.match(expr);\n return match && match.length >= pos && parseInt(match[pos], 10);\n}\n\n// Wraps the peerconnection event eventNameToWrap in a function\n// which returns the modified event object (or false to prevent\n// the event).\nexport function wrapPeerConnectionEvent(window, eventNameToWrap, wrapper) {\n if (!window.RTCPeerConnection) {\n return;\n }\n const proto = window.RTCPeerConnection.prototype;\n const nativeAddEventListener = proto.addEventListener;\n proto.addEventListener = function(nativeEventName, cb) {\n if (nativeEventName !== eventNameToWrap) {\n return nativeAddEventListener.apply(this, arguments);\n }\n const wrappedCallback = (e) => {\n const modifiedEvent = wrapper(e);\n if (modifiedEvent) {\n if (cb.handleEvent) {\n cb.handleEvent(modifiedEvent);\n } else {\n cb(modifiedEvent);\n }\n }\n };\n this._eventMap = this._eventMap || {};\n if (!this._eventMap[eventNameToWrap]) {\n this._eventMap[eventNameToWrap] = new Map();\n }\n this._eventMap[eventNameToWrap].set(cb, wrappedCallback);\n return nativeAddEventListener.apply(this, [nativeEventName,\n wrappedCallback]);\n };\n\n const nativeRemoveEventListener = proto.removeEventListener;\n proto.removeEventListener = function(nativeEventName, cb) {\n if (nativeEventName !== eventNameToWrap || !this._eventMap\n || !this._eventMap[eventNameToWrap]) {\n return nativeRemoveEventListener.apply(this, arguments);\n }\n if (!this._eventMap[eventNameToWrap].has(cb)) {\n return nativeRemoveEventListener.apply(this, arguments);\n }\n const unwrappedCb = this._eventMap[eventNameToWrap].get(cb);\n this._eventMap[eventNameToWrap].delete(cb);\n if (this._eventMap[eventNameToWrap].size === 0) {\n delete this._eventMap[eventNameToWrap];\n }\n if (Object.keys(this._eventMap).length === 0) {\n delete this._eventMap;\n }\n return nativeRemoveEventListener.apply(this, [nativeEventName,\n unwrappedCb]);\n };\n\n Object.defineProperty(proto, 'on' + eventNameToWrap, {\n get() {\n return this['_on' + eventNameToWrap];\n },\n set(cb) {\n if (this['_on' + eventNameToWrap]) {\n this.removeEventListener(eventNameToWrap,\n this['_on' + eventNameToWrap]);\n delete this['_on' + eventNameToWrap];\n }\n if (cb) {\n this.addEventListener(eventNameToWrap,\n this['_on' + eventNameToWrap] = cb);\n }\n },\n enumerable: true,\n configurable: true\n });\n}\n\nexport function disableLog(bool) {\n if (typeof bool !== 'boolean') {\n return new Error('Argument type: ' + typeof bool +\n '. Please use a boolean.');\n }\n logDisabled_ = bool;\n return (bool) ? 'adapter.js logging disabled' :\n 'adapter.js logging enabled';\n}\n\n/**\n * Disable or enable deprecation warnings\n * @param {!boolean} bool set to true to disable warnings.\n */\nexport function disableWarnings(bool) {\n if (typeof bool !== 'boolean') {\n return new Error('Argument type: ' + typeof bool +\n '. Please use a boolean.');\n }\n deprecationWarnings_ = !bool;\n return 'adapter.js deprecation warnings ' + (bool ? 'disabled' : 'enabled');\n}\n\nexport function log() {\n if (typeof window === 'object') {\n if (logDisabled_) {\n return;\n }\n if (typeof console !== 'undefined' && typeof console.log === 'function') {\n console.log.apply(console, arguments);\n }\n }\n}\n\n/**\n * Shows a deprecation warning suggesting the modern and spec-compatible API.\n */\nexport function deprecated(oldMethod, newMethod) {\n if (!deprecationWarnings_) {\n return;\n }\n console.warn(oldMethod + ' is deprecated, please use ' + newMethod +\n ' instead.');\n}\n\n/**\n * Browser detector.\n *\n * @return {object} result containing browser and version\n * properties.\n */\nexport function detectBrowser(window) {\n // Returned result object.\n const result = {browser: null, version: null};\n\n // Fail early if it's not a browser\n if (typeof window === 'undefined' || !window.navigator ||\n !window.navigator.userAgent) {\n result.browser = 'Not a browser.';\n return result;\n }\n\n const {navigator} = window;\n\n if (navigator.mozGetUserMedia) { // Firefox.\n result.browser = 'firefox';\n result.version = extractVersion(navigator.userAgent,\n /Firefox\\/(\\d+)\\./, 1);\n } else if (navigator.webkitGetUserMedia ||\n (window.isSecureContext === false && window.webkitRTCPeerConnection)) {\n // Chrome, Chromium, Webview, Opera.\n // Version matches Chrome/WebRTC version.\n // Chrome 74 removed webkitGetUserMedia on http as well so we need the\n // more complicated fallback to webkitRTCPeerConnection.\n result.browser = 'chrome';\n result.version = extractVersion(navigator.userAgent,\n /Chrom(e|ium)\\/(\\d+)\\./, 2);\n } else if (window.RTCPeerConnection &&\n navigator.userAgent.match(/AppleWebKit\\/(\\d+)\\./)) { // Safari.\n result.browser = 'safari';\n result.version = extractVersion(navigator.userAgent,\n /AppleWebKit\\/(\\d+)\\./, 1);\n result.supportsUnifiedPlan = window.RTCRtpTransceiver &&\n 'currentDirection' in window.RTCRtpTransceiver.prototype;\n } else { // Default fallthrough: not supported.\n result.browser = 'Not a supported browser.';\n return result;\n }\n\n return result;\n}\n\n/**\n * Checks if something is an object.\n *\n * @param {*} val The something you want to check.\n * @return true if val is an object, false otherwise.\n */\nfunction isObject(val) {\n return Object.prototype.toString.call(val) === '[object Object]';\n}\n\n/**\n * Remove all empty objects and undefined values\n * from a nested object -- an enhanced and vanilla version\n * of Lodash's `compact`.\n */\nexport function compactObject(data) {\n if (!isObject(data)) {\n return data;\n }\n\n return Object.keys(data).reduce(function(accumulator, key) {\n const isObj = isObject(data[key]);\n const value = isObj ? compactObject(data[key]) : data[key];\n const isEmptyObject = isObj && !Object.keys(value).length;\n if (value === undefined || isEmptyObject) {\n return accumulator;\n }\n return Object.assign(accumulator, {[key]: value});\n }, {});\n}\n\n/* iterates the stats graph recursively. */\nexport function walkStats(stats, base, resultSet) {\n if (!base || resultSet.has(base.id)) {\n return;\n }\n resultSet.set(base.id, base);\n Object.keys(base).forEach(name => {\n if (name.endsWith('Id')) {\n walkStats(stats, stats.get(base[name]), resultSet);\n } else if (name.endsWith('Ids')) {\n base[name].forEach(id => {\n walkStats(stats, stats.get(id), resultSet);\n });\n }\n });\n}\n\n/* filter getStats for a sender/receiver track. */\nexport function filterStats(result, track, outbound) {\n const streamStatsType = outbound ? 'outbound-rtp' : 'inbound-rtp';\n const filteredResult = new Map();\n if (track === null) {\n return filteredResult;\n }\n const trackStats = [];\n result.forEach(value => {\n if (value.type === 'track' &&\n value.trackIdentifier === track.id) {\n trackStats.push(value);\n }\n });\n trackStats.forEach(trackStat => {\n result.forEach(stats => {\n if (stats.type === streamStatsType && stats.trackId === trackStat.id) {\n walkStats(result, stats, filteredResult);\n }\n });\n });\n return filteredResult;\n}\n\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\nimport * as utils from '../utils.js';\nconst logging = utils.log;\n\nexport function shimGetUserMedia(window, browserDetails) {\n const navigator = window && window.navigator;\n\n if (!navigator.mediaDevices) {\n return;\n }\n\n const constraintsToChrome_ = function(c) {\n if (typeof c !== 'object' || c.mandatory || c.optional) {\n return c;\n }\n const cc = {};\n Object.keys(c).forEach(key => {\n if (key === 'require' || key === 'advanced' || key === 'mediaSource') {\n return;\n }\n const r = (typeof c[key] === 'object') ? c[key] : {ideal: c[key]};\n if (r.exact !== undefined && typeof r.exact === 'number') {\n r.min = r.max = r.exact;\n }\n const oldname_ = function(prefix, name) {\n if (prefix) {\n return prefix + name.charAt(0).toUpperCase() + name.slice(1);\n }\n return (name === 'deviceId') ? 'sourceId' : name;\n };\n if (r.ideal !== undefined) {\n cc.optional = cc.optional || [];\n let oc = {};\n if (typeof r.ideal === 'number') {\n oc[oldname_('min', key)] = r.ideal;\n cc.optional.push(oc);\n oc = {};\n oc[oldname_('max', key)] = r.ideal;\n cc.optional.push(oc);\n } else {\n oc[oldname_('', key)] = r.ideal;\n cc.optional.push(oc);\n }\n }\n if (r.exact !== undefined && typeof r.exact !== 'number') {\n cc.mandatory = cc.mandatory || {};\n cc.mandatory[oldname_('', key)] = r.exact;\n } else {\n ['min', 'max'].forEach(mix => {\n if (r[mix] !== undefined) {\n cc.mandatory = cc.mandatory || {};\n cc.mandatory[oldname_(mix, key)] = r[mix];\n }\n });\n }\n });\n if (c.advanced) {\n cc.optional = (cc.optional || []).concat(c.advanced);\n }\n return cc;\n };\n\n const shimConstraints_ = function(constraints, func) {\n if (browserDetails.version >= 61) {\n return func(constraints);\n }\n constraints = JSON.parse(JSON.stringify(constraints));\n if (constraints && typeof constraints.audio === 'object') {\n const remap = function(obj, a, b) {\n if (a in obj && !(b in obj)) {\n obj[b] = obj[a];\n delete obj[a];\n }\n };\n constraints = JSON.parse(JSON.stringify(constraints));\n remap(constraints.audio, 'autoGainControl', 'googAutoGainControl');\n remap(constraints.audio, 'noiseSuppression', 'googNoiseSuppression');\n constraints.audio = constraintsToChrome_(constraints.audio);\n }\n if (constraints && typeof constraints.video === 'object') {\n // Shim facingMode for mobile & surface pro.\n let face = constraints.video.facingMode;\n face = face && ((typeof face === 'object') ? face : {ideal: face});\n const getSupportedFacingModeLies = browserDetails.version < 66;\n\n if ((face && (face.exact === 'user' || face.exact === 'environment' ||\n face.ideal === 'user' || face.ideal === 'environment')) &&\n !(navigator.mediaDevices.getSupportedConstraints &&\n navigator.mediaDevices.getSupportedConstraints().facingMode &&\n !getSupportedFacingModeLies)) {\n delete constraints.video.facingMode;\n let matches;\n if (face.exact === 'environment' || face.ideal === 'environment') {\n matches = ['back', 'rear'];\n } else if (face.exact === 'user' || face.ideal === 'user') {\n matches = ['front'];\n }\n if (matches) {\n // Look for matches in label, or use last cam for back (typical).\n return navigator.mediaDevices.enumerateDevices()\n .then(devices => {\n devices = devices.filter(d => d.kind === 'videoinput');\n let dev = devices.find(d => matches.some(match =>\n d.label.toLowerCase().includes(match)));\n if (!dev && devices.length && matches.includes('back')) {\n dev = devices[devices.length - 1]; // more likely the back cam\n }\n if (dev) {\n constraints.video.deviceId = face.exact\n ? {exact: dev.deviceId}\n : {ideal: dev.deviceId};\n }\n constraints.video = constraintsToChrome_(constraints.video);\n logging('chrome: ' + JSON.stringify(constraints));\n return func(constraints);\n });\n }\n }\n constraints.video = constraintsToChrome_(constraints.video);\n }\n logging('chrome: ' + JSON.stringify(constraints));\n return func(constraints);\n };\n\n const shimError_ = function(e) {\n if (browserDetails.version >= 64) {\n return e;\n }\n return {\n name: {\n PermissionDeniedError: 'NotAllowedError',\n PermissionDismissedError: 'NotAllowedError',\n InvalidStateError: 'NotAllowedError',\n DevicesNotFoundError: 'NotFoundError',\n ConstraintNotSatisfiedError: 'OverconstrainedError',\n TrackStartError: 'NotReadableError',\n MediaDeviceFailedDueToShutdown: 'NotAllowedError',\n MediaDeviceKillSwitchOn: 'NotAllowedError',\n TabCaptureError: 'AbortError',\n ScreenCaptureError: 'AbortError',\n DeviceCaptureError: 'AbortError'\n }[e.name] || e.name,\n message: e.message,\n constraint: e.constraint || e.constraintName,\n toString() {\n return this.name + (this.message && ': ') + this.message;\n }\n };\n };\n\n const getUserMedia_ = function(constraints, onSuccess, onError) {\n shimConstraints_(constraints, c => {\n navigator.webkitGetUserMedia(c, onSuccess, e => {\n if (onError) {\n onError(shimError_(e));\n }\n });\n });\n };\n navigator.getUserMedia = getUserMedia_.bind(navigator);\n\n // Even though Chrome 45 has navigator.mediaDevices and a getUserMedia\n // function which returns a Promise, it does not accept spec-style\n // constraints.\n if (navigator.mediaDevices.getUserMedia) {\n const origGetUserMedia = navigator.mediaDevices.getUserMedia.\n bind(navigator.mediaDevices);\n navigator.mediaDevices.getUserMedia = function(cs) {\n return shimConstraints_(cs, c => origGetUserMedia(c).then(stream => {\n if (c.audio && !stream.getAudioTracks().length ||\n c.video && !stream.getVideoTracks().length) {\n stream.getTracks().forEach(track => {\n track.stop();\n });\n throw new DOMException('', 'NotFoundError');\n }\n return stream;\n }, e => Promise.reject(shimError_(e))));\n };\n }\n}\n","/*\n * Copyright (c) 2018 The adapter.js project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\nexport function shimGetDisplayMedia(window, getSourceId) {\n if (window.navigator.mediaDevices &&\n 'getDisplayMedia' in window.navigator.mediaDevices) {\n return;\n }\n if (!(window.navigator.mediaDevices)) {\n return;\n }\n // getSourceId is a function that returns a promise resolving with\n // the sourceId of the screen/window/tab to be shared.\n if (typeof getSourceId !== 'function') {\n console.error('shimGetDisplayMedia: getSourceId argument is not ' +\n 'a function');\n return;\n }\n window.navigator.mediaDevices.getDisplayMedia =\n function getDisplayMedia(constraints) {\n return getSourceId(constraints)\n .then(sourceId => {\n const widthSpecified = constraints.video && constraints.video.width;\n const heightSpecified = constraints.video &&\n constraints.video.height;\n const frameRateSpecified = constraints.video &&\n constraints.video.frameRate;\n constraints.video = {\n mandatory: {\n chromeMediaSource: 'desktop',\n chromeMediaSourceId: sourceId,\n maxFrameRate: frameRateSpecified || 3\n }\n };\n if (widthSpecified) {\n constraints.video.mandatory.maxWidth = widthSpecified;\n }\n if (heightSpecified) {\n constraints.video.mandatory.maxHeight = heightSpecified;\n }\n return window.navigator.mediaDevices.getUserMedia(constraints);\n });\n };\n}\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\nimport * as utils from '../utils.js';\n\nexport {shimGetUserMedia} from './getusermedia';\nexport {shimGetDisplayMedia} from './getdisplaymedia';\n\nexport function shimMediaStream(window) {\n window.MediaStream = window.MediaStream || window.webkitMediaStream;\n}\n\nexport function shimOnTrack(window) {\n if (typeof window === 'object' && window.RTCPeerConnection && !('ontrack' in\n window.RTCPeerConnection.prototype)) {\n Object.defineProperty(window.RTCPeerConnection.prototype, 'ontrack', {\n get() {\n return this._ontrack;\n },\n set(f) {\n if (this._ontrack) {\n this.removeEventListener('track', this._ontrack);\n }\n this.addEventListener('track', this._ontrack = f);\n },\n enumerable: true,\n configurable: true\n });\n const origSetRemoteDescription =\n window.RTCPeerConnection.prototype.setRemoteDescription;\n window.RTCPeerConnection.prototype.setRemoteDescription =\n function setRemoteDescription() {\n if (!this._ontrackpoly) {\n this._ontrackpoly = (e) => {\n // onaddstream does not fire when a track is added to an existing\n // stream. But stream.onaddtrack is implemented so we use that.\n e.stream.addEventListener('addtrack', te => {\n let receiver;\n if (window.RTCPeerConnection.prototype.getReceivers) {\n receiver = this.getReceivers()\n .find(r => r.track && r.track.id === te.track.id);\n } else {\n receiver = {track: te.track};\n }\n\n const event = new Event('track');\n event.track = te.track;\n event.receiver = receiver;\n event.transceiver = {receiver};\n event.streams = [e.stream];\n this.dispatchEvent(event);\n });\n e.stream.getTracks().forEach(track => {\n let receiver;\n if (window.RTCPeerConnection.prototype.getReceivers) {\n receiver = this.getReceivers()\n .find(r => r.track && r.track.id === track.id);\n } else {\n receiver = {track};\n }\n const event = new Event('track');\n event.track = track;\n event.receiver = receiver;\n event.transceiver = {receiver};\n event.streams = [e.stream];\n this.dispatchEvent(event);\n });\n };\n this.addEventListener('addstream', this._ontrackpoly);\n }\n return origSetRemoteDescription.apply(this, arguments);\n };\n } else {\n // even if RTCRtpTransceiver is in window, it is only used and\n // emitted in unified-plan. Unfortunately this means we need\n // to unconditionally wrap the event.\n utils.wrapPeerConnectionEvent(window, 'track', e => {\n if (!e.transceiver) {\n Object.defineProperty(e, 'transceiver',\n {value: {receiver: e.receiver}});\n }\n return e;\n });\n }\n}\n\nexport function shimGetSendersWithDtmf(window) {\n // Overrides addTrack/removeTrack, depends on shimAddTrackRemoveTrack.\n if (typeof window === 'object' && window.RTCPeerConnection &&\n !('getSenders' in window.RTCPeerConnection.prototype) &&\n 'createDTMFSender' in window.RTCPeerConnection.prototype) {\n const shimSenderWithDtmf = function(pc, track) {\n return {\n track,\n get dtmf() {\n if (this._dtmf === undefined) {\n if (track.kind === 'audio') {\n this._dtmf = pc.createDTMFSender(track);\n } else {\n this._dtmf = null;\n }\n }\n return this._dtmf;\n },\n _pc: pc\n };\n };\n\n // augment addTrack when getSenders is not available.\n if (!window.RTCPeerConnection.prototype.getSenders) {\n window.RTCPeerConnection.prototype.getSenders = function getSenders() {\n this._senders = this._senders || [];\n return this._senders.slice(); // return a copy of the internal state.\n };\n const origAddTrack = window.RTCPeerConnection.prototype.addTrack;\n window.RTCPeerConnection.prototype.addTrack =\n function addTrack(track, stream) {\n let sender = origAddTrack.apply(this, arguments);\n if (!sender) {\n sender = shimSenderWithDtmf(this, track);\n this._senders.push(sender);\n }\n return sender;\n };\n\n const origRemoveTrack = window.RTCPeerConnection.prototype.removeTrack;\n window.RTCPeerConnection.prototype.removeTrack =\n function removeTrack(sender) {\n origRemoveTrack.apply(this, arguments);\n const idx = this._senders.indexOf(sender);\n if (idx !== -1) {\n this._senders.splice(idx, 1);\n }\n };\n }\n const origAddStream = window.RTCPeerConnection.prototype.addStream;\n window.RTCPeerConnection.prototype.addStream = function addStream(stream) {\n this._senders = this._senders || [];\n origAddStream.apply(this, [stream]);\n stream.getTracks().forEach(track => {\n this._senders.push(shimSenderWithDtmf(this, track));\n });\n };\n\n const origRemoveStream = window.RTCPeerConnection.prototype.removeStream;\n window.RTCPeerConnection.prototype.removeStream =\n function removeStream(stream) {\n this._senders = this._senders || [];\n origRemoveStream.apply(this, [stream]);\n\n stream.getTracks().forEach(track => {\n const sender = this._senders.find(s => s.track === track);\n if (sender) { // remove sender\n this._senders.splice(this._senders.indexOf(sender), 1);\n }\n });\n };\n } else if (typeof window === 'object' && window.RTCPeerConnection &&\n 'getSenders' in window.RTCPeerConnection.prototype &&\n 'createDTMFSender' in window.RTCPeerConnection.prototype &&\n window.RTCRtpSender &&\n !('dtmf' in window.RTCRtpSender.prototype)) {\n const origGetSenders = window.RTCPeerConnection.prototype.getSenders;\n window.RTCPeerConnection.prototype.getSenders = function getSenders() {\n const senders = origGetSenders.apply(this, []);\n senders.forEach(sender => sender._pc = this);\n return senders;\n };\n\n Object.defineProperty(window.RTCRtpSender.prototype, 'dtmf', {\n get() {\n if (this._dtmf === undefined) {\n if (this.track.kind === 'audio') {\n this._dtmf = this._pc.createDTMFSender(this.track);\n } else {\n this._dtmf = null;\n }\n }\n return this._dtmf;\n }\n });\n }\n}\n\nexport function shimGetStats(window) {\n if (!window.RTCPeerConnection) {\n return;\n }\n\n const origGetStats = window.RTCPeerConnection.prototype.getStats;\n window.RTCPeerConnection.prototype.getStats = function getStats() {\n const [selector, onSucc, onErr] = arguments;\n\n // If selector is a function then we are in the old style stats so just\n // pass back the original getStats format to avoid breaking old users.\n if (arguments.length > 0 && typeof selector === 'function') {\n return origGetStats.apply(this, arguments);\n }\n\n // When spec-style getStats is supported, return those when called with\n // either no arguments or the selector argument is null.\n if (origGetStats.length === 0 && (arguments.length === 0 ||\n typeof selector !== 'function')) {\n return origGetStats.apply(this, []);\n }\n\n const fixChromeStats_ = function(response) {\n const standardReport = {};\n const reports = response.result();\n reports.forEach(report => {\n const standardStats = {\n id: report.id,\n timestamp: report.timestamp,\n type: {\n localcandidate: 'local-candidate',\n remotecandidate: 'remote-candidate'\n }[report.type] || report.type\n };\n report.names().forEach(name => {\n standardStats[name] = report.stat(name);\n });\n standardReport[standardStats.id] = standardStats;\n });\n\n return standardReport;\n };\n\n // shim getStats with maplike support\n const makeMapStats = function(stats) {\n return new Map(Object.keys(stats).map(key => [key, stats[key]]));\n };\n\n if (arguments.length >= 2) {\n const successCallbackWrapper_ = function(response) {\n onSucc(makeMapStats(fixChromeStats_(response)));\n };\n\n return origGetStats.apply(this, [successCallbackWrapper_,\n selector]);\n }\n\n // promise-support\n return new Promise((resolve, reject) => {\n origGetStats.apply(this, [\n function(response) {\n resolve(makeMapStats(fixChromeStats_(response)));\n }, reject]);\n }).then(onSucc, onErr);\n };\n}\n\nexport function shimSenderReceiverGetStats(window) {\n if (!(typeof window === 'object' && window.RTCPeerConnection &&\n window.RTCRtpSender && window.RTCRtpReceiver)) {\n return;\n }\n\n // shim sender stats.\n if (!('getStats' in window.RTCRtpSender.prototype)) {\n const origGetSenders = window.RTCPeerConnection.prototype.getSenders;\n if (origGetSenders) {\n window.RTCPeerConnection.prototype.getSenders = function getSenders() {\n const senders = origGetSenders.apply(this, []);\n senders.forEach(sender => sender._pc = this);\n return senders;\n };\n }\n\n const origAddTrack = window.RTCPeerConnection.prototype.addTrack;\n if (origAddTrack) {\n window.RTCPeerConnection.prototype.addTrack = function addTrack() {\n const sender = origAddTrack.apply(this, arguments);\n sender._pc = this;\n return sender;\n };\n }\n window.RTCRtpSender.prototype.getStats = function getStats() {\n const sender = this;\n return this._pc.getStats().then(result =>\n /* Note: this will include stats of all senders that\n * send a track with the same id as sender.track as\n * it is not possible to identify the RTCRtpSender.\n */\n utils.filterStats(result, sender.track, true));\n };\n }\n\n // shim receiver stats.\n if (!('getStats' in window.RTCRtpReceiver.prototype)) {\n const origGetReceivers = window.RTCPeerConnection.prototype.getReceivers;\n if (origGetReceivers) {\n window.RTCPeerConnection.prototype.getReceivers =\n function getReceivers() {\n const receivers = origGetReceivers.apply(this, []);\n receivers.forEach(receiver => receiver._pc = this);\n return receivers;\n };\n }\n utils.wrapPeerConnectionEvent(window, 'track', e => {\n e.receiver._pc = e.srcElement;\n return e;\n });\n window.RTCRtpReceiver.prototype.getStats = function getStats() {\n const receiver = this;\n return this._pc.getStats().then(result =>\n utils.filterStats(result, receiver.track, false));\n };\n }\n\n if (!('getStats' in window.RTCRtpSender.prototype &&\n 'getStats' in window.RTCRtpReceiver.prototype)) {\n return;\n }\n\n // shim RTCPeerConnection.getStats(track).\n const origGetStats = window.RTCPeerConnection.prototype.getStats;\n window.RTCPeerConnection.prototype.getStats = function getStats() {\n if (arguments.length > 0 &&\n arguments[0] instanceof window.MediaStreamTrack) {\n const track = arguments[0];\n let sender;\n let receiver;\n let err;\n this.getSenders().forEach(s => {\n if (s.track === track) {\n if (sender) {\n err = true;\n } else {\n sender = s;\n }\n }\n });\n this.getReceivers().forEach(r => {\n if (r.track === track) {\n if (receiver) {\n err = true;\n } else {\n receiver = r;\n }\n }\n return r.track === track;\n });\n if (err || (sender && receiver)) {\n return Promise.reject(new DOMException(\n 'There are more than one sender or receiver for the track.',\n 'InvalidAccessError'));\n } else if (sender) {\n return sender.getStats();\n } else if (receiver) {\n return receiver.getStats();\n }\n return Promise.reject(new DOMException(\n 'There is no sender or receiver for the track.',\n 'InvalidAccessError'));\n }\n return origGetStats.apply(this, arguments);\n };\n}\n\nexport function shimAddTrackRemoveTrackWithNative(window) {\n // shim addTrack/removeTrack with native variants in order to make\n // the interactions with legacy getLocalStreams behave as in other browsers.\n // Keeps a mapping stream.id => [stream, rtpsenders...]\n window.RTCPeerConnection.prototype.getLocalStreams =\n function getLocalStreams() {\n this._shimmedLocalStreams = this._shimmedLocalStreams || {};\n return Object.keys(this._shimmedLocalStreams)\n .map(streamId => this._shimmedLocalStreams[streamId][0]);\n };\n\n const origAddTrack = window.RTCPeerConnection.prototype.addTrack;\n window.RTCPeerConnection.prototype.addTrack =\n function addTrack(track, stream) {\n if (!stream) {\n return origAddTrack.apply(this, arguments);\n }\n this._shimmedLocalStreams = this._shimmedLocalStreams || {};\n\n const sender = origAddTrack.apply(this, arguments);\n if (!this._shimmedLocalStreams[stream.id]) {\n this._shimmedLocalStreams[stream.id] = [stream, sender];\n } else if (this._shimmedLocalStreams[stream.id].indexOf(sender) === -1) {\n this._shimmedLocalStreams[stream.id].push(sender);\n }\n return sender;\n };\n\n const origAddStream = window.RTCPeerConnection.prototype.addStream;\n window.RTCPeerConnection.prototype.addStream = function addStream(stream) {\n this._shimmedLocalStreams = this._shimmedLocalStreams || {};\n\n stream.getTracks().forEach(track => {\n const alreadyExists = this.getSenders().find(s => s.track === track);\n if (alreadyExists) {\n throw new DOMException('Track already exists.',\n 'InvalidAccessError');\n }\n });\n const existingSenders = this.getSenders();\n origAddStream.apply(this, arguments);\n const newSenders = this.getSenders()\n .filter(newSender => existingSenders.indexOf(newSender) === -1);\n this._shimmedLocalStreams[stream.id] = [stream].concat(newSenders);\n };\n\n const origRemoveStream = window.RTCPeerConnection.prototype.removeStream;\n window.RTCPeerConnection.prototype.removeStream =\n function removeStream(stream) {\n this._shimmedLocalStreams = this._shimmedLocalStreams || {};\n delete this._shimmedLocalStreams[stream.id];\n return origRemoveStream.apply(this, arguments);\n };\n\n const origRemoveTrack = window.RTCPeerConnection.prototype.removeTrack;\n window.RTCPeerConnection.prototype.removeTrack =\n function removeTrack(sender) {\n this._shimmedLocalStreams = this._shimmedLocalStreams || {};\n if (sender) {\n Object.keys(this._shimmedLocalStreams).forEach(streamId => {\n const idx = this._shimmedLocalStreams[streamId].indexOf(sender);\n if (idx !== -1) {\n this._shimmedLocalStreams[streamId].splice(idx, 1);\n }\n if (this._shimmedLocalStreams[streamId].length === 1) {\n delete this._shimmedLocalStreams[streamId];\n }\n });\n }\n return origRemoveTrack.apply(this, arguments);\n };\n}\n\nexport function shimAddTrackRemoveTrack(window, browserDetails) {\n if (!window.RTCPeerConnection) {\n return;\n }\n // shim addTrack and removeTrack.\n if (window.RTCPeerConnection.prototype.addTrack &&\n browserDetails.version >= 65) {\n return shimAddTrackRemoveTrackWithNative(window);\n }\n\n // also shim pc.getLocalStreams when addTrack is shimmed\n // to return the original streams.\n const origGetLocalStreams = window.RTCPeerConnection.prototype\n .getLocalStreams;\n window.RTCPeerConnection.prototype.getLocalStreams =\n function getLocalStreams() {\n const nativeStreams = origGetLocalStreams.apply(this);\n this._reverseStreams = this._reverseStreams || {};\n return nativeStreams.map(stream => this._reverseStreams[stream.id]);\n };\n\n const origAddStream = window.RTCPeerConnection.prototype.addStream;\n window.RTCPeerConnection.prototype.addStream = function addStream(stream) {\n this._streams = this._streams || {};\n this._reverseStreams = this._reverseStreams || {};\n\n stream.getTracks().forEach(track => {\n const alreadyExists = this.getSenders().find(s => s.track === track);\n if (alreadyExists) {\n throw new DOMException('Track already exists.',\n 'InvalidAccessError');\n }\n });\n // Add identity mapping for consistency with addTrack.\n // Unless this is being used with a stream from addTrack.\n if (!this._reverseStreams[stream.id]) {\n const newStream = new window.MediaStream(stream.getTracks());\n this._streams[stream.id] = newStream;\n this._reverseStreams[newStream.id] = stream;\n stream = newStream;\n }\n origAddStream.apply(this, [stream]);\n };\n\n const origRemoveStream = window.RTCPeerConnection.prototype.removeStream;\n window.RTCPeerConnection.prototype.removeStream =\n function removeStream(stream) {\n this._streams = this._streams || {};\n this._reverseStreams = this._reverseStreams || {};\n\n origRemoveStream.apply(this, [(this._streams[stream.id] || stream)]);\n delete this._reverseStreams[(this._streams[stream.id] ?\n this._streams[stream.id].id : stream.id)];\n delete this._streams[stream.id];\n };\n\n window.RTCPeerConnection.prototype.addTrack =\n function addTrack(track, stream) {\n if (this.signalingState === 'closed') {\n throw new DOMException(\n 'The RTCPeerConnection\\'s signalingState is \\'closed\\'.',\n 'InvalidStateError');\n }\n const streams = [].slice.call(arguments, 1);\n if (streams.length !== 1 ||\n !streams[0].getTracks().find(t => t === track)) {\n // this is not fully correct but all we can manage without\n // [[associated MediaStreams]] internal slot.\n throw new DOMException(\n 'The adapter.js addTrack polyfill only supports a single ' +\n ' stream which is associated with the specified track.',\n 'NotSupportedError');\n }\n\n const alreadyExists = this.getSenders().find(s => s.track === track);\n if (alreadyExists) {\n throw new DOMException('Track already exists.',\n 'InvalidAccessError');\n }\n\n this._streams = this._streams || {};\n this._reverseStreams = this._reverseStreams || {};\n const oldStream = this._streams[stream.id];\n if (oldStream) {\n // this is using odd Chrome behaviour, use with caution:\n // https://bugs.chromium.org/p/webrtc/issues/detail?id=7815\n // Note: we rely on the high-level addTrack/dtmf shim to\n // create the sender with a dtmf sender.\n oldStream.addTrack(track);\n\n // Trigger ONN async.\n Promise.resolve().then(() => {\n this.dispatchEvent(new Event('negotiationneeded'));\n });\n } else {\n const newStream = new window.MediaStream([track]);\n this._streams[stream.id] = newStream;\n this._reverseStreams[newStream.id] = stream;\n this.addStream(newStream);\n }\n return this.getSenders().find(s => s.track === track);\n };\n\n // replace the internal stream id with the external one and\n // vice versa.\n function replaceInternalStreamId(pc, description) {\n let sdp = description.sdp;\n Object.keys(pc._reverseStreams || []).forEach(internalId => {\n const externalStream = pc._reverseStreams[internalId];\n const internalStream = pc._streams[externalStream.id];\n sdp = sdp.replace(new RegExp(internalStream.id, 'g'),\n externalStream.id);\n });\n return new RTCSessionDescription({\n type: description.type,\n sdp\n });\n }\n function replaceExternalStreamId(pc, description) {\n let sdp = description.sdp;\n Object.keys(pc._reverseStreams || []).forEach(internalId => {\n const externalStream = pc._reverseStreams[internalId];\n const internalStream = pc._streams[externalStream.id];\n sdp = sdp.replace(new RegExp(externalStream.id, 'g'),\n internalStream.id);\n });\n return new RTCSessionDescription({\n type: description.type,\n sdp\n });\n }\n ['createOffer', 'createAnswer'].forEach(function(method) {\n const nativeMethod = window.RTCPeerConnection.prototype[method];\n const methodObj = {[method]() {\n const args = arguments;\n const isLegacyCall = arguments.length &&\n typeof arguments[0] === 'function';\n if (isLegacyCall) {\n return nativeMethod.apply(this, [\n (description) => {\n const desc = replaceInternalStreamId(this, description);\n args[0].apply(null, [desc]);\n },\n (err) => {\n if (args[1]) {\n args[1].apply(null, err);\n }\n }, arguments[2]\n ]);\n }\n return nativeMethod.apply(this, arguments)\n .then(description => replaceInternalStreamId(this, description));\n }};\n window.RTCPeerConnection.prototype[method] = methodObj[method];\n });\n\n const origSetLocalDescription =\n window.RTCPeerConnection.prototype.setLocalDescription;\n window.RTCPeerConnection.prototype.setLocalDescription =\n function setLocalDescription() {\n if (!arguments.length || !arguments[0].type) {\n return origSetLocalDescription.apply(this, arguments);\n }\n arguments[0] = replaceExternalStreamId(this, arguments[0]);\n return origSetLocalDescription.apply(this, arguments);\n };\n\n // TODO: mangle getStats: https://w3c.github.io/webrtc-stats/#dom-rtcmediastreamstats-streamidentifier\n\n const origLocalDescription = Object.getOwnPropertyDescriptor(\n window.RTCPeerConnection.prototype, 'localDescription');\n Object.defineProperty(window.RTCPeerConnection.prototype,\n 'localDescription', {\n get() {\n const description = origLocalDescription.get.apply(this);\n if (description.type === '') {\n return description;\n }\n return replaceInternalStreamId(this, description);\n }\n });\n\n window.RTCPeerConnection.prototype.removeTrack =\n function removeTrack(sender) {\n if (this.signalingState === 'closed') {\n throw new DOMException(\n 'The RTCPeerConnection\\'s signalingState is \\'closed\\'.',\n 'InvalidStateError');\n }\n // We can not yet check for sender instanceof RTCRtpSender\n // since we shim RTPSender. So we check if sender._pc is set.\n if (!sender._pc) {\n throw new DOMException('Argument 1 of RTCPeerConnection.removeTrack ' +\n 'does not implement interface RTCRtpSender.', 'TypeError');\n }\n const isLocal = sender._pc === this;\n if (!isLocal) {\n throw new DOMException('Sender was not created by this connection.',\n 'InvalidAccessError');\n }\n\n // Search for the native stream the senders track belongs to.\n this._streams = this._streams || {};\n let stream;\n Object.keys(this._streams).forEach(streamid => {\n const hasTrack = this._streams[streamid].getTracks()\n .find(track => sender.track === track);\n if (hasTrack) {\n stream = this._streams[streamid];\n }\n });\n\n if (stream) {\n if (stream.getTracks().length === 1) {\n // if this is the last track of the stream, remove the stream. This\n // takes care of any shimmed _senders.\n this.removeStream(this._reverseStreams[stream.id]);\n } else {\n // relying on the same odd chrome behaviour as above.\n stream.removeTrack(sender.track);\n }\n this.dispatchEvent(new Event('negotiationneeded'));\n }\n };\n}\n\nexport function shimPeerConnection(window, browserDetails) {\n if (!window.RTCPeerConnection && window.webkitRTCPeerConnection) {\n // very basic support for old versions.\n window.RTCPeerConnection = window.webkitRTCPeerConnection;\n }\n if (!window.RTCPeerConnection) {\n return;\n }\n\n // shim implicit creation of RTCSessionDescription/RTCIceCandidate\n if (browserDetails.version < 53) {\n ['setLocalDescription', 'setRemoteDescription', 'addIceCandidate']\n .forEach(function(method) {\n const nativeMethod = window.RTCPeerConnection.prototype[method];\n const methodObj = {[method]() {\n arguments[0] = new ((method === 'addIceCandidate') ?\n window.RTCIceCandidate :\n window.RTCSessionDescription)(arguments[0]);\n return nativeMethod.apply(this, arguments);\n }};\n window.RTCPeerConnection.prototype[method] = methodObj[method];\n });\n }\n}\n\n// Attempt to fix ONN in plan-b mode.\nexport function fixNegotiationNeeded(window, browserDetails) {\n utils.wrapPeerConnectionEvent(window, 'negotiationneeded', e => {\n const pc = e.target;\n if (browserDetails.version < 72 || (pc.getConfiguration &&\n pc.getConfiguration().sdpSemantics === 'plan-b')) {\n if (pc.signalingState !== 'stable') {\n return;\n }\n }\n return e;\n });\n}\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\n\nimport * as utils from '../utils';\n\nexport function shimGetUserMedia(window, browserDetails) {\n const navigator = window && window.navigator;\n const MediaStreamTrack = window && window.MediaStreamTrack;\n\n navigator.getUserMedia = function(constraints, onSuccess, onError) {\n // Replace Firefox 44+'s deprecation warning with unprefixed version.\n utils.deprecated('navigator.getUserMedia',\n 'navigator.mediaDevices.getUserMedia');\n navigator.mediaDevices.getUserMedia(constraints).then(onSuccess, onError);\n };\n\n if (!(browserDetails.version > 55 &&\n 'autoGainControl' in navigator.mediaDevices.getSupportedConstraints())) {\n const remap = function(obj, a, b) {\n if (a in obj && !(b in obj)) {\n obj[b] = obj[a];\n delete obj[a];\n }\n };\n\n const nativeGetUserMedia = navigator.mediaDevices.getUserMedia.\n bind(navigator.mediaDevices);\n navigator.mediaDevices.getUserMedia = function(c) {\n if (typeof c === 'object' && typeof c.audio === 'object') {\n c = JSON.parse(JSON.stringify(c));\n remap(c.audio, 'autoGainControl', 'mozAutoGainControl');\n remap(c.audio, 'noiseSuppression', 'mozNoiseSuppression');\n }\n return nativeGetUserMedia(c);\n };\n\n if (MediaStreamTrack && MediaStreamTrack.prototype.getSettings) {\n const nativeGetSettings = MediaStreamTrack.prototype.getSettings;\n MediaStreamTrack.prototype.getSettings = function() {\n const obj = nativeGetSettings.apply(this, arguments);\n remap(obj, 'mozAutoGainControl', 'autoGainControl');\n remap(obj, 'mozNoiseSuppression', 'noiseSuppression');\n return obj;\n };\n }\n\n if (MediaStreamTrack && MediaStreamTrack.prototype.applyConstraints) {\n const nativeApplyConstraints =\n MediaStreamTrack.prototype.applyConstraints;\n MediaStreamTrack.prototype.applyConstraints = function(c) {\n if (this.kind === 'audio' && typeof c === 'object') {\n c = JSON.parse(JSON.stringify(c));\n remap(c, 'autoGainControl', 'mozAutoGainControl');\n remap(c, 'noiseSuppression', 'mozNoiseSuppression');\n }\n return nativeApplyConstraints.apply(this, [c]);\n };\n }\n }\n}\n","/*\n * Copyright (c) 2018 The adapter.js project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\n\nexport function shimGetDisplayMedia(window, preferredMediaSource) {\n if (window.navigator.mediaDevices &&\n 'getDisplayMedia' in window.navigator.mediaDevices) {\n return;\n }\n if (!(window.navigator.mediaDevices)) {\n return;\n }\n window.navigator.mediaDevices.getDisplayMedia =\n function getDisplayMedia(constraints) {\n if (!(constraints && constraints.video)) {\n const err = new DOMException('getDisplayMedia without video ' +\n 'constraints is undefined');\n err.name = 'NotFoundError';\n // from https://heycam.github.io/webidl/#idl-DOMException-error-names\n err.code = 8;\n return Promise.reject(err);\n }\n if (constraints.video === true) {\n constraints.video = {mediaSource: preferredMediaSource};\n } else {\n constraints.video.mediaSource = preferredMediaSource;\n }\n return window.navigator.mediaDevices.getUserMedia(constraints);\n };\n}\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\n\nimport * as utils from '../utils';\nexport {shimGetUserMedia} from './getusermedia';\nexport {shimGetDisplayMedia} from './getdisplaymedia';\n\nexport function shimOnTrack(window) {\n if (typeof window === 'object' && window.RTCTrackEvent &&\n ('receiver' in window.RTCTrackEvent.prototype) &&\n !('transceiver' in window.RTCTrackEvent.prototype)) {\n Object.defineProperty(window.RTCTrackEvent.prototype, 'transceiver', {\n get() {\n return {receiver: this.receiver};\n }\n });\n }\n}\n\nexport function shimPeerConnection(window, browserDetails) {\n if (typeof window !== 'object' ||\n !(window.RTCPeerConnection || window.mozRTCPeerConnection)) {\n return; // probably media.peerconnection.enabled=false in about:config\n }\n if (!window.RTCPeerConnection && window.mozRTCPeerConnection) {\n // very basic support for old versions.\n window.RTCPeerConnection = window.mozRTCPeerConnection;\n }\n\n if (browserDetails.version < 53) {\n // shim away need for obsolete RTCIceCandidate/RTCSessionDescription.\n ['setLocalDescription', 'setRemoteDescription', 'addIceCandidate']\n .forEach(function(method) {\n const nativeMethod = window.RTCPeerConnection.prototype[method];\n const methodObj = {[method]() {\n arguments[0] = new ((method === 'addIceCandidate') ?\n window.RTCIceCandidate :\n window.RTCSessionDescription)(arguments[0]);\n return nativeMethod.apply(this, arguments);\n }};\n window.RTCPeerConnection.prototype[method] = methodObj[method];\n });\n }\n\n const modernStatsTypes = {\n inboundrtp: 'inbound-rtp',\n outboundrtp: 'outbound-rtp',\n candidatepair: 'candidate-pair',\n localcandidate: 'local-candidate',\n remotecandidate: 'remote-candidate'\n };\n\n const nativeGetStats = window.RTCPeerConnection.prototype.getStats;\n window.RTCPeerConnection.prototype.getStats = function getStats() {\n const [selector, onSucc, onErr] = arguments;\n return nativeGetStats.apply(this, [selector || null])\n .then(stats => {\n if (browserDetails.version < 53 && !onSucc) {\n // Shim only promise getStats with spec-hyphens in type names\n // Leave callback version alone; misc old uses of forEach before Map\n try {\n stats.forEach(stat => {\n stat.type = modernStatsTypes[stat.type] || stat.type;\n });\n } catch (e) {\n if (e.name !== 'TypeError') {\n throw e;\n }\n // Avoid TypeError: \"type\" is read-only, in old versions. 34-43ish\n stats.forEach((stat, i) => {\n stats.set(i, Object.assign({}, stat, {\n type: modernStatsTypes[stat.type] || stat.type\n }));\n });\n }\n }\n return stats;\n })\n .then(onSucc, onErr);\n };\n}\n\nexport function shimSenderGetStats(window) {\n if (!(typeof window === 'object' && window.RTCPeerConnection &&\n window.RTCRtpSender)) {\n return;\n }\n if (window.RTCRtpSender && 'getStats' in window.RTCRtpSender.prototype) {\n return;\n }\n const origGetSenders = window.RTCPeerConnection.prototype.getSenders;\n if (origGetSenders) {\n window.RTCPeerConnection.prototype.getSenders = function getSenders() {\n const senders = origGetSenders.apply(this, []);\n senders.forEach(sender => sender._pc = this);\n return senders;\n };\n }\n\n const origAddTrack = window.RTCPeerConnection.prototype.addTrack;\n if (origAddTrack) {\n window.RTCPeerConnection.prototype.addTrack = function addTrack() {\n const sender = origAddTrack.apply(this, arguments);\n sender._pc = this;\n return sender;\n };\n }\n window.RTCRtpSender.prototype.getStats = function getStats() {\n return this.track ? this._pc.getStats(this.track) :\n Promise.resolve(new Map());\n };\n}\n\nexport function shimReceiverGetStats(window) {\n if (!(typeof window === 'object' && window.RTCPeerConnection &&\n window.RTCRtpSender)) {\n return;\n }\n if (window.RTCRtpSender && 'getStats' in window.RTCRtpReceiver.prototype) {\n return;\n }\n const origGetReceivers = window.RTCPeerConnection.prototype.getReceivers;\n if (origGetReceivers) {\n window.RTCPeerConnection.prototype.getReceivers = function getReceivers() {\n const receivers = origGetReceivers.apply(this, []);\n receivers.forEach(receiver => receiver._pc = this);\n return receivers;\n };\n }\n utils.wrapPeerConnectionEvent(window, 'track', e => {\n e.receiver._pc = e.srcElement;\n return e;\n });\n window.RTCRtpReceiver.prototype.getStats = function getStats() {\n return this._pc.getStats(this.track);\n };\n}\n\nexport function shimRemoveStream(window) {\n if (!window.RTCPeerConnection ||\n 'removeStream' in window.RTCPeerConnection.prototype) {\n return;\n }\n window.RTCPeerConnection.prototype.removeStream =\n function removeStream(stream) {\n utils.deprecated('removeStream', 'removeTrack');\n this.getSenders().forEach(sender => {\n if (sender.track && stream.getTracks().includes(sender.track)) {\n this.removeTrack(sender);\n }\n });\n };\n}\n\nexport function shimRTCDataChannel(window) {\n // rename DataChannel to RTCDataChannel (native fix in FF60):\n // https://bugzilla.mozilla.org/show_bug.cgi?id=1173851\n if (window.DataChannel && !window.RTCDataChannel) {\n window.RTCDataChannel = window.DataChannel;\n }\n}\n\nexport function shimAddTransceiver(window) {\n // https://github.com/webrtcHacks/adapter/issues/998#issuecomment-516921647\n // Firefox ignores the init sendEncodings options passed to addTransceiver\n // https://bugzilla.mozilla.org/show_bug.cgi?id=1396918\n if (!(typeof window === 'object' && window.RTCPeerConnection)) {\n return;\n }\n const origAddTransceiver = window.RTCPeerConnection.prototype.addTransceiver;\n if (origAddTransceiver) {\n window.RTCPeerConnection.prototype.addTransceiver =\n function addTransceiver() {\n this.setParametersPromises = [];\n // WebIDL input coercion and validation\n let sendEncodings = arguments[1] && arguments[1].sendEncodings;\n if (sendEncodings === undefined) {\n sendEncodings = [];\n }\n sendEncodings = [...sendEncodings];\n const shouldPerformCheck = sendEncodings.length > 0;\n if (shouldPerformCheck) {\n // If sendEncodings params are provided, validate grammar\n sendEncodings.forEach((encodingParam) => {\n if ('rid' in encodingParam) {\n const ridRegex = /^[a-z0-9]{0,16}$/i;\n if (!ridRegex.test(encodingParam.rid)) {\n throw new TypeError('Invalid RID value provided.');\n }\n }\n if ('scaleResolutionDownBy' in encodingParam) {\n if (!(parseFloat(encodingParam.scaleResolutionDownBy) >= 1.0)) {\n throw new RangeError('scale_resolution_down_by must be >= 1.0');\n }\n }\n if ('maxFramerate' in encodingParam) {\n if (!(parseFloat(encodingParam.maxFramerate) >= 0)) {\n throw new RangeError('max_framerate must be >= 0.0');\n }\n }\n });\n }\n const transceiver = origAddTransceiver.apply(this, arguments);\n if (shouldPerformCheck) {\n // Check if the init options were applied. If not we do this in an\n // asynchronous way and save the promise reference in a global object.\n // This is an ugly hack, but at the same time is way more robust than\n // checking the sender parameters before and after the createOffer\n // Also note that after the createoffer we are not 100% sure that\n // the params were asynchronously applied so we might miss the\n // opportunity to recreate offer.\n const {sender} = transceiver;\n const params = sender.getParameters();\n if (!('encodings' in params) ||\n // Avoid being fooled by patched getParameters() below.\n (params.encodings.length === 1 &&\n Object.keys(params.encodings[0]).length === 0)) {\n params.encodings = sendEncodings;\n sender.sendEncodings = sendEncodings;\n this.setParametersPromises.push(sender.setParameters(params)\n .then(() => {\n delete sender.sendEncodings;\n }).catch(() => {\n delete sender.sendEncodings;\n })\n );\n }\n }\n return transceiver;\n };\n }\n}\n\nexport function shimGetParameters(window) {\n if (!(typeof window === 'object' && window.RTCRtpSender)) {\n return;\n }\n const origGetParameters = window.RTCRtpSender.prototype.getParameters;\n if (origGetParameters) {\n window.RTCRtpSender.prototype.getParameters =\n function getParameters() {\n const params = origGetParameters.apply(this, arguments);\n if (!('encodings' in params)) {\n params.encodings = [].concat(this.sendEncodings || [{}]);\n }\n return params;\n };\n }\n}\n\nexport function shimCreateOffer(window) {\n // https://github.com/webrtcHacks/adapter/issues/998#issuecomment-516921647\n // Firefox ignores the init sendEncodings options passed to addTransceiver\n // https://bugzilla.mozilla.org/show_bug.cgi?id=1396918\n if (!(typeof window === 'object' && window.RTCPeerConnection)) {\n return;\n }\n const origCreateOffer = window.RTCPeerConnection.prototype.createOffer;\n window.RTCPeerConnection.prototype.createOffer = function createOffer() {\n if (this.setParametersPromises && this.setParametersPromises.length) {\n return Promise.all(this.setParametersPromises)\n .then(() => {\n return origCreateOffer.apply(this, arguments);\n })\n .finally(() => {\n this.setParametersPromises = [];\n });\n }\n return origCreateOffer.apply(this, arguments);\n };\n}\n\nexport function shimCreateAnswer(window) {\n // https://github.com/webrtcHacks/adapter/issues/998#issuecomment-516921647\n // Firefox ignores the init sendEncodings options passed to addTransceiver\n // https://bugzilla.mozilla.org/show_bug.cgi?id=1396918\n if (!(typeof window === 'object' && window.RTCPeerConnection)) {\n return;\n }\n const origCreateAnswer = window.RTCPeerConnection.prototype.createAnswer;\n window.RTCPeerConnection.prototype.createAnswer = function createAnswer() {\n if (this.setParametersPromises && this.setParametersPromises.length) {\n return Promise.all(this.setParametersPromises)\n .then(() => {\n return origCreateAnswer.apply(this, arguments);\n })\n .finally(() => {\n this.setParametersPromises = [];\n });\n }\n return origCreateAnswer.apply(this, arguments);\n };\n}\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n'use strict';\nimport * as utils from '../utils';\n\nexport function shimLocalStreamsAPI(window) {\n if (typeof window !== 'object' || !window.RTCPeerConnection) {\n return;\n }\n if (!('getLocalStreams' in window.RTCPeerConnection.prototype)) {\n window.RTCPeerConnection.prototype.getLocalStreams =\n function getLocalStreams() {\n if (!this._localStreams) {\n this._localStreams = [];\n }\n return this._localStreams;\n };\n }\n if (!('addStream' in window.RTCPeerConnection.prototype)) {\n const _addTrack = window.RTCPeerConnection.prototype.addTrack;\n window.RTCPeerConnection.prototype.addStream = function addStream(stream) {\n if (!this._localStreams) {\n this._localStreams = [];\n }\n if (!this._localStreams.includes(stream)) {\n this._localStreams.push(stream);\n }\n // Try to emulate Chrome's behaviour of adding in audio-video order.\n // Safari orders by track id.\n stream.getAudioTracks().forEach(track => _addTrack.call(this, track,\n stream));\n stream.getVideoTracks().forEach(track => _addTrack.call(this, track,\n stream));\n };\n\n window.RTCPeerConnection.prototype.addTrack =\n function addTrack(track, ...streams) {\n if (streams) {\n streams.forEach((stream) => {\n if (!this._localStreams) {\n this._localStreams = [stream];\n } else if (!this._localStreams.includes(stream)) {\n this._localStreams.push(stream);\n }\n });\n }\n return _addTrack.apply(this, arguments);\n };\n }\n if (!('removeStream' in window.RTCPeerConnection.prototype)) {\n window.RTCPeerConnection.prototype.removeStream =\n function removeStream(stream) {\n if (!this._localStreams) {\n this._localStreams = [];\n }\n const index = this._localStreams.indexOf(stream);\n if (index === -1) {\n return;\n }\n this._localStreams.splice(index, 1);\n const tracks = stream.getTracks();\n this.getSenders().forEach(sender => {\n if (tracks.includes(sender.track)) {\n this.removeTrack(sender);\n }\n });\n };\n }\n}\n\nexport function shimRemoteStreamsAPI(window) {\n if (typeof window !== 'object' || !window.RTCPeerConnection) {\n return;\n }\n if (!('getRemoteStreams' in window.RTCPeerConnection.prototype)) {\n window.RTCPeerConnection.prototype.getRemoteStreams =\n function getRemoteStreams() {\n return this._remoteStreams ? this._remoteStreams : [];\n };\n }\n if (!('onaddstream' in window.RTCPeerConnection.prototype)) {\n Object.defineProperty(window.RTCPeerConnection.prototype, 'onaddstream', {\n get() {\n return this._onaddstream;\n },\n set(f) {\n if (this._onaddstream) {\n this.removeEventListener('addstream', this._onaddstream);\n this.removeEventListener('track', this._onaddstreampoly);\n }\n this.addEventListener('addstream', this._onaddstream = f);\n this.addEventListener('track', this._onaddstreampoly = (e) => {\n e.streams.forEach(stream => {\n if (!this._remoteStreams) {\n this._remoteStreams = [];\n }\n if (this._remoteStreams.includes(stream)) {\n return;\n }\n this._remoteStreams.push(stream);\n const event = new Event('addstream');\n event.stream = stream;\n this.dispatchEvent(event);\n });\n });\n }\n });\n const origSetRemoteDescription =\n window.RTCPeerConnection.prototype.setRemoteDescription;\n window.RTCPeerConnection.prototype.setRemoteDescription =\n function setRemoteDescription() {\n const pc = this;\n if (!this._onaddstreampoly) {\n this.addEventListener('track', this._onaddstreampoly = function(e) {\n e.streams.forEach(stream => {\n if (!pc._remoteStreams) {\n pc._remoteStreams = [];\n }\n if (pc._remoteStreams.indexOf(stream) >= 0) {\n return;\n }\n pc._remoteStreams.push(stream);\n const event = new Event('addstream');\n event.stream = stream;\n pc.dispatchEvent(event);\n });\n });\n }\n return origSetRemoteDescription.apply(pc, arguments);\n };\n }\n}\n\nexport function shimCallbacksAPI(window) {\n if (typeof window !== 'object' || !window.RTCPeerConnection) {\n return;\n }\n const prototype = window.RTCPeerConnection.prototype;\n const origCreateOffer = prototype.createOffer;\n const origCreateAnswer = prototype.createAnswer;\n const setLocalDescription = prototype.setLocalDescription;\n const setRemoteDescription = prototype.setRemoteDescription;\n const addIceCandidate = prototype.addIceCandidate;\n\n prototype.createOffer =\n function createOffer(successCallback, failureCallback) {\n const options = (arguments.length >= 2) ? arguments[2] : arguments[0];\n const promise = origCreateOffer.apply(this, [options]);\n if (!failureCallback) {\n return promise;\n }\n promise.then(successCallback, failureCallback);\n return Promise.resolve();\n };\n\n prototype.createAnswer =\n function createAnswer(successCallback, failureCallback) {\n const options = (arguments.length >= 2) ? arguments[2] : arguments[0];\n const promise = origCreateAnswer.apply(this, [options]);\n if (!failureCallback) {\n return promise;\n }\n promise.then(successCallback, failureCallback);\n return Promise.resolve();\n };\n\n let withCallback = function(description, successCallback, failureCallback) {\n const promise = setLocalDescription.apply(this, [description]);\n if (!failureCallback) {\n return promise;\n }\n promise.then(successCallback, failureCallback);\n return Promise.resolve();\n };\n prototype.setLocalDescription = withCallback;\n\n withCallback = function(description, successCallback, failureCallback) {\n const promise = setRemoteDescription.apply(this, [description]);\n if (!failureCallback) {\n return promise;\n }\n promise.then(successCallback, failureCallback);\n return Promise.resolve();\n };\n prototype.setRemoteDescription = withCallback;\n\n withCallback = function(candidate, successCallback, failureCallback) {\n const promise = addIceCandidate.apply(this, [candidate]);\n if (!failureCallback) {\n return promise;\n }\n promise.then(successCallback, failureCallback);\n return Promise.resolve();\n };\n prototype.addIceCandidate = withCallback;\n}\n\nexport function shimGetUserMedia(window) {\n const navigator = window && window.navigator;\n\n if (navigator.mediaDevices && navigator.mediaDevices.getUserMedia) {\n // shim not needed in Safari 12.1\n const mediaDevices = navigator.mediaDevices;\n const _getUserMedia = mediaDevices.getUserMedia.bind(mediaDevices);\n navigator.mediaDevices.getUserMedia = (constraints) => {\n return _getUserMedia(shimConstraints(constraints));\n };\n }\n\n if (!navigator.getUserMedia && navigator.mediaDevices &&\n navigator.mediaDevices.getUserMedia) {\n navigator.getUserMedia = function getUserMedia(constraints, cb, errcb) {\n navigator.mediaDevices.getUserMedia(constraints)\n .then(cb, errcb);\n }.bind(navigator);\n }\n}\n\nexport function shimConstraints(constraints) {\n if (constraints && constraints.video !== undefined) {\n return Object.assign({},\n constraints,\n {video: utils.compactObject(constraints.video)}\n );\n }\n\n return constraints;\n}\n\nexport function shimRTCIceServerUrls(window) {\n if (!window.RTCPeerConnection) {\n return;\n }\n // migrate from non-spec RTCIceServer.url to RTCIceServer.urls\n const OrigPeerConnection = window.RTCPeerConnection;\n window.RTCPeerConnection =\n function RTCPeerConnection(pcConfig, pcConstraints) {\n if (pcConfig && pcConfig.iceServers) {\n const newIceServers = [];\n for (let i = 0; i < pcConfig.iceServers.length; i++) {\n let server = pcConfig.iceServers[i];\n if (server.urls === undefined && server.url) {\n utils.deprecated('RTCIceServer.url', 'RTCIceServer.urls');\n server = JSON.parse(JSON.stringify(server));\n server.urls = server.url;\n delete server.url;\n newIceServers.push(server);\n } else {\n newIceServers.push(pcConfig.iceServers[i]);\n }\n }\n pcConfig.iceServers = newIceServers;\n }\n return new OrigPeerConnection(pcConfig, pcConstraints);\n };\n window.RTCPeerConnection.prototype = OrigPeerConnection.prototype;\n // wrap static methods. Currently just generateCertificate.\n if ('generateCertificate' in OrigPeerConnection) {\n Object.defineProperty(window.RTCPeerConnection, 'generateCertificate', {\n get() {\n return OrigPeerConnection.generateCertificate;\n }\n });\n }\n}\n\nexport function shimTrackEventTransceiver(window) {\n // Add event.transceiver member over deprecated event.receiver\n if (typeof window === 'object' && window.RTCTrackEvent &&\n 'receiver' in window.RTCTrackEvent.prototype &&\n !('transceiver' in window.RTCTrackEvent.prototype)) {\n Object.defineProperty(window.RTCTrackEvent.prototype, 'transceiver', {\n get() {\n return {receiver: this.receiver};\n }\n });\n }\n}\n\nexport function shimCreateOfferLegacy(window) {\n const origCreateOffer = window.RTCPeerConnection.prototype.createOffer;\n window.RTCPeerConnection.prototype.createOffer =\n function createOffer(offerOptions) {\n if (offerOptions) {\n if (typeof offerOptions.offerToReceiveAudio !== 'undefined') {\n // support bit values\n offerOptions.offerToReceiveAudio =\n !!offerOptions.offerToReceiveAudio;\n }\n const audioTransceiver = this.getTransceivers().find(transceiver =>\n transceiver.receiver.track.kind === 'audio');\n if (offerOptions.offerToReceiveAudio === false && audioTransceiver) {\n if (audioTransceiver.direction === 'sendrecv') {\n if (audioTransceiver.setDirection) {\n audioTransceiver.setDirection('sendonly');\n } else {\n audioTransceiver.direction = 'sendonly';\n }\n } else if (audioTransceiver.direction === 'recvonly') {\n if (audioTransceiver.setDirection) {\n audioTransceiver.setDirection('inactive');\n } else {\n audioTransceiver.direction = 'inactive';\n }\n }\n } else if (offerOptions.offerToReceiveAudio === true &&\n !audioTransceiver) {\n this.addTransceiver('audio', {direction: 'recvonly'});\n }\n\n if (typeof offerOptions.offerToReceiveVideo !== 'undefined') {\n // support bit values\n offerOptions.offerToReceiveVideo =\n !!offerOptions.offerToReceiveVideo;\n }\n const videoTransceiver = this.getTransceivers().find(transceiver =>\n transceiver.receiver.track.kind === 'video');\n if (offerOptions.offerToReceiveVideo === false && videoTransceiver) {\n if (videoTransceiver.direction === 'sendrecv') {\n if (videoTransceiver.setDirection) {\n videoTransceiver.setDirection('sendonly');\n } else {\n videoTransceiver.direction = 'sendonly';\n }\n } else if (videoTransceiver.direction === 'recvonly') {\n if (videoTransceiver.setDirection) {\n videoTransceiver.setDirection('inactive');\n } else {\n videoTransceiver.direction = 'inactive';\n }\n }\n } else if (offerOptions.offerToReceiveVideo === true &&\n !videoTransceiver) {\n this.addTransceiver('video', {direction: 'recvonly'});\n }\n }\n return origCreateOffer.apply(this, arguments);\n };\n}\n\nexport function shimAudioContext(window) {\n if (typeof window !== 'object' || window.AudioContext) {\n return;\n }\n window.AudioContext = window.webkitAudioContext;\n}\n\n","/*\n * Copyright (c) 2017 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n'use strict';\n\nimport SDPUtils from 'sdp';\nimport * as utils from './utils';\n\nexport function shimRTCIceCandidate(window) {\n // foundation is arbitrarily chosen as an indicator for full support for\n // https://w3c.github.io/webrtc-pc/#rtcicecandidate-interface\n if (!window.RTCIceCandidate || (window.RTCIceCandidate && 'foundation' in\n window.RTCIceCandidate.prototype)) {\n return;\n }\n\n const NativeRTCIceCandidate = window.RTCIceCandidate;\n window.RTCIceCandidate = function RTCIceCandidate(args) {\n // Remove the a= which shouldn't be part of the candidate string.\n if (typeof args === 'object' && args.candidate &&\n args.candidate.indexOf('a=') === 0) {\n args = JSON.parse(JSON.stringify(args));\n args.candidate = args.candidate.substring(2);\n }\n\n if (args.candidate && args.candidate.length) {\n // Augment the native candidate with the parsed fields.\n const nativeCandidate = new NativeRTCIceCandidate(args);\n const parsedCandidate = SDPUtils.parseCandidate(args.candidate);\n for (const key in parsedCandidate) {\n if (!(key in nativeCandidate)) {\n Object.defineProperty(nativeCandidate, key,\n {value: parsedCandidate[key]});\n }\n }\n\n // Override serializer to not serialize the extra attributes.\n nativeCandidate.toJSON = function toJSON() {\n return {\n candidate: nativeCandidate.candidate,\n sdpMid: nativeCandidate.sdpMid,\n sdpMLineIndex: nativeCandidate.sdpMLineIndex,\n usernameFragment: nativeCandidate.usernameFragment,\n };\n };\n return nativeCandidate;\n }\n return new NativeRTCIceCandidate(args);\n };\n window.RTCIceCandidate.prototype = NativeRTCIceCandidate.prototype;\n\n // Hook up the augmented candidate in onicecandidate and\n // addEventListener('icecandidate', ...)\n utils.wrapPeerConnectionEvent(window, 'icecandidate', e => {\n if (e.candidate) {\n Object.defineProperty(e, 'candidate', {\n value: new window.RTCIceCandidate(e.candidate),\n writable: 'false'\n });\n }\n return e;\n });\n}\n\nexport function shimRTCIceCandidateRelayProtocol(window) {\n if (!window.RTCIceCandidate || (window.RTCIceCandidate && 'relayProtocol' in\n window.RTCIceCandidate.prototype)) {\n return;\n }\n\n // Hook up the augmented candidate in onicecandidate and\n // addEventListener('icecandidate', ...)\n utils.wrapPeerConnectionEvent(window, 'icecandidate', e => {\n if (e.candidate) {\n const parsedCandidate = SDPUtils.parseCandidate(e.candidate.candidate);\n if (parsedCandidate.type === 'relay') {\n // This is a libwebrtc-specific mapping of local type preference\n // to relayProtocol.\n e.candidate.relayProtocol = {\n 0: 'tls',\n 1: 'tcp',\n 2: 'udp',\n }[parsedCandidate.priority >> 24];\n }\n }\n return e;\n });\n}\n\nexport function shimMaxMessageSize(window, browserDetails) {\n if (!window.RTCPeerConnection) {\n return;\n }\n\n if (!('sctp' in window.RTCPeerConnection.prototype)) {\n Object.defineProperty(window.RTCPeerConnection.prototype, 'sctp', {\n get() {\n return typeof this._sctp === 'undefined' ? null : this._sctp;\n }\n });\n }\n\n const sctpInDescription = function(description) {\n if (!description || !description.sdp) {\n return false;\n }\n const sections = SDPUtils.splitSections(description.sdp);\n sections.shift();\n return sections.some(mediaSection => {\n const mLine = SDPUtils.parseMLine(mediaSection);\n return mLine && mLine.kind === 'application'\n && mLine.protocol.indexOf('SCTP') !== -1;\n });\n };\n\n const getRemoteFirefoxVersion = function(description) {\n // TODO: Is there a better solution for detecting Firefox?\n const match = description.sdp.match(/mozilla...THIS_IS_SDPARTA-(\\d+)/);\n if (match === null || match.length < 2) {\n return -1;\n }\n const version = parseInt(match[1], 10);\n // Test for NaN (yes, this is ugly)\n return version !== version ? -1 : version;\n };\n\n const getCanSendMaxMessageSize = function(remoteIsFirefox) {\n // Every implementation we know can send at least 64 KiB.\n // Note: Although Chrome is technically able to send up to 256 KiB, the\n // data does not reach the other peer reliably.\n // See: https://bugs.chromium.org/p/webrtc/issues/detail?id=8419\n let canSendMaxMessageSize = 65536;\n if (browserDetails.browser === 'firefox') {\n if (browserDetails.version < 57) {\n if (remoteIsFirefox === -1) {\n // FF < 57 will send in 16 KiB chunks using the deprecated PPID\n // fragmentation.\n canSendMaxMessageSize = 16384;\n } else {\n // However, other FF (and RAWRTC) can reassemble PPID-fragmented\n // messages. Thus, supporting ~2 GiB when sending.\n canSendMaxMessageSize = 2147483637;\n }\n } else if (browserDetails.version < 60) {\n // Currently, all FF >= 57 will reset the remote maximum message size\n // to the default value when a data channel is created at a later\n // stage. :(\n // See: https://bugzilla.mozilla.org/show_bug.cgi?id=1426831\n canSendMaxMessageSize =\n browserDetails.version === 57 ? 65535 : 65536;\n } else {\n // FF >= 60 supports sending ~2 GiB\n canSendMaxMessageSize = 2147483637;\n }\n }\n return canSendMaxMessageSize;\n };\n\n const getMaxMessageSize = function(description, remoteIsFirefox) {\n // Note: 65536 bytes is the default value from the SDP spec. Also,\n // every implementation we know supports receiving 65536 bytes.\n let maxMessageSize = 65536;\n\n // FF 57 has a slightly incorrect default remote max message size, so\n // we need to adjust it here to avoid a failure when sending.\n // See: https://bugzilla.mozilla.org/show_bug.cgi?id=1425697\n if (browserDetails.browser === 'firefox'\n && browserDetails.version === 57) {\n maxMessageSize = 65535;\n }\n\n const match = SDPUtils.matchPrefix(description.sdp,\n 'a=max-message-size:');\n if (match.length > 0) {\n maxMessageSize = parseInt(match[0].substring(19), 10);\n } else if (browserDetails.browser === 'firefox' &&\n remoteIsFirefox !== -1) {\n // If the maximum message size is not present in the remote SDP and\n // both local and remote are Firefox, the remote peer can receive\n // ~2 GiB.\n maxMessageSize = 2147483637;\n }\n return maxMessageSize;\n };\n\n const origSetRemoteDescription =\n window.RTCPeerConnection.prototype.setRemoteDescription;\n window.RTCPeerConnection.prototype.setRemoteDescription =\n function setRemoteDescription() {\n this._sctp = null;\n // Chrome decided to not expose .sctp in plan-b mode.\n // As usual, adapter.js has to do an 'ugly worakaround'\n // to cover up the mess.\n if (browserDetails.browser === 'chrome' && browserDetails.version >= 76) {\n const {sdpSemantics} = this.getConfiguration();\n if (sdpSemantics === 'plan-b') {\n Object.defineProperty(this, 'sctp', {\n get() {\n return typeof this._sctp === 'undefined' ? null : this._sctp;\n },\n enumerable: true,\n configurable: true,\n });\n }\n }\n\n if (sctpInDescription(arguments[0])) {\n // Check if the remote is FF.\n const isFirefox = getRemoteFirefoxVersion(arguments[0]);\n\n // Get the maximum message size the local peer is capable of sending\n const canSendMMS = getCanSendMaxMessageSize(isFirefox);\n\n // Get the maximum message size of the remote peer.\n const remoteMMS = getMaxMessageSize(arguments[0], isFirefox);\n\n // Determine final maximum message size\n let maxMessageSize;\n if (canSendMMS === 0 && remoteMMS === 0) {\n maxMessageSize = Number.POSITIVE_INFINITY;\n } else if (canSendMMS === 0 || remoteMMS === 0) {\n maxMessageSize = Math.max(canSendMMS, remoteMMS);\n } else {\n maxMessageSize = Math.min(canSendMMS, remoteMMS);\n }\n\n // Create a dummy RTCSctpTransport object and the 'maxMessageSize'\n // attribute.\n const sctp = {};\n Object.defineProperty(sctp, 'maxMessageSize', {\n get() {\n return maxMessageSize;\n }\n });\n this._sctp = sctp;\n }\n\n return origSetRemoteDescription.apply(this, arguments);\n };\n}\n\nexport function shimSendThrowTypeError(window) {\n if (!(window.RTCPeerConnection &&\n 'createDataChannel' in window.RTCPeerConnection.prototype)) {\n return;\n }\n\n // Note: Although Firefox >= 57 has a native implementation, the maximum\n // message size can be reset for all data channels at a later stage.\n // See: https://bugzilla.mozilla.org/show_bug.cgi?id=1426831\n\n function wrapDcSend(dc, pc) {\n const origDataChannelSend = dc.send;\n dc.send = function send() {\n const data = arguments[0];\n const length = data.length || data.size || data.byteLength;\n if (dc.readyState === 'open' &&\n pc.sctp && length > pc.sctp.maxMessageSize) {\n throw new TypeError('Message too large (can send a maximum of ' +\n pc.sctp.maxMessageSize + ' bytes)');\n }\n return origDataChannelSend.apply(dc, arguments);\n };\n }\n const origCreateDataChannel =\n window.RTCPeerConnection.prototype.createDataChannel;\n window.RTCPeerConnection.prototype.createDataChannel =\n function createDataChannel() {\n const dataChannel = origCreateDataChannel.apply(this, arguments);\n wrapDcSend(dataChannel, this);\n return dataChannel;\n };\n utils.wrapPeerConnectionEvent(window, 'datachannel', e => {\n wrapDcSend(e.channel, e.target);\n return e;\n });\n}\n\n\n/* shims RTCConnectionState by pretending it is the same as iceConnectionState.\n * See https://bugs.chromium.org/p/webrtc/issues/detail?id=6145#c12\n * for why this is a valid hack in Chrome. In Firefox it is slightly incorrect\n * since DTLS failures would be hidden. See\n * https://bugzilla.mozilla.org/show_bug.cgi?id=1265827\n * for the Firefox tracking bug.\n */\nexport function shimConnectionState(window) {\n if (!window.RTCPeerConnection ||\n 'connectionState' in window.RTCPeerConnection.prototype) {\n return;\n }\n const proto = window.RTCPeerConnection.prototype;\n Object.defineProperty(proto, 'connectionState', {\n get() {\n return {\n completed: 'connected',\n checking: 'connecting'\n }[this.iceConnectionState] || this.iceConnectionState;\n },\n enumerable: true,\n configurable: true\n });\n Object.defineProperty(proto, 'onconnectionstatechange', {\n get() {\n return this._onconnectionstatechange || null;\n },\n set(cb) {\n if (this._onconnectionstatechange) {\n this.removeEventListener('connectionstatechange',\n this._onconnectionstatechange);\n delete this._onconnectionstatechange;\n }\n if (cb) {\n this.addEventListener('connectionstatechange',\n this._onconnectionstatechange = cb);\n }\n },\n enumerable: true,\n configurable: true\n });\n\n ['setLocalDescription', 'setRemoteDescription'].forEach((method) => {\n const origMethod = proto[method];\n proto[method] = function() {\n if (!this._connectionstatechangepoly) {\n this._connectionstatechangepoly = e => {\n const pc = e.target;\n if (pc._lastConnectionState !== pc.connectionState) {\n pc._lastConnectionState = pc.connectionState;\n const newEvent = new Event('connectionstatechange', e);\n pc.dispatchEvent(newEvent);\n }\n return e;\n };\n this.addEventListener('iceconnectionstatechange',\n this._connectionstatechangepoly);\n }\n return origMethod.apply(this, arguments);\n };\n });\n}\n\nexport function removeExtmapAllowMixed(window, browserDetails) {\n /* remove a=extmap-allow-mixed for webrtc.org < M71 */\n if (!window.RTCPeerConnection) {\n return;\n }\n if (browserDetails.browser === 'chrome' && browserDetails.version >= 71) {\n return;\n }\n if (browserDetails.browser === 'safari' && browserDetails.version >= 605) {\n return;\n }\n const nativeSRD = window.RTCPeerConnection.prototype.setRemoteDescription;\n window.RTCPeerConnection.prototype.setRemoteDescription =\n function setRemoteDescription(desc) {\n if (desc && desc.sdp && desc.sdp.indexOf('\\na=extmap-allow-mixed') !== -1) {\n const sdp = desc.sdp.split('\\n').filter((line) => {\n return line.trim() !== 'a=extmap-allow-mixed';\n }).join('\\n');\n // Safari enforces read-only-ness of RTCSessionDescription fields.\n if (window.RTCSessionDescription &&\n desc instanceof window.RTCSessionDescription) {\n arguments[0] = new window.RTCSessionDescription({\n type: desc.type,\n sdp,\n });\n } else {\n desc.sdp = sdp;\n }\n }\n return nativeSRD.apply(this, arguments);\n };\n}\n\nexport function shimAddIceCandidateNullOrEmpty(window, browserDetails) {\n // Support for addIceCandidate(null or undefined)\n // as well as addIceCandidate({candidate: \"\", ...})\n // https://bugs.chromium.org/p/chromium/issues/detail?id=978582\n // Note: must be called before other polyfills which change the signature.\n if (!(window.RTCPeerConnection && window.RTCPeerConnection.prototype)) {\n return;\n }\n const nativeAddIceCandidate =\n window.RTCPeerConnection.prototype.addIceCandidate;\n if (!nativeAddIceCandidate) {\n return;\n }\n window.RTCPeerConnection.prototype.addIceCandidate =\n function addIceCandidate() {\n if (!arguments[0]) {\n if (arguments[1]) {\n arguments[1].apply(null);\n }\n return Promise.resolve();\n }\n // Firefox 68+ emits and processes {candidate: \"\", ...}, ignore\n // in older versions.\n // Native support for ignoring exists for Chrome M77+.\n // Safari ignores as well, exact version unknown but works in the same\n // version that also ignores addIceCandidate(null).\n if (((browserDetails.browser === 'chrome' && browserDetails.version < 78)\n || (browserDetails.browser === 'firefox'\n && browserDetails.version < 68)\n || (browserDetails.browser === 'safari'))\n && arguments[0] && arguments[0].candidate === '') {\n return Promise.resolve();\n }\n return nativeAddIceCandidate.apply(this, arguments);\n };\n}\n\n// Note: Make sure to call this ahead of APIs that modify\n// setLocalDescription.length\nexport function shimParameterlessSetLocalDescription(window, browserDetails) {\n if (!(window.RTCPeerConnection && window.RTCPeerConnection.prototype)) {\n return;\n }\n const nativeSetLocalDescription =\n window.RTCPeerConnection.prototype.setLocalDescription;\n if (!nativeSetLocalDescription || nativeSetLocalDescription.length === 0) {\n return;\n }\n window.RTCPeerConnection.prototype.setLocalDescription =\n function setLocalDescription() {\n let desc = arguments[0] || {};\n if (typeof desc !== 'object' || (desc.type && desc.sdp)) {\n return nativeSetLocalDescription.apply(this, arguments);\n }\n // The remaining steps should technically happen when SLD comes off the\n // RTCPeerConnection's operations chain (not ahead of going on it), but\n // this is too difficult to shim. Instead, this shim only covers the\n // common case where the operations chain is empty. This is imperfect, but\n // should cover many cases. Rationale: Even if we can't reduce the glare\n // window to zero on imperfect implementations, there's value in tapping\n // into the perfect negotiation pattern that several browsers support.\n desc = {type: desc.type, sdp: desc.sdp};\n if (!desc.type) {\n switch (this.signalingState) {\n case 'stable':\n case 'have-local-offer':\n case 'have-remote-pranswer':\n desc.type = 'offer';\n break;\n default:\n desc.type = 'answer';\n break;\n }\n }\n if (desc.sdp || (desc.type !== 'offer' && desc.type !== 'answer')) {\n return nativeSetLocalDescription.apply(this, [desc]);\n }\n const func = desc.type === 'offer' ? this.createOffer : this.createAnswer;\n return func.apply(this)\n .then(d => nativeSetLocalDescription.apply(this, [d]));\n };\n}\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\nimport * as utils from './utils';\n\n// Browser shims.\nimport * as chromeShim from './chrome/chrome_shim';\nimport * as firefoxShim from './firefox/firefox_shim';\nimport * as safariShim from './safari/safari_shim';\nimport * as commonShim from './common_shim';\nimport * as sdp from 'sdp';\n\n// Shimming starts here.\nexport function adapterFactory({window} = {}, options = {\n shimChrome: true,\n shimFirefox: true,\n shimSafari: true,\n}) {\n // Utils.\n const logging = utils.log;\n const browserDetails = utils.detectBrowser(window);\n\n const adapter = {\n browserDetails,\n commonShim,\n extractVersion: utils.extractVersion,\n disableLog: utils.disableLog,\n disableWarnings: utils.disableWarnings,\n // Expose sdp as a convenience. For production apps include directly.\n sdp,\n };\n\n // Shim browser if found.\n switch (browserDetails.browser) {\n case 'chrome':\n if (!chromeShim || !chromeShim.shimPeerConnection ||\n !options.shimChrome) {\n logging('Chrome shim is not included in this adapter release.');\n return adapter;\n }\n if (browserDetails.version === null) {\n logging('Chrome shim can not determine version, not shimming.');\n return adapter;\n }\n logging('adapter.js shimming chrome.');\n // Export to the adapter global object visible in the browser.\n adapter.browserShim = chromeShim;\n\n // Must be called before shimPeerConnection.\n commonShim.shimAddIceCandidateNullOrEmpty(window, browserDetails);\n commonShim.shimParameterlessSetLocalDescription(window, browserDetails);\n\n chromeShim.shimGetUserMedia(window, browserDetails);\n chromeShim.shimMediaStream(window, browserDetails);\n chromeShim.shimPeerConnection(window, browserDetails);\n chromeShim.shimOnTrack(window, browserDetails);\n chromeShim.shimAddTrackRemoveTrack(window, browserDetails);\n chromeShim.shimGetSendersWithDtmf(window, browserDetails);\n chromeShim.shimGetStats(window, browserDetails);\n chromeShim.shimSenderReceiverGetStats(window, browserDetails);\n chromeShim.fixNegotiationNeeded(window, browserDetails);\n\n commonShim.shimRTCIceCandidate(window, browserDetails);\n commonShim.shimRTCIceCandidateRelayProtocol(window, browserDetails);\n commonShim.shimConnectionState(window, browserDetails);\n commonShim.shimMaxMessageSize(window, browserDetails);\n commonShim.shimSendThrowTypeError(window, browserDetails);\n commonShim.removeExtmapAllowMixed(window, browserDetails);\n break;\n case 'firefox':\n if (!firefoxShim || !firefoxShim.shimPeerConnection ||\n !options.shimFirefox) {\n logging('Firefox shim is not included in this adapter release.');\n return adapter;\n }\n logging('adapter.js shimming firefox.');\n // Export to the adapter global object visible in the browser.\n adapter.browserShim = firefoxShim;\n\n // Must be called before shimPeerConnection.\n commonShim.shimAddIceCandidateNullOrEmpty(window, browserDetails);\n commonShim.shimParameterlessSetLocalDescription(window, browserDetails);\n\n firefoxShim.shimGetUserMedia(window, browserDetails);\n firefoxShim.shimPeerConnection(window, browserDetails);\n firefoxShim.shimOnTrack(window, browserDetails);\n firefoxShim.shimRemoveStream(window, browserDetails);\n firefoxShim.shimSenderGetStats(window, browserDetails);\n firefoxShim.shimReceiverGetStats(window, browserDetails);\n firefoxShim.shimRTCDataChannel(window, browserDetails);\n firefoxShim.shimAddTransceiver(window, browserDetails);\n firefoxShim.shimGetParameters(window, browserDetails);\n firefoxShim.shimCreateOffer(window, browserDetails);\n firefoxShim.shimCreateAnswer(window, browserDetails);\n\n commonShim.shimRTCIceCandidate(window, browserDetails);\n commonShim.shimConnectionState(window, browserDetails);\n commonShim.shimMaxMessageSize(window, browserDetails);\n commonShim.shimSendThrowTypeError(window, browserDetails);\n break;\n case 'safari':\n if (!safariShim || !options.shimSafari) {\n logging('Safari shim is not included in this adapter release.');\n return adapter;\n }\n logging('adapter.js shimming safari.');\n // Export to the adapter global object visible in the browser.\n adapter.browserShim = safariShim;\n\n // Must be called before shimCallbackAPI.\n commonShim.shimAddIceCandidateNullOrEmpty(window, browserDetails);\n commonShim.shimParameterlessSetLocalDescription(window, browserDetails);\n\n safariShim.shimRTCIceServerUrls(window, browserDetails);\n safariShim.shimCreateOfferLegacy(window, browserDetails);\n safariShim.shimCallbacksAPI(window, browserDetails);\n safariShim.shimLocalStreamsAPI(window, browserDetails);\n safariShim.shimRemoteStreamsAPI(window, browserDetails);\n safariShim.shimTrackEventTransceiver(window, browserDetails);\n safariShim.shimGetUserMedia(window, browserDetails);\n safariShim.shimAudioContext(window, browserDetails);\n\n commonShim.shimRTCIceCandidate(window, browserDetails);\n commonShim.shimRTCIceCandidateRelayProtocol(window, browserDetails);\n commonShim.shimMaxMessageSize(window, browserDetails);\n commonShim.shimSendThrowTypeError(window, browserDetails);\n commonShim.removeExtmapAllowMixed(window, browserDetails);\n break;\n default:\n logging('Unsupported browser!');\n break;\n }\n\n return adapter;\n}\n","/*\n * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.\n *\n * Use of this source code is governed by a BSD-style license\n * that can be found in the LICENSE file in the root of the source\n * tree.\n */\n/* eslint-env node */\n\n'use strict';\n\nimport {adapterFactory} from './adapter_factory.js';\n\nconst adapter =\n adapterFactory({window: typeof window === 'undefined' ? undefined : window});\nexport default adapter;\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\n/**\n * GStreamer WebRTC configuration.\n * <p>The config can be passed on creation of the GstWebRTCAPI class.</p>\n * <p>For example:\n * <pre>\n * const signalingProtocol = window.location.protocol.startsWith(\"https\") ? \"wss\" : \"ws\";\n * const api = new GstWebRTCAPI({\n * meta: { name: `WebClient-${Date.now()}` },\n * signalingServerUrl: `${signalingProtocol}://${window.location.host}/webrtc`\n * });\n * </pre></p>\n * @typedef {object} GstWebRTCConfig\n * @property {object} meta=null - Client free-form information that will be exchanged with all peers through the\n * signaling <i>meta</i> property, its content depends on your application.\n * @property {string} signalingServerUrl=ws://127.0.0.1:8443 - The WebRTC signaling server URL.\n * @property {number} reconnectionTimeout=2500 - Timeout in milliseconds to reconnect to the signaling server in\n * case of an unexpected disconnection.\n * @property {object} webrtcConfig={iceServers...} - The WebRTC peer connection configuration passed to\n * {@link external:RTCPeerConnection}. Default configuration only includes a list of free STUN servers\n * (<i>stun[0-4].l.google.com:19302</i>).\n */\nconst defaultConfig = Object.freeze({\n meta: null,\n signalingServerUrl: \"ws://127.0.0.1:8443\",\n reconnectionTimeout: 2500,\n webrtcConfig: {\n iceServers: [\n {\n urls: [\n \"stun:stun.l.google.com:19302\",\n \"stun:stun1.l.google.com:19302\"\n ]\n }\n ]\n }\n});\n\nexport { defaultConfig as default };\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\n/**\n * Session states enumeration.<br>\n * Session state always increases from idle to closed and never switches backwards.\n * @typedef {enum} GstWebRTCAPI.SessionState\n * @readonly\n * @property {0} idle - Default state when creating a new session, goes to <i>connecting</i> when starting\n * the session.\n * @property {1} connecting - Session is trying to connect to remote peers, goes to <i>streaming</i> in case of\n * success or <i>closed</i> in case of error.\n * @property {2} streaming - Session is correctly connected to remote peers and currently streaming audio/video, goes\n * to <i>closed</i> when any peer closes the session.\n * @property {3} closed - Session is closed and can be garbage collected, state will not change anymore.\n */\nconst SessionState = Object.freeze({\n idle: 0,\n connecting: 1,\n streaming: 2,\n closed: 3\n});\n\nexport { SessionState as default };\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport SessionState from \"./session-state.js\";\n\n/**\n * Event name: \"error\".<br>\n * Triggered when any kind of error occurs.\n * <p>When emitted by a session, it is in general an unrecoverable error. Normally, the session is automatically closed\n * but in the specific case of a {@link GstWebRTCAPI.ProducerSession}, when the error occurs on an underlying\n * {@link GstWebRTCAPI.ClientSession} between the producer session and a remote client consuming the streamed media,\n * then only the failing {@link GstWebRTCAPI.ClientSession} is closed. The producer session can keep on serving the\n * other consumer peers.</p>\n * @event GstWebRTCAPI#ErrorEvent\n * @type {external:ErrorEvent}\n * @property {string} message - The error message.\n * @property {external:Error} error - The error exception.\n * @see GstWebRTCAPI.WebRTCSession\n * @see GstWebRTCAPI.RemoteController\n */\n/**\n * Event name: \"stateChanged\".<br>\n * Triggered each time a session state changes.\n * @event GstWebRTCAPI#StateChangedEvent\n * @type {external:Event}\n * @see GstWebRTCAPI.WebRTCSession#state\n */\n/**\n * Event name: \"rtcPeerConnectionChanged\".<br>\n * Triggered each time a session internal {@link external:RTCPeerConnection} changes. This can occur during the session\n * connecting state when the peer-to-peer WebRTC connection is established, and when closing the\n * {@link GstWebRTCAPI.WebRTCSession}.\n * @event GstWebRTCAPI#RTCPeerConnectionChangedEvent\n * @type {external:Event}\n * @see GstWebRTCAPI.WebRTCSession#rtcPeerConnection\n */\n/**\n * Event name: \"closed\".<br>\n * Triggered when a session is definitively closed (then it can be garbage collected as session instances are not\n * reusable).\n * @event GstWebRTCAPI#ClosedEvent\n * @type {external:Event}\n */\n\n/**\n * @class GstWebRTCAPI.WebRTCSession\n * @hideconstructor\n * @classdesc Manages a WebRTC session between a producer and a consumer (peer-to-peer channel).\n * @extends {external:EventTarget}\n * @fires {@link GstWebRTCAPI#event:ErrorEvent}\n * @fires {@link GstWebRTCAPI#event:StateChangedEvent}\n * @fires {@link GstWebRTCAPI#event:RTCPeerConnectionChangedEvent}\n * @fires {@link GstWebRTCAPI#event:ClosedEvent}\n * @see GstWebRTCAPI.ConsumerSession\n * @see GstWebRTCAPI.ProducerSession\n * @see GstWebRTCAPI.ClientSession\n */\nexport default class WebRTCSession extends EventTarget {\n constructor(peerId, comChannel) {\n super();\n\n this._peerId = peerId;\n this._sessionId = \"\";\n this._comChannel = comChannel;\n this._state = SessionState.idle;\n this._rtcPeerConnection = null;\n }\n\n /**\n * Unique identifier of the remote peer to which this session is connected.\n * @member {string} GstWebRTCAPI.WebRTCSession#peerId\n * @readonly\n */\n get peerId() {\n return this._peerId;\n }\n\n /**\n * Unique identifier of this session (defined by the signaling server).<br>\n * The local session ID equals \"\" until it is created on server side. This is done during the connection handshake.\n * The local session ID is guaranteed to be valid and to correctly reflect the signaling server value once\n * session state has switched to {@link GstWebRTCAPI.SessionState#streaming}.\n * @member {string} GstWebRTCAPI.WebRTCSession#sessionId\n * @readonly\n */\n get sessionId() {\n return this._sessionId;\n }\n\n /**\n * The current WebRTC session state.\n * @member {GstWebRTCAPI.SessionState} GstWebRTCAPI.WebRTCSession#state\n * @readonly\n */\n get state() {\n return this._state;\n }\n\n /**\n * The internal {@link external:RTCPeerConnection} used to manage the underlying WebRTC connection with session\n * peer. Value may be null if session has no active WebRTC connection. You can listen to the\n * {@link GstWebRTCAPI#event:RTCPeerConnectionChangedEvent} event to be informed when the connection is established\n * or destroyed.\n * @member {external:RTCPeerConnection} GstWebRTCAPI.WebRTCSession#rtcPeerConnection\n * @readonly\n */\n get rtcPeerConnection() {\n return this._rtcPeerConnection;\n }\n\n /**\n * Terminates the WebRTC session.<br>\n * It immediately disconnects the remote peer attached to this session and unregisters the session from the\n * signaling server.\n * @method GstWebRTCAPI.WebRTCSession#close\n */\n close() {\n if (this._state !== SessionState.closed) {\n if ((this._state !== SessionState.idle) && this._comChannel && this._sessionId) {\n this._comChannel.send({\n type: \"endSession\",\n sessionId: this._sessionId\n });\n }\n\n this._state = SessionState.closed;\n this.dispatchEvent(new Event(\"stateChanged\"));\n\n this._comChannel = null;\n\n if (this._rtcPeerConnection) {\n this._rtcPeerConnection.close();\n this._rtcPeerConnection = null;\n this.dispatchEvent(new Event(\"rtcPeerConnectionChanged\"));\n }\n\n this.dispatchEvent(new Event(\"closed\"));\n }\n }\n}\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\n// mapping is based on https://www.cl.cam.ac.uk/~mgk25/ucs/keysyms.txt\nconst uniToKeySyms = Object.freeze({\n 0x0020: \"space\",\n 0x0021: \"exclam\",\n 0x0022: \"quotedbl\",\n 0x0023: \"numbersign\",\n 0x0024: \"dollar\",\n 0x0025: \"percent\",\n 0x0026: \"ampersand\",\n 0x0027: \"apostrophe\",\n 0x0028: \"parenleft\",\n 0x0029: \"parenright\",\n 0x002a: \"asterisk\",\n 0x002b: \"plus\",\n 0x002c: \"comma\",\n 0x002d: \"minus\",\n 0x002e: \"period\",\n 0x002f: \"slash\",\n 0x0030: \"0\",\n 0x0031: \"1\",\n 0x0032: \"2\",\n 0x0033: \"3\",\n 0x0034: \"4\",\n 0x0035: \"5\",\n 0x0036: \"6\",\n 0x0037: \"7\",\n 0x0038: \"8\",\n 0x0039: \"9\",\n 0x003a: \"colon\",\n 0x003b: \"semicolon\",\n 0x003c: \"less\",\n 0x003d: \"equal\",\n 0x003e: \"greater\",\n 0x003f: \"question\",\n 0x0040: \"at\",\n 0x0041: \"A\",\n 0x0042: \"B\",\n 0x0043: \"C\",\n 0x0044: \"D\",\n 0x0045: \"E\",\n 0x0046: \"F\",\n 0x0047: \"G\",\n 0x0048: \"H\",\n 0x0049: \"I\",\n 0x004a: \"J\",\n 0x004b: \"K\",\n 0x004c: \"L\",\n 0x004d: \"M\",\n 0x004e: \"N\",\n 0x004f: \"O\",\n 0x0050: \"P\",\n 0x0051: \"Q\",\n 0x0052: \"R\",\n 0x0053: \"S\",\n 0x0054: \"T\",\n 0x0055: \"U\",\n 0x0056: \"V\",\n 0x0057: \"W\",\n 0x0058: \"X\",\n 0x0059: \"Y\",\n 0x005a: \"Z\",\n 0x005b: \"bracketleft\",\n 0x005c: \"backslash\",\n 0x005d: \"bracketright\",\n 0x005e: \"asciicircum\",\n 0x005f: \"underscore\",\n 0x0060: \"grave\",\n 0x0061: \"a\",\n 0x0062: \"b\",\n 0x0063: \"c\",\n 0x0064: \"d\",\n 0x0065: \"e\",\n 0x0066: \"f\",\n 0x0067: \"g\",\n 0x0068: \"h\",\n 0x0069: \"i\",\n 0x006a: \"j\",\n 0x006b: \"k\",\n 0x006c: \"l\",\n 0x006d: \"m\",\n 0x006e: \"n\",\n 0x006f: \"o\",\n 0x0070: \"p\",\n 0x0071: \"q\",\n 0x0072: \"r\",\n 0x0073: \"s\",\n 0x0074: \"t\",\n 0x0075: \"u\",\n 0x0076: \"v\",\n 0x0077: \"w\",\n 0x0078: \"x\",\n 0x0079: \"y\",\n 0x007a: \"z\",\n 0x007b: \"braceleft\",\n 0x007c: \"bar\",\n 0x007d: \"braceright\",\n 0x007e: \"asciitilde\",\n 0x00a0: \"nobreakspace\",\n 0x00a1: \"exclamdown\",\n 0x00a2: \"cent\",\n 0x00a3: \"sterling\",\n 0x00a4: \"currency\",\n 0x00a5: \"yen\",\n 0x00a6: \"brokenbar\",\n 0x00a7: \"section\",\n 0x00a8: \"diaeresis\",\n 0x00a9: \"copyright\",\n 0x00aa: \"ordfeminine\",\n 0x00ab: \"guillemotleft\",\n 0x00ac: \"notsign\",\n 0x00ad: \"hyphen\",\n 0x00ae: \"registered\",\n 0x00af: \"macron\",\n 0x00b0: \"degree\",\n 0x00b1: \"plusminus\",\n 0x00b2: \"twosuperior\",\n 0x00b3: \"threesuperior\",\n 0x00b4: \"acute\",\n 0x00b5: \"mu\",\n 0x00b6: \"paragraph\",\n 0x00b7: \"periodcentered\",\n 0x00b8: \"cedilla\",\n 0x00b9: \"onesuperior\",\n 0x00ba: \"masculine\",\n 0x00bb: \"guillemotright\",\n 0x00bc: \"onequarter\",\n 0x00bd: \"onehalf\",\n 0x00be: \"threequarters\",\n 0x00bf: \"questiondown\",\n 0x00c0: \"Agrave\",\n 0x00c1: \"Aacute\",\n 0x00c2: \"Acircumflex\",\n 0x00c3: \"Atilde\",\n 0x00c4: \"Adiaeresis\",\n 0x00c5: \"Aring\",\n 0x00c6: \"AE\",\n 0x00c7: \"Ccedilla\",\n 0x00c8: \"Egrave\",\n 0x00c9: \"Eacute\",\n 0x00ca: \"Ecircumflex\",\n 0x00cb: \"Ediaeresis\",\n 0x00cc: \"Igrave\",\n 0x00cd: \"Iacute\",\n 0x00ce: \"Icircumflex\",\n 0x00cf: \"Idiaeresis\",\n 0x00d0: \"ETH\",\n 0x00d1: \"Ntilde\",\n 0x00d2: \"Ograve\",\n 0x00d3: \"Oacute\",\n 0x00d4: \"Ocircumflex\",\n 0x00d5: \"Otilde\",\n 0x00d6: \"Odiaeresis\",\n 0x00d7: \"multiply\",\n 0x00d8: \"Ooblique\",\n 0x00d9: \"Ugrave\",\n 0x00da: \"Uacute\",\n 0x00db: \"Ucircumflex\",\n 0x00dc: \"Udiaeresis\",\n 0x00dd: \"Yacute\",\n 0x00de: \"THORN\",\n 0x00df: \"ssharp\",\n 0x00e0: \"agrave\",\n 0x00e1: \"aacute\",\n 0x00e2: \"acircumflex\",\n 0x00e3: \"atilde\",\n 0x00e4: \"adiaeresis\",\n 0x00e5: \"aring\",\n 0x00e6: \"ae\",\n 0x00e7: \"ccedilla\",\n 0x00e8: \"egrave\",\n 0x00e9: \"eacute\",\n 0x00ea: \"ecircumflex\",\n 0x00eb: \"ediaeresis\",\n 0x00ec: \"igrave\",\n 0x00ed: \"iacute\",\n 0x00ee: \"icircumflex\",\n 0x00ef: \"idiaeresis\",\n 0x00f0: \"eth\",\n 0x00f1: \"ntilde\",\n 0x00f2: \"ograve\",\n 0x00f3: \"oacute\",\n 0x00f4: \"ocircumflex\",\n 0x00f5: \"otilde\",\n 0x00f6: \"odiaeresis\",\n 0x00f7: \"division\",\n 0x00f8: \"oslash\",\n 0x00f9: \"ugrave\",\n 0x00fa: \"uacute\",\n 0x00fb: \"ucircumflex\",\n 0x00fc: \"udiaeresis\",\n 0x00fd: \"yacute\",\n 0x00fe: \"thorn\",\n 0x00ff: \"ydiaeresis\",\n 0x0104: \"Aogonek\",\n 0x02d8: \"breve\",\n 0x0141: \"Lstroke\",\n 0x013d: \"Lcaron\",\n 0x015a: \"Sacute\",\n 0x0160: \"Scaron\",\n 0x015e: \"Scedilla\",\n 0x0164: \"Tcaron\",\n 0x0179: \"Zacute\",\n 0x017d: \"Zcaron\",\n 0x017b: \"Zabovedot\",\n 0x0105: \"aogonek\",\n 0x02db: \"ogonek\",\n 0x0142: \"lstroke\",\n 0x013e: \"lcaron\",\n 0x015b: \"sacute\",\n 0x02c7: \"caron\",\n 0x0161: \"scaron\",\n 0x015f: \"scedilla\",\n 0x0165: \"tcaron\",\n 0x017a: \"zacute\",\n 0x02dd: \"doubleacute\",\n 0x017e: \"zcaron\",\n 0x017c: \"zabovedot\",\n 0x0154: \"Racute\",\n 0x0102: \"Abreve\",\n 0x0139: \"Lacute\",\n 0x0106: \"Cacute\",\n 0x010c: \"Ccaron\",\n 0x0118: \"Eogonek\",\n 0x011a: \"Ecaron\",\n 0x010e: \"Dcaron\",\n 0x0110: \"Dstroke\",\n 0x0143: \"Nacute\",\n 0x0147: \"Ncaron\",\n 0x0150: \"Odoubleacute\",\n 0x0158: \"Rcaron\",\n 0x016e: \"Uring\",\n 0x0170: \"Udoubleacute\",\n 0x0162: \"Tcedilla\",\n 0x0155: \"racute\",\n 0x0103: \"abreve\",\n 0x013a: \"lacute\",\n 0x0107: \"cacute\",\n 0x010d: \"ccaron\",\n 0x0119: \"eogonek\",\n 0x011b: \"ecaron\",\n 0x010f: \"dcaron\",\n 0x0111: \"dstroke\",\n 0x0144: \"nacute\",\n 0x0148: \"ncaron\",\n 0x0151: \"odoubleacute\",\n 0x0159: \"rcaron\",\n 0x016f: \"uring\",\n 0x0171: \"udoubleacute\",\n 0x0163: \"tcedilla\",\n 0x02d9: \"abovedot\",\n 0x0126: \"Hstroke\",\n 0x0124: \"Hcircumflex\",\n 0x0130: \"Iabovedot\",\n 0x011e: \"Gbreve\",\n 0x0134: \"Jcircumflex\",\n 0x0127: \"hstroke\",\n 0x0125: \"hcircumflex\",\n 0x0131: \"idotless\",\n 0x011f: \"gbreve\",\n 0x0135: \"jcircumflex\",\n 0x010a: \"Cabovedot\",\n 0x0108: \"Ccircumflex\",\n 0x0120: \"Gabovedot\",\n 0x011c: \"Gcircumflex\",\n 0x016c: \"Ubreve\",\n 0x015c: \"Scircumflex\",\n 0x010b: \"cabovedot\",\n 0x0109: \"ccircumflex\",\n 0x0121: \"gabovedot\",\n 0x011d: \"gcircumflex\",\n 0x016d: \"ubreve\",\n 0x015d: \"scircumflex\",\n 0x0138: \"kra\",\n 0x0156: \"Rcedilla\",\n 0x0128: \"Itilde\",\n 0x013b: \"Lcedilla\",\n 0x0112: \"Emacron\",\n 0x0122: \"Gcedilla\",\n 0x0166: \"Tslash\",\n 0x0157: \"rcedilla\",\n 0x0129: \"itilde\",\n 0x013c: \"lcedilla\",\n 0x0113: \"emacron\",\n 0x0123: \"gcedilla\",\n 0x0167: \"tslash\",\n 0x014a: \"ENG\",\n 0x014b: \"eng\",\n 0x0100: \"Amacron\",\n 0x012e: \"Iogonek\",\n 0x0116: \"Eabovedot\",\n 0x012a: \"Imacron\",\n 0x0145: \"Ncedilla\",\n 0x014c: \"Omacron\",\n 0x0136: \"Kcedilla\",\n 0x0172: \"Uogonek\",\n 0x0168: \"Utilde\",\n 0x016a: \"Umacron\",\n 0x0101: \"amacron\",\n 0x012f: \"iogonek\",\n 0x0117: \"eabovedot\",\n 0x012b: \"imacron\",\n 0x0146: \"ncedilla\",\n 0x014d: \"omacron\",\n 0x0137: \"kcedilla\",\n 0x0173: \"uogonek\",\n 0x0169: \"utilde\",\n 0x016b: \"umacron\",\n 0x203e: \"overline\",\n 0x3002: \"kana_fullstop\",\n 0x300c: \"kana_openingbracket\",\n 0x300d: \"kana_closingbracket\",\n 0x3001: \"kana_comma\",\n 0x30fb: \"kana_conjunctive\",\n 0x30f2: \"kana_WO\",\n 0x30a1: \"kana_a\",\n 0x30a3: \"kana_i\",\n 0x30a5: \"kana_u\",\n 0x30a7: \"kana_e\",\n 0x30a9: \"kana_o\",\n 0x30e3: \"kana_ya\",\n 0x30e5: \"kana_yu\",\n 0x30e7: \"kana_yo\",\n 0x30c3: \"kana_tsu\",\n 0x30fc: \"prolongedsound\",\n 0x30a2: \"kana_A\",\n 0x30a4: \"kana_I\",\n 0x30a6: \"kana_U\",\n 0x30a8: \"kana_E\",\n 0x30aa: \"kana_O\",\n 0x30ab: \"kana_KA\",\n 0x30ad: \"kana_KI\",\n 0x30af: \"kana_KU\",\n 0x30b1: \"kana_KE\",\n 0x30b3: \"kana_KO\",\n 0x30b5: \"kana_SA\",\n 0x30b7: \"kana_SHI\",\n 0x30b9: \"kana_SU\",\n 0x30bb: \"kana_SE\",\n 0x30bd: \"kana_SO\",\n 0x30bf: \"kana_TA\",\n 0x30c1: \"kana_CHI\",\n 0x30c4: \"kana_TSU\",\n 0x30c6: \"kana_TE\",\n 0x30c8: \"kana_TO\",\n 0x30ca: \"kana_NA\",\n 0x30cb: \"kana_NI\",\n 0x30cc: \"kana_NU\",\n 0x30cd: \"kana_NE\",\n 0x30ce: \"kana_NO\",\n 0x30cf: \"kana_HA\",\n 0x30d2: \"kana_HI\",\n 0x30d5: \"kana_FU\",\n 0x30d8: \"kana_HE\",\n 0x30db: \"kana_HO\",\n 0x30de: \"kana_MA\",\n 0x30df: \"kana_MI\",\n 0x30e0: \"kana_MU\",\n 0x30e1: \"kana_ME\",\n 0x30e2: \"kana_MO\",\n 0x30e4: \"kana_YA\",\n 0x30e6: \"kana_YU\",\n 0x30e8: \"kana_YO\",\n 0x30e9: \"kana_RA\",\n 0x30ea: \"kana_RI\",\n 0x30eb: \"kana_RU\",\n 0x30ec: \"kana_RE\",\n 0x30ed: \"kana_RO\",\n 0x30ef: \"kana_WA\",\n 0x30f3: \"kana_N\",\n 0x309b: \"voicedsound\",\n 0x309c: \"semivoicedsound\",\n 0x060c: \"Arabic_comma\",\n 0x061b: \"Arabic_semicolon\",\n 0x061f: \"Arabic_question_mark\",\n 0x0621: \"Arabic_hamza\",\n 0x0622: \"Arabic_maddaonalef\",\n 0x0623: \"Arabic_hamzaonalef\",\n 0x0624: \"Arabic_hamzaonwaw\",\n 0x0625: \"Arabic_hamzaunderalef\",\n 0x0626: \"Arabic_hamzaonyeh\",\n 0x0627: \"Arabic_alef\",\n 0x0628: \"Arabic_beh\",\n 0x0629: \"Arabic_tehmarbuta\",\n 0x062a: \"Arabic_teh\",\n 0x062b: \"Arabic_theh\",\n 0x062c: \"Arabic_jeem\",\n 0x062d: \"Arabic_hah\",\n 0x062e: \"Arabic_khah\",\n 0x062f: \"Arabic_dal\",\n 0x0630: \"Arabic_thal\",\n 0x0631: \"Arabic_ra\",\n 0x0632: \"Arabic_zain\",\n 0x0633: \"Arabic_seen\",\n 0x0634: \"Arabic_sheen\",\n 0x0635: \"Arabic_sad\",\n 0x0636: \"Arabic_dad\",\n 0x0637: \"Arabic_tah\",\n 0x0638: \"Arabic_zah\",\n 0x0639: \"Arabic_ain\",\n 0x063a: \"Arabic_ghain\",\n 0x0640: \"Arabic_tatweel\",\n 0x0641: \"Arabic_feh\",\n 0x0642: \"Arabic_qaf\",\n 0x0643: \"Arabic_kaf\",\n 0x0644: \"Arabic_lam\",\n 0x0645: \"Arabic_meem\",\n 0x0646: \"Arabic_noon\",\n 0x0647: \"Arabic_ha\",\n 0x0648: \"Arabic_waw\",\n 0x0649: \"Arabic_alefmaksura\",\n 0x064a: \"Arabic_yeh\",\n 0x064b: \"Arabic_fathatan\",\n 0x064c: \"Arabic_dammatan\",\n 0x064d: \"Arabic_kasratan\",\n 0x064e: \"Arabic_fatha\",\n 0x064f: \"Arabic_damma\",\n 0x0650: \"Arabic_kasra\",\n 0x0651: \"Arabic_shadda\",\n 0x0652: \"Arabic_sukun\",\n 0x0452: \"Serbian_dje\",\n 0x0453: \"Macedonia_gje\",\n 0x0451: \"Cyrillic_io\",\n 0x0454: \"Ukrainian_ie\",\n 0x0455: \"Macedonia_dse\",\n 0x0456: \"Ukrainian_i\",\n 0x0457: \"Ukrainian_yi\",\n 0x0458: \"Cyrillic_je\",\n 0x0459: \"Cyrillic_lje\",\n 0x045a: \"Cyrillic_nje\",\n 0x045b: \"Serbian_tshe\",\n 0x045c: \"Macedonia_kje\",\n 0x045e: \"Byelorussian_shortu\",\n 0x045f: \"Cyrillic_dzhe\",\n 0x2116: \"numerosign\",\n 0x0402: \"Serbian_DJE\",\n 0x0403: \"Macedonia_GJE\",\n 0x0401: \"Cyrillic_IO\",\n 0x0404: \"Ukrainian_IE\",\n 0x0405: \"Macedonia_DSE\",\n 0x0406: \"Ukrainian_I\",\n 0x0407: \"Ukrainian_YI\",\n 0x0408: \"Cyrillic_JE\",\n 0x0409: \"Cyrillic_LJE\",\n 0x040a: \"Cyrillic_NJE\",\n 0x040b: \"Serbian_TSHE\",\n 0x040c: \"Macedonia_KJE\",\n 0x040e: \"Byelorussian_SHORTU\",\n 0x040f: \"Cyrillic_DZHE\",\n 0x044e: \"Cyrillic_yu\",\n 0x0430: \"Cyrillic_a\",\n 0x0431: \"Cyrillic_be\",\n 0x0446: \"Cyrillic_tse\",\n 0x0434: \"Cyrillic_de\",\n 0x0435: \"Cyrillic_ie\",\n 0x0444: \"Cyrillic_ef\",\n 0x0433: \"Cyrillic_ghe\",\n 0x0445: \"Cyrillic_ha\",\n 0x0438: \"Cyrillic_i\",\n 0x0439: \"Cyrillic_shorti\",\n 0x043a: \"Cyrillic_ka\",\n 0x043b: \"Cyrillic_el\",\n 0x043c: \"Cyrillic_em\",\n 0x043d: \"Cyrillic_en\",\n 0x043e: \"Cyrillic_o\",\n 0x043f: \"Cyrillic_pe\",\n 0x044f: \"Cyrillic_ya\",\n 0x0440: \"Cyrillic_er\",\n 0x0441: \"Cyrillic_es\",\n 0x0442: \"Cyrillic_te\",\n 0x0443: \"Cyrillic_u\",\n 0x0436: \"Cyrillic_zhe\",\n 0x0432: \"Cyrillic_ve\",\n 0x044c: \"Cyrillic_softsign\",\n 0x044b: \"Cyrillic_yeru\",\n 0x0437: \"Cyrillic_ze\",\n 0x0448: \"Cyrillic_sha\",\n 0x044d: \"Cyrillic_e\",\n 0x0449: \"Cyrillic_shcha\",\n 0x0447: \"Cyrillic_che\",\n 0x044a: \"Cyrillic_hardsign\",\n 0x042e: \"Cyrillic_YU\",\n 0x0410: \"Cyrillic_A\",\n 0x0411: \"Cyrillic_BE\",\n 0x0426: \"Cyrillic_TSE\",\n 0x0414: \"Cyrillic_DE\",\n 0x0415: \"Cyrillic_IE\",\n 0x0424: \"Cyrillic_EF\",\n 0x0413: \"Cyrillic_GHE\",\n 0x0425: \"Cyrillic_HA\",\n 0x0418: \"Cyrillic_I\",\n 0x0419: \"Cyrillic_SHORTI\",\n 0x041a: \"Cyrillic_KA\",\n 0x041b: \"Cyrillic_EL\",\n 0x041c: \"Cyrillic_EM\",\n 0x041d: \"Cyrillic_EN\",\n 0x041e: \"Cyrillic_O\",\n 0x041f: \"Cyrillic_PE\",\n 0x042f: \"Cyrillic_YA\",\n 0x0420: \"Cyrillic_ER\",\n 0x0421: \"Cyrillic_ES\",\n 0x0422: \"Cyrillic_TE\",\n 0x0423: \"Cyrillic_U\",\n 0x0416: \"Cyrillic_ZHE\",\n 0x0412: \"Cyrillic_VE\",\n 0x042c: \"Cyrillic_SOFTSIGN\",\n 0x042b: \"Cyrillic_YERU\",\n 0x0417: \"Cyrillic_ZE\",\n 0x0428: \"Cyrillic_SHA\",\n 0x042d: \"Cyrillic_E\",\n 0x0429: \"Cyrillic_SHCHA\",\n 0x0427: \"Cyrillic_CHE\",\n 0x042a: \"Cyrillic_HARDSIGN\",\n 0x0386: \"Greek_ALPHAaccent\",\n 0x0388: \"Greek_EPSILONaccent\",\n 0x0389: \"Greek_ETAaccent\",\n 0x038a: \"Greek_IOTAaccent\",\n 0x03aa: \"Greek_IOTAdiaeresis\",\n 0x038c: \"Greek_OMICRONaccent\",\n 0x038e: \"Greek_UPSILONaccent\",\n 0x03ab: \"Greek_UPSILONdieresis\",\n 0x038f: \"Greek_OMEGAaccent\",\n 0x0385: \"Greek_accentdieresis\",\n 0x2015: \"Greek_horizbar\",\n 0x03ac: \"Greek_alphaaccent\",\n 0x03ad: \"Greek_epsilonaccent\",\n 0x03ae: \"Greek_etaaccent\",\n 0x03af: \"Greek_iotaaccent\",\n 0x03ca: \"Greek_iotadieresis\",\n 0x0390: \"Greek_iotaaccentdieresis\",\n 0x03cc: \"Greek_omicronaccent\",\n 0x03cd: \"Greek_upsilonaccent\",\n 0x03cb: \"Greek_upsilondieresis\",\n 0x03b0: \"Greek_upsilonaccentdieresis\",\n 0x03ce: \"Greek_omegaaccent\",\n 0x0391: \"Greek_ALPHA\",\n 0x0392: \"Greek_BETA\",\n 0x0393: \"Greek_GAMMA\",\n 0x0394: \"Greek_DELTA\",\n 0x0395: \"Greek_EPSILON\",\n 0x0396: \"Greek_ZETA\",\n 0x0397: \"Greek_ETA\",\n 0x0398: \"Greek_THETA\",\n 0x0399: \"Greek_IOTA\",\n 0x039a: \"Greek_KAPPA\",\n 0x039b: \"Greek_LAMBDA\",\n 0x039c: \"Greek_MU\",\n 0x039d: \"Greek_NU\",\n 0x039e: \"Greek_XI\",\n 0x039f: \"Greek_OMICRON\",\n 0x03a0: \"Greek_PI\",\n 0x03a1: \"Greek_RHO\",\n 0x03a3: \"Greek_SIGMA\",\n 0x03a4: \"Greek_TAU\",\n 0x03a5: \"Greek_UPSILON\",\n 0x03a6: \"Greek_PHI\",\n 0x03a7: \"Greek_CHI\",\n 0x03a8: \"Greek_PSI\",\n 0x03a9: \"Greek_OMEGA\",\n 0x03b1: \"Greek_alpha\",\n 0x03b2: \"Greek_beta\",\n 0x03b3: \"Greek_gamma\",\n 0x03b4: \"Greek_delta\",\n 0x03b5: \"Greek_epsilon\",\n 0x03b6: \"Greek_zeta\",\n 0x03b7: \"Greek_eta\",\n 0x03b8: \"Greek_theta\",\n 0x03b9: \"Greek_iota\",\n 0x03ba: \"Greek_kappa\",\n 0x03bb: \"Greek_lambda\",\n 0x03bc: \"Greek_mu\",\n 0x03bd: \"Greek_nu\",\n 0x03be: \"Greek_xi\",\n 0x03bf: \"Greek_omicron\",\n 0x03c0: \"Greek_pi\",\n 0x03c1: \"Greek_rho\",\n 0x03c3: \"Greek_sigma\",\n 0x03c2: \"Greek_finalsmallsigma\",\n 0x03c4: \"Greek_tau\",\n 0x03c5: \"Greek_upsilon\",\n 0x03c6: \"Greek_phi\",\n 0x03c7: \"Greek_chi\",\n 0x03c8: \"Greek_psi\",\n 0x03c9: \"Greek_omega\",\n 0x23b7: \"leftradical\",\n 0x2320: \"topintegral\",\n 0x2321: \"botintegral\",\n 0x23a1: \"topleftsqbracket\",\n 0x23a3: \"botleftsqbracket\",\n 0x23a4: \"toprightsqbracket\",\n 0x23a6: \"botrightsqbracket\",\n 0x239b: \"topleftparens\",\n 0x239d: \"botleftparens\",\n 0x239e: \"toprightparens\",\n 0x23a0: \"botrightparens\",\n 0x23a8: \"leftmiddlecurlybrace\",\n 0x23ac: \"rightmiddlecurlybrace\",\n 0x2264: \"lessthanequal\",\n 0x2260: \"notequal\",\n 0x2265: \"greaterthanequal\",\n 0x222b: \"integral\",\n 0x2234: \"therefore\",\n 0x221d: \"variation\",\n 0x221e: \"infinity\",\n 0x2207: \"nabla\",\n 0x223c: \"approximate\",\n 0x2243: \"similarequal\",\n 0x21d4: \"ifonlyif\",\n 0x21d2: \"implies\",\n 0x2261: \"identical\",\n 0x221a: \"radical\",\n 0x2282: \"includedin\",\n 0x2283: \"includes\",\n 0x2229: \"intersection\",\n 0x222a: \"union\",\n 0x2227: \"logicaland\",\n 0x2228: \"logicalor\",\n 0x2202: \"partialderivative\",\n 0x0192: \"function\",\n 0x2190: \"leftarrow\",\n 0x2191: \"uparrow\",\n 0x2192: \"rightarrow\",\n 0x2193: \"downarrow\",\n 0x25c6: \"soliddiamond\",\n 0x2592: \"checkerboard\",\n 0x2409: \"ht\",\n 0x240c: \"ff\",\n 0x240d: \"cr\",\n 0x240a: \"lf\",\n 0x2424: \"nl\",\n 0x240b: \"vt\",\n 0x2518: \"lowrightcorner\",\n 0x2510: \"uprightcorner\",\n 0x250c: \"upleftcorner\",\n 0x2514: \"lowleftcorner\",\n 0x253c: \"crossinglines\",\n 0x23ba: \"horizlinescan1\",\n 0x23bb: \"horizlinescan3\",\n 0x2500: \"horizlinescan5\",\n 0x23bc: \"horizlinescan7\",\n 0x23bd: \"horizlinescan9\",\n 0x251c: \"leftt\",\n 0x2524: \"rightt\",\n 0x2534: \"bott\",\n 0x252c: \"topt\",\n 0x2502: \"vertbar\",\n 0x2003: \"emspace\",\n 0x2002: \"enspace\",\n 0x2004: \"em3space\",\n 0x2005: \"em4space\",\n 0x2007: \"digitspace\",\n 0x2008: \"punctspace\",\n 0x2009: \"thinspace\",\n 0x200a: \"hairspace\",\n 0x2014: \"emdash\",\n 0x2013: \"endash\",\n 0x2423: \"signifblank\",\n 0x2026: \"ellipsis\",\n 0x2025: \"doubbaselinedot\",\n 0x2153: \"onethird\",\n 0x2154: \"twothirds\",\n 0x2155: \"onefifth\",\n 0x2156: \"twofifths\",\n 0x2157: \"threefifths\",\n 0x2158: \"fourfifths\",\n 0x2159: \"onesixth\",\n 0x215a: \"fivesixths\",\n 0x2105: \"careof\",\n 0x2012: \"figdash\",\n 0x27e8: \"leftanglebracket\",\n 0x27e9: \"rightanglebracket\",\n 0x215b: \"oneeighth\",\n 0x215c: \"threeeighths\",\n 0x215d: \"fiveeighths\",\n 0x215e: \"seveneighths\",\n 0x2122: \"trademark\",\n 0x2613: \"signaturemark\",\n 0x25c1: \"leftopentriangle\",\n 0x25b7: \"rightopentriangle\",\n 0x25af: \"emopenrectangle\",\n 0x2018: \"leftsinglequotemark\",\n 0x2019: \"rightsinglequotemark\",\n 0x201c: \"leftdoublequotemark\",\n 0x201d: \"rightdoublequotemark\",\n 0x211e: \"prescription\",\n 0x2032: \"minutes\",\n 0x2033: \"seconds\",\n 0x271d: \"latincross\",\n 0x25ac: \"filledrectbullet\",\n 0x25c0: \"filledlefttribullet\",\n 0x25b6: \"filledrighttribullet\",\n 0x25cf: \"emfilledcircle\",\n 0x25ae: \"emfilledrect\",\n 0x25e6: \"enopencircbullet\",\n 0x25ab: \"enopensquarebullet\",\n 0x25ad: \"openrectbullet\",\n 0x25b3: \"opentribulletup\",\n 0x25bd: \"opentribulletdown\",\n 0x2606: \"openstar\",\n 0x2022: \"enfilledcircbullet\",\n 0x25aa: \"enfilledsqbullet\",\n 0x25b2: \"filledtribulletup\",\n 0x25bc: \"filledtribulletdown\",\n 0x261c: \"leftpointer\",\n 0x261e: \"rightpointer\",\n 0x2663: \"club\",\n 0x2666: \"diamond\",\n 0x2665: \"heart\",\n 0x2720: \"maltesecross\",\n 0x2020: \"dagger\",\n 0x2021: \"doubledagger\",\n 0x2713: \"checkmark\",\n 0x2717: \"ballotcross\",\n 0x266f: \"musicalsharp\",\n 0x266d: \"musicalflat\",\n 0x2642: \"malesymbol\",\n 0x2640: \"femalesymbol\",\n 0x260e: \"telephone\",\n 0x2315: \"telephonerecorder\",\n 0x2117: \"phonographcopyright\",\n 0x2038: \"caret\",\n 0x201a: \"singlelowquotemark\",\n 0x201e: \"doublelowquotemark\",\n 0x22a5: \"downtack\",\n 0x230a: \"downstile\",\n 0x2218: \"jot\",\n 0x2395: \"quad\",\n 0x22a4: \"uptack\",\n 0x25cb: \"circle\",\n 0x2308: \"upstile\",\n 0x22a2: \"lefttack\",\n 0x22a3: \"righttack\",\n 0x2017: \"hebrew_doublelowline\",\n 0x05d0: \"hebrew_aleph\",\n 0x05d1: \"hebrew_beth\",\n 0x05d2: \"hebrew_gimmel\",\n 0x05d3: \"hebrew_daleth\",\n 0x05d4: \"hebrew_he\",\n 0x05d5: \"hebrew_waw\",\n 0x05d6: \"hebrew_zayin\",\n 0x05d7: \"hebrew_het\",\n 0x05d8: \"hebrew_teth\",\n 0x05d9: \"hebrew_yod\",\n 0x05da: \"hebrew_finalkaph\",\n 0x05db: \"hebrew_kaph\",\n 0x05dc: \"hebrew_lamed\",\n 0x05dd: \"hebrew_finalmem\",\n 0x05de: \"hebrew_mem\",\n 0x05df: \"hebrew_finalnun\",\n 0x05e0: \"hebrew_nun\",\n 0x05e1: \"hebrew_samekh\",\n 0x05e2: \"hebrew_ayin\",\n 0x05e3: \"hebrew_finalpe\",\n 0x05e4: \"hebrew_pe\",\n 0x05e5: \"hebrew_finalzadi\",\n 0x05e6: \"hebrew_zadi\",\n 0x05e7: \"hebrew_qoph\",\n 0x05e8: \"hebrew_resh\",\n 0x05e9: \"hebrew_shin\",\n 0x05ea: \"hebrew_taw\",\n 0x0e01: \"Thai_kokai\",\n 0x0e02: \"Thai_khokhai\",\n 0x0e03: \"Thai_khokhuat\",\n 0x0e04: \"Thai_khokhwai\",\n 0x0e05: \"Thai_khokhon\",\n 0x0e06: \"Thai_khorakhang\",\n 0x0e07: \"Thai_ngongu\",\n 0x0e08: \"Thai_chochan\",\n 0x0e09: \"Thai_choching\",\n 0x0e0a: \"Thai_chochang\",\n 0x0e0b: \"Thai_soso\",\n 0x0e0c: \"Thai_chochoe\",\n 0x0e0d: \"Thai_yoying\",\n 0x0e0e: \"Thai_dochada\",\n 0x0e0f: \"Thai_topatak\",\n 0x0e10: \"Thai_thothan\",\n 0x0e11: \"Thai_thonangmontho\",\n 0x0e12: \"Thai_thophuthao\",\n 0x0e13: \"Thai_nonen\",\n 0x0e14: \"Thai_dodek\",\n 0x0e15: \"Thai_totao\",\n 0x0e16: \"Thai_thothung\",\n 0x0e17: \"Thai_thothahan\",\n 0x0e18: \"Thai_thothong\",\n 0x0e19: \"Thai_nonu\",\n 0x0e1a: \"Thai_bobaimai\",\n 0x0e1b: \"Thai_popla\",\n 0x0e1c: \"Thai_phophung\",\n 0x0e1d: \"Thai_fofa\",\n 0x0e1e: \"Thai_phophan\",\n 0x0e1f: \"Thai_fofan\",\n 0x0e20: \"Thai_phosamphao\",\n 0x0e21: \"Thai_moma\",\n 0x0e22: \"Thai_yoyak\",\n 0x0e23: \"Thai_rorua\",\n 0x0e24: \"Thai_ru\",\n 0x0e25: \"Thai_loling\",\n 0x0e26: \"Thai_lu\",\n 0x0e27: \"Thai_wowaen\",\n 0x0e28: \"Thai_sosala\",\n 0x0e29: \"Thai_sorusi\",\n 0x0e2a: \"Thai_sosua\",\n 0x0e2b: \"Thai_hohip\",\n 0x0e2c: \"Thai_lochula\",\n 0x0e2d: \"Thai_oang\",\n 0x0e2e: \"Thai_honokhuk\",\n 0x0e2f: \"Thai_paiyannoi\",\n 0x0e30: \"Thai_saraa\",\n 0x0e31: \"Thai_maihanakat\",\n 0x0e32: \"Thai_saraaa\",\n 0x0e33: \"Thai_saraam\",\n 0x0e34: \"Thai_sarai\",\n 0x0e35: \"Thai_saraii\",\n 0x0e36: \"Thai_saraue\",\n 0x0e37: \"Thai_sarauee\",\n 0x0e38: \"Thai_sarau\",\n 0x0e39: \"Thai_sarauu\",\n 0x0e3a: \"Thai_phinthu\",\n 0x0e3f: \"Thai_baht\",\n 0x0e40: \"Thai_sarae\",\n 0x0e41: \"Thai_saraae\",\n 0x0e42: \"Thai_sarao\",\n 0x0e43: \"Thai_saraaimaimuan\",\n 0x0e44: \"Thai_saraaimaimalai\",\n 0x0e45: \"Thai_lakkhangyao\",\n 0x0e46: \"Thai_maiyamok\",\n 0x0e47: \"Thai_maitaikhu\",\n 0x0e48: \"Thai_maiek\",\n 0x0e49: \"Thai_maitho\",\n 0x0e4a: \"Thai_maitri\",\n 0x0e4b: \"Thai_maichattawa\",\n 0x0e4c: \"Thai_thanthakhat\",\n 0x0e4d: \"Thai_nikhahit\",\n 0x0e50: \"Thai_leksun\",\n 0x0e51: \"Thai_leknung\",\n 0x0e52: \"Thai_leksong\",\n 0x0e53: \"Thai_leksam\",\n 0x0e54: \"Thai_leksi\",\n 0x0e55: \"Thai_lekha\",\n 0x0e56: \"Thai_lekhok\",\n 0x0e57: \"Thai_lekchet\",\n 0x0e58: \"Thai_lekpaet\",\n 0x0e59: \"Thai_lekkao\",\n 0x3131: \"Hangul_Kiyeog\",\n 0x3132: \"Hangul_SsangKiyeog\",\n 0x3133: \"Hangul_KiyeogSios\",\n 0x3134: \"Hangul_Nieun\",\n 0x3135: \"Hangul_NieunJieuj\",\n 0x3136: \"Hangul_NieunHieuh\",\n 0x3137: \"Hangul_Dikeud\",\n 0x3138: \"Hangul_SsangDikeud\",\n 0x3139: \"Hangul_Rieul\",\n 0x313a: \"Hangul_RieulKiyeog\",\n 0x313b: \"Hangul_RieulMieum\",\n 0x313c: \"Hangul_RieulPieub\",\n 0x313d: \"Hangul_RieulSios\",\n 0x313e: \"Hangul_RieulTieut\",\n 0x313f: \"Hangul_RieulPhieuf\",\n 0x3140: \"Hangul_RieulHieuh\",\n 0x3141: \"Hangul_Mieum\",\n 0x3142: \"Hangul_Pieub\",\n 0x3143: \"Hangul_SsangPieub\",\n 0x3144: \"Hangul_PieubSios\",\n 0x3145: \"Hangul_Sios\",\n 0x3146: \"Hangul_SsangSios\",\n 0x3147: \"Hangul_Ieung\",\n 0x3148: \"Hangul_Jieuj\",\n 0x3149: \"Hangul_SsangJieuj\",\n 0x314a: \"Hangul_Cieuc\",\n 0x314b: \"Hangul_Khieuq\",\n 0x314c: \"Hangul_Tieut\",\n 0x314d: \"Hangul_Phieuf\",\n 0x314e: \"Hangul_Hieuh\",\n 0x314f: \"Hangul_A\",\n 0x3150: \"Hangul_AE\",\n 0x3151: \"Hangul_YA\",\n 0x3152: \"Hangul_YAE\",\n 0x3153: \"Hangul_EO\",\n 0x3154: \"Hangul_E\",\n 0x3155: \"Hangul_YEO\",\n 0x3156: \"Hangul_YE\",\n 0x3157: \"Hangul_O\",\n 0x3158: \"Hangul_WA\",\n 0x3159: \"Hangul_WAE\",\n 0x315a: \"Hangul_OE\",\n 0x315b: \"Hangul_YO\",\n 0x315c: \"Hangul_U\",\n 0x315d: \"Hangul_WEO\",\n 0x315e: \"Hangul_WE\",\n 0x315f: \"Hangul_WI\",\n 0x3160: \"Hangul_YU\",\n 0x3161: \"Hangul_EU\",\n 0x3162: \"Hangul_YI\",\n 0x3163: \"Hangul_I\",\n 0x11a8: \"Hangul_J_Kiyeog\",\n 0x11a9: \"Hangul_J_SsangKiyeog\",\n 0x11aa: \"Hangul_J_KiyeogSios\",\n 0x11ab: \"Hangul_J_Nieun\",\n 0x11ac: \"Hangul_J_NieunJieuj\",\n 0x11ad: \"Hangul_J_NieunHieuh\",\n 0x11ae: \"Hangul_J_Dikeud\",\n 0x11af: \"Hangul_J_Rieul\",\n 0x11b0: \"Hangul_J_RieulKiyeog\",\n 0x11b1: \"Hangul_J_RieulMieum\",\n 0x11b2: \"Hangul_J_RieulPieub\",\n 0x11b3: \"Hangul_J_RieulSios\",\n 0x11b4: \"Hangul_J_RieulTieut\",\n 0x11b5: \"Hangul_J_RieulPhieuf\",\n 0x11b6: \"Hangul_J_RieulHieuh\",\n 0x11b7: \"Hangul_J_Mieum\",\n 0x11b8: \"Hangul_J_Pieub\",\n 0x11b9: \"Hangul_J_PieubSios\",\n 0x11ba: \"Hangul_J_Sios\",\n 0x11bb: \"Hangul_J_SsangSios\",\n 0x11bc: \"Hangul_J_Ieung\",\n 0x11bd: \"Hangul_J_Jieuj\",\n 0x11be: \"Hangul_J_Cieuc\",\n 0x11bf: \"Hangul_J_Khieuq\",\n 0x11c0: \"Hangul_J_Tieut\",\n 0x11c1: \"Hangul_J_Phieuf\",\n 0x11c2: \"Hangul_J_Hieuh\",\n 0x316d: \"Hangul_RieulYeorinHieuh\",\n 0x3171: \"Hangul_SunkyeongeumMieum\",\n 0x3178: \"Hangul_SunkyeongeumPieub\",\n 0x317f: \"Hangul_PanSios\",\n 0x3181: \"Hangul_KkogjiDalrinIeung\",\n 0x3184: \"Hangul_SunkyeongeumPhieuf\",\n 0x3186: \"Hangul_YeorinHieuh\",\n 0x318d: \"Hangul_AraeA\",\n 0x318e: \"Hangul_AraeAE\",\n 0x11eb: \"Hangul_J_PanSios\",\n 0x11f0: \"Hangul_J_KkogjiDalrinIeung\",\n 0x11f9: \"Hangul_J_YeorinHieuh\",\n 0x0152: \"OE\",\n 0x0153: \"oe\",\n 0x0178: \"Ydiaeresis\",\n 0x20a0: \"EcuSign\",\n 0x20a1: \"ColonSign\",\n 0x20a2: \"CruzeiroSign\",\n 0x20a3: \"FFrancSign\",\n 0x20a4: \"LiraSign\",\n 0x20a5: \"MillSign\",\n 0x20a6: \"NairaSign\",\n 0x20a7: \"PesetaSign\",\n 0x20a8: \"RupeeSign\",\n 0x20a9: \"WonSign\",\n 0x20aa: \"NewSheqelSign\",\n 0x20ab: \"DongSign\",\n 0x20ac: \"EuroSign\",\n 0x0300: \"dead_grave\",\n 0x0301: \"dead_acute\",\n 0x0302: \"dead_circumflex\",\n 0x0303: \"dead_tilde\",\n 0x0304: \"dead_macron\",\n 0x0306: \"dead_breve\",\n 0x0307: \"dead_abovedot\",\n 0x0308: \"dead_diaeresis\",\n 0x030a: \"dead_abovering\",\n 0x030b: \"dead_doubleacute\",\n 0x030c: \"dead_caron\",\n 0x0327: \"dead_cedilla\",\n 0x0328: \"dead_ogonek\",\n 0x0345: \"dead_iota\",\n 0x3099: \"dead_voiced_sound\",\n 0x309a: \"dead_semivoiced_sound\",\n 0x0008: \"BackSpace\",\n 0x0009: \"Tab\",\n 0x000a: \"Linefeed\",\n 0x000b: \"Clear\",\n 0x000d: \"Return\",\n 0x0013: \"Pause\",\n 0x0014: \"Scroll_Lock\",\n 0x0015: \"Sys_Req\",\n 0x001b: \"Escape\",\n 0x0491: \"Ukrainian_ghe_with_upturn\",\n 0x0490: \"Ukrainian_GHE_WITH_UPTURN\",\n 0x0587: \"Armenian_ligature_ew\",\n 0x0589: \"Armenian_verjaket\",\n 0x055d: \"Armenian_but\",\n 0x058a: \"Armenian_yentamna\",\n 0x055c: \"Armenian_amanak\",\n 0x055b: \"Armenian_shesht\",\n 0x055e: \"Armenian_paruyk\",\n 0x0531: \"Armenian_AYB\",\n 0x0561: \"Armenian_ayb\",\n 0x0532: \"Armenian_BEN\",\n 0x0562: \"Armenian_ben\",\n 0x0533: \"Armenian_GIM\",\n 0x0563: \"Armenian_gim\",\n 0x0534: \"Armenian_DA\",\n 0x0564: \"Armenian_da\",\n 0x0535: \"Armenian_YECH\",\n 0x0565: \"Armenian_yech\",\n 0x0536: \"Armenian_ZA\",\n 0x0566: \"Armenian_za\",\n 0x0537: \"Armenian_E\",\n 0x0567: \"Armenian_e\",\n 0x0538: \"Armenian_AT\",\n 0x0568: \"Armenian_at\",\n 0x0539: \"Armenian_TO\",\n 0x0569: \"Armenian_to\",\n 0x053a: \"Armenian_ZHE\",\n 0x056a: \"Armenian_zhe\",\n 0x053b: \"Armenian_INI\",\n 0x056b: \"Armenian_ini\",\n 0x053c: \"Armenian_LYUN\",\n 0x056c: \"Armenian_lyun\",\n 0x053d: \"Armenian_KHE\",\n 0x056d: \"Armenian_khe\",\n 0x053e: \"Armenian_TSA\",\n 0x056e: \"Armenian_tsa\",\n 0x053f: \"Armenian_KEN\",\n 0x056f: \"Armenian_ken\",\n 0x0540: \"Armenian_HO\",\n 0x0570: \"Armenian_ho\",\n 0x0541: \"Armenian_DZA\",\n 0x0571: \"Armenian_dza\",\n 0x0542: \"Armenian_GHAT\",\n 0x0572: \"Armenian_ghat\",\n 0x0543: \"Armenian_TCHE\",\n 0x0573: \"Armenian_tche\",\n 0x0544: \"Armenian_MEN\",\n 0x0574: \"Armenian_men\",\n 0x0545: \"Armenian_HI\",\n 0x0575: \"Armenian_hi\",\n 0x0546: \"Armenian_NU\",\n 0x0576: \"Armenian_nu\",\n 0x0547: \"Armenian_SHA\",\n 0x0577: \"Armenian_sha\",\n 0x0548: \"Armenian_VO\",\n 0x0578: \"Armenian_vo\",\n 0x0549: \"Armenian_CHA\",\n 0x0579: \"Armenian_cha\",\n 0x054a: \"Armenian_PE\",\n 0x057a: \"Armenian_pe\",\n 0x054b: \"Armenian_JE\",\n 0x057b: \"Armenian_je\",\n 0x054c: \"Armenian_RA\",\n 0x057c: \"Armenian_ra\",\n 0x054d: \"Armenian_SE\",\n 0x057d: \"Armenian_se\",\n 0x054e: \"Armenian_VEV\",\n 0x057e: \"Armenian_vev\",\n 0x054f: \"Armenian_TYUN\",\n 0x057f: \"Armenian_tyun\",\n 0x0550: \"Armenian_RE\",\n 0x0580: \"Armenian_re\",\n 0x0551: \"Armenian_TSO\",\n 0x0581: \"Armenian_tso\",\n 0x0552: \"Armenian_VYUN\",\n 0x0582: \"Armenian_vyun\",\n 0x0553: \"Armenian_PYUR\",\n 0x0583: \"Armenian_pyur\",\n 0x0554: \"Armenian_KE\",\n 0x0584: \"Armenian_ke\",\n 0x0555: \"Armenian_O\",\n 0x0585: \"Armenian_o\",\n 0x0556: \"Armenian_FE\",\n 0x0586: \"Armenian_fe\",\n 0x055a: \"Armenian_apostrophe\",\n 0x10d0: \"Georgian_an\",\n 0x10d1: \"Georgian_ban\",\n 0x10d2: \"Georgian_gan\",\n 0x10d3: \"Georgian_don\",\n 0x10d4: \"Georgian_en\",\n 0x10d5: \"Georgian_vin\",\n 0x10d6: \"Georgian_zen\",\n 0x10d7: \"Georgian_tan\",\n 0x10d8: \"Georgian_in\",\n 0x10d9: \"Georgian_kan\",\n 0x10da: \"Georgian_las\",\n 0x10db: \"Georgian_man\",\n 0x10dc: \"Georgian_nar\",\n 0x10dd: \"Georgian_on\",\n 0x10de: \"Georgian_par\",\n 0x10df: \"Georgian_zhar\",\n 0x10e0: \"Georgian_rae\",\n 0x10e1: \"Georgian_san\",\n 0x10e2: \"Georgian_tar\",\n 0x10e3: \"Georgian_un\",\n 0x10e4: \"Georgian_phar\",\n 0x10e5: \"Georgian_khar\",\n 0x10e6: \"Georgian_ghan\",\n 0x10e7: \"Georgian_qar\",\n 0x10e8: \"Georgian_shin\",\n 0x10e9: \"Georgian_chin\",\n 0x10ea: \"Georgian_can\",\n 0x10eb: \"Georgian_jil\",\n 0x10ec: \"Georgian_cil\",\n 0x10ed: \"Georgian_char\",\n 0x10ee: \"Georgian_xan\",\n 0x10ef: \"Georgian_jhan\",\n 0x10f0: \"Georgian_hae\",\n 0x10f1: \"Georgian_he\",\n 0x10f2: \"Georgian_hie\",\n 0x10f3: \"Georgian_we\",\n 0x10f4: \"Georgian_har\",\n 0x10f5: \"Georgian_hoe\",\n 0x10f6: \"Georgian_fi\",\n 0x1e02: \"Babovedot\",\n 0x1e03: \"babovedot\",\n 0x1e0a: \"Dabovedot\",\n 0x1e80: \"Wgrave\",\n 0x1e82: \"Wacute\",\n 0x1e0b: \"dabovedot\",\n 0x1ef2: \"Ygrave\",\n 0x1e1e: \"Fabovedot\",\n 0x1e1f: \"fabovedot\",\n 0x1e40: \"Mabovedot\",\n 0x1e41: \"mabovedot\",\n 0x1e56: \"Pabovedot\",\n 0x1e81: \"wgrave\",\n 0x1e57: \"pabovedot\",\n 0x1e83: \"wacute\",\n 0x1e60: \"Sabovedot\",\n 0x1ef3: \"ygrave\",\n 0x1e84: \"Wdiaeresis\",\n 0x1e85: \"wdiaeresis\",\n 0x1e61: \"sabovedot\",\n 0x0174: \"Wcircumflex\",\n 0x1e6a: \"Tabovedot\",\n 0x0176: \"Ycircumflex\",\n 0x0175: \"wcircumflex\",\n 0x1e6b: \"tabovedot\",\n 0x0177: \"ycircumflex\",\n 0x06f0: \"Farsi_0\",\n 0x06f1: \"Farsi_1\",\n 0x06f2: \"Farsi_2\",\n 0x06f3: \"Farsi_3\",\n 0x06f4: \"Farsi_4\",\n 0x06f5: \"Farsi_5\",\n 0x06f6: \"Farsi_6\",\n 0x06f7: \"Farsi_7\",\n 0x06f8: \"Farsi_8\",\n 0x06f9: \"Farsi_9\",\n 0x066a: \"Arabic_percent\",\n 0x0670: \"Arabic_superscript_alef\",\n 0x0679: \"Arabic_tteh\",\n 0x067e: \"Arabic_peh\",\n 0x0686: \"Arabic_tcheh\",\n 0x0688: \"Arabic_ddal\",\n 0x0691: \"Arabic_rreh\",\n 0x06d4: \"Arabic_fullstop\",\n 0x0660: \"Arabic_0\",\n 0x0661: \"Arabic_1\",\n 0x0662: \"Arabic_2\",\n 0x0663: \"Arabic_3\",\n 0x0664: \"Arabic_4\",\n 0x0665: \"Arabic_5\",\n 0x0666: \"Arabic_6\",\n 0x0667: \"Arabic_7\",\n 0x0668: \"Arabic_8\",\n 0x0669: \"Arabic_9\",\n 0x0653: \"Arabic_madda_above\",\n 0x0654: \"Arabic_hamza_above\",\n 0x0655: \"Arabic_hamza_below\",\n 0x0698: \"Arabic_jeh\",\n 0x06a4: \"Arabic_veh\",\n 0x06a9: \"Arabic_keheh\",\n 0x06af: \"Arabic_gaf\",\n 0x06ba: \"Arabic_noon_ghunna\",\n 0x06be: \"Arabic_heh_doachashmee\",\n 0x06cc: \"Farsi_yeh\",\n 0x06d2: \"Arabic_yeh_baree\",\n 0x06c1: \"Arabic_heh_goal\",\n 0x0492: \"Cyrillic_GHE_bar\",\n 0x0496: \"Cyrillic_ZHE_descender\",\n 0x049a: \"Cyrillic_KA_descender\",\n 0x049c: \"Cyrillic_KA_vertstroke\",\n 0x04a2: \"Cyrillic_EN_descender\",\n 0x04ae: \"Cyrillic_U_straight\",\n 0x04b0: \"Cyrillic_U_straight_bar\",\n 0x04b2: \"Cyrillic_HA_descender\",\n 0x04b6: \"Cyrillic_CHE_descender\",\n 0x04b8: \"Cyrillic_CHE_vertstroke\",\n 0x04ba: \"Cyrillic_SHHA\",\n 0x04d8: \"Cyrillic_SCHWA\",\n 0x04e2: \"Cyrillic_I_macron\",\n 0x04e8: \"Cyrillic_O_bar\",\n 0x04ee: \"Cyrillic_U_macron\",\n 0x0493: \"Cyrillic_ghe_bar\",\n 0x0497: \"Cyrillic_zhe_descender\",\n 0x049b: \"Cyrillic_ka_descender\",\n 0x049d: \"Cyrillic_ka_vertstroke\",\n 0x04a3: \"Cyrillic_en_descender\",\n 0x04af: \"Cyrillic_u_straight\",\n 0x04b1: \"Cyrillic_u_straight_bar\",\n 0x04b3: \"Cyrillic_ha_descender\",\n 0x04b7: \"Cyrillic_che_descender\",\n 0x04b9: \"Cyrillic_che_vertstroke\",\n 0x04bb: \"Cyrillic_shha\",\n 0x04d9: \"Cyrillic_schwa\",\n 0x04e3: \"Cyrillic_i_macron\",\n 0x04e9: \"Cyrillic_o_bar\",\n 0x04ef: \"Cyrillic_u_macron\",\n 0x1e8a: \"Xabovedot\",\n 0x012c: \"Ibreve\",\n 0x01b5: \"Zstroke\",\n 0x01e6: \"Gcaron\",\n 0x019f: \"Obarred\",\n 0x1e8b: \"xabovedot\",\n 0x012d: \"ibreve\",\n 0x01b6: \"zstroke\",\n 0x01e7: \"gcaron\",\n 0x01d2: \"ocaron\",\n 0x0275: \"obarred\",\n 0x018f: \"SCHWA\",\n 0x0259: \"schwa\",\n 0x1e36: \"Lbelowdot\",\n 0x1e37: \"lbelowdot\",\n 0x1ea0: \"Abelowdot\",\n 0x1ea1: \"abelowdot\",\n 0x1ea2: \"Ahook\",\n 0x1ea3: \"ahook\",\n 0x1ea4: \"Acircumflexacute\",\n 0x1ea5: \"acircumflexacute\",\n 0x1ea6: \"Acircumflexgrave\",\n 0x1ea7: \"acircumflexgrave\",\n 0x1ea8: \"Acircumflexhook\",\n 0x1ea9: \"acircumflexhook\",\n 0x1eaa: \"Acircumflextilde\",\n 0x1eab: \"acircumflextilde\",\n 0x1eac: \"Acircumflexbelowdot\",\n 0x1ead: \"acircumflexbelowdot\",\n 0x1eae: \"Abreveacute\",\n 0x1eaf: \"abreveacute\",\n 0x1eb0: \"Abrevegrave\",\n 0x1eb1: \"abrevegrave\",\n 0x1eb2: \"Abrevehook\",\n 0x1eb3: \"abrevehook\",\n 0x1eb4: \"Abrevetilde\",\n 0x1eb5: \"abrevetilde\",\n 0x1eb6: \"Abrevebelowdot\",\n 0x1eb7: \"abrevebelowdot\",\n 0x1eb8: \"Ebelowdot\",\n 0x1eb9: \"ebelowdot\",\n 0x1eba: \"Ehook\",\n 0x1ebb: \"ehook\",\n 0x1ebc: \"Etilde\",\n 0x1ebd: \"etilde\",\n 0x1ebe: \"Ecircumflexacute\",\n 0x1ebf: \"ecircumflexacute\",\n 0x1ec0: \"Ecircumflexgrave\",\n 0x1ec1: \"ecircumflexgrave\",\n 0x1ec2: \"Ecircumflexhook\",\n 0x1ec3: \"ecircumflexhook\",\n 0x1ec4: \"Ecircumflextilde\",\n 0x1ec5: \"ecircumflextilde\",\n 0x1ec6: \"Ecircumflexbelowdot\",\n 0x1ec7: \"ecircumflexbelowdot\",\n 0x1ec8: \"Ihook\",\n 0x1ec9: \"ihook\",\n 0x1eca: \"Ibelowdot\",\n 0x1ecb: \"ibelowdot\",\n 0x1ecc: \"Obelowdot\",\n 0x1ecd: \"obelowdot\",\n 0x1ece: \"Ohook\",\n 0x1ecf: \"ohook\",\n 0x1ed0: \"Ocircumflexacute\",\n 0x1ed1: \"ocircumflexacute\",\n 0x1ed2: \"Ocircumflexgrave\",\n 0x1ed3: \"ocircumflexgrave\",\n 0x1ed4: \"Ocircumflexhook\",\n 0x1ed5: \"ocircumflexhook\",\n 0x1ed6: \"Ocircumflextilde\",\n 0x1ed7: \"ocircumflextilde\",\n 0x1ed8: \"Ocircumflexbelowdot\",\n 0x1ed9: \"ocircumflexbelowdot\",\n 0x1eda: \"Ohornacute\",\n 0x1edb: \"ohornacute\",\n 0x1edc: \"Ohorngrave\",\n 0x1edd: \"ohorngrave\",\n 0x1ede: \"Ohornhook\",\n 0x1edf: \"ohornhook\",\n 0x1ee0: \"Ohorntilde\",\n 0x1ee1: \"ohorntilde\",\n 0x1ee2: \"Ohornbelowdot\",\n 0x1ee3: \"ohornbelowdot\",\n 0x1ee4: \"Ubelowdot\",\n 0x1ee5: \"ubelowdot\",\n 0x1ee6: \"Uhook\",\n 0x1ee7: \"uhook\",\n 0x1ee8: \"Uhornacute\",\n 0x1ee9: \"uhornacute\",\n 0x1eea: \"Uhorngrave\",\n 0x1eeb: \"uhorngrave\",\n 0x1eec: \"Uhornhook\",\n 0x1eed: \"uhornhook\",\n 0x1eee: \"Uhorntilde\",\n 0x1eef: \"uhorntilde\",\n 0x1ef0: \"Uhornbelowdot\",\n 0x1ef1: \"uhornbelowdot\",\n 0x1ef4: \"Ybelowdot\",\n 0x1ef5: \"ybelowdot\",\n 0x1ef6: \"Yhook\",\n 0x1ef7: \"yhook\",\n 0x1ef8: \"Ytilde\",\n 0x1ef9: \"ytilde\",\n 0x01a0: \"Ohorn\",\n 0x01a1: \"ohorn\",\n 0x01af: \"Uhorn\",\n 0x01b0: \"uhorn\",\n 0x0323: \"dead_belowdot\",\n 0x0309: \"dead_hook\",\n 0x031b: \"dead_horn\"\n});\n\n// mapping is based on https://developer.mozilla.org/en-US/docs/Web/API/UI_Events/Keyboard_event_key_values\nconst kbEventCodesToKeySyms = Object.freeze({\n \"AltLeft\": \"Alt_L\",\n \"AltRight\": \"Alt_R\",\n \"ArrowDown\": \"Down\",\n \"ArrowLeft\": \"Left\",\n \"ArrowRight\": \"Right\",\n \"ArrowUp\": \"Up\",\n \"Backspace\": \"BackSpace\",\n \"CapsLock\": \"Caps_Lock\",\n \"ControlLeft\": \"Control_L\",\n \"ControlRight\": \"Control_R\",\n \"Enter\": \"Return\",\n \"HyperLeft\": \"Hyper_L\",\n \"HyperRight\": \"Hyper_R\",\n \"NumLock\": \"Num_Lock\",\n \"NumpadEnter\": \"Return\",\n \"MetaLeft\": \"Meta_L\",\n \"MetaRight\": \"Meta_R\",\n \"PageDown\": \"Page_Down\",\n \"PageUp\": \"Page_Up\",\n \"ScrollLock\": \"Scroll_Lock\",\n \"ShiftLeft\": \"Shift_L\",\n \"ShiftRight\": \"Shift_R\",\n \"SuperLeft\": \"Super_L\",\n \"SuperRight\": \"Super_R\"\n});\n\n// these Keyboard Event codes direclty map to X11 Keysyms\nconst knownKbEventCodes = new Set([\n \"Clear\", \"Copy\", \"Cut\", \"Delete\", \"End\", \"F1\", \"F2\", \"F3\", \"F4\", \"F5\", \"F6\", \"F7\", \"F8\", \"F9\", \"F10\", \"F11\", \"F12\",\n \"Home\", \"Insert\", \"Paste\", \"Redo\", \"Tab\", \"Undo\"\n]);\n\n/**\n * Returns X11 keySym (defined in https://www.cl.cam.ac.uk/~mgk25/ucs/keysyms.txt) for a given key/code from the key[up/down] event\n * For keys with length 1 (ASCII, Cyrillic etc) - uses uniToKeySyms mapping\n * For keys with length > 1 (Modifiers, Whitespaces, Navigation etc) - uses knownKbEventCodes and kbEventCodesToKeySyms mapping\n *\n * @param {string} key 'key' from the key[up/down] event\n * @param {string} code 'code' from the key[up/down] event\n * @return {string} keySymString (X11 keysym string)\n */\nexport default function getKeysymString(key, code) {\n var keySym = \"Unidentified\";\n if (key.length === 1) {\n const keyCodeUni = key.charCodeAt(0);\n if (keyCodeUni in uniToKeySyms) {\n keySym = uniToKeySyms[keyCodeUni];\n }\n } else if (code in kbEventCodesToKeySyms) {\n keySym = kbEventCodesToKeySyms[code];\n } else if (knownKbEventCodes.has(code)) {\n keySym = code;\n }\n return keySym;\n}\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport getKeysymString from \"./keysyms.js\";\n\nconst eventsNames = Object.freeze([\n \"wheel\",\n \"contextmenu\",\n \"mousemove\",\n \"mousedown\",\n \"mouseup\",\n \"touchstart\",\n \"touchend\",\n \"touchmove\",\n \"touchcancel\",\n \"keyup\",\n \"keydown\"\n]);\n\nconst mouseEventsNames = Object.freeze({\n mousemove: \"MouseMove\",\n mousedown: \"MouseButtonPress\",\n mouseup: \"MouseButtonRelease\"\n});\n\nconst touchEventsNames = Object.freeze({\n touchstart: \"TouchDown\",\n touchend: \"TouchUp\",\n touchmove: \"TouchMotion\",\n touchcancel: \"TouchUp\"\n});\n\nconst keyboardEventsNames = Object.freeze({\n keydown: \"KeyPress\",\n keyup: \"KeyRelease\"\n});\n\nfunction getModifiers(event) {\n const modifiers = [];\n if (event.altKey) {\n modifiers.push(\"mod1-mask\");\n }\n\n if (event.ctrlKey) {\n modifiers.push(\"control-mask\");\n }\n\n if (event.metaKey) {\n modifiers.push(\"meta-mask\");\n }\n\n if (event.shiftKey) {\n modifiers.push(\"shift-mask\");\n }\n\n return modifiers.join(\"+\");\n}\n\n/**\n * @class GstWebRTCAPI.RemoteController\n * @hideconstructor\n * @classdesc Manages a specific WebRTC data channel created by a remote GStreamer webrtcsink producer and offering\n * remote control of the producer through\n * [GstNavigation]{@link https://gstreamer.freedesktop.org/documentation/video/gstnavigation.html} events.\n * <p>The remote control data channel is created by the GStreamer webrtcsink element on the producer side. Then it is\n * announced through the consumer session thanks to the {@link gstWebRTCAPI#event:RemoteControllerChangedEvent}\n * event.</p>\n * <p>You can attach an {@link external:HTMLVideoElement} to the remote controller, then all mouse and keyboard events\n * emitted by this element will be automatically relayed to the remote producer.</p>\n * @extends {external:EventTarget}\n * @fires {@link GstWebRTCAPI#event:ErrorEvent}\n * @fires {@link GstWebRTCAPI#event:ClosedEvent}\n * @see GstWebRTCAPI.ConsumerSession#remoteController\n * @see GstWebRTCAPI.RemoteController#attachVideoElement\n * @see https://gitlab.freedesktop.org/gstreamer/gst-plugins-rs/-/tree/main/net/webrtc/gstwebrtc-api#produce-a-gstreamer-interactive-webrtc-stream-with-remote-control\n */\nexport default class RemoteController extends EventTarget {\n constructor(rtcDataChannel, consumerSession) {\n super();\n\n this._rtcDataChannel = rtcDataChannel;\n this._consumerSession = consumerSession;\n\n this._videoElement = null;\n this._videoElementComputedStyle = null;\n this._videoElementKeyboard = null;\n this._lastTouchEventTimestamp = 0;\n\n rtcDataChannel.addEventListener(\"close\", () => {\n if (this._rtcDataChannel === rtcDataChannel) {\n this.close();\n }\n });\n\n rtcDataChannel.addEventListener(\"error\", (event) => {\n if (this._rtcDataChannel === rtcDataChannel) {\n const error = event.error;\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: (error && error.message) || \"Remote controller error\",\n error: error || new Error(\"unknown error on the remote controller data channel\")\n }));\n }\n });\n }\n\n /**\n * The underlying WebRTC data channel connected to a remote GStreamer webrtcsink producer offering remote control.\n * The value may be null if the remote controller has been closed.\n * @member {external:RTCDataChannel} GstWebRTCAPI.RemoteController#rtcDataChannel\n * @readonly\n */\n get rtcDataChannel() {\n return this._rtcDataChannel;\n }\n\n /**\n * The consumer session associated with this remote controller.\n * @member {GstWebRTCAPI.ConsumerSession} GstWebRTCAPI.RemoteController#consumerSession\n * @readonly\n */\n get consumerSession() {\n return this._consumerSession;\n }\n\n /**\n * The video element that is currently used to send all mouse and keyboard events to the remote producer. Value may\n * be null if no video element is attached.\n * @member {external:HTMLVideoElement} GstWebRTCAPI.RemoteController#videoElement\n * @readonly\n * @see GstWebRTCAPI.RemoteController#attachVideoElement\n */\n get videoElement() {\n return this._videoElement;\n }\n\n /**\n * Associates a video element with this remote controller.<br>\n * When a video element is attached to this remote controller, all mouse and keyboard events emitted by this\n * element will be sent to the remote GStreamer webrtcink producer.\n * @method GstWebRTCAPI.RemoteController#attachVideoElement\n * @param {external:HTMLVideoElement|null} element - the video element to use to relay mouse and keyboard events,\n * or null to detach any previously attached element. If the provided element parameter is not null and not a\n * valid instance of an {@link external:HTMLVideoElement}, then the method does nothing.\n */\n attachVideoElement(element) {\n if ((element instanceof HTMLVideoElement) && (element !== this._videoElement)) {\n if (this._videoElement) {\n this.attachVideoElement(null);\n }\n\n this._videoElement = element;\n this._videoElementComputedStyle = window.getComputedStyle(element);\n\n for (const eventName of eventsNames) {\n element.addEventListener(eventName, this);\n }\n\n element.setAttribute(\"tabindex\", \"0\");\n } else if ((element === null) && this._videoElement) {\n const previousElement = this._videoElement;\n previousElement.removeAttribute(\"tabindex\");\n\n this._videoElement = null;\n this._videoElementComputedStyle = null;\n\n this._lastTouchEventTimestamp = 0;\n\n for (const eventName of eventsNames) {\n previousElement.removeEventListener(eventName, this);\n }\n }\n }\n\n /**\n * Closes the remote controller channel.<br>\n * It immediately shuts down the underlying WebRTC data channel connected to a remote GStreamer webrtcsink\n * producer and detaches any video element that may be used to relay mouse and keyboard events.\n * @method GstWebRTCAPI.RemoteController#close\n */\n close() {\n this.attachVideoElement(null);\n\n const rtcDataChannel = this._rtcDataChannel;\n this._rtcDataChannel = null;\n\n if (rtcDataChannel) {\n rtcDataChannel.close();\n this.dispatchEvent(new Event(\"closed\"));\n }\n }\n\n _sendGstNavigationEvent(data) {\n try {\n if (!data || (typeof (data) !== \"object\")) {\n throw new Error(\"invalid GstNavigation event\");\n }\n\n if (!this._rtcDataChannel) {\n throw new Error(\"remote controller data channel is closed\");\n }\n\n this._rtcDataChannel.send(JSON.stringify(data));\n } catch (ex) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: `cannot send GstNavigation event over session ${this._consumerSession.sessionId} remote controller`,\n error: ex\n }));\n }\n }\n\n _computeVideoMousePosition(event) {\n const mousePos = { x: 0, y: 0 };\n if (!this._videoElement || (this._videoElement.videoWidth <= 0) || (this._videoElement.videoHeight <= 0)) {\n return mousePos;\n }\n\n const padding = {\n left: parseFloat(this._videoElementComputedStyle.paddingLeft),\n right: parseFloat(this._videoElementComputedStyle.paddingRight),\n top: parseFloat(this._videoElementComputedStyle.paddingTop),\n bottom: parseFloat(this._videoElementComputedStyle.paddingBottom)\n };\n\n if ((\"offsetX\" in event) && (\"offsetY\" in event)) {\n mousePos.x = event.offsetX - padding.left;\n mousePos.y = event.offsetY - padding.top;\n } else {\n const clientRect = this._videoElement.getBoundingClientRect();\n const border = {\n left: parseFloat(this._videoElementComputedStyle.borderLeftWidth),\n top: parseFloat(this._videoElementComputedStyle.borderTopWidth)\n };\n mousePos.x = event.clientX - clientRect.left - border.left - padding.left;\n mousePos.y = event.clientY - clientRect.top - border.top - padding.top;\n }\n\n const videoOffset = {\n x: this._videoElement.clientWidth - (padding.left + padding.right),\n y: this._videoElement.clientHeight - (padding.top + padding.bottom)\n };\n\n const ratio = Math.min(videoOffset.x / this._videoElement.videoWidth, videoOffset.y / this._videoElement.videoHeight);\n videoOffset.x = Math.max(0.5 * (videoOffset.x - this._videoElement.videoWidth * ratio), 0);\n videoOffset.y = Math.max(0.5 * (videoOffset.y - this._videoElement.videoHeight * ratio), 0);\n\n const invRatio = (ratio !== 0) ? (1 / ratio) : 0;\n mousePos.x = (mousePos.x - videoOffset.x) * invRatio;\n mousePos.y = (mousePos.y - videoOffset.y) * invRatio;\n\n mousePos.x = Math.min(Math.max(mousePos.x, 0), this._videoElement.videoWidth);\n mousePos.y = Math.min(Math.max(mousePos.y, 0), this._videoElement.videoHeight);\n\n return mousePos;\n }\n\n handleEvent(event) {\n if (!this._videoElement) {\n return;\n }\n\n switch (event.type) {\n case \"wheel\":\n event.preventDefault();\n {\n const mousePos = this._computeVideoMousePosition(event);\n this._sendGstNavigationEvent({\n event: \"MouseScroll\",\n x: mousePos.x,\n y: mousePos.y,\n delta_x: -event.deltaX, // eslint-disable-line camelcase\n delta_y: -event.deltaY, // eslint-disable-line camelcase\n modifier_state: getModifiers(event) // eslint-disable-line camelcase\n });\n }\n break;\n\n case \"contextmenu\":\n event.preventDefault();\n break;\n\n case \"mousemove\":\n case \"mousedown\":\n case \"mouseup\":\n event.preventDefault();\n {\n const mousePos = this._computeVideoMousePosition(event);\n const data = {\n event: mouseEventsNames[event.type],\n x: mousePos.x,\n y: mousePos.y,\n modifier_state: getModifiers(event) // eslint-disable-line camelcase\n };\n\n if (event.type !== \"mousemove\") {\n data.button = event.button + 1;\n\n if ((event.type === \"mousedown\") && (event.button === 0)) {\n this._videoElement.focus();\n }\n }\n\n this._sendGstNavigationEvent(data);\n }\n break;\n\n case \"touchstart\":\n case \"touchend\":\n case \"touchmove\":\n case \"touchcancel\":\n for (const touch of event.changedTouches) {\n const mousePos = this._computeVideoMousePosition(touch);\n const data = {\n event: touchEventsNames[event.type],\n identifier: touch.identifier,\n x: mousePos.x,\n y: mousePos.y,\n modifier_state: getModifiers(event) // eslint-disable-line camelcase\n };\n\n if ((\"force\" in touch) && ((event.type === \"touchstart\") || (event.type === \"touchmove\"))) {\n data.pressure = touch.force;\n }\n\n this._sendGstNavigationEvent(data);\n }\n\n if (event.timeStamp > this._lastTouchEventTimestamp) {\n this._lastTouchEventTimestamp = event.timeStamp;\n this._sendGstNavigationEvent({\n event: \"TouchFrame\",\n modifier_state: getModifiers(event) // eslint-disable-line camelcase\n });\n }\n break;\n case \"keyup\":\n case \"keydown\":\n event.preventDefault();\n {\n const data = {\n event: keyboardEventsNames[event.type],\n key: getKeysymString(event.key, event.code),\n modifier_state: getModifiers(event) // eslint-disable-line camelcase\n };\n this._sendGstNavigationEvent(data);\n }\n break;\n }\n }\n}\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport WebRTCSession from \"./webrtc-session.js\";\nimport SessionState from \"./session-state.js\";\nimport RemoteController from \"./remote-controller.js\";\n\n/**\n * Event name: \"streamsChanged\".<br>\n * Triggered when the underlying media streams of a {@link GstWebRTCAPI.ConsumerSession} change.\n * @event GstWebRTCAPI#StreamsChangedEvent\n * @type {external:Event}\n * @see GstWebRTCAPI.ConsumerSession#streams\n */\n/**\n * Event name: \"remoteControllerChanged\".<br>\n * Triggered when the underlying remote controller of a {@link GstWebRTCAPI.ConsumerSession} changes.\n * @event GstWebRTCAPI#RemoteControllerChangedEvent\n * @type {external:Event}\n * @see GstWebRTCAPI.ConsumerSession#remoteController\n */\n\n/**\n * @class GstWebRTCAPI.ConsumerSession\n * @hideconstructor\n * @classdesc Consumer session managing a peer-to-peer WebRTC channel between a remote producer and this client\n * instance.\n * <p>Call {@link GstWebRTCAPI#createConsumerSession} to create a ConsumerSession instance.</p>\n * @extends {GstWebRTCAPI.WebRTCSession}\n * @fires {@link GstWebRTCAPI#event:StreamsChangedEvent}\n * @fires {@link GstWebRTCAPI#event:RemoteControllerChangedEvent}\n */\nexport default class ConsumerSession extends WebRTCSession {\n constructor(peerId, comChannel) {\n super(peerId, comChannel);\n this._streams = [];\n this._remoteController = null;\n\n this.addEventListener(\"closed\", () => {\n this._streams = [];\n\n if (this._remoteController) {\n this._remoteController.close();\n }\n });\n }\n\n /**\n * The array of remote media streams consumed locally through this WebRTC channel.\n * @member {external:MediaStream[]} GstWebRTCAPI.ConsumerSession#streams\n * @readonly\n */\n get streams() {\n return this._streams;\n }\n\n /**\n * The remote controller associated with this WebRTC consumer session. Value may be null if consumer session\n * has no remote controller.\n * @member {GstWebRTCAPI.RemoteController} GstWebRTCAPI.ConsumerSession#remoteController\n * @readonly\n */\n get remoteController() {\n return this._remoteController;\n }\n\n /**\n * Connects the consumer session to its remote producer.<br>\n * This method must be called after creating the consumer session in order to start receiving the remote streams.\n * It registers this consumer session to the signaling server and gets ready to receive audio/video streams.\n * <p>Even on success, streaming can fail later if any error occurs during or after connection. In order to know\n * the effective streaming state, you should be listening to the [error]{@link GstWebRTCAPI#event:ErrorEvent},\n * [stateChanged]{@link GstWebRTCAPI#event:StateChangedEvent} and/or [closed]{@link GstWebRTCAPI#event:ClosedEvent}\n * events.</p>\n * @method GstWebRTCAPI.ConsumerSession#connect\n * @returns {boolean} true in case of success (may fail later during or after connection) or false in case of\n * immediate error (wrong session state or no connection to the signaling server).\n */\n connect() {\n if (!this._comChannel || (this._state === SessionState.closed)) {\n return false;\n }\n\n if (this._state !== SessionState.idle) {\n return true;\n }\n\n const msg = {\n type: \"startSession\",\n peerId: this._peerId\n };\n if (!this._comChannel.send(msg)) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"cannot connect consumer session\",\n error: new Error(\"cannot send startSession message to signaling server\")\n }));\n\n this.close();\n return false;\n }\n\n this._state = SessionState.connecting;\n this.dispatchEvent(new Event(\"stateChanged\"));\n return true;\n }\n\n onSessionStarted(peerId, sessionId) {\n if ((this._peerId === peerId) && (this._state === SessionState.connecting) && !this._sessionId) {\n this._sessionId = sessionId;\n }\n }\n\n onSessionPeerMessage(msg) {\n if ((this._state === SessionState.closed) || !this._comChannel || !this._sessionId) {\n return;\n }\n\n if (!this._rtcPeerConnection) {\n const connection = new RTCPeerConnection(this._comChannel.webrtcConfig);\n this._rtcPeerConnection = connection;\n\n connection.ontrack = (event) => {\n if ((this._rtcPeerConnection === connection) && event.streams && (event.streams.length > 0)) {\n if (this._state === SessionState.connecting) {\n this._state = SessionState.streaming;\n this.dispatchEvent(new Event(\"stateChanged\"));\n }\n\n let streamsChanged = false;\n for (const stream of event.streams) {\n if (!this._streams.includes(stream)) {\n this._streams.push(stream);\n streamsChanged = true;\n }\n }\n\n if (streamsChanged) {\n this.dispatchEvent(new Event(\"streamsChanged\"));\n }\n }\n };\n\n connection.ondatachannel = (event) => {\n const rtcDataChannel = event.channel;\n if (rtcDataChannel && (rtcDataChannel.label === \"input\")) {\n if (this._remoteController) {\n const previousController = this._remoteController;\n this._remoteController = null;\n previousController.close();\n }\n\n const remoteController = new RemoteController(rtcDataChannel, this);\n this._remoteController = remoteController;\n this.dispatchEvent(new Event(\"remoteControllerChanged\"));\n\n remoteController.addEventListener(\"closed\", () => {\n if (this._remoteController === remoteController) {\n this._remoteController = null;\n this.dispatchEvent(new Event(\"remoteControllerChanged\"));\n }\n });\n }\n };\n\n connection.onicecandidate = (event) => {\n if ((this._rtcPeerConnection === connection) && event.candidate && this._comChannel) {\n this._comChannel.send({\n type: \"peer\",\n sessionId: this._sessionId,\n ice: event.candidate.toJSON()\n });\n }\n };\n\n this.dispatchEvent(new Event(\"rtcPeerConnectionChanged\"));\n }\n\n if (msg.sdp) {\n this._rtcPeerConnection.setRemoteDescription(msg.sdp).then(() => {\n if (this._rtcPeerConnection) {\n return this._rtcPeerConnection.createAnswer();\n } else {\n return null;\n }\n }).then((desc) => {\n if (this._rtcPeerConnection && desc) {\n return this._rtcPeerConnection.setLocalDescription(desc);\n } else {\n return null;\n }\n }).then(() => {\n if (this._rtcPeerConnection && this._comChannel) {\n const sdp = {\n type: \"peer\",\n sessionId: this._sessionId,\n sdp: this._rtcPeerConnection.localDescription.toJSON()\n };\n if (!this._comChannel.send(sdp)) {\n throw new Error(\"cannot send local SDP configuration to WebRTC peer\");\n }\n }\n }).catch((ex) => {\n if (this._state !== SessionState.closed) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"an unrecoverable error occurred during SDP handshake\",\n error: ex\n }));\n\n this.close();\n }\n });\n } else if (msg.ice) {\n const candidate = new RTCIceCandidate(msg.ice);\n this._rtcPeerConnection.addIceCandidate(candidate).catch((ex) => {\n if (this._state !== SessionState.closed) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"an unrecoverable error occurred during ICE handshake\",\n error: ex\n }));\n\n this.close();\n }\n });\n } else {\n throw new Error(`invalid empty peer message received from consumer session ${this._sessionId}`);\n }\n }\n}\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport WebRTCSession from \"./webrtc-session.js\";\nimport SessionState from \"./session-state.js\";\n\n/**\n * @class GstWebRTCAPI.ClientSession\n * @hideconstructor\n * @classdesc Client session representing a link between a remote consumer and a local producer session.\n * @extends {GstWebRTCAPI.WebRTCSession}\n */\nclass ClientSession extends WebRTCSession {\n constructor(peerId, sessionId, comChannel, stream) {\n super(peerId, comChannel);\n this._sessionId = sessionId;\n this._state = SessionState.streaming;\n\n const connection = new RTCPeerConnection(this._comChannel.webrtcConfig);\n this._rtcPeerConnection = connection;\n\n for (const track of stream.getTracks()) {\n connection.addTrack(track, stream);\n }\n\n connection.onicecandidate = (event) => {\n if ((this._rtcPeerConnection === connection) && event.candidate && this._comChannel) {\n this._comChannel.send({\n type: \"peer\",\n sessionId: this._sessionId,\n ice: event.candidate.toJSON()\n });\n }\n };\n\n this.dispatchEvent(new Event(\"rtcPeerConnectionChanged\"));\n\n connection.setLocalDescription().then(() => {\n if ((this._rtcPeerConnection === connection) && this._comChannel) {\n const sdp = {\n type: \"peer\",\n sessionId: this._sessionId,\n sdp: this._rtcPeerConnection.localDescription.toJSON()\n };\n if (!this._comChannel.send(sdp)) {\n throw new Error(\"cannot send local SDP configuration to WebRTC peer\");\n }\n }\n }).catch((ex) => {\n if (this._state !== SessionState.closed) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"an unrecoverable error occurred during SDP handshake\",\n error: ex\n }));\n\n this.close();\n }\n });\n }\n\n onSessionPeerMessage(msg) {\n if ((this._state === SessionState.closed) || !this._rtcPeerConnection) {\n return;\n }\n\n if (msg.sdp) {\n this._rtcPeerConnection.setRemoteDescription(msg.sdp).catch((ex) => {\n if (this._state !== SessionState.closed) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"an unrecoverable error occurred during SDP handshake\",\n error: ex\n }));\n\n this.close();\n }\n });\n } else if (msg.ice) {\n const candidate = new RTCIceCandidate(msg.ice);\n this._rtcPeerConnection.addIceCandidate(candidate).catch((ex) => {\n if (this._state !== SessionState.closed) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"an unrecoverable error occurred during ICE handshake\",\n error: ex\n }));\n\n this.close();\n }\n });\n } else {\n throw new Error(`invalid empty peer message received from producer's client session ${this._peerId}`);\n }\n }\n}\n\n/**\n * Event name: \"clientConsumerAdded\".<br>\n * Triggered when a remote consumer peer connects to a local {@link GstWebRTCAPI.ProducerSession}.\n * @event GstWebRTCAPI#ClientConsumerAddedEvent\n * @type {external:CustomEvent}\n * @property {GstWebRTCAPI.ClientSession} detail - The WebRTC session associated with the added consumer peer.\n * @see GstWebRTCAPI.ProducerSession\n */\n/**\n * Event name: \"clientConsumerRemoved\".<br>\n * Triggered when a remote consumer peer disconnects from a local {@link GstWebRTCAPI.ProducerSession}.\n * @event GstWebRTCAPI#ClientConsumerRemovedEvent\n * @type {external:CustomEvent}\n * @property {GstWebRTCAPI.ClientSession} detail - The WebRTC session associated with the removed consumer peer.\n * @see GstWebRTCAPI.ProducerSession\n */\n\n/**\n * @class GstWebRTCAPI.ProducerSession\n * @hideconstructor\n * @classdesc Producer session managing the streaming out of a local {@link external:MediaStream}.<br>\n * It manages all underlying WebRTC connections to each peer client consuming the stream.\n * <p>Call {@link GstWebRTCAPI#createProducerSession} to create a ProducerSession instance.</p>\n * @extends {external:EventTarget}\n * @fires {@link GstWebRTCAPI#event:ErrorEvent}\n * @fires {@link GstWebRTCAPI#event:StateChangedEvent}\n * @fires {@link GstWebRTCAPI#event:ClosedEvent}\n * @fires {@link GstWebRTCAPI#event:ClientConsumerAddedEvent}\n * @fires {@link GstWebRTCAPI#event:ClientConsumerRemovedEvent}\n */\nexport default class ProducerSession extends EventTarget {\n constructor(comChannel, stream) {\n super();\n\n this._comChannel = comChannel;\n this._stream = stream;\n this._state = SessionState.idle;\n this._clientSessions = {};\n }\n\n /**\n * The local stream produced out by this session.\n * @member {external:MediaStream} GstWebRTCAPI.ProducerSession#stream\n * @readonly\n */\n get stream() {\n return this._stream;\n }\n\n /**\n * The current producer session state.\n * @member {GstWebRTCAPI.SessionState} GstWebRTCAPI.ProducerSession#state\n * @readonly\n */\n get state() {\n return this._state;\n }\n\n /**\n * Starts the producer session.<br>\n * This method must be called after creating the producer session in order to start streaming. It registers this\n * producer session to the signaling server and gets ready to serve peer requests from consumers.\n * <p>Even on success, streaming can fail later if any error occurs during or after connection. In order to know\n * the effective streaming state, you should be listening to the [error]{@link GstWebRTCAPI#event:ErrorEvent},\n * [stateChanged]{@link GstWebRTCAPI#event:StateChangedEvent} and/or [closed]{@link GstWebRTCAPI#event:ClosedEvent}\n * events.</p>\n * @method GstWebRTCAPI.ProducerSession#start\n * @returns {boolean} true in case of success (may fail later during or after connection) or false in case of\n * immediate error (wrong session state or no connection to the signaling server).\n */\n start() {\n if (!this._comChannel || (this._state === SessionState.closed)) {\n return false;\n }\n\n if (this._state !== SessionState.idle) {\n return true;\n }\n\n const msg = {\n type: \"setPeerStatus\",\n roles: [\"listener\", \"producer\"],\n meta: this._comChannel.meta\n };\n if (!this._comChannel.send(msg)) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"cannot start producer session\",\n error: new Error(\"cannot register producer to signaling server\")\n }));\n\n this.close();\n return false;\n }\n\n this._state = SessionState.connecting;\n this.dispatchEvent(new Event(\"stateChanged\"));\n return true;\n }\n\n /**\n * Terminates the producer session.<br>\n * It immediately disconnects all peer consumers attached to this producer session and unregisters the producer\n * from the signaling server.\n * @method GstWebRTCAPI.ProducerSession#close\n */\n close() {\n if (this._state !== SessionState.closed) {\n for (const track of this._stream.getTracks()) {\n track.stop();\n }\n\n if ((this._state !== SessionState.idle) && this._comChannel) {\n this._comChannel.send({\n type: \"setPeerStatus\",\n roles: [\"listener\"],\n meta: this._comChannel.meta\n });\n }\n\n this._state = SessionState.closed;\n this.dispatchEvent(new Event(\"stateChanged\"));\n\n this._comChannel = null;\n this._stream = null;\n\n for (const clientSession of Object.values(this._clientSessions)) {\n clientSession.close();\n }\n this._clientSessions = {};\n\n this.dispatchEvent(new Event(\"closed\"));\n }\n }\n\n onProducerRegistered() {\n if (this._state === SessionState.connecting) {\n this._state = SessionState.streaming;\n this.dispatchEvent(new Event(\"stateChanged\"));\n }\n }\n\n onStartSessionMessage(msg) {\n if (this._comChannel && this._stream && !(msg.sessionId in this._clientSessions)) {\n const session = new ClientSession(msg.peerId, msg.sessionId, this._comChannel, this._stream);\n this._clientSessions[msg.sessionId] = session;\n\n session.addEventListener(\"closed\", (event) => {\n const sessionId = event.target.sessionId;\n if ((sessionId in this._clientSessions) && (this._clientSessions[sessionId] === session)) {\n delete this._clientSessions[sessionId];\n this.dispatchEvent(new CustomEvent(\"clientConsumerRemoved\", { detail: session }));\n }\n });\n\n session.addEventListener(\"error\", (event) => {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: `error from client consumer ${event.target.peerId}: ${event.message}`,\n error: event.error\n }));\n });\n\n this.dispatchEvent(new CustomEvent(\"clientConsumerAdded\", { detail: session }));\n }\n }\n\n onEndSessionMessage(msg) {\n if (msg.sessionId in this._clientSessions) {\n this._clientSessions[msg.sessionId].close();\n }\n }\n\n onSessionPeerMessage(msg) {\n if (msg.sessionId in this._clientSessions) {\n this._clientSessions[msg.sessionId].onSessionPeerMessage(msg);\n }\n }\n}\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport ConsumerSession from \"./consumer-session.js\";\nimport ProducerSession from \"./producer-session.js\";\n\nconst SignallingServerMessageType = Object.freeze({\n welcome: \"welcome\",\n peerStatusChanged: \"peerStatusChanged\",\n list: \"list\",\n sessionStarted: \"sessionStarted\",\n peer: \"peer\",\n startSession: \"startSession\",\n endSession: \"endSession\",\n error: \"error\"\n});\n\nfunction normalizeProducer(producer, excludedId) {\n if (!producer || (typeof (producer) !== \"object\")) {\n return null;\n }\n\n const normalizedProducer = {\n id: \"\",\n meta: {}\n };\n\n if (producer.id && (typeof (producer.id) === \"string\")) {\n normalizedProducer.id = producer.id;\n } else if (producer.peerId && (typeof (producer.peerId) === \"string\")) {\n normalizedProducer.id = producer.peerId;\n } else {\n return null;\n }\n\n if (normalizedProducer.id === excludedId) {\n return null;\n }\n\n if (producer.meta && (typeof (producer.meta) === \"object\")) {\n normalizedProducer.meta = producer.meta;\n }\n\n Object.freeze(normalizedProducer.meta);\n return Object.freeze(normalizedProducer);\n}\n\nexport default class ComChannel extends EventTarget {\n constructor(url, meta, webrtcConfig) {\n super();\n\n this._meta = meta;\n this._webrtcConfig = webrtcConfig;\n this._ws = new WebSocket(url);\n this._ready = false;\n this._channelId = \"\";\n this._producerSession = null;\n this._consumerSessions = {};\n\n this._ws.onerror = (event) => {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: event.message || \"WebSocket error\",\n error: event.error || new Error(\n this._ready ? \"transportation error\" : \"cannot connect to signaling server\")\n }));\n this.close();\n };\n\n this._ws.onclose = () => {\n this._ready = false;\n this._channelId = \"\";\n this._ws = null;\n\n this.closeAllConsumerSessions();\n\n if (this._producerSession) {\n this._producerSession.close();\n this._producerSession = null;\n }\n\n this.dispatchEvent(new Event(\"closed\"));\n };\n\n this._ws.onmessage = (event) => {\n try {\n const msg = JSON.parse(event.data);\n if (msg && (typeof (msg) === \"object\")) {\n switch (msg.type) {\n\n case SignallingServerMessageType.welcome:\n this._channelId = msg.peerId;\n try {\n this._ws.send(JSON.stringify({\n type: \"setPeerStatus\",\n roles: [\"listener\"],\n meta: meta\n }));\n } catch (ex) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"cannot initialize connection to signaling server\",\n error: ex\n }));\n this.close();\n }\n break;\n\n case SignallingServerMessageType.peerStatusChanged:\n if (msg.peerId === this._channelId) {\n if (!this._ready && msg.roles.includes(\"listener\")) {\n this._ready = true;\n this.dispatchEvent(new Event(\"ready\"));\n this.send({ type: \"list\" });\n }\n\n if (this._producerSession && msg.roles.includes(\"producer\")) {\n this._producerSession.onProducerRegistered();\n }\n } else {\n const normalizedProducer = normalizeProducer(msg, this._channelId);\n if (normalizedProducer) {\n if (msg.roles.includes(\"producer\")) {\n this.dispatchEvent(new CustomEvent(\"producerAdded\", { detail: normalizedProducer }));\n } else {\n this.dispatchEvent(new CustomEvent(\"producerRemoved\", { detail: normalizedProducer }));\n }\n }\n }\n break;\n\n case SignallingServerMessageType.list:\n for (const producer of msg.producers) {\n const normalizedProducer = normalizeProducer(producer, this._channelId);\n if (normalizedProducer) {\n this.dispatchEvent(new CustomEvent(\"producerAdded\", { detail: normalizedProducer }));\n }\n }\n break;\n\n case SignallingServerMessageType.sessionStarted:\n {\n const session = this.getConsumerSession(msg.peerId);\n if (session) {\n delete this._consumerSessions[msg.peerId];\n\n session.onSessionStarted(msg.peerId, msg.sessionId);\n if (session.sessionId && !(session.sessionId in this._consumerSessions)) {\n this._consumerSessions[session.sessionId] = session;\n } else {\n session.close();\n }\n }\n }\n break;\n\n case SignallingServerMessageType.peer:\n {\n const session = this.getConsumerSession(msg.sessionId);\n if (session) {\n session.onSessionPeerMessage(msg);\n } else if (this._producerSession) {\n this._producerSession.onSessionPeerMessage(msg);\n }\n }\n break;\n\n case SignallingServerMessageType.startSession:\n if (this._producerSession) {\n this._producerSession.onStartSessionMessage(msg);\n }\n break;\n\n case SignallingServerMessageType.endSession:\n {\n const session = this.getConsumerSession(msg.sessionId);\n if (session) {\n session.close();\n } else if (this._producerSession) {\n this._producerSession.onEndSessionMessage(msg);\n }\n }\n break;\n\n case SignallingServerMessageType.error:\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"error received from signaling server\",\n error: new Error(msg.details)\n }));\n break;\n\n default:\n throw new Error(`unknown message type: \"${msg.type}\"`);\n }\n }\n } catch (ex) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"cannot parse incoming message from signaling server\",\n error: ex\n }));\n }\n };\n }\n\n get meta() {\n return this._meta;\n }\n\n get webrtcConfig() {\n return this._webrtcConfig;\n }\n\n get ready() {\n return this._ready;\n }\n\n get channelId() {\n return this._channelId;\n }\n\n get producerSession() {\n return this._producerSession;\n }\n\n createProducerSession(stream) {\n if (!this._ready || !(stream instanceof MediaStream)) {\n return null;\n }\n\n if (this._producerSession) {\n if (this._producerSession.stream === stream) {\n return this._producerSession;\n } else {\n return null;\n }\n }\n\n const session = new ProducerSession(this, stream);\n this._producerSession = session;\n\n session.addEventListener(\"closed\", () => {\n if (this._producerSession === session) {\n this._producerSession = null;\n }\n });\n\n return session;\n }\n\n createConsumerSession(producerId) {\n if (!this._ready || !producerId || (typeof (producerId) !== \"string\")) {\n return null;\n }\n\n if (producerId in this._consumerSessions) {\n return this._consumerSessions[producerId];\n }\n\n for (const session of Object.values(this._consumerSessions)) {\n if (session.peerId === producerId) {\n return session;\n }\n }\n\n const session = new ConsumerSession(producerId, this);\n this._consumerSessions[producerId] = session;\n\n session.addEventListener(\"closed\", (event) => {\n let sessionId = event.target.sessionId;\n if (!sessionId) {\n sessionId = event.target.peerId;\n }\n\n if ((sessionId in this._consumerSessions) && (this._consumerSessions[sessionId] === session)) {\n delete this._consumerSessions[sessionId];\n }\n });\n\n return session;\n }\n\n getConsumerSession(sessionId) {\n if (sessionId in this._consumerSessions) {\n return this._consumerSessions[sessionId];\n } else {\n return null;\n }\n }\n\n closeAllConsumerSessions() {\n for (const session of Object.values(this._consumerSessions)) {\n session.close();\n }\n\n this._consumerSessions = {};\n }\n\n send(data) {\n if (this._ready && data && (typeof (data) === \"object\")) {\n try {\n this._ws.send(JSON.stringify(data));\n return true;\n } catch (ex) {\n this.dispatchEvent(new ErrorEvent(\"error\", {\n message: \"cannot send message to signaling server\",\n error: ex\n }));\n }\n }\n\n return false;\n }\n\n close() {\n if (this._ws) {\n this._ready = false;\n this._channelId = \"\";\n this._ws.close();\n\n this.closeAllConsumerSessions();\n\n if (this._producerSession) {\n this._producerSession.close();\n this._producerSession = null;\n }\n }\n }\n}\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport defaultConfig from \"./config.js\";\nimport ComChannel from \"./com-channel.js\";\nimport SessionState from \"./session-state.js\";\n\n/**\n * @class GstWebRTCAPI\n * @classdesc The API entry point that manages a WebRTC.\n */\nexport default class GstWebRTCAPI {\n /**\n * @constructor GstWebRTCAPI\n * @param {GstWebRTCConfig} [userConfig] - The user configuration.<br>Only the parameters different from the default\n * ones need to be provided.\n */\n constructor(userConfig) {\n this._channel = null;\n this._producers = {};\n this._connectionListeners = [];\n this._producersListeners = [];\n\n const config = Object.assign({}, defaultConfig);\n if (userConfig && (typeof (userConfig) === \"object\")) {\n Object.assign(config, userConfig);\n }\n\n if (typeof (config.meta) !== \"object\") {\n config.meta = null;\n }\n\n this._config = config;\n this.connectChannel();\n }\n\n /**\n * @interface GstWebRTCAPI.ConnectionListener\n */\n /**\n * Callback method called when this client connects to the WebRTC signaling server.\n * The callback implementation should not throw any exception.\n * @method GstWebRTCAPI.ConnectionListener#connected\n * @abstract\n * @param {string} clientId - The unique identifier of this WebRTC client.<br>This identifier is provided by the\n * signaling server to uniquely identify each connected peer.\n */\n /**\n * Callback method called when this client disconnects from the WebRTC signaling server.\n * The callback implementation should not throw any exception.\n * @method GstWebRTCAPI.ConnectionListener#disconnected\n * @abstract\n */\n\n /**\n * Registers a connection listener that will be called each time the WebRTC API connects to or disconnects from the\n * signaling server.\n * @method GstWebRTCAPI#registerConnectionListener\n * @param {GstWebRTCAPI.ConnectionListener} listener - The connection listener to register.\n * @returns {boolean} true in case of success (or if the listener was already registered), or false if the listener\n * doesn't implement all callback functions and cannot be registered.\n */\n registerConnectionListener(listener) {\n if (!listener || (typeof (listener) !== \"object\") ||\n (typeof (listener.connected) !== \"function\") ||\n (typeof (listener.disconnected) !== \"function\")) {\n return false;\n }\n\n if (!this._connectionListeners.includes(listener)) {\n this._connectionListeners.push(listener);\n }\n\n return true;\n }\n\n /**\n * Unregisters a connection listener.<br>\n * The removed listener will never be called again and can be garbage collected.\n * @method GstWebRTCAPI#unregisterConnectionListener\n * @param {GstWebRTCAPI.ConnectionListener} listener - The connection listener to unregister.\n * @returns {boolean} true if the listener is found and unregistered, or false if the listener was not previously\n * registered.\n */\n unregisterConnectionListener(listener) {\n const idx = this._connectionListeners.indexOf(listener);\n if (idx >= 0) {\n this._connectionListeners.splice(idx, 1);\n return true;\n }\n\n return false;\n }\n\n /**\n * Unregisters all previously registered connection listeners.\n * @method GstWebRTCAPI#unregisterAllConnectionListeners\n */\n unregisterAllConnectionListeners() {\n this._connectionListeners = [];\n }\n\n /**\n * Creates a new producer session.\n * <p>You can only create one producer session at a time.<br>\n * To request streaming from a new stream you will first need to close the previous producer session.</p>\n * <p>You can only request a producer session while you are connected to the signaling server. You can use the\n * {@link GstWebRTCAPI.ConnectionListener} interface and {@link GstWebRTCAPI#registerConnectionListener} method to\n * listen to the connection state.</p>\n * @method GstWebRTCAPI#createProducerSession\n * @param {external:MediaStream} stream - The audio/video stream to offer as a producer through WebRTC.\n * @returns {GstWebRTCAPI.ProducerSession} The created producer session or null in case of error. To start streaming,\n * you still need to call {@link GstWebRTCAPI.ProducerSession#start} after adding on the returned session all the event\n * listeners you may need.\n */\n createProducerSession(stream) {\n if (this._channel) {\n return this._channel.createProducerSession(stream);\n }\n return null;\n }\n\n /**\n * Information about a remote producer registered by the signaling server.\n * @typedef {object} GstWebRTCAPI.Producer\n * @readonly\n * @property {string} id - The remote producer unique identifier set by the signaling server (always non-empty).\n * @property {object} meta - Free-form object containing extra information about the remote producer (always non-null,\n * but may be empty). Its content depends on your application.\n */\n\n /**\n * Gets the list of all remote WebRTC producers available on the signaling server.\n * <p>The remote producers list is only populated once you've connected to the signaling server. You can use the\n * {@link GstWebRTCAPI.ConnectionListener} interface and {@link GstWebRTCAPI#registerConnectionListener} method to\n * listen to the connection state.</p>\n * @method GstWebRTCAPI#getAvailableProducers\n * @returns {GstWebRTCAPI.Producer[]} The list of remote WebRTC producers available.\n */\n getAvailableProducers() {\n return Object.values(this._producers);\n }\n\n /**\n * @interface GstWebRTCAPI.ProducersListener\n */\n /**\n * Callback method called when a remote producer is added on the signaling server.\n * The callback implementation should not throw any exception.\n * @method GstWebRTCAPI.ProducersListener#producerAdded\n * @abstract\n * @param {GstWebRTCAPI.Producer} producer - The remote producer added on server-side.\n */\n /**\n * Callback method called when a remote producer is removed from the signaling server.\n * The callback implementation should not throw any exception.\n * @method GstWebRTCAPI.ProducersListener#producerRemoved\n * @abstract\n * @param {GstWebRTCAPI.Producer} producer - The remote producer removed on server-side.\n */\n\n /**\n * Registers a producers listener that will be called each time a producer is added or removed on the signaling\n * server.\n * @method GstWebRTCAPI#registerProducersListener\n * @param {GstWebRTCAPI.ProducersListener} listener - The producer listener to register.\n * @returns {boolean} true in case of success (or if the listener was already registered), or false if the listener\n * doesn't implement all callback functions and cannot be registered.\n */\n registerProducersListener(listener) {\n if (!listener || (typeof (listener) !== \"object\") ||\n (typeof (listener.producerAdded) !== \"function\") ||\n (typeof (listener.producerRemoved) !== \"function\")) {\n return false;\n }\n\n if (!this._producersListeners.includes(listener)) {\n this._producersListeners.push(listener);\n }\n\n return true;\n }\n\n /**\n * Unregisters a producers listener.<br>\n * The removed listener will never be called again and can be garbage collected.\n * @method GstWebRTCAPI#unregisterProducersListener\n * @param {GstWebRTCAPI.ProducersListener} listener - The producers listener to unregister.\n * @returns {boolean} true if the listener is found and unregistered, or false if the listener was not previously\n * registered.\n */\n unregisterProducersListener(listener) {\n const idx = this._producersListeners.indexOf(listener);\n if (idx >= 0) {\n this._producersListeners.splice(idx, 1);\n return true;\n }\n\n return false;\n }\n\n /**\n * Unregisters all previously registered producers listeners.\n * @method GstWebRTCAPI#unregisterAllProducersListeners\n */\n unregisterAllProducersListeners() {\n this._producersListeners = [];\n }\n\n /**\n * Creates a consumer session by connecting the local client to a remote WebRTC producer.\n * <p>You can only create one consumer session per remote producer.</p>\n * <p>You can only request a new consumer session while you are connected to the signaling server. You can use the\n * {@link GstWebRTCAPI.ConnectionListener} interface and {@link GstWebRTCAPI#registerConnectionListener} method to\n * listen to the connection state.</p>\n * @method GstWebRTCAPI#createConsumerSession\n * @param {string} producerId - The unique identifier of the remote producer to connect to.\n * @returns {GstWebRTCAPI.ConsumerSession} The WebRTC session between the selected remote producer and this local\n * consumer, or null in case of error. To start connecting and receiving the remote streams, you still need to call\n * {@link GstWebRTCAPI.ConsumerSession#connect} after adding on the returned session all the event listeners you may\n * need.\n */\n createConsumerSession(producerId) {\n if (this._channel) {\n return this._channel.createConsumerSession(producerId);\n }\n return null;\n }\n\n connectChannel() {\n if (this._channel) {\n const oldChannel = this._channel;\n this._channel = null;\n oldChannel.close();\n for (const key in this._producers) {\n this.triggerProducerRemoved(key);\n }\n this._producers = {};\n this.triggerDisconnected();\n }\n\n this._channel = new ComChannel(\n this._config.signalingServerUrl,\n this._config.meta,\n this._config.webrtcConfig\n );\n\n this._channel.addEventListener(\"error\", (event) => {\n if (event.target === this._channel) {\n console.error(event.message, event.error);\n }\n });\n\n this._channel.addEventListener(\"closed\", (event) => {\n if (event.target !== this._channel) {\n return;\n }\n this._channel = null;\n for (const key in this._producers) {\n this.triggerProducerRemoved(key);\n }\n this._producers = {};\n this.triggerDisconnected();\n if (this._config.reconnectionTimeout > 0) {\n window.setTimeout(() => {\n this.connectChannel();\n }, this._config.reconnectionTimeout);\n }\n });\n\n this._channel.addEventListener(\"ready\", (event) => {\n if (event.target === this._channel) {\n this.triggerConnected(this._channel.channelId);\n }\n });\n\n this._channel.addEventListener(\"producerAdded\", (event) => {\n if (event.target === this._channel) {\n this.triggerProducerAdded(event.detail);\n }\n });\n\n this._channel.addEventListener(\"producerRemoved\", (event) => {\n if (event.target === this._channel) {\n this.triggerProducerRemoved(event.detail.id);\n }\n });\n }\n\n triggerConnected(clientId) {\n for (const listener of this._connectionListeners) {\n try {\n listener.connected(clientId);\n } catch (ex) {\n console.error(\"a listener callback should not throw any exception\", ex);\n }\n }\n }\n\n triggerDisconnected() {\n for (const listener of this._connectionListeners) {\n try {\n listener.disconnected();\n } catch (ex) {\n console.error(\"a listener callback should not throw any exception\", ex);\n }\n }\n }\n\n triggerProducerAdded(producer) {\n if (producer.id in this._producers) {\n return;\n }\n\n this._producers[producer.id] = producer;\n for (const listener of this._producersListeners) {\n try {\n listener.producerAdded(producer);\n } catch (ex) {\n console.error(\"a listener callback should not throw any exception\", ex);\n }\n }\n }\n\n triggerProducerRemoved(producerId) {\n if (producerId in this._producers) {\n const producer = this._producers[producerId];\n delete this._producers[producerId];\n\n for (const listener of this._producersListeners) {\n try {\n listener.producerRemoved(producer);\n } catch (ex) {\n console.error(\"a listener callback should not throw any exception\", ex);\n }\n }\n }\n }\n}\n\nGstWebRTCAPI.SessionState = SessionState;\n","/*\n * gstwebrtc-api\n *\n * Copyright (C) 2022 Igalia S.L. <info@igalia.com>\n * Author: Loïc Le Page <llepage@igalia.com>\n *\n * This Source Code Form is subject to the terms of the Mozilla Public\n * License, v. 2.0. If a copy of the MPL was not distributed with this\n * file, You can obtain one at http://mozilla.org/MPL/2.0/.\n */\n\nimport \"webrtc-adapter\";\nimport GstWebRTCAPI from \"./gstwebrtc-api.js\";\n\n/**\n * @external MediaStream\n * @see https://developer.mozilla.org/en-US/docs/Web/API/MediaStream\n */\n/**\n * @external RTCPeerConnection\n * @see https://developer.mozilla.org/en-US/docs/Web/API/RTCPeerConnection\n */\n/**\n * @external RTCDataChannel\n * @see https://developer.mozilla.org/en-US/docs/Web/API/RTCDataChannel\n */\n/**\n * @external EventTarget\n * @see https://developer.mozilla.org/en-US/docs/Web/API/EventTarget\n */\n/**\n * @external Event\n * @see https://developer.mozilla.org/en-US/docs/Web/API/Event\n */\n/**\n * @external ErrorEvent\n * @see https://developer.mozilla.org/en-US/docs/Web/API/ErrorEvent\n */\n/**\n * @external CustomEvent\n * @see https://developer.mozilla.org/en-US/docs/Web/API/CustomEvent\n */\n/**\n * @external Error\n * @see https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error\n */\n/**\n * @external HTMLVideoElement\n * @see https://developer.mozilla.org/en-US/docs/Web/API/HTMLVideoElement\n */\n\nif (!window.GstWebRTCAPI) {\n window.GstWebRTCAPI = GstWebRTCAPI;\n}\n"],"names":["SDPUtils","Math","random","toString","substring","localCName","generateIdentifier","splitLines","blob","trim","split","map","line","splitSections","part","index","getDescription","sections","getMediaSections","shift","matchPrefix","prefix","filter","indexOf","parseCandidate","parts","candidate","foundation","component","protocol","toLowerCase","priority","parseInt","ip","address","port","type","i","length","relatedAddress","relatedPort","tcpType","ufrag","usernameFragment","undefined","writeCandidate","sdp","push","toUpperCase","join","parseIceOptions","parseRtpMap","parsed","payloadType","name","clockRate","channels","numChannels","writeRtpMap","codec","pt","preferredPayloadType","parseExtmap","id","direction","uri","attributes","slice","writeExtmap","headerExtension","preferredId","parseFmtp","kv","j","writeFmtp","parameters","Object","keys","params","forEach","param","parseRtcpFb","parameter","writeRtcpFb","lines","rtcpFeedback","fb","parseSsrcMedia","sp","ssrc","colon","attribute","value","parseSsrcGroup","semantics","ssrcs","getMid","mediaSection","mid","parseFingerprint","algorithm","getDtlsParameters","sessionpart","role","fingerprints","writeDtlsParameters","setupType","fp","parseCryptoLine","tag","cryptoSuite","keyParams","sessionParams","writeCryptoLine","writeCryptoKeyParams","parseCryptoKeyParams","keyMethod","keySalt","lifeTime","mkiValue","mkiLength","getCryptoParameters","getIceParameters","pwd","password","writeIceParameters","iceLite","parseRtpParameters","description","codecs","headerExtensions","fecMechanisms","rtcp","mline","profile","rtpmapline","fmtps","wildcardRtcpFb","find","existingFeedback","writeRtpDescription","kind","caps","maxptime","extension","parseRtpEncodingParameters","encodingParameters","hasRed","hasUlpfec","primarySsrc","secondarySsrc","flows","apt","encParam","codecPayloadType","rtx","JSON","parse","stringify","fec","mechanism","bandwidth","maxBitrate","parseRtcpParameters","rtcpParameters","remoteSsrc","obj","cname","rsize","reducedSize","compound","mux","writeRtcpParameters","parseMsid","spec","stream","track","planB","msidParts","parseSctpDescription","parseMLine","maxSizeLine","maxMessageSize","isNaN","sctpPort","fmt","sctpMapLines","writeSctpDescription","media","sctp","output","generateSessionId","substr","writeSessionBoilerplate","sessId","sessVer","sessUser","sessionId","version","getDirection","getKind","isRejected","parseOLine","username","sessionVersion","netType","addressType","isValidSDP","charAt","module","exports","__webpack_module_cache__","__webpack_require__","moduleId","cachedModule","__webpack_modules__","n","getter","__esModule","d","a","definition","key","o","defineProperty","enumerable","get","prop","prototype","hasOwnProperty","call","r","Symbol","toStringTag","logDisabled_","deprecationWarnings_","extractVersion","uastring","expr","pos","match","wrapPeerConnectionEvent","window","eventNameToWrap","wrapper","RTCPeerConnection","proto","nativeAddEventListener","addEventListener","nativeEventName","cb","apply","this","arguments","wrappedCallback","e","modifiedEvent","handleEvent","_eventMap","Map","set","nativeRemoveEventListener","removeEventListener","has","unwrappedCb","delete","size","configurable","disableLog","bool","Error","disableWarnings","log","console","deprecated","oldMethod","newMethod","warn","isObject","val","compactObject","data","reduce","accumulator","isObj","isEmptyObject","assign","walkStats","stats","base","resultSet","endsWith","filterStats","result","outbound","streamStatsType","filteredResult","trackStats","trackIdentifier","trackStat","trackId","logging","shimGetUserMedia","browserDetails","navigator","mediaDevices","constraintsToChrome_","c","mandatory","optional","cc","ideal","exact","min","max","oldname_","oc","mix","advanced","concat","shimConstraints_","constraints","func","audio","remap","b","video","face","facingMode","getSupportedFacingModeLies","getSupportedConstraints","matches","enumerateDevices","then","devices","dev","some","label","includes","deviceId","shimError_","PermissionDeniedError","PermissionDismissedError","InvalidStateError","DevicesNotFoundError","ConstraintNotSatisfiedError","TrackStartError","MediaDeviceFailedDueToShutdown","MediaDeviceKillSwitchOn","TabCaptureError","ScreenCaptureError","DeviceCaptureError","message","constraint","constraintName","getUserMedia","onSuccess","onError","webkitGetUserMedia","bind","origGetUserMedia","cs","getAudioTracks","getVideoTracks","getTracks","stop","DOMException","Promise","reject","shimGetDisplayMedia","getSourceId","getDisplayMedia","sourceId","widthSpecified","width","heightSpecified","height","frameRateSpecified","frameRate","chromeMediaSource","chromeMediaSourceId","maxFrameRate","maxWidth","maxHeight","error","shimMediaStream","MediaStream","webkitMediaStream","shimOnTrack","_ontrack","f","origSetRemoteDescription","setRemoteDescription","_ontrackpoly","te","receiver","getReceivers","event","Event","transceiver","streams","dispatchEvent","shimGetSendersWithDtmf","shimSenderWithDtmf","pc","dtmf","_dtmf","createDTMFSender","_pc","getSenders","_senders","origAddTrack","addTrack","sender","origRemoveTrack","removeTrack","idx","splice","origAddStream","addStream","origRemoveStream","removeStream","s","RTCRtpSender","origGetSenders","senders","shimGetStats","origGetStats","getStats","selector","onSucc","onErr","fixChromeStats_","response","standardReport","report","standardStats","timestamp","localcandidate","remotecandidate","names","stat","makeMapStats","successCallbackWrapper_","resolve","shimSenderReceiverGetStats","RTCRtpReceiver","origGetReceivers","receivers","srcElement","MediaStreamTrack","err","shimAddTrackRemoveTrackWithNative","getLocalStreams","_shimmedLocalStreams","streamId","existingSenders","newSenders","newSender","shimAddTrackRemoveTrack","origGetLocalStreams","nativeStreams","_reverseStreams","_streams","newStream","replaceInternalStreamId","internalId","externalStream","internalStream","replace","RegExp","RTCSessionDescription","signalingState","t","oldStream","method","nativeMethod","methodObj","args","desc","origSetLocalDescription","setLocalDescription","replaceExternalStreamId","origLocalDescription","getOwnPropertyDescriptor","streamid","shimPeerConnection","webkitRTCPeerConnection","RTCIceCandidate","fixNegotiationNeeded","target","getConfiguration","sdpSemantics","nativeGetUserMedia","getSettings","nativeGetSettings","applyConstraints","nativeApplyConstraints","preferredMediaSource","code","mediaSource","RTCTrackEvent","mozRTCPeerConnection","modernStatsTypes","inboundrtp","outboundrtp","candidatepair","nativeGetStats","shimSenderGetStats","shimReceiverGetStats","shimRemoveStream","shimRTCDataChannel","DataChannel","RTCDataChannel","shimAddTransceiver","origAddTransceiver","addTransceiver","setParametersPromises","sendEncodings","shouldPerformCheck","encodingParam","test","rid","TypeError","parseFloat","scaleResolutionDownBy","RangeError","maxFramerate","getParameters","encodings","setParameters","catch","shimGetParameters","origGetParameters","shimCreateOffer","origCreateOffer","createOffer","all","finally","shimCreateAnswer","origCreateAnswer","createAnswer","shimLocalStreamsAPI","_localStreams","_addTrack","tracks","shimRemoteStreamsAPI","getRemoteStreams","_remoteStreams","_onaddstream","_onaddstreampoly","shimCallbacksAPI","addIceCandidate","successCallback","failureCallback","options","promise","withCallback","_getUserMedia","shimConstraints","errcb","shimRTCIceServerUrls","OrigPeerConnection","pcConfig","pcConstraints","iceServers","newIceServers","server","urls","url","generateCertificate","shimTrackEventTransceiver","shimCreateOfferLegacy","offerOptions","offerToReceiveAudio","audioTransceiver","getTransceivers","setDirection","offerToReceiveVideo","videoTransceiver","shimAudioContext","AudioContext","webkitAudioContext","shimRTCIceCandidate","NativeRTCIceCandidate","nativeCandidate","parsedCandidate","toJSON","sdpMid","sdpMLineIndex","writable","shimRTCIceCandidateRelayProtocol","relayProtocol","shimMaxMessageSize","_sctp","browser","mLine","sctpInDescription","isFirefox","getRemoteFirefoxVersion","canSendMMS","remoteIsFirefox","canSendMaxMessageSize","getCanSendMaxMessageSize","remoteMMS","getMaxMessageSize","Number","POSITIVE_INFINITY","shimSendThrowTypeError","wrapDcSend","dc","origDataChannelSend","send","byteLength","readyState","origCreateDataChannel","createDataChannel","dataChannel","channel","shimConnectionState","completed","checking","iceConnectionState","_onconnectionstatechange","origMethod","_connectionstatechangepoly","_lastConnectionState","connectionState","newEvent","removeExtmapAllowMixed","nativeSRD","shimAddIceCandidateNullOrEmpty","nativeAddIceCandidate","shimParameterlessSetLocalDescription","nativeSetLocalDescription","shimChrome","shimFirefox","shimSafari","userAgent","mozGetUserMedia","isSecureContext","supportsUnifiedPlan","RTCRtpTransceiver","adapter","commonShim","browserShim","adapterFactory","defaultConfig","freeze","meta","signalingServerUrl","reconnectionTimeout","webrtcConfig","SessionState","idle","connecting","streaming","closed","WebRTCSession","EventTarget","constructor","peerId","comChannel","super","_peerId","_sessionId","_comChannel","_state","_rtcPeerConnection","state","rtcPeerConnection","close","uniToKeySyms","kbEventCodesToKeySyms","knownKbEventCodes","Set","getKeysymString","keySym","keyCodeUni","charCodeAt","eventsNames","mouseEventsNames","mousemove","mousedown","mouseup","touchEventsNames","touchstart","touchend","touchmove","touchcancel","keyboardEventsNames","keydown","keyup","getModifiers","modifiers","altKey","ctrlKey","metaKey","shiftKey","RemoteController","rtcDataChannel","consumerSession","_rtcDataChannel","_consumerSession","_videoElement","_videoElementComputedStyle","_videoElementKeyboard","_lastTouchEventTimestamp","ErrorEvent","videoElement","attachVideoElement","element","HTMLVideoElement","getComputedStyle","eventName","setAttribute","previousElement","removeAttribute","_sendGstNavigationEvent","ex","_computeVideoMousePosition","mousePos","x","y","videoWidth","videoHeight","padding","paddingLeft","paddingRight","paddingTop","paddingBottom","offsetX","offsetY","clientRect","getBoundingClientRect","border","left","borderLeftWidth","top","borderTopWidth","clientX","clientY","videoOffset","clientWidth","clientHeight","ratio","invRatio","preventDefault","delta_x","deltaX","delta_y","deltaY","modifier_state","button","focus","touch","changedTouches","identifier","pressure","force","timeStamp","ConsumerSession","_remoteController","remoteController","connect","msg","onSessionStarted","onSessionPeerMessage","connection","ontrack","streamsChanged","ondatachannel","previousController","onicecandidate","ice","localDescription","ClientSession","ProducerSession","_stream","_clientSessions","start","roles","clientSession","values","onProducerRegistered","onStartSessionMessage","session","CustomEvent","detail","onEndSessionMessage","SignallingServerMessageType","welcome","peerStatusChanged","list","sessionStarted","peer","startSession","endSession","normalizeProducer","producer","excludedId","normalizedProducer","ComChannel","_meta","_webrtcConfig","_ws","WebSocket","_ready","_channelId","_producerSession","_consumerSessions","onerror","onclose","closeAllConsumerSessions","onmessage","producers","getConsumerSession","details","ready","channelId","producerSession","createProducerSession","createConsumerSession","producerId","GstWebRTCAPI","userConfig","_channel","_producers","_connectionListeners","_producersListeners","config","_config","connectChannel","registerConnectionListener","listener","unregisterConnectionListener","unregisterAllConnectionListeners","getAvailableProducers","registerProducersListener","unregisterProducersListener","unregisterAllProducersListeners","oldChannel","triggerProducerRemoved","triggerDisconnected","setTimeout","triggerConnected","triggerProducerAdded","clientId","connected","disconnected","producerAdded","producerRemoved"],"sourceRoot":""}