else:
interval = int(self.get_argument('interval'))
- speed = int(self.get_argument('speed'))
+ framerate = int(self.get_argument('framerate'))
- logging.debug('preparing timelapse movie for group %(group)s of camera %(id)s with rate %(speed)s/%(int)s' % {
- 'group': group, 'id': camera_id, 'speed': speed, 'int': interval})
+ logging.debug('preparing timelapse movie for group %(group)s of camera %(id)s with rate %(framerate)s/%(int)s' % {
+ 'group': group, 'id': camera_id, 'framerate': framerate, 'int': interval})
camera_config = config.get_camera(camera_id)
if utils.local_camera(camera_config):
'group': group, 'id': camera_id, 'key': key})
self.finish_json({'key': key})
- mediafiles.get_timelapse_movie(camera_config, speed, interval, callback=on_timelapse, group=group)
+ mediafiles.get_timelapse_movie(camera_config, framerate, interval, callback=on_timelapse, group=group)
else: # remote camera
def on_response(response=None, error=None):
'group': group, 'id': camera_id, 'key': key})
self.finish_json({'key': key})
- remote.get_timelapse_movie(camera_config, speed, interval, callback=on_response, group=group)
+ remote.get_timelapse_movie(camera_config, framerate, interval, callback=on_response, group=group)
def try_finish(self, content):
try:
root = os.path.join(dir, prefix)
for name in os.listdir(root):
- if name == 'lastsnap.jpg': # ignore the lastsnap.jpg file
+ if name == 'lastsnap.jpg' or name.startswith('.'): # ignore the lastsnap.jpg and hidden files
continue
full_path = os.path.join(root, name)
else:
for root, dirs, files in os.walk(dir): # @UnusedVariable # TODO os.walk can be rewritten to return stat info
for name in files:
- if name == 'lastsnap.jpg': # ignore the lastsnap.jpg file
+ if name == 'lastsnap.jpg' or name.startswith('.'): # ignore the lastsnap.jpg and hidden files
continue
full_path = os.path.join(root, name)
poll_process()
-def get_timelapse_movie(camera_config, speed, interval, callback, group):
+def get_timelapse_movie(camera_config, framerate, interval, callback, group):
target_dir = camera_config.get('target_dir')
# create a subprocess to retrieve media files
def make_movie(pictures):
cmd = 'rm -f %(tmp_filename)s;'
- cmd += 'cat %(jpegs)s | ffmpeg -framerate %(speed)s/%(interval)s -f image2pipe -vcodec mjpeg -i - -vcodec mpeg4 -b %(bitrate)s -f avi %(tmp_filename)s'
+ cmd += 'cat %(jpegs)s | ffmpeg -framerate %(framerate)s -f image2pipe -vcodec mjpeg -i - -vcodec mpeg4 -b:v %(bitrate)s -q:v 0 -f avi %(tmp_filename)s'
- bitrate = 9999990
+ bitrate = 9999999
cmd = cmd % {
'tmp_filename': tmp_filename,
'jpegs': ' '.join((p['path'] for p in pictures)),
- 'interval': interval,
- 'speed': speed,
+ 'framerate': framerate,
'bitrate': bitrate
}
- process[0] = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, shell=True)
+
+ logging.debug('executing "%s"' % cmd)
+
+ process[0] = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=None, shell=True)
started[0] = datetime.datetime.now()
poll_movie_process()
http_client.fetch(request, on_prepare)
-def get_timelapse_movie(local_config, speed, interval, callback, group):
+def get_timelapse_movie(local_config, framerate, interval, callback, group):
host = local_config.get('@host', local_config.get('host'))
port = local_config.get('@port', local_config.get('port'))
username = local_config.get('@username', local_config.get('username'))
uri = local_config.get('@uri', local_config.get('uri')) or ''
camera_id = local_config.get('@remote_camera_id', local_config.get('remote_camera_id'))
- logging.debug('downloading timelapse movie for group %(group)s of remote camera %(id)s with rate %(speed)s/%(int)s on %(url)s' % {
+ logging.debug('downloading timelapse movie for group %(group)s of remote camera %(id)s with rate %(framerate)s/%(int)s on %(url)s' % {
'group': group,
'id': camera_id,
- 'speed': speed,
+ 'framerate': framerate,
'int': interval,
'url': make_camera_url(local_config)})
- prepare_uri = uri + '/picture/%(id)s/timelapse/%(group)s/?interval=%(int)s&speed=%(speed)s' % {
+ prepare_uri = uri + '/picture/%(id)s/timelapse/%(group)s/?interval=%(int)s&framerate=%(framerate)s' % {
'id': camera_id,
'int': interval,
- 'speed': speed,
+ 'framerate': framerate,
'group': group}
# timeout here is 100 times larger than usual - we expect a big delay
def on_prepare(response):
if response.error:
- logging.error('failed to download timelapse movie for group %(group)s of remote camera %(id)s with rate %(speed)s/%(int)s on %(url)s: %(msg)s' % {
+ logging.error('failed to download timelapse movie for group %(group)s of remote camera %(id)s with rate %(framerate)s/%(int)s on %(url)s: %(msg)s' % {
'group': group,
'id': camera_id,
'url': make_camera_url(local_config),
'int': interval,
- 'speed': speed,
+ 'framerate': framerate,
'msg': unicode(response.error)})
return callback(error=unicode(response.error))
def on_download(response):
if response.error:
- logging.error('failed to download timelapse movie for group %(group)s of remote camera %(id)s with rate %(speed)s/%(int)s on %(url)s: %(msg)s' % {
+ logging.error('failed to download timelapse movie for group %(group)s of remote camera %(id)s with rate %(framerate)s/%(int)s on %(url)s: %(msg)s' % {
'group': group,
'id': camera_id,
'url': make_camera_url(local_config),
'int': interval,
- 'speed': speed,
+ 'framerate': framerate,
'msg': unicode(response.error)})
return callback(error=unicode(response.error))
'<td><span class="help-mark" title="choose the interval of time between two selected pictures">?</span></td>' +
'</tr>' +
'<tr>' +
- '<td class="dialog-item-label"><span class="dialog-item-label">Timelapse speed factor</span></td>' +
- '<td class="dialog-item-value">' +
- '<select class="styled timelapse" id="speedSelect">' +
- '<option value="1">1x</option>' +
- '<option value="10">10x</option>' +
- '<option value="100">100x</option>' +
- '<option value="1000">1000x</option>' +
- '<option value="10000">10000x</option>' +
- '<option value="100000">100000x</option>' +
- '</select>' +
- '</td>' +
+ '<td class="dialog-item-label"><span class="dialog-item-label">Movie framerate</span></td>' +
+ '<td class="dialog-item-value"><input type="text" class="styled range" id="framerateSlider"></td>' +
'<td><span class="help-mark" title="choose how fast you want the timelapse playback to be">?</span></td>' +
'</tr>' +
'</table>');
var intervalSelect = content.find('#intervalSelect');
- var speedSelect = content.find('#speedSelect');
+ var framerateSlider = content.find('#framerateSlider');
+
+ makeSlider(framerateSlider, 1, 100, 0, [
+ {value: 1, label: '1'},
+ {value: 20, label: '20'},
+ {value: 40, label: '40'},
+ {value: 60, label: '60'},
+ {value: 80, label: '80'},
+ {value: 100, label: '100'}
+ ], null, 0);
+ intervalSelect.val(60);
+ framerateSlider.val(20).each(function () {this.update()});
+
runModalDialog({
title: 'Create Timelapse Movie',
closeButton: true,
onOk: function () {
showModalDialog('<div class="modal-progress"></div>', null, null, true);
ajax('GET', '/picture/' + cameraId + '/timelapse/' + groupKey + '/',
- {interval: intervalSelect.val(), speed: speedSelect.val()}, function (data) {
+ {interval: intervalSelect.val(), framerate: framerateSlider.val()}, function (data) {
hideModalDialog(); /* progress */
hideModalDialog(); /* timelapse dialog */