import * as fileStorage from "./file-storage" ; import { prot } from "./protocol" ; import { dce , gebi } from "./util" ; export const features = { "continuous" : 0x1 , "rtc" : 0x2 , "videorec" : 0x4 , "transcription" : 0x8 , "recordOnly" : 0x100 , "rtennuiAudio" : 0x200 , "rtennuiVideo" : 0x400 } ; export const url = new URL ( < any > window . location ) ; const params = new URLSearchParams ( url . search ) ; export let config = null ; export let iconfig = null ; export let username = null ; export let jitsiUrl = null ; export let rtennuiUrl = null ; export let useFlac = false ; export let useContinuous = false ; export let useRTC = false ; export const useRTEnnui = { audio : false , video : false } ; export let useVideoRec = false ; export let useTranscription = false ; export let useRecordOnly = false ; export let useDebug = false ; /**
 * Load configuration information.
 */ export async function load ( ) { let shortForm = null ; Array . from ( ( < any > params ) . entries ( ) ) . forEach ( function ( key ) { key = key [ 0 ] ; if ( /-/ . test ( key ) ) shortForm = key ; } ) ; if ( shortForm ) { const sfParts = shortForm . split ( "-" ) ; params . set ( "i" , sfParts [ 0 ] ) ; params . set ( "k" , sfParts [ 1 ] ) ; sfParts . slice ( 2 ) . forEach ( function ( part ) { params . set ( part [ 0 ] , part . slice ( 1 ) ) ; } ) ; params . delete ( shortForm ) ; } const preEc = gebi ( "pre-ec" ) ; const loginTarget = gebi ( "login-ec" ) || document . body ; config = { id : params . get ( "i" ) , key : params . get ( "k" ) , format : params . get ( "f" ) } ; iconfig = { } ; const port = params . get ( "p" ) ; const master = params . get ( "m" ) ; const selector = params . get ( "s" ) ; const monitor = params . get ( "mon" ) ; username = params . get ( "nm" ) ; if ( config . id === null ) { window . location = < any > "/" ; return false ; } config . id = iconfig . id = Number . parseInt ( config . id , 36 ) ; if ( config . key === null ) { const div = dce ( "div" ) ; div . innerHTML = "Invalid key!" ; loginTarget . appendChild ( div ) ; if ( preEc ) preEc . style . display = "" ; return false ; } config . key = iconfig . key = Number . parseInt ( config . key , 36 ) ; if ( master !== null ) config . master = iconfig . master = Number . parseInt ( master , 36 ) ; if ( port !== null ) config . port = iconfig . port = Number . parseInt ( port , 36 ) ; if ( config . format === null ) config . format = "0" ; config . format = iconfig . format = Number . parseInt ( config . format , 36 ) ; if ( selector ) { let div = dce ( "div" ) ; div . innerText = "Client links:" ; loginTarget . appendChild ( div ) ; if ( preEc ) preEc . style . display = "" ; const sb = "?i=" + config . id . toString ( 36 ) + "&k=" + config . key . toString ( 36 ) + "&p=" + config . port . toString ( 36 ) ; for ( let opt = 0 ; opt <= config . format ; opt ++ ) { if ( ( opt & config . format ) !== opt ) continue ; if ( ( opt & features . rtc ) !== ( config . format & features . rtc ) ) continue ; div = dce ( "div" ) ; const a = dce ( "a" ) ; if ( opt === 0 ) url . search = sb ; else url . search = sb + "&f=" + opt . toString ( 36 ) ; a . href = url . toString ( ) ; a . innerText = ( ( ( opt & prot . flags . dataTypeMask ) === prot . flags . dataType . flac ) ? "FLAC" : "Opus" ) + ( ( opt & features . continuous ) ? " continuous" : "" ) ; div . appendChild ( a ) ; loginTarget . appendChild ( div ) ; } return false ; } if ( monitor ) { const scr = dce ( "script" ) ; scr . src = "ennuicastr-monitor.js?v=1" ; scr . async = true ; loginTarget . appendChild ( scr ) ; if ( preEc ) preEc . style . display = "" ; return false ; } url . search = "?i=" + config . id . toString ( 36 ) ; window . history . pushState ( { } , "Ennuicastr" , url . toString ( ) ) ; if ( params . get ( "dc" ) ) { const sp = dce ( "span" ) ; sp . innerText = "Disconnected! " ; const a = dce ( "a" ) ; let href = "?" ; for ( const key in config ) href += key [ 0 ] + "=" + ( < any > config ) [ key ] . toString ( 36 ) + "&" ; href += "nm=" + encodeURIComponent ( username ) ; a . href = href ; a . innerText = "Attempt reconnection" ; sp . appendChild ( a ) ; loginTarget . appendChild ( sp ) ; if ( preEc ) preEc . style . display = "" ; return false ; } if ( username === null || username === "" ) { const div = dce ( "div" ) ; const span = dce ( "span" ) ; span . innerHTML = "You have been invited to join a recording on Ennuicastr. Please enter a username.<br/><br/>" ; div . appendChild ( span ) ; const form = dce ( "form" ) ; form . action = "?" ; form . method = "GET" ; let def = "" ; if ( typeof localStorage !== "undefined" ) def = localStorage . getItem ( "username" ) || "" ; def = def . replace ( /&/g , "&amp;" ) . replace ( /</g , "&lt;" ) . replace ( />/g , "&gt;" ) . replace ( /"/g , "&quot;" ) ; let html = "<label for=\"nm\">Username: </label><input name=\"nm\" id=\"nm\" type=\"text\" value=\"" + def + "\" /> " ; for ( const key in config ) html += "<input name=\"" + key [ 0 ] + "\" type=\"hidden\" value=\"" + config [ key ] . toString ( 36 ) + "\" />" ; html += "<input type=\"submit\" value=\"Join\" />" ; form . innerHTML = html ; form . onsubmit = function ( ev ) { let target = "?" ; for ( const key in config ) target += key [ 0 ] + "=" + config [ key ] . toString ( 36 ) + "&" ; target += "nm=" + encodeURIComponent ( gebi ( "nm" ) . value ) ; if ( params . get ( "debug" ) ) target += "&debug=1" ; const height = ( "master" in config ) ? 480 : 240 ; if ( window . open ( target , "" , "width=640,height=" + height + ",menubar=0,toolbar=0,location=0,personalbar=0,status=0" ) === null ) { return true ; } div . innerHTML = "Connecting in a new window. You may now close this tab." ; ev . preventDefault ( ) ; return false ; } ; div . appendChild ( form ) ; loginTarget . appendChild ( div ) ; if ( preEc ) preEc . style . display = "" ; const nmBox = gebi ( "nm" ) ; nmBox . focus ( ) ; nmBox . select ( ) ; return false ; } else { if ( typeof localStorage !== "undefined" ) localStorage . setItem ( "username" , username ) ; } jitsiUrl = "//jitsi." + url . hostname + "/http-bind" ; { const tmp = new URL ( url ) ; tmp . protocol = ( tmp . protocol === "http:" ? "ws:" : "wss:" ) ; tmp . pathname = url . pathname . replace ( /\/[^\/]*$/ , "/rtennui/ws" ) ; tmp . search = "" ; tmp . hash = "" ; rtennuiUrl = tmp . toString ( ) ; } useFlac = ( ( config . format & prot . flags . dataTypeMask ) === prot . flags . dataType . flac ) ; useContinuous = ! ! ( config . format & features . continuous ) ; useRTC = ! ! ( config . format & features . rtc ) ; useVideoRec = ! ! ( config . format & features . videorec ) ; useTranscription = ! ! ( config . format & features . transcription ) ; useRecordOnly = ! ! ( config . format & features . recordOnly ) ; useRTEnnui . audio = ! ! ( config . format & features . rtennuiAudio ) ; useRTEnnui . video = useRTEnnui . audio && ! ! ( config . format & features . rtennuiVideo ) ; useDebug = ! ! ( params . get ( "debug" ) ) ; if ( useContinuous ) waveVADColors = waveVADColorSets . sc ; if ( "master" in config && useVideoRec ) { let persistent = false ; if ( navigator . storage && navigator . storage . persist && navigator . storage . persisted ) { persistent = await navigator . storage . persisted ( ) ; if ( ! persistent ) persistent = await navigator . storage . persist ( ) ; if ( ! persistent && typeof Notification !== "undefined" && Notification . requestPermission ) { await Notification . requestPermission ( ) ; persistent = await navigator . storage . persist ( ) ; } } } await fileStorage . clearExpired ( ) ; return true ; } export function wsUrl ( ) { return ( url . protocol === "http:" ? "ws" : "wss" ) + "://" + url . hostname + ":" + config . port ; } export function disconnect ( ) { try { let href = "?" ; for ( const key in config ) href += key [ 0 ] + "=" + ( < any > config ) [ key ] . toString ( 36 ) + "&" ; href += "nm=" + encodeURIComponent ( username ) + "&dc=1" ; document . location . href = href ; } catch ( ex ) { document . location . href = "?" ; } } export function resolve ( ) { let p = Promise . all ( [ ] ) ; if ( ! config . port ) { p = p . then ( ( ) => { const req = { lid : config . id , key : config . key } ; if ( "master" in config ) req . master = config . master ; return fetch ( "lobby/" , { method : "POST" , headers : { "content-type" : "application/json" } , body : JSON . stringify ( req ) } ) ; } ) . then ( res => { if ( ! res . ok ) return disconnect ( ) ; return res . json ( ) ; } ) . then ( res => { config . id = res . id ; config . port = res . port ; config . key = res . key ; if ( "master" in res ) config . master = res . master ; } ) ; } return p ; } const waveVADColorSets = { "sv" : [ "#000" , "#753" , "#730" , "#a30" ] , "sc" : [ "#000" , "#730" , "#730" , "#a30" ] , "rv" : [ "#000" , "#aaa" , "#073" , "#0a3" ] , "rc" : [ "#000" , "#073" , "#073" , "#0a3" ] } ; export let waveVADColors = waveVADColorSets . sv ; export function setWaveVADColors ( to ) { waveVADColors = ( < any > waveVADColorSets ) [ to ] ; }