- Svelte 68.3%
- TypeScript 29.2%
- CSS 1.4%
- JavaScript 0.8%
- HTML 0.2%
Hayafin now runs on Meta Quest 3 (installable PWA + WebXR cinema mode via quad media layer, full-rate playback validated on device), login latency is fixed (requests serialized and /Items/Latest replaced with sorted /Items queries to work around a Jellyfin 10.11 server freeze), and the desktop Tauri build is verified against this tree (msi/nsis bundles, app launches). Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> |
||
|---|---|---|
| .claude | ||
| .github | ||
| .vscode | ||
| assets | ||
| changelogs | ||
| lessons | ||
| src | ||
| src-tauri | ||
| static | ||
| .gitignore | ||
| .npmrc | ||
| components.json | ||
| CONTRIBUTING.md | ||
| eslint.config.js | ||
| LECONS.md | ||
| LICENSE | ||
| package.json | ||
| pnpm-lock.yaml | ||
| postcss.config.js | ||
| README-android.md | ||
| README-tauri.md | ||
| README.md | ||
| SECURITY.md | ||
| SUPPORT.md | ||
| svelte.config.js | ||
| tailwind.config.ts | ||
| test-avatar.js | ||
| tsconfig.json | ||
| tsconfig.node.json | ||
| tsconfig.web.json | ||
| vite.config.ts | ||
Hayafin
Hayafin est une interface web moderne pour Jellyfin, pensée pour le salon : navigation au clavier, à la manette ou à la télécommande, lecture directe sans transcodage inutile, et un mode cinéma en réalité virtuelle. C'est un fork de l'interface Hayase adapté au backend Jellyfin.
L'application est une SPA statique : elle se déploie sur n'importe quel serveur web et parle directement à votre serveur Jellyfin.
Fonctionnalités
- Lecture optimale — profil d'appareil construit dynamiquement (
canPlayType) pour maximiser le direct play ; remux ou transcodage HLS uniquement quand nécessaire ; option de transcodage forcé HDR → SDR pour les écrans non-HDR. - Player persistant — l'élément vidéo survit aux navigations (mini-player / PiP), reprise de lecture, contrôle de vitesse, chapitres.
- Sous-titres avancés — rendu ASS/SSA fidèle via JASSUB (WASM), en plus des pistes texte classiques.
- Mode cinéma VR 🥽 — sur casque autonome (validé sur Meta Quest 3), projection du film sur un écran virtuel via l'API WebXR Layers : gâchette = lecture/pause, stick = avance/retour 15 s. Voir Notes VR.
- Navigation spatiale — utilisable intégralement au d-pad / à la manette (TV, casque VR, Steam Deck).
- PWA installable — manifest + service worker (workbox) : installation sur mobile, TV et Quest, cache hors-ligne de l'interface.
- Watch Together — synchronisation de lecture via Jellyfin SyncPlay, chat P2P.
- Multi-plateforme — web, desktop natif léger (Tauri 2, WebView système) et APK Android. Voir README-tauri.md et README-android.md.
Démarrage rapide
Prérequis : Node 20+ (validé sur Node 24) et pnpm (via corepack).
corepack pnpm i # installer les dépendances
corepack pnpm run dev # serveur de développement (Vite)
corepack pnpm run build # build de production → build/
Vérifications avant commit :
corepack pnpm run sync && corepack pnpm run lint && corepack pnpm run check
Applications natives (Tauri)
corepack pnpm run tauri:dev # fenêtre native sur le dev server
corepack pnpm run tauri:build # installeur desktop (msi/nsis, dmg, deb/appimage)
Prérequis, builds Android et limitations : README-tauri.md, README-android.md.
Déploiement
Le build produit une SPA statique dans build/ : servez ce dossier avec n'importe quel serveur web (nginx, Caddy, …) avec un fallback SPA vers index.html. Aucun runtime côté serveur n'est requis ; l'application communique directement avec le serveur Jellyfin configuré à la première ouverture.
Mode cinéma VR
Le mode cinéma (src/lib/modules/xr.ts) utilise le chemin média de l'API WebXR Layers (XRMediaBinding.createQuadLayer) : la vidéo est remise directement au compositeur du casque — résolution native, pas de copie WebGL, consommation minimale. Fonctionne en direct play comme en transcodage HLS.
Le module contourne plusieurs particularités du navigateur Meta Quest, documentées dans l'en-tête du fichier (cylinder layer rendue noire, pause automatique à l'entrée en session, throttling du pipeline vidéo une fois la page 2D masquée). Limitation connue : les sous-titres texte (overlays DOM/canvas) ne sont pas composités dans la layer VR — les sous-titres incrustés par transcodage s'affichent normalement.
Compatibilité serveur
Testé contre Jellyfin 10.11. Deux mesures de robustesse côté client méritent d'être connues :
- Les requêtes vers l'API Jellyfin sont sérialisées (une à la fois) : sur Jellyfin 10.11, certaines requêtes concurrentes peuvent geler le serveur pendant ~90 s.
- L'endpoint
/Items/Latestn'est pas utilisé (il participe au gel ci-dessus) ; les nouveautés sont récupérées via/Itemstrié parDateCreated/DateLastContentAdded.
Contribuer
Lisez CONTRIBUTING.md, ainsi que LECONS.md et lessons/ qui consignent les pièges connus du code. Politique de sécurité : SECURITY.md — support : SUPPORT.md.
Licence
Distribué sous Business Source License 1.1 — voir LICENSE.
Important
Les développeurs de cette application n'ont aucune affiliation avec de quelconques fournisseurs de contenu, et cette application n'héberge aucun contenu.