UNPKG

shinobi-video-synopsis

Version:

Create Video Synopsis from provided videos. Frames are extracted from each video provided and backgrounds are subtracted around moving elements and merged into a single video for quick review.

83 lines (81 loc) 3.24 kB
const { mainDirectory, stripNameJpg, splitForFfmpeg, } = require('./utils.js'); const fs = require('fs'); const spawn = require('child_process').spawn; exports.createVideoFromJpegImages = (options) => { const engine = options.engine const ffmpegBinary = options.ffmpegBinary || 'ffmpeg' const frameDirectory = options.mergedFramesDirectory const frames = options.frames || [] var framesPerSecond = isNaN(options.fps) ? 2 : parseInt(options.fps) const videoOutputLocation = options.output || mainDirectory + 'videoOutput.mp4' return new Promise((resolve,reject) => { var concatFiles = [] const stripName = (name) => { return parseInt(name.replace('.jpg','')) } frames.forEach(function(filename){ var n = stripName(filename) concatFiles[n] = frameDirectory + filename }) if(concatFiles.length > framesPerSecond){ var commandTempLocation = `concatImagesAndMakeVideo.sh` var currentFile = 0 var commandString = `${ffmpegBinary} -y -pattern_type glob -f image2pipe -vcodec mjpeg -r ${framesPerSecond} -analyzeduration 10 -i - -q:v 1 -c:v libx264 -r ${framesPerSecond} "${videoOutputLocation}"` fs.writeFileSync(commandTempLocation,commandString) var videoBuildProcess = spawn('sh',[commandTempLocation]) var isKilling = false var killTimeout const exitBuilding = () => { engine.videoBuildProcess = null setTimeout(()=>{ resolve({ ok: true, fileLocation: videoOutputLocation, msg: 'Done Building' }) },5000) } videoBuildProcess.stderr.on('data',function(data){ engine.logStderr(data.toString()) clearTimeout(killTimeout) killTimeout = setTimeout(()=>{ if(isKilling)return; isKilling = true videoBuildProcess.kill('SIGTERM') },4000) }) videoBuildProcess.stdout.on('data',function(data){ engine.logStderr(data.toString()) }) videoBuildProcess.on('exit',function(data){ exitBuilding() }) engine.videoBuildProcess = videoBuildProcess var readFile = function(){ engine.logStderr(filePath) var filePath = concatFiles[currentFile] fs.readFile(filePath,function(err,buffer){ if(!err)videoBuildProcess.stdin.write(buffer) if(currentFile === concatFiles.length - 1){ //is last }else{ setTimeout(function(){ ++currentFile readFile() },1/framesPerSecond) } }) } readFile() }else{ resolve({ ok: false, msg: 'More Frames or Lower FPS' }) } }) }