From 962a7c82131dc1c04336b7f82139d5b1ea0a4e9c Mon Sep 17 00:00:00 2001 From: mmcw-dev Date: Mon, 11 Feb 2019 01:08:20 -0500 Subject: [PATCH] Fix loop bug. When selection a video as a projector (need to work on this metaphor) the loops are automatically set. Previous issues were due to id re-use. Also, (almost) you can choose a light color value that a frame will be overlayed on with a Darken composite mode. This is almost working but is kludgey because the first frame is always coming up black. Will need to make adjustments in the light module. --- app/css/app.css | 6 +++--- app/index.html | 2 +- app/less/seq.less | 5 +---- app/lib/ffmpeg/index.js | 27 ++++++++++++++++++----- app/lib/ui/cmd.js | 20 +++++++++--------- app/lib/ui/devices.js | 4 ++++ app/lib/ui/light.js | 7 +++--- app/main.js | 47 ++++++++++++++++++++++------------------- 8 files changed, 70 insertions(+), 48 deletions(-) diff --git a/app/css/app.css b/app/css/app.css index 1ac2729..508f0e1 100644 --- a/app/css/app.css +++ b/app/css/app.css @@ -381,16 +381,16 @@ button:focus { font-weight: 600; float: right; } -#seq_loop { +#seq_loop_wrap { width: 40%; float: left; padding: 0 0 0 56px; } -#seq_loop h3 { +#seq_loop_wrap h3 { font-size: 20px; margin: 12px 0 3px; } -#seq_loop input { +#seq_loop_wrap input { font-family: 'Menlo', monospace; background: rgba(255, 255, 255, 0.05); color: #fff; diff --git a/app/index.html b/app/index.html index b7e120c..ea7dc23 100644 --- a/app/index.html +++ b/app/index.html @@ -58,7 +58,7 @@
Camera end: 00000
Projector end: 00000
-
+

LOOPS

diff --git a/app/less/seq.less b/app/less/seq.less index 2b6907a..c550afe 100644 --- a/app/less/seq.less +++ b/app/less/seq.less @@ -45,7 +45,7 @@ .timing{ } } -#seq_loop{ +#seq_loop_wrap{ width: 40%; float: left; padding: 0 0 0 56px; @@ -64,9 +64,6 @@ } } -#sequencer{ - -} #sequence{ width: 970px; padding-bottom: 21px; diff --git a/app/lib/ffmpeg/index.js b/app/lib/ffmpeg/index.js index d6bdb0e..5231f1a 100644 --- a/app/lib/ffmpeg/index.js +++ b/app/lib/ffmpeg/index.js @@ -20,24 +20,32 @@ function padded_frame (i) { return str; } -async function frame (state) { +async function frame (state, light) { let frame = state.frame let video = state.path let w = state.info.width let h = state.info.height let padded = padded_frame(frame) let ext = 'tif' + let rgb = light.on; let tmpoutput let cmd let output + let cmd2 + let output2 if (system.platform !== 'nix') { ext = 'png' } - tmpoutput = path.join(TMPDIR, `export-${padded}.${ext}`) + rgb = rgb.map(e => { + return parseInt(e); + }); - cmd = `ffmpeg -i "${video}" -vf "select='gte(n\\,${frame})',scale=${w}:${h}" -vframes 1 -compression_algo raw -pix_fmt rgb24 "${tmpoutput}"` + tmpoutput = path.join(TMPDIR, `export-${padded}.${ext}`); + + cmd = `ffmpeg -i "${video}" -vf "select='gte(n\\,${frame})',scale=${w}:${h}" -vframes 1 -compression_algo raw -pix_fmt rgb24 "${tmpoutput}"`; + cmd2 = `convert "${tmpoutput}" -resize ${w}x${h} -size ${w}x${h} xc:"rgb(${rgb[0]},${rgb[1]},${rgb[2]})" +swap -compose Darken -composite "${tmpoutput}"`; //ffmpeg -i "${video}" -ss 00:00:07.000 -vframes 1 "export-${time}.jpg" //ffmpeg -i "${video}" -compression_algo raw -pix_fmt rgb24 "export-%05d.tiff" @@ -49,9 +57,18 @@ async function frame (state) { } catch (err) { console.error(err); } + if (output && output.stdout) console.log(`"${output.stdout}"`); - if (output) console.log(`"${output}"`); - + if (rgb[0] !== 255 || rgb[1] !== 255 || rgb[2] !== 255) { + try { + console.log(cmd2); + output2 = await exec(cmd2); + } catch (err) { + console.error(err); + } + } + + if (output2 && output2.stdout) console.log(`"${output2.stdout}"`); } async function frames (video, obj) { diff --git a/app/lib/ui/cmd.js b/app/lib/ui/cmd.js index 604d41c..a7fed65 100644 --- a/app/lib/ui/cmd.js +++ b/app/lib/ui/cmd.js @@ -47,7 +47,7 @@ cmd.cam_forward = function (rgb, callback) { gui.updateState(); setTimeout(function () { light.display(off); - light.set(off, function () { + light.set(off, false, function () { $('#cmd_cam_forward').removeClass('active'); if (callback) { callback(ms); } }); @@ -58,7 +58,7 @@ cmd.cam_forward = function (rgb, callback) { cam.set(true, function () { setTimeout( function () { light.display(rgb); - light.set(rgb, function () { + light.set(rgb, true, function () { setTimeout( function () { cam.move(res); }, mcopy.cfg.arduino.serialDelay); @@ -67,7 +67,7 @@ cmd.cam_forward = function (rgb, callback) { }); } else { light.display(rgb); - light.set(rgb, function () { + light.set(rgb, true, function () { setTimeout(function () { cam.move(res); }, mcopy.cfg.arduino.serialDelay); @@ -87,7 +87,7 @@ cmd.black_forward = function (callback) { cam.set(true, function () { setTimeout( function () { light.display(off); - light.set(off, function () { + light.set(off, false, function () { setTimeout( function () { cam.move(res); }, mcopy.cfg.arduino.serialDelay); @@ -96,7 +96,7 @@ cmd.black_forward = function (callback) { }); } else { light.display(off); - light.set(off, function () { + light.set(off, false, function () { setTimeout(function () { cam.move(res); }, mcopy.cfg.arduino.serialDelay); @@ -109,7 +109,7 @@ cmd.cam_backward = function (rgb, callback) { var res = function (ms) { gui.updateState(); light.display(off); - light.set(off, function () { + light.set(off, false, function () { $('#cmd_cam_backward').removeClass('active'); if (callback) { callback(ms); } }); @@ -119,7 +119,7 @@ cmd.cam_backward = function (rgb, callback) { cam.set(false, function () { setTimeout(function () { light.display(rgb); - light.set(rgb, function () { + light.set(rgb, true, function () { cam.move(res); }); }, mcopy.cfg.arduino.serialDelay); @@ -127,7 +127,7 @@ cmd.cam_backward = function (rgb, callback) { } else { setTimeout(function () { light.display(rgb); - light.set(rgb, function () { + light.set(rgb, true, function () { cam.move(res); }); }, mcopy.cfg.arduino.serialDelay); @@ -146,7 +146,7 @@ cmd.black_backward = function (callback) { cam.set(false, function () { setTimeout(function () { light.display(off); - light.set(off, function () { + light.set(off, false, function () { cam.move(res); }); }, mcopy.cfg.arduino.serialDelay); @@ -154,7 +154,7 @@ cmd.black_backward = function (callback) { } else { setTimeout(function () { light.display(off); - light.set(off, function () { + light.set(off, false, function () { cam.move(res); }); }, mcopy.cfg.arduino.serialDelay); diff --git a/app/lib/ui/devices.js b/app/lib/ui/devices.js index 4302e29..8fe670b 100644 --- a/app/lib/ui/devices.js +++ b/app/lib/ui/devices.js @@ -191,6 +191,7 @@ devices.digital = function () { devices.digitalCb = function (evt, args) { 'use strict'; let state; + let color = [255,255,255]; gui.spinner(false); gui.overlay(false); if (args.valid && args.valid === true) { @@ -201,9 +202,12 @@ devices.digitalCb = function (evt, args) { gui.notify('DEVICES', `Using video ${state.fileName}`); mcopy.state.sequence.arr = ['PF', 'CF']; + gui.grid.setLight(1, color); gui.grid.state(0); gui.grid.state(1); + $('#seq_loop').val(`${state.frames}`).trigger('change'); + gui.updateState(); } else { $('#projector_type_digital').prop('checked', 'checked'); diff --git a/app/lib/ui/light.js b/app/lib/ui/light.js index 95c6852..d521385 100644 --- a/app/lib/ui/light.js +++ b/app/lib/ui/light.js @@ -111,7 +111,7 @@ light.colorPickers = function () { light.kelvin.init(); //light.cmy.init(); }; -light.set = function (rgb, callback) { //rgb = [0,0,0] +light.set = function (rgb, on, callback) { //rgb = [0,0,0] 'use strict'; var obj; @@ -121,8 +121,9 @@ light.set = function (rgb, callback) { //rgb = [0,0,0] } obj = { - rgb : rgb, - id : uuid.v4() + rgb, + id : uuid.v4(), + on }; ipcRenderer.sendSync('light', obj); diff --git a/app/main.js b/app/main.js index 1a88013..9a23659 100644 --- a/app/main.js +++ b/app/main.js @@ -21,6 +21,7 @@ const settings = require('settings') const system = require('system') const Server = require('server') const Intval = require('intval') +const delay = require('delay') const mcopy = {} const log = {} @@ -44,12 +45,6 @@ let display let ffmpeg let ffprobe -async function delay (ms) { - return new Promise(resolve => { - return setTimeout(resolve, ms) - }) -} - mcopy.cfg = require('./data/cfg.json') mcopy.settings = {} @@ -367,13 +362,18 @@ var createWindow = function () { }) } +light.state = { + color : [0, 0, 0], + on : [0, 0, 0] +} + light.init = function () { light.listen() } light.listen = function () { ipcMain.on('light', async (event, arg) => { try { - await light.set(arg.rgb, arg.id) + await light.set(arg.rgb, arg.id, arg.on) }catch (err) { console.error(err) return reject(err) @@ -381,9 +381,12 @@ light.listen = function () { event.returnValue = true }) } -light.set = async function (rgb, id) { +light.set = async function (rgb, id, on) { const str = rgb.join(','); let ms + light.state.color = rgb; + if (on) light.state.on = rgb; + console.dir(light.state) try { ms = arduino.send('light', mcopy.cfg.arduino.cmd.light) } catch (err) { @@ -518,7 +521,7 @@ proj.connectDigital = async function (evt, arg) { dig.state.frames = frames; dig.state.info = info; - console.dir(dig.state); + //console.dir(dig.state); log.info(`Opened ${dig.state.fileName}`, 'DIGITAL', true, true); log.info(`Frames : ${frames}`, 'DIGITAL', true, true); @@ -563,7 +566,7 @@ dig.move = async function () { } try { - await ffmpeg.frame(dig.state) + await ffmpeg.frame(dig.state, light.state) } catch (err) { console.error(err) } @@ -659,7 +662,6 @@ cam.connectIntval = async function (event, arg) { return resolve(false) } }) - } cam.listen = function () { @@ -784,9 +786,9 @@ transfer.listen = function () { var init = async function () { try { - SYSTEM = await system(); + SYSTEM = await system() } catch (err) { - console.error(err); + console.error(err) } createWindow() @@ -799,25 +801,26 @@ var init = async function () { dev.init() seq.init() - - //capture = require('capture')(SYSTEM); //redundant - display = require('display')(SYSTEM); - ffmpeg = require('ffmpeg')(SYSTEM); - ffprobe = require('ffprobe')(SYSTEM); - + //capture = require('capture')(SYSTEM) //redundant + display = require('display')(SYSTEM) + ffmpeg = require('ffmpeg')(SYSTEM) + ffprobe = require('ffprobe')(SYSTEM) //transfer.init() //capture.init() arduino = require('./lib/arduino')(mcopy.cfg, ee) mscript = require('./lib/mscript') - settings.restore() mcopy.settings = settings.all() await delay(2000) - await dev.enumerate() + try { + await dev.enumerate() + } catch (err) { + console.error(err) + } } app.on('ready', init) @@ -837,4 +840,4 @@ app.on('activate', () => { mcopy.relaunch = function () { app.relaunch({args: process.argv.slice(1).concat(['--relaunch'])}) app.exit(0) -} +} \ No newline at end of file