From: Calin Crisan Date: Sun, 29 Sep 2013 19:01:53 +0000 (+0300) Subject: added motion restarting mechanism X-Git-Url: http://www.vanbest.org/gitweb/?a=commitdiff_plain;h=a13c150212993a80bbc525e447dd7e6525acb05a;p=motioneye-debian added motion restarting mechanism --- diff --git a/doc/todo.txt b/doc/todo.txt index d1032ac..0e36e92 100644 --- a/doc/todo.txt +++ b/doc/todo.txt @@ -1,6 +1,7 @@ -> camera not available background and icon design -> remove current snapshot GET logs -> a nice shadow behind the header +-> add a motion running status indicator (and maybe a start/stop button) -> group @config rules to top -> browser compatibility test diff --git a/motioneye.py b/motioneye.py index ad239fb..9eb0d0c 100644 --- a/motioneye.py +++ b/motioneye.py @@ -1,6 +1,7 @@ #!/usr/bin/env python2 import logging +import motionctl import os.path import signal import sys @@ -22,6 +23,10 @@ def _configure_signals(): ioloop.stop() logging.info('server stopped') + + if motionctl.running(): + motionctl.stop() + logging.info('motion stopped') signal.signal(signal.SIGINT, bye_handler) signal.signal(signal.SIGTERM, bye_handler) @@ -40,18 +45,14 @@ def _start_server(): tornado.ioloop.IOLoop.instance().start() +def _start_motion(): + if not motionctl.running(): + motionctl.start() + logging.info('motion started') + + if __name__ == '__main__': _configure_signals() _configure_logging() + _start_motion() _start_server() - -# import config # TODO remove this -# main_config = config.get_main() -# config.add_camera('v4l2:///dev/video0') -# #data = config.get_camera(1) -# #data['@enabled'] = True -# #config.set_camera(1, data) -# config.rem_camera(1) - -# import motionctl -# motionctl.start() diff --git a/src/config.py b/src/config.py index 8e3c617..262ec4e 100644 --- a/src/config.py +++ b/src/config.py @@ -509,8 +509,9 @@ def _set_default_motion_camera(data): data.setdefault('quality', 75) data.setdefault('@preserve_images', 0) - data.setdefault('movie_filename', '') data.setdefault('ffmpeg_variable_bitrate', 14) + data.setdefault('movie_filename', '') + data.setdefault('ffmpeg_cap_new', False) data.setdefault('@preserve_movies', 0) data.setdefault('@motion_notifications', False) diff --git a/src/handlers.py b/src/handlers.py index 17f9e8f..c0cd554 100644 --- a/src/handlers.py +++ b/src/handlers.py @@ -6,6 +6,7 @@ from tornado.web import RequestHandler, HTTPError import config import mjpgclient +import motionctl import template import v4l2ctl @@ -111,30 +112,42 @@ class ConfigHandler(BaseHandler): raise - if camera_id: - logging.debug('setting config for camera %(id)s' % {'id': camera_id}) - - camera_ids = config.get_camera_ids() - if camera_id not in camera_ids: - raise HTTPError(404, 'no such camera') - - data = self._camera_ui_to_dict(data) - config.set_camera(camera_id, data) - - else: - logging.debug('setting main config') - - try: - data = json.loads(self.request.body) - - except Exception as e: - logging.error('could not decode json: %(msg)s' % {'msg': unicode(e)}) + restart = bool(data.get('restart')) + if restart and motionctl.running(): + motionctl.stop() + + try: + if camera_id: + logging.debug('setting config for camera %(id)s' % {'id': camera_id}) - raise - - data = self._main_ui_to_dict(data) - config.set_main(data) + camera_ids = config.get_camera_ids() + if camera_id not in camera_ids: + raise HTTPError(404, 'no such camera') + + data = self._camera_ui_to_dict(data) + config.set_camera(camera_id, data) + else: + logging.debug('setting main config') + + try: + data = json.loads(self.request.body) + + except Exception as e: + logging.error('could not decode json: %(msg)s' % {'msg': unicode(e)}) + + raise + + data = self._main_ui_to_dict(data) + config.set_main(data) + + except: + raise + + finally: + if restart: + motionctl.start() + def set_preview(self, camera_id): try: controls = json.loads(self.request.body) @@ -276,10 +289,9 @@ class ConfigHandler(BaseHandler): '@preserve_images': int(ui.get('preserve_images', 0)), # movies - 'ffmpeg_variable_bitrate': 0, - 'ffmpeg_video_codec': 'mpeg4', - 'ffmpeg_cap_new': True, - 'movie_filename': '', + 'ffmpeg_variable_bitrate': 2 + int((100 - int(ui.get('movie_quality', 75))) * 0.29), + 'ffmpeg_cap_new': ui.get('motion_movies', False), + 'movie_filename': ui.get('movie_file_name', '%Y-%m-%d-%H-%M-%S-%q'), '@preserve_movies': int(ui.get('preserve_movies', 0)), # motion detection @@ -341,10 +353,6 @@ class ConfigHandler(BaseHandler): data['quality'] = max(1, int(ui.get('image_quality', 75))) - if ui.get('motion_movies', False): - data['ffmpeg_variable_bitrate'] = 2 + int((100 - int(ui.get('movie_quality', 75))) * 0.29) - data['movie_filename'] = ui.get('movie_file_name', '%Y-%m-%d-%H-%M-%S-%q') - if ui.get('working_schedule', False): data['@working_schedule'] = ( ui.get('monday_from', '') + '-' + ui.get('monday_to') + '|' + diff --git a/static/css/main.css b/static/css/main.css index efe24fc..d4b21e0 100644 --- a/static/css/main.css +++ b/static/css/main.css @@ -353,6 +353,23 @@ div.camera-placeholder { background-color: #555; } +div.camera-progress { + position: absolute; + top: 0px; + right: 0px; + bottom: 0px; + left: 0px; + opacity: 0; + transition: all 0.2s linear; + text-align: center; +} + +img.camera-progress { + margin-top: 28%; + border: 10px solid white; + border-radius: 10px; +} + /* media queries */ diff --git a/static/img/camera-progress.gif b/static/img/camera-progress.gif new file mode 100644 index 0000000..023347e Binary files /dev/null and b/static/img/camera-progress.gif differ diff --git a/static/js/main.js b/static/js/main.js index c6ae76f..70e6ee5 100644 --- a/static/js/main.js +++ b/static/js/main.js @@ -618,6 +618,9 @@ function showProgress() { applyButton.css('display', 'inline-block'); applyButton.animate({'opacity': '1'}, 100); applyButton.addClass('progress'); + + $('img.camera').css('opacity', '0.3'); + $('div.camera-progress').css('opacity', '0.5'); } function hideApply() { @@ -640,6 +643,9 @@ function endProgress() { else { showApply(); } + + $('div.camera-progress').css('opacity', '0'); + $('img.camera').css('opacity', '1'); } function isProgress() { @@ -679,6 +685,9 @@ function doApply() { for (var i = 0; i < configs.length; i++) { var config = configs[i]; + if (i === configs.length - 1) { + config.config['restart'] = true; + } ajax('POST', '/config/' + config.key + '/set/', config.config, function () { finishedCount++; testReady(); @@ -785,6 +794,7 @@ function addCameraFrameUi(cameraId, cameraName, framerate) { '
' + '
' + '' + + '
' + '
' + ''); @@ -792,11 +802,13 @@ function addCameraFrameUi(cameraId, cameraName, framerate) { var configureButton = cameraFrameDiv.find('div.camera-button.configure'); var closeButton = cameraFrameDiv.find('div.camera-button.close'); var cameraImg = cameraFrameDiv.find('img.camera'); + var progressImg = cameraFrameDiv.find('img.camera-progress'); cameraFrameDiv.attr('id', 'camera' + cameraId); cameraFrameDiv[0].framerate = framerate; cameraFrameDiv[0].refreshDivider = 0; nameSpan.html(cameraName); + progressImg.attr('src', staticUrl + 'img/camera-progress.gif'); /* insert the new camera frame at the right position, * with respect to the camera id */