diff --git a/composeApp/libs/lib-nuvio-engine-android-0.1.0.aar b/composeApp/libs/lib-nuvio-engine-android-0.1.1.aar similarity index 65% rename from composeApp/libs/lib-nuvio-engine-android-0.1.0.aar rename to composeApp/libs/lib-nuvio-engine-android-0.1.1.aar index 16dbe39b8..abd3606ec 100644 Binary files a/composeApp/libs/lib-nuvio-engine-android-0.1.0.aar and b/composeApp/libs/lib-nuvio-engine-android-0.1.1.aar differ diff --git a/composeApp/src/androidHostTest/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngineAndroidTest.kt b/composeApp/src/androidHostTest/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngineAndroidTest.kt index 393e18eaa..e9ebaad7f 100644 --- a/composeApp/src/androidHostTest/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngineAndroidTest.kt +++ b/composeApp/src/androidHostTest/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngineAndroidTest.kt @@ -89,4 +89,53 @@ class P2pStreamingEngineAndroidTest { ), ) } + + @Test + fun globalCachePressureDoesNotBecomeTerminalError() { + assertNull( + unexpectedTorrentError( + requestId = 0L, + eventTorrentId = null, + currentTorrentId = "torrent", + message = "disk cache budget is exceeded by protected torrent data", + fallbackMessage = "unknown", + ) + ) + } + + @Test + fun matchingUnsolicitedTorrentFailureBecomesTerminalError() { + assertEquals( + P2pStreamingState.Error("file write failed"), + unexpectedTorrentError( + requestId = 0L, + eventTorrentId = "torrent", + currentTorrentId = "torrent", + message = "file write failed", + fallbackMessage = "unknown", + ), + ) + } + + @Test + fun commandAndStaleTorrentFailuresAreIgnored() { + assertNull( + unexpectedTorrentError( + requestId = 9L, + eventTorrentId = "torrent", + currentTorrentId = "torrent", + message = "failed", + fallbackMessage = "unknown", + ) + ) + assertNull( + unexpectedTorrentError( + requestId = 0L, + eventTorrentId = "old-torrent", + currentTorrentId = "torrent", + message = "failed", + fallbackMessage = "unknown", + ) + ) + } } diff --git a/composeApp/src/androidMain/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngine.android.kt b/composeApp/src/androidMain/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngine.android.kt index b7523e666..2bd8066e3 100644 --- a/composeApp/src/androidMain/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngine.android.kt +++ b/composeApp/src/androidMain/kotlin/com/nuvio/app/features/p2p/P2pStreamingEngine.android.kt @@ -73,6 +73,25 @@ internal fun unexpectedStreamStopError( ) } +internal fun unexpectedTorrentError( + requestId: Long, + eventTorrentId: String?, + currentTorrentId: String?, + message: String?, + fallbackMessage: String, +): P2pStreamingState.Error? { + if (requestId != 0L || + eventTorrentId == null || + currentTorrentId == null || + eventTorrentId != currentTorrentId + ) { + return null + } + return P2pStreamingState.Error( + message?.trim()?.takeIf(String::isNotEmpty) ?: fallbackMessage, + ) +} + actual object P2pStreamingEngine { private data class EngineConfigurationKey( val uploadEnabled: Boolean, @@ -517,16 +536,16 @@ actual object P2pStreamingEngine { if (engine !== activeEngine) return@collect when (event.type) { NuvioEventType.TorrentError -> { - if (event.requestId != 0L) return@collect - val terminalError = P2pStreamingState.Error( - event.message ?: localizedP2pUnknownTorrentError() - ) + val fallbackMessage = localizedP2pUnknownTorrentError() synchronized(lifecycleLock) { - if (engine !== activeEngine || - (event.torrentId != null && event.torrentId != currentTorrentId) - ) { - return@synchronized - } + if (engine !== activeEngine) return@synchronized + val terminalError = unexpectedTorrentError( + requestId = event.requestId, + eventTorrentId = event.torrentId, + currentTorrentId = currentTorrentId, + message = event.message, + fallbackMessage = fallbackMessage, + ) ?: return@synchronized streamGeneration += 1 statsJob?.cancel() statsJob = null diff --git a/composeApp/src/commonMain/composeResources/values-sk/strings.xml b/composeApp/src/commonMain/composeResources/values-sk/strings.xml index b707e5b53..82ab4bd6e 100644 --- a/composeApp/src/commonMain/composeResources/values-sk/strings.xml +++ b/composeApp/src/commonMain/composeResources/values-sk/strings.xml @@ -1556,12 +1556,12 @@ %1$s je teraz dostupný Vydania epizód Alkohol/Drogy - Desivé + Strašidelnosť Nahota Vulgárny jazyk - Mierny - Stredný - Závažný + Nízke + Mierne + Intenzívne Násilie Tvorca Režisér @@ -1927,4 +1927,134 @@ Kompatibilita libmpv YUV420P Vynútiť výstup YUV420P pre zariadenia s problémami renderera alebo farieb. Načítavajú sa segmenty preskočenia… + + + Jazyky + Zásady ochrany osobných údajov + Zistite, ako Nuvio spracováva vaše údaje + DIAGNOSTIKA + Hlásenia o pádoch (Sentry) + Odosielať hlásenia o pádoch a zamrznutiach (ANR) s bezpečným kontextom. Predvolene zapnuté. + Zapnúť hlásenia o pádoch? + Hlásenia o pádoch pomáhajú identifikovať chyby špecifické pre konkrétne zariadenia bez toho, aby ste museli chybové záznamy (ADB logy) vytvárať ručne. + Vypnúť hlásenia o pádoch? + Budúce pády a zamrznutia z tohto zariadenia nebudú nahlásené. To môže výrazne skomplikovať opravu chýb na tomto zariadení. + Ako to pomáha + Hlásenia sa zoskupujú podľa verzie aplikácie, modelu zariadenia, verzie systému Android a výpisu zásobníka (stack trace), aby sa najprv opravili najčastejšie reálne pády. + Odosiela sa + Pády, aktuálne ANR (zamrznutia), výpisy zásobníka, verzia aplikácie, typ zostavy, variant (flavor), metadáta zariadenia a OS plus bezpečné sieťové stopy (metóda, hostiteľ, cesta, stav, trvanie a typ výnimky). + Neodosiela sa + Heslá, prístupové tokeny, obnovovacie tokeny, telá požiadaviek a odpovedí, hlavičky, cookies, snímky obrazovky, štruktúra zobrazenia (view hierarchy), záznam relácie, neupravená diagnostika a hodnoty parametrov alebo fragmentov v URL adrese streamu. + Ponechať zapnuté + Vypnúť + Zapnúť + Otvoriť priečinok stiahnutých súborov + Nepodarilo sa otvoriť priečinok stiahnutých súborov + Navigačný panel + Štýl navigačného panela + Adaptívny + Vždy rozbalený + Vždy kompaktný + Klasický + Zobrazovať typ katalógu + Zobraziť príponu typu vedľa názvu katalógu (Film/Seriál). + EFEKT HĹBKY KARTY + Pridá osvetlený horný okraj a jemný lesk k obrazovým kartám pre jemný pocit hĺbky. + Povoliť efekt hĺbky + Žiara okraja + Jemná + Vyvážená + Tučná + Horný lesk + Vypnuté + Jemný + Jasný + Aplikovať na + Prispôsobiť + Detailné nastavenie hĺbky + Potiahnite bod doprava pre jasnejšiu hranu, nahor pre väčší lesk. Pomocou posuvníka rozšírite žiaru po celom obvode. + Žiara okraja → + ↑ Lesk + Žiara okraja + Lesk + Pokrytie okraja + Iba horná časť + Polovica + Celý obvod + Pokrytie okraja + Názov epizódy + S1 · E1 · 45 min + Plagáty + Kde ste skončili + Karty epizód + Obsadenie + Upútavky + Oddeliť riadok Nespustené + Presunúť neodvysielané epizódy do samostatného riadka Nespustené + Nespustené + Režim pozadia + Vyberte, ako sa má zobrazovať pozadie za stránkami s metadátami. + Normálny + Použiť štandardné pozadie aplikácie. + Kino + Zobraziť jemne rozostrené pozadie za stránkou. + Dominantná farba + Prispôsobiť pozadie stránky dominantnej farbe z obrázka na pozadí. + Upozornenia na obsah + Zobraziť rodičovské upozornenie pri spustení prehrávania. + Dátumy vydania + Používať dátumy vysielania z TMDB namiesto presných časov vydania z doplnkov + MyAnimeList + Test bannera dokončený + Zobraziť náhľad bannera a simulovaného priebehu sťahovania. + Otestovať banner aktualizácie + Neboli poskytnuté žiadne poznámky k vydaniu. + Vaša autorizácia v službe Trakt vypršala. Znova pripojte svoj účet Trakt. + ID zbierky „%1$s“ sa používa viac ako raz. + ID priečinka „%1$s“ sa v „%2$s“ používajú viac ako raz. + Všetky typy + Vybrať zoznam + Zoradiť knižnicu + Vybrať typ + Zobraziť horizontálne poličky + Zobraziť vertikálnu mriežku + Najstaršie pridané + Najnovšie pridané + Názov A–Z + Názov Z–A + Poradie Trakt + Hľadať v cloudovej knižnici + Profil pre torrenty + Šetrný + Vyvážený + Rýchly + Používa menej spojení (peerov) na zníženie záťaže batérie a siete + Odporúčaný pomer medzi rýchlosťou spustenia a stabilitou pripojenia + Používa viac spojení (peerov) pre náročné torrenty alebo torrenty s vysokým dátovým tokom + Veľkosť vyrovnávacej pamäte torrentov + Bez trvalej vyrovnávacej pamäte + 2 GB + 5 GB + 10 GB + Vymazať vyrovnávaciu pamäť torrentov + Aktuálne využité: %1$s + Využitie sa meria po spustení P2P; klepnutím vymažete vyrovnávaciu pamäť torrentov + Mažú sa neaktívne dáta torrentov… + Pred vymazaním vyrovnávacej pamäte zastavte prehrávanie P2P + Vymazaných %1$s neaktívnych dát torrentov + Nepodarilo sa vymazať vyrovnávaciu pamäť torrentov + Získavajú sa metadáta torrentu… + Pripravuje sa stream torrentu… + %1$s · %2$s · %3$s + Stiahnuté: %1$s · %2$s · %3$s + Dátum narodenia + Miesto narodenia + Tvorba / Účinkovanie + Biografia + Krajina + Typ + Katalóg + O programe + Načítavajú sa titulky z doplnkov... + Sťahujú sa titulky... diff --git a/composeApp/src/commonMain/kotlin/com/nuvio/app/features/search/SearchScreen.kt b/composeApp/src/commonMain/kotlin/com/nuvio/app/features/search/SearchScreen.kt index 3e30922fe..15348f7c5 100644 --- a/composeApp/src/commonMain/kotlin/com/nuvio/app/features/search/SearchScreen.kt +++ b/composeApp/src/commonMain/kotlin/com/nuvio/app/features/search/SearchScreen.kt @@ -17,7 +17,6 @@ import androidx.compose.foundation.lazy.items import androidx.compose.foundation.lazy.rememberLazyListState import androidx.compose.material.icons.Icons import androidx.compose.material.icons.rounded.Close -import androidx.compose.material.icons.rounded.History import androidx.compose.material3.Icon import androidx.compose.material3.IconButton import androidx.compose.material3.MaterialTheme @@ -478,21 +477,6 @@ private fun SearchRecentRow( horizontalArrangement = Arrangement.spacedBy(8.dp), verticalAlignment = Alignment.CenterVertically, ) { - Box( - modifier = Modifier - .background( - color = MaterialTheme.colorScheme.surface, - shape = RoundedCornerShape(999.dp), - ) - .padding(8.dp), - contentAlignment = Alignment.Center, - ) { - Icon( - imageVector = Icons.Rounded.History, - contentDescription = null, - tint = MaterialTheme.colorScheme.onSurfaceVariant, - ) - } Text( text = query, modifier = Modifier.weight(1f),