Backend FastAPI complet : camera gphoto2, filtres/overlays Pillow, chroma key OpenCV, multi-shot/collage, GIF, impression CUPS, email SMTP, QR code. Frontend web vanilla (HTML/CSS/JS) pour Chromium kiosk. Menu admin cache (appui long coin ecran). Toutes les fonctionnalites activables/desactivables. Scripts install + systemd pour RPi4. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
42 lines
1.0 KiB
Python
42 lines
1.0 KiB
Python
import logging
|
|
from pathlib import Path
|
|
|
|
from PIL import Image
|
|
|
|
from backend.config import DOSSIER_EXPORTS, charger_config
|
|
|
|
log = logging.getLogger("photobooth.gif")
|
|
|
|
|
|
def creer_gif(photos: list[Path], duree_frame_ms: int | None = None) -> Path:
|
|
"""Cree un GIF anime a partir d'une liste de photos."""
|
|
config = charger_config()
|
|
if duree_frame_ms is None:
|
|
duree_frame_ms = config.get("gif", {}).get("duree_frame_ms", 300)
|
|
|
|
images = []
|
|
for p in photos:
|
|
img = Image.open(p).convert("RGB")
|
|
# Redimensionner pour un GIF leger
|
|
img.thumbnail((800, 600), Image.LANCZOS)
|
|
images.append(img)
|
|
|
|
if not images:
|
|
log.error("Aucune image pour le GIF")
|
|
return None
|
|
|
|
nom = f"gif_{photos[0].stem}.gif"
|
|
chemin = DOSSIER_EXPORTS / nom
|
|
|
|
images[0].save(
|
|
chemin,
|
|
save_all=True,
|
|
append_images=images[1:],
|
|
duration=duree_frame_ms,
|
|
loop=0,
|
|
optimize=True,
|
|
)
|
|
|
|
log.info(f"GIF cree : {chemin} ({len(images)} frames, {duree_frame_ms}ms)")
|
|
return chemin
|