@ -9,45 +9,105 @@ pageSetup = function() {
alert ( "No video available for stream." ) ;
alert ( "No video available for stream." ) ;
return ;
return ;
}
}
//data = testThrimShim;
desertBusStart = new Date ( data . bustime _start ) ;
desertBusStart = new Date ( data . bustime _start ) ;
document . getElementById ( "VideoTitlePrefix" ) . value = data . title _prefix ;
document . getElementById ( "VideoTitle" ) . setAttribute ( "maxlength" , data . title _max _length ) ;
document . getElementById ( "StreamName" ) . value = data . video _channel ;
document . getElementById ( "hiddenSubmissionID" ) . value = data . id ;
document . getElementById ( "hiddenSubmissionID" ) . value = data . id ;
document . getElementById ( "StreamName" ) . value = data . video _channel ? data . video _channel : document . getElementById ( "StreamName" ) . value ;
// set stream start/end, then copy to bustime inputs
document . getElementById ( "StreamStart" ) . value = data . event _start ;
document . getElementById ( "StreamStart" ) . value = data . event _start ;
document . getElementById ( "BusTimeStart" ) . value = ( new Date ( data . event _start + "Z" ) < desertBusStart ? "-" : "" ) + videojs . formatTime ( Math . abs ( ( new Date ( data . event _start + "Z" ) - desertBusStart ) / 1000 ) , 600.01 ) . padStart ( 7 , "0:" ) ;
document . getElementById ( "StreamEnd" ) . value = data . event _end ;
document . getElementById ( "StreamEnd" ) . value = data . event _end ;
document . getElementById ( "BusTimeEnd" ) . value = ( new Date ( data . event _end + "Z" ) < desertBusStart ? "-" : "" ) + videojs . formatTime ( Math . abs ( ( new Date ( data . event _end + "Z" ) - desertBusStart ) / 1000 ) , 600.01 ) . padStart ( 7 , "0:" ) ;
setBustimeRange ( ) ;
document . getElementById ( "VideoTitle" ) . value = data . video _title ? data . video _title : document . getElementById ( "VideoTitle" ) . value ;
// title and description both default to row description
document . getElementById ( "VideoDescription" ) . value = data . video _description ? data . video _description : data . description ;
document . getElementById ( "VideoTitle" ) . value = data . video _title ? data . video _title : data . description ;
document . getElementById ( "VideoDescription" ) . value = data . video _description ? data . video _description : data . description ;
// If any edit notes, show them
if ( data . notes . length > 0 ) {
document . getElementById ( "EditNotes" ) . value = data . notes ;
document . getElementById ( "EditNotesPane" ) . style . display = "block" ;
}
// Restore advanced options. If any of these are non-default, automatically expand the advanced options pane.
setOptions ( 'uploadLocation' , data . upload _locations , data . upload _location ) ;
document . getElementById ( "AllowHoles" ) . checked = data . allow _holes ;
document . getElementById ( "uploaderWhitelist" ) . value = ( ! ! data . uploader _whitelist ) ? data . uploader _whitelist . join ( "," ) : "" ;
if (
( data . upload _locations . length > 0 && data . upload _location != data . upload _locations [ 0 ] )
|| data . allow _holes
|| ! ! data . uploader _whitelist
) {
document . getElementById ( 'wubloaderAdvancedInputTable' ) . style . display = "block" ;
}
loadPlaylist ( data . video _start , data . video _end ) ;
loadPlaylist ( data . video _start , data . video _end , data . video _quality );
} ) ;
} ) ;
}
}
else {
else {
document . getElementById ( 'SubmitButton' ) . disabled = true ;
document . getElementById ( 'SubmitButton' ) . disabled = true ;
var startOfHour = new Date ( new Date ( ) . setMinutes ( 0 , 0 , 0 ) ) ;
fetch ( "/thrimshim/defaults" ) . then ( data => data . json ( ) ) . then ( function ( data ) {
document . getElementById ( "StreamStart" ) . value = new Date ( startOfHour . getTime ( ) - 1000 * 60 * 60 ) . toISOString ( ) . substring ( 0 , 19 ) ;
desertBusStart = new Date ( data . bustime _start ) ;
document . getElementById ( "StreamEnd" ) . value = startOfHour . toISOString ( ) . substring ( 0 , 19 ) ;
document . getElementById ( "VideoTitlePrefix" ) . value = data . title _prefix ;
document . getElementById ( "VideoTitle" ) . setAttribute ( "maxlength" , data . title _max _length ) ;
document . getElementById ( "StreamName" ) . value = data . video _channel ;
setOptions ( 'uploadLocation' , data . upload _locations ) ;
// Default time range to the last 10min. This is useful for giffers, immediate replay, etc.
document . getElementById ( "StreamStart" ) . value = new Date ( new Date ( ) . getTime ( ) - 1000 * 60 * 10 ) . toISOString ( ) . substring ( 0 , 19 ) ;
document . getElementById ( "StreamEnd" ) . value = new Date ( ) . toISOString ( ) . substring ( 0 , 19 ) ;
setBustimeRange ( ) ;
} ) ;
loadPlaylist ( ) ;
loadPlaylist ( ) ;
}
}
} ;
} ;
loadPlaylist = function ( startTrim , endTrim ) {
timestampToBustime = function ( ts ) {
var playlist = "/playlist/" + document . getElementById ( "StreamName" ) . value + ".m3u8" ;
date = new Date ( ts + "Z" ) ;
return ( date < desertBusStart ? "-" : "" ) + videojs . formatTime ( Math . abs ( ( date - desertBusStart ) / 1000 ) , 600.01 ) . padStart ( 7 , "0:" ) ;
} ;
if ( document . getElementById ( "BusTimeToggleBus" ) . checked ) {
bustimeToTimestamp = function ( bustime ) {
var streamStart = desertBusStart ;
direction = 1 ;
var busTimeStart = document . getElementById ( "BusTimeStart" ) . value ;
if ( bustime . startsWith ( "-" ) ) {
var busTimeEnd = document . getElementById ( "BusTimeEnd" ) . value ;
bustime = bustime . slice ( 1 ) ;
direction = - 1 ;
}
parts = bustime . split ( ':' )
bustime _ms = ( parseInt ( parts [ 0 ] ) + parts [ 1 ] / 60 + parts [ 2 ] / 3600 ) * 1000 * 60 * 60 ;
return new Date ( desertBusStart . getTime ( ) + direction * bustime _ms ) . toISOString ( ) . substring ( 0 , 19 ) ;
} ;
setBustimeRange = function ( ) {
document . getElementById ( "BusTimeStart" ) . value = timestampToBustime ( document . getElementById ( "StreamStart" ) . value ) ;
document . getElementById ( "BusTimeEnd" ) . value = timestampToBustime ( document . getElementById ( "StreamEnd" ) . value ) ;
} ;
//Convert BusTime to milliseconds from start of stream
setStreamRange = function ( ) {
busTimeStart = ( parseInt ( busTimeStart . split ( ':' ) [ 0 ] ) + busTimeStart . split ( ':' ) [ 1 ] / 60 ) * 1000 * 60 * 60 ;
document . getElementById ( "StreamStart" ) . value = bustimeToTimestamp ( document . getElementById ( "BusTimeStart" ) . value ) ;
busTimeEnd = ( parseInt ( busTimeEnd . split ( ':' ) [ 0 ] ) + busTimeEnd . split ( ':' ) [ 1 ] / 60 ) * 1000 * 60 * 60 ;
document . getElementById ( "StreamEnd" ) . value = bustimeToTimestamp ( document . getElementById ( "BusTimeEnd" ) . value ) ;
}
document . getElementById ( "StreamStart" ) . value = new Date ( streamStart . getTime ( ) + busTimeStart ) . toISOString ( ) . substring ( 0 , 19 ) ;
// For a given select input element id, add the given list of options.
document . getElementById ( "StreamEnd" ) . value = new Date ( streamStart . getTime ( ) + busTimeEnd ) . toISOString ( ) . substring ( 0 , 19 ) ;
// If selected is given, it should be the name of an option to select.
// Otherwise the first one is used.
setOptions = function ( element , options , selected ) {
if ( ! selected && options . length > 0 ) {
selected = options [ 0 ]
}
options . forEach ( function ( option ) {
document . getElementById ( element ) . innerHTML += '<option value="' + option + '" ' + ( option == selected ? 'selected' : '' ) + '>' + option + '</option>' ;
} ) ;
}
loadPlaylist = function ( startTrim , endTrim , defaultQuality ) {
var playlist = "/playlist/" + document . getElementById ( "StreamName" ) . value + ".m3u8" ;
// If we're using bustime, update stream start/end from it first
if ( document . getElementById ( "BusTimeToggleBus" ) . checked ) {
setStreamRange ( ) ;
}
}
var streamStart = document . getElementById ( "StreamStart" ) . value ? "start=" + document . getElementById ( "StreamStart" ) . value : null ;
var streamStart = document . getElementById ( "StreamStart" ) . value ? "start=" + document . getElementById ( "StreamStart" ) . value : null ;
@ -64,18 +124,15 @@ loadPlaylist = function(startTrim, endTrim) {
return ;
return ;
}
}
var qualityLevels = data . sort ( ) . reverse ( ) ;
var qualityLevels = data . sort ( ) . reverse ( ) ;
qualityLevels . forEach ( function ( level , index ) {
setOptions ( 'qualityLevel' , qualityLevels , defaultQuality ) ;
document . getElementById ( 'qualityLevel' ) . innerHTML += '<option value="' + level + '" ' + ( index == 0 ? 'selected' : '' ) + '>' + level + '</option>' ;
if ( ! ! defaultQuality && qualityLevels . length > 0 && defaultQuality != qualityLevels [ 0 ] ) {
} ) ;
document . getElementById ( 'wubloaderAdvancedInputTable' ) . style . display = "block" ;
}
} ) ;
} ) ;
} ;
} ;
thrimbletrimmerSubmit = function ( state ) {
thrimbletrimmerSubmit = function ( state ) {
document . getElementById ( 'SubmitButton' ) . disabled = true ;
document . getElementById ( 'SubmitButton' ) . disabled = true ;
if ( player . trimmingControls ( ) . options . startTrim >= player . trimmingControls ( ) . options . endTrim ) {
alert ( "End Time must be greater than Start Time" ) ;
document . getElementById ( 'SubmitButton' ) . disabled = false ;
} else {
var discontinuities = mapDiscontinuities ( ) ;
var discontinuities = mapDiscontinuities ( ) ;
var wubData = {
var wubData = {
@ -83,15 +140,16 @@ thrimbletrimmerSubmit = function(state) {
video _end : getRealTimeForPlayerTime ( discontinuities , player . trimmingControls ( ) . options . endTrim ) . replace ( 'Z' , '' ) ,
video _end : getRealTimeForPlayerTime ( discontinuities , player . trimmingControls ( ) . options . endTrim ) . replace ( 'Z' , '' ) ,
video _title : document . getElementById ( "VideoTitle" ) . value ,
video _title : document . getElementById ( "VideoTitle" ) . value ,
video _description : document . getElementById ( "VideoDescription" ) . value ,
video _description : document . getElementById ( "VideoDescription" ) . value ,
allow _holes : String ( document . getElementById ( 'AllowHoles' ) . checked ) ,
allow _holes : document . getElementById ( 'AllowHoles' ) . checked ,
upload _location : document . getElementById ( 'uploadLocation' ) . value ,
upload _location : document . getElementById ( 'uploadLocation' ) . value ,
video _channel : document . getElementById ( "StreamName" ) . value ,
video _channel : document . getElementById ( "StreamName" ) . value ,
video _quality : document . getElementById ( 'qualityLevel' ) . options [ document . getElementById ( 'qualityLevel' ) . options . selectedIndex ] . value ,
video _quality : document . getElementById ( 'qualityLevel' ) . options [ document . getElementById ( 'qualityLevel' ) . options . selectedIndex ] . value ,
uploader _whitelist : ( document . getElementById ( 'uploaderWhitelist' ) . value ? document . getElementById ( 'uploaderWhitelist' ) . value . split ( ',' ) : null ) ,
uploader _whitelist : ( document . getElementById ( 'uploaderWhitelist' ) . value ? document . getElementById ( 'uploaderWhitelist' ) . value . split ( ',' ) : null ) ,
state : state ,
state : state ,
token : user . getAuthResponse ( ) . id _token
} ;
} ;
// state_columns = ['state', 'uploader', 'error', 'video_link']
if ( ! ! user ) {
wubData . token = user . getAuthResponse ( ) . id _token
}
console . log ( wubData ) ;
console . log ( wubData ) ;
console . log ( JSON . stringify ( wubData ) ) ;
console . log ( JSON . stringify ( wubData ) ) ;
@ -105,17 +163,23 @@ thrimbletrimmerSubmit = function(state) {
} ,
} ,
body : JSON . stringify ( wubData )
body : JSON . stringify ( wubData )
} )
} )
. then ( response => { if ( ! response . ok ) { throw Error ( response . statusText ) ; } ; return response ; } )
. then ( response => response . text ( ) . then ( text => {
. then ( data => { console . log ( data ) ; setTimeout ( ( ) => { window . location . href = '/thrimbletrimmer/dashboard.html' ; } , 500 ) ; } )
if ( ! response . ok ) {
. catch ( error => { console . log ( error ) ; alert ( error ) ; } ) ;
error = response . statusText + ": " + text ;
console . log ( error ) ;
alert ( error ) ;
} else if ( state == 'EDITED' ) {
// Only return to dashboard if submitted, not for save draft
setTimeout ( ( ) => { window . location . href = '/thrimbletrimmer/dashboard.html' ; } , 500 ) ;
return
}
}
document . getElementById ( 'SubmitButton' ) . disabled = false ;
} ) ) ;
} ;
} ;
thrimbletrimmerDownload = function ( ) {
thrimbletrimmerDownload = function ( ) {
document . getElementById ( 'SubmitButton' ) . disabled = true ;
if ( player . trimmingControls ( ) . options . startTrim >= player . trimmingControls ( ) . options . endTrim ) {
if ( player . trimmingControls ( ) . options . startTrim >= player . trimmingControls ( ) . options . endTrim ) {
alert ( "End Time must be greater than Start Time" ) ;
alert ( "End Time must be greater than Start Time" ) ;
document . getElementById ( 'SubmitButton' ) . disabled = false ;
} else {
} else {
var discontinuities = mapDiscontinuities ( ) ;
var discontinuities = mapDiscontinuities ( ) ;
@ -133,36 +197,66 @@ thrimbletrimmerDownload = function() {
} ;
} ;
thrimbletrimmerManualLink = function ( ) {
thrimbletrimmerManualLink = function ( ) {
document . getElementById ( "ManualButton" ) . disabled = true ;
var rowId = /id=(.*)(?:&|$)/ . exec ( document . location . search ) [ 1 ] ;
var rowId = /id=(.*)(?:&|$)/ . exec ( document . location . search ) [ 1 ] ;
body = { link : document . getElementById ( "ManualLink" ) . value } ;
if ( ! ! user ) {
body . token = user . getAuthResponse ( ) . id _token ;
}
fetch ( "/thrimshim/manual-link/" + rowId , {
fetch ( "/thrimshim/manual-link/" + rowId , {
method : 'POST' ,
method : 'POST' ,
headers : {
headers : {
'Accept' : 'application/json' ,
'Accept' : 'application/json' ,
'Content-Type' : 'application/json'
'Content-Type' : 'application/json'
} ,
} ,
body : JSON . stringify ( {
body : JSON . stringify ( body )
link : document . getElementById ( "ManualLink" ) . value ,
token : user . getAuthResponse ( ) . id _token
} )
} )
} )
. then ( response => { if ( ! response . ok ) { throw Error ( response . statusText ) ; } ; return response ; } )
. then ( response => response . text ( ) . then ( text => {
. then ( data => { console . log ( data ) ; setTimeout ( ( ) => { alert ( "Manual link set" ) ; } , 500 ) ; } )
if ( ! response . ok ) {
. catch ( error => { console . log ( error ) ; alert ( error ) ; } ) ;
error = response . statusText + ": " + text ;
console . log ( error ) ;
alert ( error ) ;
document . getElementById ( "ManualButton" ) . disabled = false ;
} else {
alert ( "Manual link set to " + body . link ) ;
setTimeout ( ( ) => { window . location . href = '/thrimbletrimmer/dashboard.html' ; } , 500 ) ;
}
} ) ) ;
} ;
} ;
thrimbletrimmerResetLink = function ( ) {
thrimbletrimmerResetLink = function ( ) {
var rowId = /id=(.*)(?:&|$)/ . exec ( document . location . search ) [ 1 ] ;
var rowId = /id=(.*)(?:&|$)/ . exec ( document . location . search ) [ 1 ] ;
if ( confirm ( 'Are you sure you want to reset this event?' ) ) {
if ( ! confirm (
'Are you sure you want to reset this event? ' +
'This will set the row back to UNEDITED and forget about any video that already may exist. ' +
'It is intended as a last-ditch command to clear a malfunctioning cutter, ' +
'or if a video needs to be re-edited and replaced. ' +
'IT IS YOUR RESPONSIBILITY TO DEAL WITH ANY VIDEO THAT MAY HAVE ALREADY BEEN UPLOADED. '
) ) {
return ;
}
document . getElementById ( "ResetButton" ) . disabled = true ;
body = { }
if ( ! ! user ) {
body . token = user . getAuthResponse ( ) . id _token ;
}
fetch ( "/thrimshim/reset/" + rowId , {
fetch ( "/thrimshim/reset/" + rowId , {
method : 'POST' ,
method : 'POST' ,
headers : {
headers : {
'Accept' : 'application/json' ,
'Accept' : 'application/json' ,
'Content-Type' : 'application/json'
'Content-Type' : 'application/json'
} ,
} ,
body : JSON . stringify ( { token : user . getAuthResponse ( ) . id _token } )
body : JSON . stringify ( body )
} )
} )
. then ( response => { if ( ! response . ok ) { throw Error ( response . statusText ) ; } ; return response ; } )
. then ( response => response . text ( ) . then ( text => {
. then ( data => { console . log ( data ) ; setTimeout ( ( ) => { window . location . reload ( ) } , 500 ) ; } )
if ( ! response . ok ) {
. catch ( error => { console . log ( error ) ; alert ( error ) ; } ) ;
error = response . statusText + ": " + text ;
console . log ( error ) ;
alert ( error ) ;
document . getElementById ( "ResetButton" ) . disabled = false ;
} else {
alert ( "Row has been reset. Reloading..." ) ;
setTimeout ( ( ) => { window . location . reload ( ) ; } , 500 ) ;
}
}
} ) ) ;
} ;
} ;