use webvvt to overlay timestamp (honoring Monitor.LabelFormat) to videos in timeline and event
also fixed bug which prevented seeking in timeline video previewpull/1166/head
parent
1e5c82937c
commit
5ea11a8bfe
|
@ -261,3 +261,38 @@ if ( focusWindow )
|
|||
}
|
||||
window.addEvent( 'domready', checkSize);
|
||||
|
||||
function convertLabelFormat(LabelFormat, monitorName){
|
||||
//convert label format from strftime to moment's format (modified from
|
||||
//https://raw.githubusercontent.com/benjaminoakes/moment-strftime/master/lib/moment-strftime.js
|
||||
//added %f and %N below (TODO: add %Q)
|
||||
var replacements = { a: 'ddd', A: 'dddd', b: 'MMM', B: 'MMMM', d: 'DD', e: 'D', F: 'YYYY-MM-DD', H: 'HH', I: 'hh', j: 'DDDD', k: 'H', l: 'h', m: 'MM', M: 'mm', p: 'A', S: 'ss', u: 'E', w: 'd', W: 'WW', y: 'YY', Y: 'YYYY', z: 'ZZ', Z: 'z', 'f': 'SS', 'N': "["+monitorName+"]", '%': '%' };
|
||||
var momentLabelFormat = Object.keys(replacements).reduce(function (momentFormat, key) {
|
||||
var value = replacements[key];
|
||||
return momentFormat.replace("%" + key, value);
|
||||
}, LabelFormat);
|
||||
return momentLabelFormat;
|
||||
}
|
||||
|
||||
function addVideoTimingTrack(video, LabelFormat, monitorName, duration, startTime){
|
||||
var labelFormat = convertLabelFormat(LabelFormat, monitorName);
|
||||
var webvttformat = 'HH:mm:ss.SSS', webvttdata="WEBVTT\n\n";
|
||||
|
||||
startTime = moment(startTime);
|
||||
|
||||
var seconds = moment({s:0}), endduration = moment({s:duration});
|
||||
while(seconds.isBefore(endduration)){
|
||||
webvttdata += seconds.format(webvttformat) + " --> ";
|
||||
seconds.add(1,'s');
|
||||
webvttdata += seconds.format(webvttformat) + "\n";
|
||||
webvttdata += startTime.format(labelFormat) + "\n\n";
|
||||
startTime.add(1, 's');
|
||||
}
|
||||
var track = document.createElement('track');
|
||||
track.kind = "captions";
|
||||
track.srclang = "en";
|
||||
track.label = "English";
|
||||
track['default'] = true;
|
||||
track.src = 'data:plain/text;charset=utf-8,'+encodeURIComponent(webvttdata);
|
||||
video.appendChild(track);
|
||||
}
|
||||
|
||||
|
|
|
@ -27,7 +27,7 @@ if ( !canView( 'Events' ) )
|
|||
$eid = validInt( $_REQUEST['eid'] );
|
||||
$fid = !empty($_REQUEST['fid'])?validInt($_REQUEST['fid']):1;
|
||||
|
||||
$sql = 'SELECT E.*,M.Name AS MonitorName,M.Width,M.Height,M.DefaultRate,M.DefaultScale,M.VideoWriter,M.SaveJPEGs,M.Orientation FROM Events AS E INNER JOIN Monitors AS M ON E.MonitorId = M.Id WHERE E.Id = ?';
|
||||
$sql = 'SELECT E.*,M.Name AS MonitorName,M.Width,M.Height,M.DefaultRate,M.DefaultScale,M.VideoWriter,M.SaveJPEGs,M.Orientation,M.LabelFormat FROM Events AS E INNER JOIN Monitors AS M ON E.MonitorId = M.Id WHERE E.Id = ?';
|
||||
$sql_values = array( $eid );
|
||||
|
||||
if ( $user['MonitorIds'] ) {
|
||||
|
@ -141,15 +141,24 @@ if ( $event['SaveJPEGs'] & 3 )
|
|||
if ( $event['DefaultVideo'] )
|
||||
{
|
||||
?>
|
||||
<link href="//vjs.zencdn.net/4.11/video-js.css" rel="stylesheet">
|
||||
<script src="//vjs.zencdn.net/4.11/video.js"></script>
|
||||
<script src='./js/videojs.zoomrotate.js'></script>
|
||||
<div id="videoFeed">
|
||||
<video id="videoobj" class="video-js vjs-default-skin" width="<?php echo reScale( $event['Width'], $scale ) ?>" height="<?php echo reScale( $event['Height'], $scale ) ?>" data-setup='{ "controls": true, "playbackRates": [0.5, 1, 1.5, 2, 4, 8, 16, 32, 64, 128, 256], "autoplay": true, "preload": "auto", "plugins": { "zoomrotate": { "rotate": "<?php echo $Rotation ?>", "zoom": "<?php echo $Zoom ?>"}}}'>
|
||||
<source src="<?php echo getEventDefaultVideoPath($event) ?>" type="video/mp4">
|
||||
Your browser does not support the video tag.
|
||||
</video>
|
||||
</div>
|
||||
<!--script>includeVideoJs();</script-->
|
||||
<link href="//vjs.zencdn.net/4.11/video-js.css" rel="stylesheet">
|
||||
<script src="//vjs.zencdn.net/4.11/video.js"></script>
|
||||
<script src="./js/videojs.zoomrotate.js"></script>
|
||||
<script src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.10.6/moment.min.js"></script>
|
||||
<script>
|
||||
var LabelFormat = "<?php echo validJsStr($event['LabelFormat'])?>";
|
||||
var monitorName = "<?php echo validJsStr($event['MonitorName'])?>";
|
||||
var duration = <?php echo $event['Length'] ?>, startTime = '<?php echo $event['StartTime'] ?>';
|
||||
|
||||
addVideoTimingTrack(document.getElementById('videoobj'), LabelFormat, monitorName, duration, startTime);
|
||||
</script>
|
||||
|
||||
<?php
|
||||
}
|
||||
|
|
|
@ -105,14 +105,15 @@ function previewEvent( eventId, frameId )
|
|||
|
||||
if ( events[eventId] )
|
||||
{
|
||||
if ( events[eventId]['frames'] )
|
||||
var event = events[eventId];
|
||||
if ( event['frames'] )
|
||||
{
|
||||
if ( events[eventId]['frames'][frameId] )
|
||||
if ( event['frames'][frameId] )
|
||||
{
|
||||
showEventDetail( events[eventId]['frames'][frameId]['html'] );
|
||||
var imagePath = events[eventId].frames[frameId].Image.imagePath;
|
||||
var videoName = events[eventId].DefaultVideo;
|
||||
loadEventImage( imagePath, eventId, frameId, events[eventId].Width, events[eventId].Height, events[eventId].Frames/events[eventId].Length, videoName);
|
||||
showEventDetail( event['frames'][frameId]['html'] );
|
||||
var imagePath = event.frames[frameId].Image.imagePath;
|
||||
var videoName = event.DefaultVideo;
|
||||
loadEventImage( imagePath, eventId, frameId, event.Width, event.Height, event.Frames/event.Length, videoName, event.Length, event.StartTime, monitors[event.MonitorId]);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
@ -120,7 +121,7 @@ function previewEvent( eventId, frameId )
|
|||
requestFrameData( eventId, frameId );
|
||||
}
|
||||
|
||||
function loadEventImage( imagePath, eid, fid, width, height, fps, videoName )
|
||||
function loadEventImage( imagePath, eid, fid, width, height, fps, videoName, duration, startTime, Monitor )
|
||||
{
|
||||
var vid= $('preview');
|
||||
var imageSrc = $('imageSrc');
|
||||
|
@ -137,14 +138,18 @@ function loadEventImage( imagePath, eid, fid, width, height, fps, videoName )
|
|||
//it is possible to set a long source list here will that be unworkable?
|
||||
var sources = vid.getElementsByTagName('source');
|
||||
sources[0].src=newsource;
|
||||
var tracks = vid.getElementsByTagName('track');
|
||||
if(tracks.length){
|
||||
tracks[0].parentNode.removeChild(tracks[0]);
|
||||
}
|
||||
vid.load();
|
||||
vid.oncanplay=function(){ vid.currentTime=fid/fps;} //25.0
|
||||
addVideoTimingTrack(vid, Monitor.LabelFormat, Monitor.Name, duration, startTime)
|
||||
vid.currentTime = fid/fps;
|
||||
}
|
||||
else
|
||||
{
|
||||
vid.oncanplay=null;//console.log("canplay");}
|
||||
if(!vid.seeking)
|
||||
vid.currentTime=fid/fps;//25.0;
|
||||
vid.currentTime=fid/fps;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
|
|
@ -2,7 +2,7 @@ var filterQuery = '<?php echo validJsStr($filterQuery) ?>';
|
|||
|
||||
<?php
|
||||
$jsMonitors = array();
|
||||
$fields = array('Name', 'SaveJPEGs', 'VideoWriter');
|
||||
$fields = array('Name', 'LabelFormat', 'SaveJPEGs', 'VideoWriter');
|
||||
foreach ( $monitors as $monitor )
|
||||
{
|
||||
if ( !empty($monitorIds[$monitor['Id']]) )
|
||||
|
|
|
@ -813,7 +813,11 @@ xhtmlHeaders(__FILE__, translate('Timeline') );
|
|||
<div id="imagePanel">
|
||||
<div id="image" class="imageHeight">
|
||||
<img id="imageSrc" class="imageWidth" src="graphics/transparent.gif" alt="<?php echo translate('ViewEvent') ?>" title="<?php echo translate('ViewEvent') ?>"/>
|
||||
<video id="preview" width="100%" controls>
|
||||
<?php
|
||||
//due to chrome bug, has to enable https://code.google.com/p/chromium/issues/detail?id=472300
|
||||
//crossorigin has to be added below to make caption work in chrome
|
||||
?>
|
||||
<video id="preview" width="100%" controls crossorigin="anonymous">
|
||||
<source src="<?php echo "/events/".getEventPath($event)."/event.mp4"; ?>" type="video/mp4">
|
||||
Your browser does not support the video tag.
|
||||
</video>
|
||||
|
@ -979,5 +983,6 @@ foreach( array_keys($monEventSlots) as $monitorId )
|
|||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<script src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.10.6/moment.min.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
Loading…
Reference in New Issue