Update preview
This commit is contained in:
parent
9d40f213be
commit
d75427eac1
|
|
@ -184,3 +184,9 @@ poetry.toml
|
||||||
pyrightconfig.json
|
pyrightconfig.json
|
||||||
|
|
||||||
# End of https://www.toptal.com/developers/gitignore/api/python
|
# End of https://www.toptal.com/developers/gitignore/api/python
|
||||||
|
|
||||||
|
|
||||||
|
# Custom ignores
|
||||||
|
src/nenuscanner/static/feed.jpg
|
||||||
|
db.sqlite
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,6 @@
|
||||||
import subprocess
|
import subprocess
|
||||||
|
|
||||||
|
from flask import jsonify
|
||||||
import gphoto2 as gp
|
import gphoto2 as gp
|
||||||
import shutil
|
import shutil
|
||||||
from . import leds, config
|
from . import leds, config
|
||||||
|
|
@ -75,6 +77,16 @@ class RealCamera(Camera):
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print('An error occured when capturing photo', e)
|
print('An error occured when capturing photo', e)
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
def capture_preview(self):
|
||||||
|
try:
|
||||||
|
subprocess.run(
|
||||||
|
"gphoto2 --capture-preview --stdout > src/nenuscanner/static/feed.jpg",
|
||||||
|
shell=True, check=True
|
||||||
|
)
|
||||||
|
except subprocess.CalledProcessError as e:
|
||||||
|
print('An error occured when capturing photo', e)
|
||||||
|
raise CameraException(f"Erreur lors de la capture de l'image: {e}")
|
||||||
|
|
||||||
def save(self, capture, output_file):
|
def save(self, capture, output_file):
|
||||||
preview = self.inner.file_get(capture.folder, capture.name[:-3] + 'JPG', gp.GP_FILE_TYPE_NORMAL)
|
preview = self.inner.file_get(capture.folder, capture.name[:-3] + 'JPG', gp.GP_FILE_TYPE_NORMAL)
|
||||||
|
|
@ -146,3 +158,8 @@ def config():
|
||||||
|
|
||||||
def set_config(parameter, value):
|
def set_config(parameter, value):
|
||||||
return camera.set_config(parameter, value)
|
return camera.set_config(parameter, value)
|
||||||
|
|
||||||
|
class CameraException(Exception):
|
||||||
|
"""Exception personnalisée pour les erreurs liées à la caméra."""
|
||||||
|
def __init__(self, message):
|
||||||
|
super().__init__(message)
|
||||||
|
|
@ -1,8 +1,10 @@
|
||||||
from flask import Blueprint, render_template, request, send_file, jsonify
|
from flask import Blueprint, render_template, request, send_file, jsonify
|
||||||
import json
|
import json
|
||||||
|
import subprocess
|
||||||
|
|
||||||
from .. import camera as C
|
from .. import camera as C
|
||||||
|
|
||||||
|
|
||||||
blueprint = Blueprint('camera', __name__)
|
blueprint = Blueprint('camera', __name__)
|
||||||
|
|
||||||
# Routes for object management
|
# Routes for object management
|
||||||
|
|
@ -76,4 +78,16 @@ def get_camera_config():
|
||||||
'params': section_params
|
'params': section_params
|
||||||
})
|
})
|
||||||
|
|
||||||
return jsonify(grouped_params)
|
return jsonify(grouped_params)
|
||||||
|
|
||||||
|
@blueprint.route('/capture_preview', methods=['POST'])
|
||||||
|
def capture_preview():
|
||||||
|
"""
|
||||||
|
Capture un aperçu avec gphoto2 et sauvegarde dans static/feed.jpg
|
||||||
|
"""
|
||||||
|
try:
|
||||||
|
cam = C.get()
|
||||||
|
cam.capture_preview()
|
||||||
|
return jsonify({'status': 'ok'})
|
||||||
|
except C.CameraException as e:
|
||||||
|
return jsonify({'status': 'error', 'error': str(e)}), 500
|
||||||
|
|
@ -10,29 +10,17 @@
|
||||||
<div id="camera-config-container"></div>
|
<div id="camera-config-container"></div>
|
||||||
</div>
|
</div>
|
||||||
<div class="column is-half has-text-centered">
|
<div class="column is-half has-text-centered">
|
||||||
{#
|
|
||||||
<figure class="image is-4by3" style="max-width: 480px; margin: auto;">
|
<figure class="image is-4by3" style="max-width: 480px; margin: auto;">
|
||||||
<img id="camera-preview" src="/camera/feed.jpg?{{ range(1000000)|random }}" alt="Camera Preview"
|
<img id="camera-preview" src="/static/feed.jpg?{{ range(1000000)|random }}" alt="Camera Preview"
|
||||||
style="border: 1px solid #ccc;">
|
style="border: 1px solid #ccc;">
|
||||||
</figure>
|
</figure>
|
||||||
#}
|
<button class="button is-small is-info mt-2" type="button" onclick="refreshPreview()">Rafraîchir
|
||||||
|
l’aperçu
|
||||||
<video id="video" controls autoplay></video>
|
</button>
|
||||||
<script src="https://cdn.jsdelivr.net/npm/hls.js@latest"></script>
|
<button class="button is-small is-info mt-2" type="button" onclick="CapturePreview()">Acquistion camera
|
||||||
<script>
|
|
||||||
if (Hls.isSupported()) {
|
</button>
|
||||||
var video = document.getElementById('video');
|
|
||||||
var hls = new Hls({
|
|
||||||
startPosition: -1
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
hls.loadSource('/static/stream.m3u8');
|
|
||||||
hls.attachMedia(video);
|
|
||||||
} else if (video.canPlayType('application/vnd.apple.mpegurl')) {
|
|
||||||
video.src = '/static/stream.m3u8';
|
|
||||||
}
|
|
||||||
</script>
|
|
||||||
<nav class="level">
|
<nav class="level">
|
||||||
<div class="level-item has-text-centered">
|
<div class="level-item has-text-centered">
|
||||||
<div>
|
<div>
|
||||||
|
|
@ -59,8 +47,6 @@ if (Hls.isSupported()) {
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</nav>
|
</nav>
|
||||||
<button class="button is-small is-info mt-2" type="button" onclick="refreshPreview()">Rafraîchir
|
|
||||||
l’aperçu</button>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</form>
|
</form>
|
||||||
|
|
@ -81,10 +67,10 @@ if (Hls.isSupported()) {
|
||||||
|
|
||||||
window.refreshPreview = function () {
|
window.refreshPreview = function () {
|
||||||
const img = document.getElementById('camera-preview');
|
const img = document.getElementById('camera-preview');
|
||||||
const url = '/camera/feed.jpg?' + new Date().getTime();
|
const url = '/static/feed.jpg?' + new Date().getTime();
|
||||||
img.src = url;
|
img.src = url;
|
||||||
}
|
}
|
||||||
//setInterval(window.refreshPreview, 2000);
|
//setInterval(window.refreshPreview, 1000); // Refresh every second
|
||||||
|
|
||||||
document.addEventListener('DOMContentLoaded', function () {
|
document.addEventListener('DOMContentLoaded', function () {
|
||||||
fetch('/camera/config')
|
fetch('/camera/config')
|
||||||
|
|
@ -162,5 +148,16 @@ if (Hls.isSupported()) {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
function CapturePreview() {
|
||||||
|
fetch('/camera/capture_preview', {method: 'POST'})
|
||||||
|
.then(response => response.json())
|
||||||
|
.then(data => {
|
||||||
|
if (data.status === 'ok') {
|
||||||
|
refreshPreview(); // Rafraîchir l'image après la capture
|
||||||
|
} else {
|
||||||
|
alert('Erreur lors de la capture : ' + (data.error || 'inconnue'));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
{% endblock extrajs %}
|
{% endblock extrajs %}
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Strame ok mais stream imge fixe
|
||||||
|
#gphoto2 --stdout --capture-movie | ffmpeg -i - -c:v libx264 -f hls -hls_time 2 -hls_list_size 3 -hls_flags delete_segments src/nenuscanner/static/stream.m3u8
|
||||||
|
|
||||||
|
|
||||||
|
gphoto2 --capture-image-and-download -F 0 -I 2 --stdout | ffmpeg -f image2pipe -framerate 0.5 -i - -r 25 -c:v libx264 -f hls -hls_time 2 -hls_list_size 3 -hls_flags delete_segments -g 50 -keyint_min 50 src/nenuscanner/static/stream.m3u8
|
||||||
Loading…
Reference in New Issue