From 3ae2488adf0f164be1ccbd3a2c514ffb1ecb8511 Mon Sep 17 00:00:00 2001 From: edde746 <86283021+edde746@users.noreply.github.com> Date: Sun, 22 Mar 2026 11:47:59 +0100 Subject: [PATCH] feat: screen lock close #286 --- lib/i18n/da.i18n.json | 4 + lib/i18n/de.i18n.json | 4 + lib/i18n/en.i18n.json | 4 + lib/i18n/es.i18n.json | 4 + lib/i18n/fr.i18n.json | 4 + lib/i18n/it.i18n.json | 4 + lib/i18n/ja.i18n.json | 4 + lib/i18n/ko.i18n.json | 4 + lib/i18n/nb.i18n.json | 4 + lib/i18n/nl.i18n.json | 4 + lib/i18n/pl.i18n.json | 4 + lib/i18n/pt.i18n.json | 4 + lib/i18n/ru.i18n.json | 4 + lib/i18n/strings.g.dart | 4 +- lib/i18n/strings_da.g.dart | 12 ++- lib/i18n/strings_de.g.dart | 12 ++- lib/i18n/strings_en.g.dart | 20 ++++- lib/i18n/strings_es.g.dart | 12 ++- lib/i18n/strings_fr.g.dart | 12 ++- lib/i18n/strings_it.g.dart | 12 ++- lib/i18n/strings_ja.g.dart | 12 ++- lib/i18n/strings_ko.g.dart | 12 ++- lib/i18n/strings_nb.g.dart | 12 ++- lib/i18n/strings_nl.g.dart | 12 ++- lib/i18n/strings_pl.g.dart | 12 ++- lib/i18n/strings_pt.g.dart | 12 ++- lib/i18n/strings_ru.g.dart | 12 ++- lib/i18n/strings_sv.g.dart | 12 ++- lib/i18n/strings_zh.g.dart | 12 ++- lib/i18n/sv.i18n.json | 4 + lib/i18n/zh.i18n.json | 4 + .../models/track_controls_state.dart | 4 + .../video_controls/video_controls.dart | 74 +++++++++++++++++++ .../widgets/track_chapter_controls.dart | 20 +++++ 34 files changed, 318 insertions(+), 32 deletions(-) diff --git a/lib/i18n/da.i18n.json b/lib/i18n/da.i18n.json index 4ee2b1a3..6e0e2b97 100644 --- a/lib/i18n/da.i18n.json +++ b/lib/i18n/da.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Forlad fuldskærm", "alwaysOnTopButton": "Altid øverst", "rotationLockButton": "Rotationslås", + "lockScreen": "Lås skærm", + "unlockScreen": "Lås skærm op", + "screenLockButton": "Skærmlås", + "longPressToUnlock": "Langt tryk for at låse op", "timelineSlider": "Videotidslinje", "volumeSlider": "Lydstyrkeniveau", "endsAt": "Slutter kl. ${time}", diff --git a/lib/i18n/de.i18n.json b/lib/i18n/de.i18n.json index a13d4f22..fa8ef702 100644 --- a/lib/i18n/de.i18n.json +++ b/lib/i18n/de.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Vollbild verlassen", "alwaysOnTopButton": "Immer im Vordergrund", "rotationLockButton": "Dreh­sperre", + "lockScreen": "Bildschirm sperren", + "unlockScreen": "Bildschirm entsperren", + "screenLockButton": "Bildschirmsperre", + "longPressToUnlock": "Lange drücken zum Entsperren", "timelineSlider": "Video-Zeitleiste", "volumeSlider": "Lautstärkepegel", "endsAt": "Endet um ${time}", diff --git a/lib/i18n/en.i18n.json b/lib/i18n/en.i18n.json index 29d4b46d..f489e7fb 100644 --- a/lib/i18n/en.i18n.json +++ b/lib/i18n/en.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Exit fullscreen", "alwaysOnTopButton": "Always on top", "rotationLockButton": "Rotation lock", + "lockScreen": "Lock screen", + "unlockScreen": "Unlock screen", + "screenLockButton": "Screen lock", + "longPressToUnlock": "Long press to unlock", "timelineSlider": "Video timeline", "volumeSlider": "Volume level", "endsAt": "Ends at ${time}", diff --git a/lib/i18n/es.i18n.json b/lib/i18n/es.i18n.json index aa582e2b..90e205a4 100644 --- a/lib/i18n/es.i18n.json +++ b/lib/i18n/es.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Salir de pantalla completa", "alwaysOnTopButton": "Siempre visible", "rotationLockButton": "Bloqueo de rotación", + "lockScreen": "Bloquear pantalla", + "unlockScreen": "Desbloquear pantalla", + "screenLockButton": "Bloqueo de pantalla", + "longPressToUnlock": "Mantén pulsado para desbloquear", "timelineSlider": "Línea de tiempo del video", "volumeSlider": "Nivel de volumen", "endsAt": "Termina a las ${time}", diff --git a/lib/i18n/fr.i18n.json b/lib/i18n/fr.i18n.json index 21248182..2bb7381a 100644 --- a/lib/i18n/fr.i18n.json +++ b/lib/i18n/fr.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Quitter le mode plein écran", "alwaysOnTopButton": "Toujours au premier plan", "rotationLockButton": "Verrouillage de rotation", + "lockScreen": "Verrouiller l'écran", + "unlockScreen": "Déverrouiller l'écran", + "screenLockButton": "Verrouillage de l'écran", + "longPressToUnlock": "Appui long pour déverrouiller", "timelineSlider": "Timeline vidéo", "volumeSlider": "Niveau sonore", "endsAt": "Fin à ${time}", diff --git a/lib/i18n/it.i18n.json b/lib/i18n/it.i18n.json index 1096b61d..d5475b64 100644 --- a/lib/i18n/it.i18n.json +++ b/lib/i18n/it.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Esci da schermo intero", "alwaysOnTopButton": "Sempre in primo piano", "rotationLockButton": "Blocco rotazione", + "lockScreen": "Blocca schermo", + "unlockScreen": "Sblocca schermo", + "screenLockButton": "Blocco schermo", + "longPressToUnlock": "Premi a lungo per sbloccare", "timelineSlider": "Timeline video", "volumeSlider": "Livello volume", "endsAt": "Finisce alle ${time}", diff --git a/lib/i18n/ja.i18n.json b/lib/i18n/ja.i18n.json index 4844f19a..06b20b31 100644 --- a/lib/i18n/ja.i18n.json +++ b/lib/i18n/ja.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "フルスクリーンを終了", "alwaysOnTopButton": "常に前面に表示", "rotationLockButton": "回転ロック", + "lockScreen": "画面をロック", + "unlockScreen": "画面のロックを解除", + "screenLockButton": "画面ロック", + "longPressToUnlock": "長押しでロック解除", "timelineSlider": "動画タイムライン", "volumeSlider": "音量レベル", "endsAt": "${time}に終了", diff --git a/lib/i18n/ko.i18n.json b/lib/i18n/ko.i18n.json index 48b47931..e794bb2f 100644 --- a/lib/i18n/ko.i18n.json +++ b/lib/i18n/ko.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "전체화면 종료", "alwaysOnTopButton": "창 최상위 고정", "rotationLockButton": "회전 잠금", + "lockScreen": "화면 잠금", + "unlockScreen": "화면 잠금 해제", + "screenLockButton": "화면 잠금", + "longPressToUnlock": "길게 눌러 잠금 해제", "timelineSlider": "타임라인", "volumeSlider": "볼륨 조절", "endsAt": "${time}에 종료", diff --git a/lib/i18n/nb.i18n.json b/lib/i18n/nb.i18n.json index 9315c9ac..67571722 100644 --- a/lib/i18n/nb.i18n.json +++ b/lib/i18n/nb.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Avslutt fullskjerm", "alwaysOnTopButton": "Alltid øverst", "rotationLockButton": "Rotasjonslås", + "lockScreen": "Lås skjerm", + "unlockScreen": "Lås opp skjerm", + "screenLockButton": "Skjermlås", + "longPressToUnlock": "Langt trykk for å låse opp", "timelineSlider": "Videotidslinje", "volumeSlider": "Volumnivå", "endsAt": "Slutter kl. ${time}", diff --git a/lib/i18n/nl.i18n.json b/lib/i18n/nl.i18n.json index cec40d5b..d8607562 100644 --- a/lib/i18n/nl.i18n.json +++ b/lib/i18n/nl.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Volledig scherm verlaten", "alwaysOnTopButton": "Altijd bovenop", "rotationLockButton": "Rotatievergrendeling", + "lockScreen": "Vergrendel scherm", + "unlockScreen": "Ontgrendel scherm", + "screenLockButton": "Schermvergrendeling", + "longPressToUnlock": "Lang indrukken om te ontgrendelen", "timelineSlider": "Videotijdlijn", "volumeSlider": "Volumeniveau", "endsAt": "Eindigt om ${time}", diff --git a/lib/i18n/pl.i18n.json b/lib/i18n/pl.i18n.json index a3f07e48..7c2c1952 100644 --- a/lib/i18n/pl.i18n.json +++ b/lib/i18n/pl.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Wyjdź z pełnego ekranu", "alwaysOnTopButton": "Zawsze na wierzchu", "rotationLockButton": "Blokada obrotu", + "lockScreen": "Zablokuj ekran", + "unlockScreen": "Odblokuj ekran", + "screenLockButton": "Blokada ekranu", + "longPressToUnlock": "Przytrzymaj, aby odblokować", "timelineSlider": "Oś czasu wideo", "volumeSlider": "Poziom głośności", "endsAt": "Kończy się o ${time}", diff --git a/lib/i18n/pt.i18n.json b/lib/i18n/pt.i18n.json index c829f6bc..425d3029 100644 --- a/lib/i18n/pt.i18n.json +++ b/lib/i18n/pt.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Sair da tela cheia", "alwaysOnTopButton": "Sempre no topo", "rotationLockButton": "Travar rotação", + "lockScreen": "Travar tela", + "unlockScreen": "Destravar tela", + "screenLockButton": "Travar tela", + "longPressToUnlock": "Pressione e segure para destravar", "timelineSlider": "Linha do tempo do vídeo", "volumeSlider": "Nível de volume", "endsAt": "Termina às ${time}", diff --git a/lib/i18n/ru.i18n.json b/lib/i18n/ru.i18n.json index a1a3212f..e6d373d7 100644 --- a/lib/i18n/ru.i18n.json +++ b/lib/i18n/ru.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Выйти из полноэкранного режима", "alwaysOnTopButton": "Всегда поверх", "rotationLockButton": "Блокировка поворота", + "lockScreen": "Заблокировать экран", + "unlockScreen": "Разблокировать экран", + "screenLockButton": "Блокировка экрана", + "longPressToUnlock": "Удерживайте для разблокировки", "timelineSlider": "Временная шкала", "volumeSlider": "Уровень громкости", "endsAt": "Закончится в ${time}", diff --git a/lib/i18n/strings.g.dart b/lib/i18n/strings.g.dart index 439bf8d1..947574f1 100644 --- a/lib/i18n/strings.g.dart +++ b/lib/i18n/strings.g.dart @@ -4,9 +4,9 @@ /// To regenerate, run: `dart run slang` /// /// Locales: 15 -/// Strings: 11910 (794 per locale) +/// Strings: 11970 (798 per locale) /// -/// Built on 2026-03-22 at 08:19 UTC +/// Built on 2026-03-22 at 10:44 UTC // coverage:ignore-file // ignore_for_file: type=lint, unused_import diff --git a/lib/i18n/strings_da.g.dart b/lib/i18n/strings_da.g.dart index 2c743146..d9263f92 100644 --- a/lib/i18n/strings_da.g.dart +++ b/lib/i18n/strings_da.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsDa implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Forlad fuldskærm'; @override String get alwaysOnTopButton => 'Altid øverst'; @override String get rotationLockButton => 'Rotationslås'; + @override String get lockScreen => 'Lås skærm'; + @override String get unlockScreen => 'Lås skærm op'; + @override String get screenLockButton => 'Skærmlås'; + @override String get longPressToUnlock => 'Langt tryk for at låse op'; @override String get timelineSlider => 'Videotidslinje'; @override String get volumeSlider => 'Lydstyrkeniveau'; @override String endsAt({required Object time}) => 'Slutter kl. ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsDa { 'videoControls.exitFullscreenButton' => 'Forlad fuldskærm', 'videoControls.alwaysOnTopButton' => 'Altid øverst', 'videoControls.rotationLockButton' => 'Rotationslås', + 'videoControls.lockScreen' => 'Lås skærm', + 'videoControls.unlockScreen' => 'Lås skærm op', + 'videoControls.screenLockButton' => 'Skærmlås', + 'videoControls.longPressToUnlock' => 'Langt tryk for at låse op', 'videoControls.timelineSlider' => 'Videotidslinje', 'videoControls.volumeSlider' => 'Lydstyrkeniveau', 'videoControls.endsAt' => ({required Object time}) => 'Slutter kl. ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsDa { 'liveTv.lateNight' => 'Sen aften', 'liveTv.whatsOn' => 'Hvad der kører', 'liveTv.watchChannel' => 'Se kanal', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoritter', 'collections.title' => 'Samlinger', 'collections.collection' => 'Samling', 'collections.empty' => 'Samlingen er tom', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Kan ikke slette: Ukendt bibliotekssektion', 'collections.deleteCollection' => 'Slet samling', 'collections.deleteConfirm' => ({required Object title}) => 'Er du sikker på, at du vil slette "${title}"? Denne handling kan ikke fortrydes.', diff --git a/lib/i18n/strings_de.g.dart b/lib/i18n/strings_de.g.dart index 5d783612..d879fef7 100644 --- a/lib/i18n/strings_de.g.dart +++ b/lib/i18n/strings_de.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsDe implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Vollbild verlassen'; @override String get alwaysOnTopButton => 'Immer im Vordergrund'; @override String get rotationLockButton => 'Dreh­sperre'; + @override String get lockScreen => 'Bildschirm sperren'; + @override String get unlockScreen => 'Bildschirm entsperren'; + @override String get screenLockButton => 'Bildschirmsperre'; + @override String get longPressToUnlock => 'Lange drücken zum Entsperren'; @override String get timelineSlider => 'Video-Zeitleiste'; @override String get volumeSlider => 'Lautstärkepegel'; @override String endsAt({required Object time}) => 'Endet um ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsDe { 'videoControls.exitFullscreenButton' => 'Vollbild verlassen', 'videoControls.alwaysOnTopButton' => 'Immer im Vordergrund', 'videoControls.rotationLockButton' => 'Dreh­sperre', + 'videoControls.lockScreen' => 'Bildschirm sperren', + 'videoControls.unlockScreen' => 'Bildschirm entsperren', + 'videoControls.screenLockButton' => 'Bildschirmsperre', + 'videoControls.longPressToUnlock' => 'Lange drücken zum Entsperren', 'videoControls.timelineSlider' => 'Video-Zeitleiste', 'videoControls.volumeSlider' => 'Lautstärkepegel', 'videoControls.endsAt' => ({required Object time}) => 'Endet um ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsDe { 'liveTv.lateNight' => 'Spätnacht', 'liveTv.whatsOn' => 'Jetzt im TV', 'liveTv.watchChannel' => 'Kanal ansehen', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoriten', 'downloads.title' => 'Downloads', 'downloads.manage' => 'Verwalten', 'downloads.tvShows' => 'Serien', - _ => null, - } ?? switch (path) { 'downloads.movies' => 'Filme', 'downloads.noDownloads' => 'Noch keine Downloads', 'downloads.noDownloadsDescription' => 'Heruntergeladene Inhalte werden hier für die Offline-Wiedergabe angezeigt', diff --git a/lib/i18n/strings_en.g.dart b/lib/i18n/strings_en.g.dart index 5aa40377..53664828 100644 --- a/lib/i18n/strings_en.g.dart +++ b/lib/i18n/strings_en.g.dart @@ -1100,6 +1100,18 @@ class TranslationsVideoControlsEn { /// en: 'Rotation lock' String get rotationLockButton => 'Rotation lock'; + /// en: 'Lock screen' + String get lockScreen => 'Lock screen'; + + /// en: 'Unlock screen' + String get unlockScreen => 'Unlock screen'; + + /// en: 'Screen lock' + String get screenLockButton => 'Screen lock'; + + /// en: 'Long press to unlock' + String get longPressToUnlock => 'Long press to unlock'; + /// en: 'Video timeline' String get timelineSlider => 'Video timeline'; @@ -3196,6 +3208,10 @@ extension on Translations { 'videoControls.exitFullscreenButton' => 'Exit fullscreen', 'videoControls.alwaysOnTopButton' => 'Always on top', 'videoControls.rotationLockButton' => 'Rotation lock', + 'videoControls.lockScreen' => 'Lock screen', + 'videoControls.unlockScreen' => 'Unlock screen', + 'videoControls.screenLockButton' => 'Screen lock', + 'videoControls.longPressToUnlock' => 'Long press to unlock', 'videoControls.timelineSlider' => 'Video timeline', 'videoControls.volumeSlider' => 'Volume level', 'videoControls.endsAt' => ({required Object time}) => 'Ends at ${time}', @@ -3384,12 +3400,12 @@ extension on Translations { 'liveTv.lateNight' => 'Late Night', 'liveTv.whatsOn' => 'What\'s On', 'liveTv.watchChannel' => 'Watch Channel', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favorites', 'collections.title' => 'Collections', 'collections.collection' => 'Collection', 'collections.empty' => 'Collection is empty', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Cannot delete: Unknown library section', 'collections.deleteCollection' => 'Delete Collection', 'collections.deleteConfirm' => ({required Object title}) => 'Are you sure you want to delete "${title}"? This action cannot be undone.', diff --git a/lib/i18n/strings_es.g.dart b/lib/i18n/strings_es.g.dart index ff8ef949..61af57f6 100644 --- a/lib/i18n/strings_es.g.dart +++ b/lib/i18n/strings_es.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsEs implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Salir de pantalla completa'; @override String get alwaysOnTopButton => 'Siempre visible'; @override String get rotationLockButton => 'Bloqueo de rotación'; + @override String get lockScreen => 'Bloquear pantalla'; + @override String get unlockScreen => 'Desbloquear pantalla'; + @override String get screenLockButton => 'Bloqueo de pantalla'; + @override String get longPressToUnlock => 'Mantén pulsado para desbloquear'; @override String get timelineSlider => 'Línea de tiempo del video'; @override String get volumeSlider => 'Nivel de volumen'; @override String endsAt({required Object time}) => 'Termina a las ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsEs { 'videoControls.exitFullscreenButton' => 'Salir de pantalla completa', 'videoControls.alwaysOnTopButton' => 'Siempre visible', 'videoControls.rotationLockButton' => 'Bloqueo de rotación', + 'videoControls.lockScreen' => 'Bloquear pantalla', + 'videoControls.unlockScreen' => 'Desbloquear pantalla', + 'videoControls.screenLockButton' => 'Bloqueo de pantalla', + 'videoControls.longPressToUnlock' => 'Mantén pulsado para desbloquear', 'videoControls.timelineSlider' => 'Línea de tiempo del video', 'videoControls.volumeSlider' => 'Nivel de volumen', 'videoControls.endsAt' => ({required Object time}) => 'Termina a las ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsEs { 'liveTv.lateNight' => 'Trasnoche', 'liveTv.whatsOn' => 'En emisión', 'liveTv.watchChannel' => 'Ver canal', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoritos', 'collections.title' => 'Colecciones', 'collections.collection' => 'Colección', 'collections.empty' => 'La colección está vacía', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'No se puede eliminar: Sección de biblioteca desconocida', 'collections.deleteCollection' => 'Eliminar Colección', 'collections.deleteConfirm' => ({required Object title}) => '¿Estás seguro de que quieres eliminar "${title}"? Esta acción no se puede deshacer.', diff --git a/lib/i18n/strings_fr.g.dart b/lib/i18n/strings_fr.g.dart index a5c65639..cff9533a 100644 --- a/lib/i18n/strings_fr.g.dart +++ b/lib/i18n/strings_fr.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsFr implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Quitter le mode plein écran'; @override String get alwaysOnTopButton => 'Toujours au premier plan'; @override String get rotationLockButton => 'Verrouillage de rotation'; + @override String get lockScreen => 'Verrouiller l\'écran'; + @override String get unlockScreen => 'Déverrouiller l\'écran'; + @override String get screenLockButton => 'Verrouillage de l\'écran'; + @override String get longPressToUnlock => 'Appui long pour déverrouiller'; @override String get timelineSlider => 'Timeline vidéo'; @override String get volumeSlider => 'Niveau sonore'; @override String endsAt({required Object time}) => 'Fin à ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsFr { 'videoControls.exitFullscreenButton' => 'Quitter le mode plein écran', 'videoControls.alwaysOnTopButton' => 'Toujours au premier plan', 'videoControls.rotationLockButton' => 'Verrouillage de rotation', + 'videoControls.lockScreen' => 'Verrouiller l\'écran', + 'videoControls.unlockScreen' => 'Déverrouiller l\'écran', + 'videoControls.screenLockButton' => 'Verrouillage de l\'écran', + 'videoControls.longPressToUnlock' => 'Appui long pour déverrouiller', 'videoControls.timelineSlider' => 'Timeline vidéo', 'videoControls.volumeSlider' => 'Niveau sonore', 'videoControls.endsAt' => ({required Object time}) => 'Fin à ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsFr { 'liveTv.lateNight' => 'Nuit tardive', 'liveTv.whatsOn' => 'En ce moment', 'liveTv.watchChannel' => 'Regarder la chaîne', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoris', 'collections.title' => 'Collections', 'collections.collection' => 'Collection', 'collections.empty' => 'La collection est vide', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Impossible de supprimer : section de bibliothèque inconnue', 'collections.deleteCollection' => 'Supprimer la collection', 'collections.deleteConfirm' => ({required Object title}) => 'Êtes-vous sûr de vouloir supprimer "${title}" ? Cette action ne peut pas être annulée.', diff --git a/lib/i18n/strings_it.g.dart b/lib/i18n/strings_it.g.dart index c2065d85..5837d733 100644 --- a/lib/i18n/strings_it.g.dart +++ b/lib/i18n/strings_it.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsIt implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Esci da schermo intero'; @override String get alwaysOnTopButton => 'Sempre in primo piano'; @override String get rotationLockButton => 'Blocco rotazione'; + @override String get lockScreen => 'Blocca schermo'; + @override String get unlockScreen => 'Sblocca schermo'; + @override String get screenLockButton => 'Blocco schermo'; + @override String get longPressToUnlock => 'Premi a lungo per sbloccare'; @override String get timelineSlider => 'Timeline video'; @override String get volumeSlider => 'Livello volume'; @override String endsAt({required Object time}) => 'Finisce alle ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsIt { 'videoControls.exitFullscreenButton' => 'Esci da schermo intero', 'videoControls.alwaysOnTopButton' => 'Sempre in primo piano', 'videoControls.rotationLockButton' => 'Blocco rotazione', + 'videoControls.lockScreen' => 'Blocca schermo', + 'videoControls.unlockScreen' => 'Sblocca schermo', + 'videoControls.screenLockButton' => 'Blocco schermo', + 'videoControls.longPressToUnlock' => 'Premi a lungo per sbloccare', 'videoControls.timelineSlider' => 'Timeline video', 'videoControls.volumeSlider' => 'Livello volume', 'videoControls.endsAt' => ({required Object time}) => 'Finisce alle ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsIt { 'liveTv.lateNight' => 'Notte tarda', 'liveTv.whatsOn' => 'In onda ora', 'liveTv.watchChannel' => 'Guarda canale', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Preferiti', 'downloads.title' => 'Download', 'downloads.manage' => 'Gestisci', 'downloads.tvShows' => 'Serie TV', - _ => null, - } ?? switch (path) { 'downloads.movies' => 'Film', 'downloads.noDownloads' => 'Nessun download', 'downloads.noDownloadsDescription' => 'I contenuti scaricati appariranno qui per la visualizzazione offline', diff --git a/lib/i18n/strings_ja.g.dart b/lib/i18n/strings_ja.g.dart index 1607c6f0..6b5cbe6c 100644 --- a/lib/i18n/strings_ja.g.dart +++ b/lib/i18n/strings_ja.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsJa implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'フルスクリーンを終了'; @override String get alwaysOnTopButton => '常に前面に表示'; @override String get rotationLockButton => '回転ロック'; + @override String get lockScreen => '画面をロック'; + @override String get unlockScreen => '画面のロックを解除'; + @override String get screenLockButton => '画面ロック'; + @override String get longPressToUnlock => '長押しでロック解除'; @override String get timelineSlider => '動画タイムライン'; @override String get volumeSlider => '音量レベル'; @override String endsAt({required Object time}) => '${time}に終了'; @@ -1601,6 +1605,10 @@ extension on TranslationsJa { 'videoControls.exitFullscreenButton' => 'フルスクリーンを終了', 'videoControls.alwaysOnTopButton' => '常に前面に表示', 'videoControls.rotationLockButton' => '回転ロック', + 'videoControls.lockScreen' => '画面をロック', + 'videoControls.unlockScreen' => '画面のロックを解除', + 'videoControls.screenLockButton' => '画面ロック', + 'videoControls.longPressToUnlock' => '長押しでロック解除', 'videoControls.timelineSlider' => '動画タイムライン', 'videoControls.volumeSlider' => '音量レベル', 'videoControls.endsAt' => ({required Object time}) => '${time}に終了', @@ -1789,12 +1797,12 @@ extension on TranslationsJa { 'liveTv.lateNight' => '深夜', 'liveTv.whatsOn' => '放送中', 'liveTv.watchChannel' => 'チャンネルを視聴', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'お気に入り', 'collections.title' => 'コレクション', 'collections.collection' => 'コレクション', 'collections.empty' => 'コレクションは空です', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => '削除できません:不明なライブラリセクション', 'collections.deleteCollection' => 'コレクションを削除', 'collections.deleteConfirm' => ({required Object title}) => '"${title}"を削除してもよろしいですか?この操作は元に戻せません。', diff --git a/lib/i18n/strings_ko.g.dart b/lib/i18n/strings_ko.g.dart index 6e8c4aa2..5fcc8286 100644 --- a/lib/i18n/strings_ko.g.dart +++ b/lib/i18n/strings_ko.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsKo implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => '전체화면 종료'; @override String get alwaysOnTopButton => '창 최상위 고정'; @override String get rotationLockButton => '회전 잠금'; + @override String get lockScreen => '화면 잠금'; + @override String get unlockScreen => '화면 잠금 해제'; + @override String get screenLockButton => '화면 잠금'; + @override String get longPressToUnlock => '길게 눌러 잠금 해제'; @override String get timelineSlider => '타임라인'; @override String get volumeSlider => '볼륨 조절'; @override String endsAt({required Object time}) => '${time}에 종료'; @@ -1601,6 +1605,10 @@ extension on TranslationsKo { 'videoControls.exitFullscreenButton' => '전체화면 종료', 'videoControls.alwaysOnTopButton' => '창 최상위 고정', 'videoControls.rotationLockButton' => '회전 잠금', + 'videoControls.lockScreen' => '화면 잠금', + 'videoControls.unlockScreen' => '화면 잠금 해제', + 'videoControls.screenLockButton' => '화면 잠금', + 'videoControls.longPressToUnlock' => '길게 눌러 잠금 해제', 'videoControls.timelineSlider' => '타임라인', 'videoControls.volumeSlider' => '볼륨 조절', 'videoControls.endsAt' => ({required Object time}) => '${time}에 종료', @@ -1789,12 +1797,12 @@ extension on TranslationsKo { 'liveTv.lateNight' => '심야 방송', 'liveTv.whatsOn' => '지금 방송 중', 'liveTv.watchChannel' => '채널 시청', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => '즐겨찾기', 'collections.title' => '컬렉션', 'collections.collection' => '컬렉션', 'collections.empty' => '컬렉션이 비어 있습니다', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => '삭제할 수 없습니다: 알 수 없는 미디어 라이브러리 섹션입니다', 'collections.deleteCollection' => '컬렉션 삭제', 'collections.deleteConfirm' => ({required Object title}) => '"${title}"을(를) 삭제 하시겠습니까? 이 작업은 되돌릴 수 없습니다.', diff --git a/lib/i18n/strings_nb.g.dart b/lib/i18n/strings_nb.g.dart index ba4e5a7a..cb265005 100644 --- a/lib/i18n/strings_nb.g.dart +++ b/lib/i18n/strings_nb.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsNb implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Avslutt fullskjerm'; @override String get alwaysOnTopButton => 'Alltid øverst'; @override String get rotationLockButton => 'Rotasjonslås'; + @override String get lockScreen => 'Lås skjerm'; + @override String get unlockScreen => 'Lås opp skjerm'; + @override String get screenLockButton => 'Skjermlås'; + @override String get longPressToUnlock => 'Langt trykk for å låse opp'; @override String get timelineSlider => 'Videotidslinje'; @override String get volumeSlider => 'Volumnivå'; @override String endsAt({required Object time}) => 'Slutter kl. ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsNb { 'videoControls.exitFullscreenButton' => 'Avslutt fullskjerm', 'videoControls.alwaysOnTopButton' => 'Alltid øverst', 'videoControls.rotationLockButton' => 'Rotasjonslås', + 'videoControls.lockScreen' => 'Lås skjerm', + 'videoControls.unlockScreen' => 'Lås opp skjerm', + 'videoControls.screenLockButton' => 'Skjermlås', + 'videoControls.longPressToUnlock' => 'Langt trykk for å låse opp', 'videoControls.timelineSlider' => 'Videotidslinje', 'videoControls.volumeSlider' => 'Volumnivå', 'videoControls.endsAt' => ({required Object time}) => 'Slutter kl. ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsNb { 'liveTv.lateNight' => 'Sen kveld', 'liveTv.whatsOn' => 'Hva går nå', 'liveTv.watchChannel' => 'Se kanal', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoritter', 'collections.title' => 'Samlinger', 'collections.collection' => 'Samling', 'collections.empty' => 'Samlingen er tom', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Kan ikke slette: Ukjent bibliotekseksjon', 'collections.deleteCollection' => 'Slett samling', 'collections.deleteConfirm' => ({required Object title}) => 'Er du sikker på at du vil slette "${title}"? Denne handlingen kan ikke angres.', diff --git a/lib/i18n/strings_nl.g.dart b/lib/i18n/strings_nl.g.dart index 1ba076e4..70202177 100644 --- a/lib/i18n/strings_nl.g.dart +++ b/lib/i18n/strings_nl.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsNl implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Volledig scherm verlaten'; @override String get alwaysOnTopButton => 'Altijd bovenop'; @override String get rotationLockButton => 'Rotatievergrendeling'; + @override String get lockScreen => 'Vergrendel scherm'; + @override String get unlockScreen => 'Ontgrendel scherm'; + @override String get screenLockButton => 'Schermvergrendeling'; + @override String get longPressToUnlock => 'Lang indrukken om te ontgrendelen'; @override String get timelineSlider => 'Videotijdlijn'; @override String get volumeSlider => 'Volumeniveau'; @override String endsAt({required Object time}) => 'Eindigt om ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsNl { 'videoControls.exitFullscreenButton' => 'Volledig scherm verlaten', 'videoControls.alwaysOnTopButton' => 'Altijd bovenop', 'videoControls.rotationLockButton' => 'Rotatievergrendeling', + 'videoControls.lockScreen' => 'Vergrendel scherm', + 'videoControls.unlockScreen' => 'Ontgrendel scherm', + 'videoControls.screenLockButton' => 'Schermvergrendeling', + 'videoControls.longPressToUnlock' => 'Lang indrukken om te ontgrendelen', 'videoControls.timelineSlider' => 'Videotijdlijn', 'videoControls.volumeSlider' => 'Volumeniveau', 'videoControls.endsAt' => ({required Object time}) => 'Eindigt om ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsNl { 'liveTv.lateNight' => 'Late avond', 'liveTv.whatsOn' => 'Nu op TV', 'liveTv.watchChannel' => 'Kanaal bekijken', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favorieten', 'downloads.title' => 'Downloads', 'downloads.manage' => 'Beheren', 'downloads.tvShows' => 'Series', - _ => null, - } ?? switch (path) { 'downloads.movies' => 'Films', 'downloads.noDownloads' => 'Nog geen downloads', 'downloads.noDownloadsDescription' => 'Gedownloade content verschijnt hier voor offline weergave', diff --git a/lib/i18n/strings_pl.g.dart b/lib/i18n/strings_pl.g.dart index bb9dff67..05d2a137 100644 --- a/lib/i18n/strings_pl.g.dart +++ b/lib/i18n/strings_pl.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsPl implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Wyjdź z pełnego ekranu'; @override String get alwaysOnTopButton => 'Zawsze na wierzchu'; @override String get rotationLockButton => 'Blokada obrotu'; + @override String get lockScreen => 'Zablokuj ekran'; + @override String get unlockScreen => 'Odblokuj ekran'; + @override String get screenLockButton => 'Blokada ekranu'; + @override String get longPressToUnlock => 'Przytrzymaj, aby odblokować'; @override String get timelineSlider => 'Oś czasu wideo'; @override String get volumeSlider => 'Poziom głośności'; @override String endsAt({required Object time}) => 'Kończy się o ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsPl { 'videoControls.exitFullscreenButton' => 'Wyjdź z pełnego ekranu', 'videoControls.alwaysOnTopButton' => 'Zawsze na wierzchu', 'videoControls.rotationLockButton' => 'Blokada obrotu', + 'videoControls.lockScreen' => 'Zablokuj ekran', + 'videoControls.unlockScreen' => 'Odblokuj ekran', + 'videoControls.screenLockButton' => 'Blokada ekranu', + 'videoControls.longPressToUnlock' => 'Przytrzymaj, aby odblokować', 'videoControls.timelineSlider' => 'Oś czasu wideo', 'videoControls.volumeSlider' => 'Poziom głośności', 'videoControls.endsAt' => ({required Object time}) => 'Kończy się o ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsPl { 'liveTv.lateNight' => 'Późna noc', 'liveTv.whatsOn' => 'Co leci', 'liveTv.watchChannel' => 'Oglądaj kanał', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Ulubione', 'collections.title' => 'Kolekcje', 'collections.collection' => 'Kolekcja', 'collections.empty' => 'Kolekcja jest pusta', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Nie można usunąć: Nieznana sekcja biblioteki', 'collections.deleteCollection' => 'Usuń kolekcję', 'collections.deleteConfirm' => ({required Object title}) => 'Czy na pewno chcesz usunąć "${title}"? Tej operacji nie można cofnąć.', diff --git a/lib/i18n/strings_pt.g.dart b/lib/i18n/strings_pt.g.dart index 0c82084b..92197766 100644 --- a/lib/i18n/strings_pt.g.dart +++ b/lib/i18n/strings_pt.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsPt implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Sair da tela cheia'; @override String get alwaysOnTopButton => 'Sempre no topo'; @override String get rotationLockButton => 'Travar rotação'; + @override String get lockScreen => 'Travar tela'; + @override String get unlockScreen => 'Destravar tela'; + @override String get screenLockButton => 'Travar tela'; + @override String get longPressToUnlock => 'Pressione e segure para destravar'; @override String get timelineSlider => 'Linha do tempo do vídeo'; @override String get volumeSlider => 'Nível de volume'; @override String endsAt({required Object time}) => 'Termina às ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsPt { 'videoControls.exitFullscreenButton' => 'Sair da tela cheia', 'videoControls.alwaysOnTopButton' => 'Sempre no topo', 'videoControls.rotationLockButton' => 'Travar rotação', + 'videoControls.lockScreen' => 'Travar tela', + 'videoControls.unlockScreen' => 'Destravar tela', + 'videoControls.screenLockButton' => 'Travar tela', + 'videoControls.longPressToUnlock' => 'Pressione e segure para destravar', 'videoControls.timelineSlider' => 'Linha do tempo do vídeo', 'videoControls.volumeSlider' => 'Nível de volume', 'videoControls.endsAt' => ({required Object time}) => 'Termina às ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsPt { 'liveTv.lateNight' => 'Madrugada', 'liveTv.whatsOn' => 'O que Está Passando', 'liveTv.watchChannel' => 'Assistir Canal', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoritos', 'collections.title' => 'Coleções', 'collections.collection' => 'Coleção', 'collections.empty' => 'A coleção está vazia', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Não é possível excluir: Seção de biblioteca desconhecida', 'collections.deleteCollection' => 'Excluir Coleção', 'collections.deleteConfirm' => ({required Object title}) => 'Tem certeza que deseja excluir "${title}"? Esta ação não pode ser desfeita.', diff --git a/lib/i18n/strings_ru.g.dart b/lib/i18n/strings_ru.g.dart index 4d9f6749..1a2c72bd 100644 --- a/lib/i18n/strings_ru.g.dart +++ b/lib/i18n/strings_ru.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsRu implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Выйти из полноэкранного режима'; @override String get alwaysOnTopButton => 'Всегда поверх'; @override String get rotationLockButton => 'Блокировка поворота'; + @override String get lockScreen => 'Заблокировать экран'; + @override String get unlockScreen => 'Разблокировать экран'; + @override String get screenLockButton => 'Блокировка экрана'; + @override String get longPressToUnlock => 'Удерживайте для разблокировки'; @override String get timelineSlider => 'Временная шкала'; @override String get volumeSlider => 'Уровень громкости'; @override String endsAt({required Object time}) => 'Закончится в ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsRu { 'videoControls.exitFullscreenButton' => 'Выйти из полноэкранного режима', 'videoControls.alwaysOnTopButton' => 'Всегда поверх', 'videoControls.rotationLockButton' => 'Блокировка поворота', + 'videoControls.lockScreen' => 'Заблокировать экран', + 'videoControls.unlockScreen' => 'Разблокировать экран', + 'videoControls.screenLockButton' => 'Блокировка экрана', + 'videoControls.longPressToUnlock' => 'Удерживайте для разблокировки', 'videoControls.timelineSlider' => 'Временная шкала', 'videoControls.volumeSlider' => 'Уровень громкости', 'videoControls.endsAt' => ({required Object time}) => 'Закончится в ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsRu { 'liveTv.lateNight' => 'Поздний вечер', 'liveTv.whatsOn' => 'Что идёт', 'liveTv.watchChannel' => 'Смотреть канал', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Избранное', 'collections.title' => 'Коллекции', 'collections.collection' => 'Коллекция', 'collections.empty' => 'Коллекция пуста', - _ => null, - } ?? switch (path) { 'collections.unknownLibrarySection' => 'Невозможно удалить: неизвестный раздел библиотеки', 'collections.deleteCollection' => 'Удалить коллекцию', 'collections.deleteConfirm' => ({required Object title}) => 'Вы уверены, что хотите удалить "${title}"? Это действие нельзя отменить.', diff --git a/lib/i18n/strings_sv.g.dart b/lib/i18n/strings_sv.g.dart index f1d90b9b..5e9888fa 100644 --- a/lib/i18n/strings_sv.g.dart +++ b/lib/i18n/strings_sv.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsSv implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => 'Avsluta helskärm'; @override String get alwaysOnTopButton => 'Alltid överst'; @override String get rotationLockButton => 'Rotationslås'; + @override String get lockScreen => 'Lås skärm'; + @override String get unlockScreen => 'Lås upp skärm'; + @override String get screenLockButton => 'Skärmlås'; + @override String get longPressToUnlock => 'Tryck länge för att låsa upp'; @override String get timelineSlider => 'Videotidslinje'; @override String get volumeSlider => 'Volymnivå'; @override String endsAt({required Object time}) => 'Slutar ${time}'; @@ -1601,6 +1605,10 @@ extension on TranslationsSv { 'videoControls.exitFullscreenButton' => 'Avsluta helskärm', 'videoControls.alwaysOnTopButton' => 'Alltid överst', 'videoControls.rotationLockButton' => 'Rotationslås', + 'videoControls.lockScreen' => 'Lås skärm', + 'videoControls.unlockScreen' => 'Lås upp skärm', + 'videoControls.screenLockButton' => 'Skärmlås', + 'videoControls.longPressToUnlock' => 'Tryck länge för att låsa upp', 'videoControls.timelineSlider' => 'Videotidslinje', 'videoControls.volumeSlider' => 'Volymnivå', 'videoControls.endsAt' => ({required Object time}) => 'Slutar ${time}', @@ -1789,12 +1797,12 @@ extension on TranslationsSv { 'liveTv.lateNight' => 'Sen kväll', 'liveTv.whatsOn' => 'På TV nu', 'liveTv.watchChannel' => 'Titta på kanal', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => 'Favoriter', 'downloads.title' => 'Nedladdningar', 'downloads.manage' => 'Hantera', 'downloads.tvShows' => 'TV-serier', - _ => null, - } ?? switch (path) { 'downloads.movies' => 'Filmer', 'downloads.noDownloads' => 'Inga nedladdningar ännu', 'downloads.noDownloadsDescription' => 'Nedladdat innehåll visas här för offline-visning', diff --git a/lib/i18n/strings_zh.g.dart b/lib/i18n/strings_zh.g.dart index 9f4eb661..809eef08 100644 --- a/lib/i18n/strings_zh.g.dart +++ b/lib/i18n/strings_zh.g.dart @@ -493,6 +493,10 @@ class _TranslationsVideoControlsZh implements TranslationsVideoControlsEn { @override String get exitFullscreenButton => '退出全屏'; @override String get alwaysOnTopButton => '置顶窗口'; @override String get rotationLockButton => '旋转锁定'; + @override String get lockScreen => '锁定屏幕'; + @override String get unlockScreen => '解锁屏幕'; + @override String get screenLockButton => '屏幕锁定'; + @override String get longPressToUnlock => '长按解锁'; @override String get timelineSlider => '视频时间轴'; @override String get volumeSlider => '音量调节'; @override String endsAt({required Object time}) => '${time} 结束'; @@ -1601,6 +1605,10 @@ extension on TranslationsZh { 'videoControls.exitFullscreenButton' => '退出全屏', 'videoControls.alwaysOnTopButton' => '置顶窗口', 'videoControls.rotationLockButton' => '旋转锁定', + 'videoControls.lockScreen' => '锁定屏幕', + 'videoControls.unlockScreen' => '解锁屏幕', + 'videoControls.screenLockButton' => '屏幕锁定', + 'videoControls.longPressToUnlock' => '长按解锁', 'videoControls.timelineSlider' => '视频时间轴', 'videoControls.volumeSlider' => '音量调节', 'videoControls.endsAt' => ({required Object time}) => '${time} 结束', @@ -1789,12 +1797,12 @@ extension on TranslationsZh { 'liveTv.lateNight' => '深夜', 'liveTv.whatsOn' => '正在播出', 'liveTv.watchChannel' => '观看频道', + _ => null, + } ?? switch (path) { 'liveTv.favorites' => '收藏', 'downloads.title' => '下载', 'downloads.manage' => '管理', 'downloads.tvShows' => '电视剧', - _ => null, - } ?? switch (path) { 'downloads.movies' => '电影', 'downloads.noDownloads' => '暂无下载', 'downloads.noDownloadsDescription' => '下载的内容将在此处显示以供离线观看', diff --git a/lib/i18n/sv.i18n.json b/lib/i18n/sv.i18n.json index 95186a47..3354ee52 100644 --- a/lib/i18n/sv.i18n.json +++ b/lib/i18n/sv.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "Avsluta helskärm", "alwaysOnTopButton": "Alltid överst", "rotationLockButton": "Rotationslås", + "lockScreen": "Lås skärm", + "unlockScreen": "Lås upp skärm", + "screenLockButton": "Skärmlås", + "longPressToUnlock": "Tryck länge för att låsa upp", "timelineSlider": "Videotidslinje", "volumeSlider": "Volymnivå", "endsAt": "Slutar ${time}", diff --git a/lib/i18n/zh.i18n.json b/lib/i18n/zh.i18n.json index 03510f90..1c74972e 100644 --- a/lib/i18n/zh.i18n.json +++ b/lib/i18n/zh.i18n.json @@ -346,6 +346,10 @@ "exitFullscreenButton": "退出全屏", "alwaysOnTopButton": "置顶窗口", "rotationLockButton": "旋转锁定", + "lockScreen": "锁定屏幕", + "unlockScreen": "解锁屏幕", + "screenLockButton": "屏幕锁定", + "longPressToUnlock": "长按解锁", "timelineSlider": "视频时间轴", "volumeSlider": "音量调节", "endsAt": "${time} 结束", diff --git a/lib/widgets/video_controls/models/track_controls_state.dart b/lib/widgets/video_controls/models/track_controls_state.dart index 44557201..236b25dd 100644 --- a/lib/widgets/video_controls/models/track_controls_state.dart +++ b/lib/widgets/video_controls/models/track_controls_state.dart @@ -13,11 +13,13 @@ class TrackControlsState { final int audioSyncOffset; final int subtitleSyncOffset; final bool isRotationLocked; + final bool isScreenLocked; final bool isFullscreen; final bool isAlwaysOnTop; final VoidCallback? onTogglePIPMode; final VoidCallback? onCycleBoxFitMode; final VoidCallback? onToggleRotationLock; + final VoidCallback? onToggleScreenLock; final VoidCallback? onToggleFullscreen; final VoidCallback? onToggleAlwaysOnTop; final Function(int)? onSwitchVersion; @@ -46,11 +48,13 @@ class TrackControlsState { this.audioSyncOffset = 0, this.subtitleSyncOffset = 0, this.isRotationLocked = false, + this.isScreenLocked = false, this.isFullscreen = false, this.isAlwaysOnTop = false, this.onTogglePIPMode, this.onCycleBoxFitMode, this.onToggleRotationLock, + this.onToggleScreenLock, this.onToggleFullscreen, this.onToggleAlwaysOnTop, this.onSwitchVersion, diff --git a/lib/widgets/video_controls/video_controls.dart b/lib/widgets/video_controls/video_controls.dart index 356cd29a..528849fc 100644 --- a/lib/widgets/video_controls/video_controls.dart +++ b/lib/widgets/video_controls/video_controls.dart @@ -225,6 +225,9 @@ class _PlexVideoControlsState extends State with WindowListen int _audioSyncOffset = 0; // Default, loaded from settings int _subtitleSyncOffset = 0; // Default, loaded from settings bool _isRotationLocked = true; // Default locked (landscape only) + bool _isScreenLocked = false; // Touch lock during playback + bool _showLockIcon = false; // Whether to show the lock overlay icon + Timer? _lockIconTimer; bool _clickVideoTogglesPlayback = false; // Default, loaded from settings bool _isContentStripVisible = false; // Whether the swipe-up content strip is showing @@ -663,6 +666,7 @@ class _PlexVideoControlsState extends State with WindowListen widget.hasFirstFrame?.removeListener(_onFirstFrameReady); _hideTimer?.cancel(); _feedbackTimer?.cancel(); + _lockIconTimer?.cancel(); _autoSkipTimer?.cancel(); _skipButtonDismissTimer?.cancel(); _singleTapTimer?.cancel(); @@ -900,6 +904,38 @@ class _PlexVideoControlsState extends State with WindowListen } } + void _toggleScreenLock() { + final locking = !_isScreenLocked; + setState(() { + _isScreenLocked = locking; + if (locking) { + _showLockIcon = true; + } + }); + if (locking) { + _hideControls(); + _startLockIconHideTimer(); + } + } + + void _startLockIconHideTimer() { + _lockIconTimer?.cancel(); + _lockIconTimer = Timer(const Duration(seconds: 3), () { + if (mounted) setState(() => _showLockIcon = false); + }); + } + + void _unlockScreen() { + setState(() { + _isScreenLocked = false; + _showLockIcon = false; + _showControls = true; + }); + _lockIconTimer?.cancel(); + widget.controlsVisible?.value = true; + _startHideTimer(); + } + void _updateTrafficLightVisibility() async { // When maximized or fullscreen, always keep traffic lights visible so the // user can reach them without the controls-hide-on-mouse-leave race. @@ -1050,6 +1086,7 @@ class _PlexVideoControlsState extends State with WindowListen audioSyncOffset: _audioSyncOffset, subtitleSyncOffset: _subtitleSyncOffset, isRotationLocked: _isRotationLocked, + isScreenLocked: _isScreenLocked, isFullscreen: _isFullscreen, isAlwaysOnTop: _isAlwaysOnTop, onTogglePIPMode: (_isPipSupported && !PlatformDetector.isTV()) @@ -1057,6 +1094,7 @@ class _PlexVideoControlsState extends State with WindowListen : null, onCycleBoxFitMode: widget.player.playerType != 'exoplayer' ? widget.onCycleBoxFitMode : null, onToggleRotationLock: _toggleRotationLock, + onToggleScreenLock: _toggleScreenLock, onToggleFullscreen: _toggleFullscreen, onToggleAlwaysOnTop: onToggleAlwaysOnTop, onSwitchVersion: _switchMediaVersion, @@ -2110,6 +2148,42 @@ class _PlexVideoControlsState extends State with WindowListen left: 16, child: IgnorePointer(child: PlayerPerformanceOverlay(player: widget.player)), ), + // Screen lock overlay - absorbs all touches when active + if (_isScreenLocked) + Positioned.fill( + child: GestureDetector( + behavior: HitTestBehavior.opaque, + onTap: () { + setState(() => _showLockIcon = true); + _startLockIconHideTimer(); + }, + onLongPress: _unlockScreen, + child: AnimatedOpacity( + opacity: _showLockIcon ? 1.0 : 0.0, + duration: const Duration(milliseconds: 200), + child: Center( + child: Container( + padding: const EdgeInsets.symmetric(horizontal: 20, vertical: 14), + decoration: BoxDecoration( + color: Colors.black.withValues(alpha: 0.6), + borderRadius: const BorderRadius.all(Radius.circular(28)), + ), + child: Row( + mainAxisSize: MainAxisSize.min, + children: [ + const AppIcon(Symbols.lock_rounded, fill: 1, color: Colors.white, size: 20), + const SizedBox(width: 8), + Text( + t.videoControls.longPressToUnlock, + style: const TextStyle(color: Colors.white, fontSize: 14, fontWeight: FontWeight.w500), + ), + ], + ), + ), + ), + ), + ), + ), ], ), ), diff --git a/lib/widgets/video_controls/widgets/track_chapter_controls.dart b/lib/widgets/video_controls/widgets/track_chapter_controls.dart index cb27a71b..192d873f 100644 --- a/lib/widgets/video_controls/widgets/track_chapter_controls.dart +++ b/lib/widgets/video_controls/widgets/track_chapter_controls.dart @@ -70,11 +70,13 @@ class TrackChapterControls extends StatelessWidget { int get audioSyncOffset => trackControlsState.audioSyncOffset; int get subtitleSyncOffset => trackControlsState.subtitleSyncOffset; bool get isRotationLocked => trackControlsState.isRotationLocked; + bool get isScreenLocked => trackControlsState.isScreenLocked; bool get isFullscreen => trackControlsState.isFullscreen; bool get isAlwaysOnTop => trackControlsState.isAlwaysOnTop; VoidCallback? get onTogglePIPMode => trackControlsState.onTogglePIPMode; VoidCallback? get onCycleBoxFitMode => trackControlsState.onCycleBoxFitMode; VoidCallback? get onToggleRotationLock => trackControlsState.onToggleRotationLock; + VoidCallback? get onToggleScreenLock => trackControlsState.onToggleScreenLock; VoidCallback? get onToggleFullscreen => trackControlsState.onToggleFullscreen; VoidCallback? get onToggleAlwaysOnTop => trackControlsState.onToggleAlwaysOnTop; Function(int)? get onSwitchVersion => trackControlsState.onSwitchVersion; @@ -404,6 +406,24 @@ class TrackChapterControls extends StatelessWidget { buttonIndex++; } + // Screen lock button (mobile only, not on TV) + if (isMobile && !PlatformDetector.isTV()) { + final currentIndex = buttonIndex; + buttons.add( + _buildTrackButton( + buttonIndex: currentIndex, + icon: Symbols.lock_rounded, + tooltip: t.videoControls.lockScreen, + semanticLabel: t.videoControls.screenLockButton, + tracks: tracks, + isMobile: isMobile, + isDesktop: isDesktop, + onPressed: onToggleScreenLock, + ), + ); + buttonIndex++; + } + // Always on top button (desktop only, not TV) if (isDesktop && onToggleAlwaysOnTop != null) { final currentIndex = buttonIndex;