Compare commits

..

24 Commits

Author SHA1 Message Date
f3e1fb7664
update gitignore 2025-05-30 17:15:05 +01:00
Jobobby04
cc934607c8 SpotlessApply 2025-05-24 21:07:29 -04:00
Weblate (bot)
5074e68b9c
Translations update from Hosted Weblate (#1442)
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy-plurals/ar/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy-plurals/my/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy-plurals/vi/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/ar/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/de/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/es/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/fil/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/fr/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/id/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/it/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/ja/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/ne/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/pt_BR/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/ru/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/tr/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/uk/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/zh_Hans/
Translate-URL: https://hosted.weblate.org/projects/mihon/tachiyomisy/zh_Hant/
Translation: Mihon/TachiyomiSY
Translation: Mihon/TachiyomiSY Plurals

Co-authored-by: Alex Maryson Jr <akamar87@gmail.com>
Co-authored-by: B4LiN7 <87660017+B4LiN7@users.noreply.github.com>
Co-authored-by: Dexroneum <Rozhenkov69@gmail.com>
Co-authored-by: FateXBlood <fatexblood@gmail.com>
Co-authored-by: Frosted <frosted@users.noreply.hosted.weblate.org>
Co-authored-by: Hualiang <642615676@qq.com>
Co-authored-by: Infy's Tagalog Translations <ced.paltep10@gmail.com>
Co-authored-by: Kosťantin Horovij <lg096066587039@gmail.com>
Co-authored-by: Lapis (Bas77) <sebastianramli77@gmail.com>
Co-authored-by: LordTenebrous <danielmorenoperez836@gmail.com>
Co-authored-by: Mohamed kh <mohamedkhamekhami@gmail.com>
Co-authored-by: Sky children of the Light <tu25261@gmail.com>
Co-authored-by: Swyter <swyterzone@gmail.com>
Co-authored-by: ZerOriSama <godarms2010@live.com>
Co-authored-by: akir45 <akkn0708@gmail.com>
Co-authored-by: edgole <test.backache009@aleeas.com>
Co-authored-by: fl0k1 <michele.carnova@gmail.com>
Co-authored-by: naikhon <naikhon5@gmail.com>
Co-authored-by: qaugji <asteeky9@gmail.com>
Co-authored-by: ɴᴇᴋᴏ <s99095lkjjim@gmail.com>
Co-authored-by: Георгій Обушенков <heorhii.obushenkov@gmail.com>
Co-authored-by: ابومسلم <linuxmint1978@gmail.com>
2025-05-24 20:47:35 -04:00
多能豆
ade41f113d
Fix E-Hentai Jump/Seek match for detailed date (#1450) 2025-05-24 20:44:55 -04:00
Jobobby04
95dc82594f More guards against edited data 2025-05-24 20:44:27 -04:00
NGB-Was-Taken
80e585fa91
Change log file extension to .txt (#1449) 2025-05-24 20:19:17 -04:00
Jobobby04
9f110f9db8 Bump version so migation actually runs 2025-05-24 20:18:14 -04:00
NGB-Was-Taken
71470b9e02
Remove the unused mark duplicate as read preference. (#1448)
* Remove the unused mark duplicate as read preference.

* Migrate the old preference to new preference
2025-05-24 20:16:44 -04:00
renovate[bot]
4fd24accac
Update dependency net.zetetic:sqlcipher-android to v4.9.0 (#1447)
Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
2025-05-24 20:15:17 -04:00
NGB-Was-Taken
31312fecac
Fixes screen staying on in library tab. (#1451) 2025-05-24 20:13:43 -04:00
Mend Renovate
b80d057922 Update dependency androidx.compose:compose-bom to v2025.05.01 (#2133)
(cherry picked from commit 92b376d9af93da988b695c36c4775d5e6947c048)
2025-05-24 20:12:57 -04:00
Mend Renovate
f01d8bc835 Update dependency gradle to v8.14.1 (#2138)
(cherry picked from commit 1a2f09a622017dc5b201eadc6acc667487cf3d4d)
2025-05-24 20:12:48 -04:00
Jobobby04
ddffe71a22 SpotlessApply 2025-05-24 20:12:38 -04:00
AntsyLich
649a19ec57 Fix content cut off in home screen
Closes #2141

(cherry picked from commit 209e982fe4f1da5d1d49cfbfdd178625ee3c70f4)

# Conflicts:
#	app/src/main/java/eu/kanade/tachiyomi/ui/home/HomeScreen.kt
2025-05-24 20:10:18 -04:00
Mend Renovate
e82fd99a09 Update plugin org.gradle.toolchains.foojay-resolver-convention to v1 (#2130)
(cherry picked from commit 0109102901f942502807e2a7a9f1a58f951c763f)
2025-05-24 20:09:57 -04:00
Mend Renovate
67a9b8e2a0 Update dependency com.pinterest.ktlint:ktlint-cli to v1.6.0 (#2129)
(cherry picked from commit 4117a5167470ae36b4172721b4e4d40373f2a3c6)
2025-05-24 20:09:51 -04:00
Mend Renovate
2000f947c3 Update xml.serialization.version to v0.91.1 (#2112)
(cherry picked from commit 4090a61d08964a8e82f943ac4eb81a52c110005f)
2025-05-24 20:09:45 -04:00
Jobobby04
f992ada0a8 SpotlessApply 2025-05-16 21:16:09 -04:00
Jobobby04
f876cdb037 Use MediaServer in Json for NHentai
Co-authored-by: 4521 <18432684+az4521@users.noreply.github.com>
2025-05-16 20:34:03 -04:00
Jobobby04
f919d42370 Hello Discord 2025-05-16 12:02:37 -04:00
Mend Renovate
ab5ff00c39 Update kotlin monorepo to v2.1.21 (#2102)
(cherry picked from commit 625c85cbd68086d605553b2d5ab9cc9cc9460688)
2025-05-15 13:50:17 -04:00
Mend Renovate
422738af56 Update dependency org.jetbrains.kotlinx:kotlinx-collections-immutable to v0.4.0 (#2104)
(cherry picked from commit 737ceeea576074cffcd2e96933aceffdbcc0a03a)
2025-05-15 13:50:08 -04:00
Mend Renovate
81751fc9ce Update dependency io.coil-kt.coil3:coil-bom to v3.2.0 (#2101)
(cherry picked from commit 7933c9eeb7b28ecc2ae31fa337654a80f2371b85)
2025-05-15 13:49:58 -04:00
Jobobby04
9b6c5effc9 Minor refactors 2025-05-15 13:38:03 -04:00
82 changed files with 599 additions and 499 deletions

3
.gitignore vendored
View File

@ -19,3 +19,6 @@ local.properties
google-services.json
/app/src/main/assets/client_secrets.json
*.apk
# Custom ignores
/keys

View File

@ -31,7 +31,7 @@ android {
defaultConfig {
applicationId = "eu.kanade.tachiyomi.sy"
versionCode = 74
versionCode = 75
versionName = "1.12.0"
buildConfigField("String", "COMMIT_COUNT", "\"${getCommitCount()}\"")

View File

@ -28,7 +28,6 @@ import tachiyomi.data.source.SavedSearchRepositoryImpl
import tachiyomi.domain.chapter.interactor.DeleteChapters
import tachiyomi.domain.chapter.interactor.GetChapterByUrl
import tachiyomi.domain.chapter.interactor.GetMergedChaptersByMangaId
import tachiyomi.domain.history.interactor.GetHistoryByMangaId
import tachiyomi.domain.manga.interactor.DeleteByMergeId
import tachiyomi.domain.manga.interactor.DeleteFavoriteEntries
import tachiyomi.domain.manga.interactor.DeleteMangaById
@ -88,7 +87,6 @@ class SYDomainModule : InjektModule {
addFactory { DeleteChapters(get()) }
addFactory { DeleteMangaById(get()) }
addFactory { FilterSerializer() }
addFactory { GetHistoryByMangaId(get()) }
addFactory { GetChapterByUrl(get()) }
addFactory { GetSourceCategories(get()) }
addFactory { CreateSourceCategory(get()) }

View File

@ -23,7 +23,7 @@ class GetPagePreviews(
return try {
val pagePreviews = try {
pagePreviewCache.getPageListFromCache(manga, chapterIds, page)
} catch (e: Exception) {
} catch (_: Exception) {
source.getPagePreviewList(manga.toSManga(), chapters.map { it.toSChapter() }, page).also {
pagePreviewCache.putPageListToCache(manga, chapterIds, it)
}

View File

@ -38,12 +38,14 @@ fun Manga.chaptersFiltered(): Boolean {
fun Manga.toSManga(): SManga = SManga.create().also {
it.url = url
it.title = title
it.artist = artist
it.author = author
it.description = description
it.genre = genre.orEmpty().joinToString()
it.status = status.toInt()
// SY -->
it.title = ogTitle
it.artist = ogArtist
it.author = ogAuthor
it.description = ogDescription
it.genre = ogGenre.orEmpty().joinToString()
it.status = ogStatus.toInt()
// SY <--
it.thumbnail_url = thumbnailUrl
it.initialized = initialized
}

View File

@ -88,5 +88,32 @@ class SourcePreferences(
BANDWIDTH_HERO,
WSRV_NL,
}
fun migrateFlags() = preferenceStore.getInt("migrate_flags", Int.MAX_VALUE)
fun defaultMangaOrder() = preferenceStore.getString("default_manga_order", "")
fun migrationSources() = preferenceStore.getString("migrate_sources", "")
fun smartMigration() = preferenceStore.getBoolean("smart_migrate", false)
fun useSourceWithMost() = preferenceStore.getBoolean("use_source_with_most", false)
fun skipPreMigration() = preferenceStore.getBoolean(Preference.appStateKey("skip_pre_migration"), false)
fun hideNotFoundMigration() = preferenceStore.getBoolean("hide_not_found_migration", false)
fun showOnlyUpdatesMigration() = preferenceStore.getBoolean("show_only_updates_migration", false)
fun allowLocalSourceHiddenFolders() = preferenceStore.getBoolean("allow_local_source_hidden_folders", false)
fun preferredMangaDexId() = preferenceStore.getString("preferred_mangaDex_id", "0")
fun mangadexSyncToLibraryIndexes() = preferenceStore.getStringSet(
"pref_mangadex_sync_to_library_indexes",
emptySet(),
)
fun recommendationSearchFlags() = preferenceStore.getInt("rec_search_flags", Int.MAX_VALUE)
// SY <--
}

View File

@ -13,13 +13,13 @@ import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.window.DialogProperties
import eu.kanade.tachiyomi.util.system.toast
import exh.log.xLogE
import exh.source.ExhPreferences
import exh.uconfig.EHConfigurator
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.NonCancellable
import kotlinx.coroutines.delay
import kotlinx.coroutines.withContext
import tachiyomi.core.common.util.lang.launchUI
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.MR
import tachiyomi.i18n.sy.SYMR
import tachiyomi.presentation.core.i18n.stringResource
@ -29,8 +29,8 @@ import kotlin.time.Duration.Companion.seconds
@Composable
fun ConfigureExhDialog(run: Boolean, onRunning: () -> Unit) {
val unsortedPreferences = remember {
Injekt.get<UnsortedPreferences>()
val exhPreferences = remember {
Injekt.get<ExhPreferences>()
}
var warnDialogOpen by remember { mutableStateOf(false) }
var configureDialogOpen by remember { mutableStateOf(false) }
@ -38,7 +38,7 @@ fun ConfigureExhDialog(run: Boolean, onRunning: () -> Unit) {
LaunchedEffect(run) {
if (run) {
if (unsortedPreferences.exhShowSettingsUploadWarning().get()) {
if (exhPreferences.exhShowSettingsUploadWarning().get()) {
warnDialogOpen = true
} else {
configureDialogOpen = true
@ -57,7 +57,7 @@ fun ConfigureExhDialog(run: Boolean, onRunning: () -> Unit) {
confirmButton = {
TextButton(
onClick = {
unsortedPreferences.exhShowSettingsUploadWarning().set(false)
exhPreferences.exhShowSettingsUploadWarning().set(false)
configureDialogOpen = true
warnDialogOpen = false
},

View File

@ -72,6 +72,7 @@ import exh.pref.DelegateSourcePreferences
import exh.source.BlacklistedSources
import exh.source.EH_SOURCE_ID
import exh.source.EXH_SOURCE_ID
import exh.source.ExhPreferences
import exh.util.toAnnotatedString
import kotlinx.collections.immutable.persistentListOf
import kotlinx.collections.immutable.persistentMapOf
@ -86,7 +87,6 @@ import tachiyomi.core.common.util.lang.launchNonCancellable
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.core.common.util.system.ImageUtil
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.chapter.interactor.GetChaptersByMangaId
import tachiyomi.domain.library.service.LibraryPreferences
import tachiyomi.domain.manga.interactor.GetAllManga
@ -701,14 +701,14 @@ object SettingsAdvancedScreen : SearchableSettings {
val context = LocalContext.current
val navigator = LocalNavigator.currentOrThrow
val sourcePreferences = remember { Injekt.get<SourcePreferences>() }
val unsortedPreferences = remember { Injekt.get<UnsortedPreferences>() }
val exhPreferences = remember { Injekt.get<ExhPreferences>() }
val delegateSourcePreferences = remember { Injekt.get<DelegateSourcePreferences>() }
val securityPreferences = remember { Injekt.get<SecurityPreferences>() }
return Preference.PreferenceGroup(
title = stringResource(SYMR.strings.developer_tools),
preferenceItems = persistentListOf(
Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.isHentaiEnabled(),
preference = exhPreferences.isHentaiEnabled(),
title = stringResource(SYMR.strings.toggle_hentai_features),
subtitle = stringResource(SYMR.strings.toggle_hentai_features_summary),
onValueChanged = {
@ -733,7 +733,7 @@ object SettingsAdvancedScreen : SearchableSettings {
),
),
Preference.PreferenceItem.ListPreference(
preference = unsortedPreferences.logLevel(),
preference = exhPreferences.logLevel(),
title = stringResource(SYMR.strings.log_level),
subtitle = stringResource(SYMR.strings.log_level_summary),
entries = EHLogLevel.entries.mapIndexed { index, ehLogLevel ->

View File

@ -20,7 +20,6 @@ import eu.kanade.tachiyomi.util.system.AuthenticatorUtil.authenticate
import kotlinx.collections.immutable.persistentListOf
import mihon.domain.extensionrepo.interactor.GetExtensionRepoCount
import tachiyomi.core.common.i18n.stringResource
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.MR
import tachiyomi.i18n.sy.SYMR
import tachiyomi.presentation.core.i18n.pluralStringResource
@ -49,7 +48,6 @@ object SettingsBrowseScreen : SearchableSettings {
val scope = rememberCoroutineScope()
val hideFeedTab by remember { Injekt.get<UiPreferences>().hideFeedTab().asState(scope) }
val uiPreferences = remember { Injekt.get<UiPreferences>() }
val unsortedPreferences = remember { Injekt.get<UnsortedPreferences>() }
// SY <--
return listOf(
// SY -->
@ -77,7 +75,7 @@ object SettingsBrowseScreen : SearchableSettings {
subtitle = stringResource(SYMR.strings.pref_source_navigation_summery),
),
Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.allowLocalSourceHiddenFolders(),
preference = sourcePreferences.allowLocalSourceHiddenFolders(),
title = stringResource(SYMR.strings.pref_local_source_hidden_folders),
subtitle = stringResource(SYMR.strings.pref_local_source_hidden_folders_summery),
),
@ -131,6 +129,24 @@ object SettingsBrowseScreen : SearchableSettings {
Preference.PreferenceItem.InfoPreference(stringResource(MR.strings.parental_controls_info)),
),
),
getMigrationCategory(sourcePreferences),
)
}
@Composable
fun getMigrationCategory(sourcePreferences: SourcePreferences): Preference.PreferenceGroup {
val skipPreMigration by sourcePreferences.skipPreMigration().collectAsState()
val migrationSources by sourcePreferences.migrationSources().collectAsState()
return Preference.PreferenceGroup(
stringResource(SYMR.strings.migration),
enabled = skipPreMigration || migrationSources.isNotEmpty(),
preferenceItems = persistentListOf(
Preference.PreferenceItem.SwitchPreference(
preference = sourcePreferences.skipPreMigration(),
title = stringResource(SYMR.strings.skip_pre_migration),
subtitle = stringResource(SYMR.strings.pref_skip_pre_migration_summary),
),
),
)
}
}

View File

@ -51,6 +51,7 @@ import exh.eh.EHentaiUpdateWorker
import exh.eh.EHentaiUpdateWorkerConstants
import exh.eh.EHentaiUpdaterStats
import exh.metadata.metadata.EHentaiSearchMetadata
import exh.source.ExhPreferences
import exh.ui.login.EhLoginActivity
import exh.util.nullIfBlank
import kotlinx.collections.immutable.persistentListOf
@ -63,7 +64,6 @@ import tachiyomi.core.common.util.lang.launchNonCancellable
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.library.service.LibraryPreferences.Companion.DEVICE_CHARGING
import tachiyomi.domain.library.service.LibraryPreferences.Companion.DEVICE_ONLY_ON_WIFI
import tachiyomi.domain.manga.interactor.DeleteFavoriteEntries
@ -88,22 +88,22 @@ object SettingsEhScreen : SearchableSettings {
@Composable
override fun getTitleRes() = SYMR.strings.pref_category_eh
override fun isEnabled(): Boolean = Injekt.get<UnsortedPreferences>().isHentaiEnabled().get()
override fun isEnabled(): Boolean = Injekt.get<ExhPreferences>().isHentaiEnabled().get()
@Composable
fun Reconfigure(
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
openWarnConfigureDialogController: () -> Unit,
) {
var initialLoadGuard by remember { mutableStateOf(false) }
val useHentaiAtHome by unsortedPreferences.useHentaiAtHome().collectAsState()
val useJapaneseTitle by unsortedPreferences.useJapaneseTitle().collectAsState()
val useOriginalImages by unsortedPreferences.exhUseOriginalImages().collectAsState()
val ehTagFilterValue by unsortedPreferences.ehTagFilterValue().collectAsState()
val ehTagWatchingValue by unsortedPreferences.ehTagWatchingValue().collectAsState()
val settingsLanguages by unsortedPreferences.exhSettingsLanguages().collectAsState()
val enabledCategories by unsortedPreferences.exhEnabledCategories().collectAsState()
val imageQuality by unsortedPreferences.imageQuality().collectAsState()
val useHentaiAtHome by exhPreferences.useHentaiAtHome().collectAsState()
val useJapaneseTitle by exhPreferences.useJapaneseTitle().collectAsState()
val useOriginalImages by exhPreferences.exhUseOriginalImages().collectAsState()
val ehTagFilterValue by exhPreferences.ehTagFilterValue().collectAsState()
val ehTagWatchingValue by exhPreferences.ehTagWatchingValue().collectAsState()
val settingsLanguages by exhPreferences.exhSettingsLanguages().collectAsState()
val enabledCategories by exhPreferences.exhEnabledCategories().collectAsState()
val imageQuality by exhPreferences.imageQuality().collectAsState()
DisposableEffect(
useHentaiAtHome,
useJapaneseTitle,
@ -124,15 +124,15 @@ object SettingsEhScreen : SearchableSettings {
@Composable
override fun getPreferences(): List<Preference> {
val unsortedPreferences: UnsortedPreferences = remember { Injekt.get() }
val exhPreferences: ExhPreferences = remember { Injekt.get() }
val getFlatMetadataById: GetFlatMetadataById = remember { Injekt.get() }
val deleteFavoriteEntries: DeleteFavoriteEntries = remember { Injekt.get() }
val getExhFavoriteMangaWithMetadata: GetExhFavoriteMangaWithMetadata = remember { Injekt.get() }
val exhentaiEnabled by unsortedPreferences.enableExhentai().collectAsState()
val exhentaiEnabled by exhPreferences.enableExhentai().collectAsState()
var runConfigureDialog by remember { mutableStateOf(false) }
val openWarnConfigureDialogController = { runConfigureDialog = true }
Reconfigure(unsortedPreferences, openWarnConfigureDialogController)
Reconfigure(exhPreferences, openWarnConfigureDialogController)
ConfigureExhDialog(run = runConfigureDialog, onRunning = { runConfigureDialog = false })
@ -140,36 +140,36 @@ object SettingsEhScreen : SearchableSettings {
Preference.PreferenceGroup(
stringResource(SYMR.strings.ehentai_prefs_account_settings),
preferenceItems = persistentListOf(
getLoginPreference(unsortedPreferences, openWarnConfigureDialogController),
useHentaiAtHome(exhentaiEnabled, unsortedPreferences),
useJapaneseTitle(exhentaiEnabled, unsortedPreferences),
useOriginalImages(exhentaiEnabled, unsortedPreferences),
getLoginPreference(exhPreferences, openWarnConfigureDialogController),
useHentaiAtHome(exhentaiEnabled, exhPreferences),
useJapaneseTitle(exhentaiEnabled, exhPreferences),
useOriginalImages(exhentaiEnabled, exhPreferences),
watchedTags(exhentaiEnabled),
tagFilterThreshold(exhentaiEnabled, unsortedPreferences),
tagWatchingThreshold(exhentaiEnabled, unsortedPreferences),
settingsLanguages(exhentaiEnabled, unsortedPreferences),
enabledCategories(exhentaiEnabled, unsortedPreferences),
watchedListDefaultState(exhentaiEnabled, unsortedPreferences),
imageQuality(exhentaiEnabled, unsortedPreferences),
enhancedEhentaiView(unsortedPreferences),
tagFilterThreshold(exhentaiEnabled, exhPreferences),
tagWatchingThreshold(exhentaiEnabled, exhPreferences),
settingsLanguages(exhentaiEnabled, exhPreferences),
enabledCategories(exhentaiEnabled, exhPreferences),
watchedListDefaultState(exhentaiEnabled, exhPreferences),
imageQuality(exhentaiEnabled, exhPreferences),
enhancedEhentaiView(exhPreferences),
),
),
Preference.PreferenceGroup(
stringResource(SYMR.strings.favorites_sync),
preferenceItems = persistentListOf(
readOnlySync(unsortedPreferences),
readOnlySync(exhPreferences),
syncFavoriteNotes(),
lenientSync(unsortedPreferences),
lenientSync(exhPreferences),
forceSyncReset(deleteFavoriteEntries),
),
),
Preference.PreferenceGroup(
stringResource(SYMR.strings.gallery_update_checker),
preferenceItems = persistentListOf(
updateCheckerFrequency(unsortedPreferences),
autoUpdateRequirements(unsortedPreferences),
updateCheckerFrequency(exhPreferences),
autoUpdateRequirements(exhPreferences),
updaterStatistics(
unsortedPreferences,
exhPreferences,
getExhFavoriteMangaWithMetadata,
getFlatMetadataById,
),
@ -180,7 +180,7 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun getLoginPreference(
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
openWarnConfigureDialogController: () -> Unit,
): Preference.PreferenceItem.SwitchPreference {
val activityResultContract =
@ -191,9 +191,9 @@ object SettingsEhScreen : SearchableSettings {
}
}
val context = LocalContext.current
val value by unsortedPreferences.enableExhentai().collectAsState()
val value by exhPreferences.enableExhentai().collectAsState()
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.enableExhentai(),
preference = exhPreferences.enableExhentai(),
title = stringResource(SYMR.strings.enable_exhentai),
subtitle = if (!value) {
stringResource(SYMR.strings.requires_login)
@ -202,7 +202,7 @@ object SettingsEhScreen : SearchableSettings {
},
onValueChanged = { newVal ->
if (!newVal) {
unsortedPreferences.enableExhentai().set(false)
exhPreferences.enableExhentai().set(false)
true
} else {
activityResultContract.launch(EhLoginActivity.newIntent(context))
@ -215,10 +215,10 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun useHentaiAtHome(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.ListPreference<Int> {
return Preference.PreferenceItem.ListPreference(
preference = unsortedPreferences.useHentaiAtHome(),
preference = exhPreferences.useHentaiAtHome(),
title = stringResource(SYMR.strings.use_hentai_at_home),
subtitle = stringResource(SYMR.strings.use_hentai_at_home_summary),
entries = persistentMapOf(
@ -232,11 +232,11 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun useJapaneseTitle(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.SwitchPreference {
val value by unsortedPreferences.useJapaneseTitle().collectAsState()
val value by exhPreferences.useJapaneseTitle().collectAsState()
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.useJapaneseTitle(),
preference = exhPreferences.useJapaneseTitle(),
title = stringResource(SYMR.strings.show_japanese_titles),
subtitle = if (value) {
stringResource(SYMR.strings.show_japanese_titles_option_1)
@ -250,11 +250,11 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun useOriginalImages(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.SwitchPreference {
val value by unsortedPreferences.exhUseOriginalImages().collectAsState()
val value by exhPreferences.exhUseOriginalImages().collectAsState()
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.exhUseOriginalImages(),
preference = exhPreferences.exhUseOriginalImages(),
title = stringResource(SYMR.strings.use_original_images),
subtitle = if (value) {
stringResource(SYMR.strings.use_original_images_on)
@ -351,9 +351,9 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun tagFilterThreshold(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.TextPreference {
val value by unsortedPreferences.ehTagFilterValue().collectAsState()
val value by exhPreferences.ehTagFilterValue().collectAsState()
var dialogOpen by remember { mutableStateOf(false) }
if (dialogOpen) {
TagThresholdDialog(
@ -364,7 +364,7 @@ object SettingsEhScreen : SearchableSettings {
outsideRangeError = stringResource(SYMR.strings.tag_filtering_threshhold_error),
onValueChange = {
dialogOpen = false
unsortedPreferences.ehTagFilterValue().set(it)
exhPreferences.ehTagFilterValue().set(it)
},
)
}
@ -381,9 +381,9 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun tagWatchingThreshold(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.TextPreference {
val value by unsortedPreferences.ehTagWatchingValue().collectAsState()
val value by exhPreferences.ehTagWatchingValue().collectAsState()
var dialogOpen by remember { mutableStateOf(false) }
if (dialogOpen) {
TagThresholdDialog(
@ -394,7 +394,7 @@ object SettingsEhScreen : SearchableSettings {
outsideRangeError = stringResource(SYMR.strings.tag_watching_threshhold_error),
onValueChange = {
dialogOpen = false
unsortedPreferences.ehTagWatchingValue().set(it)
exhPreferences.ehTagWatchingValue().set(it)
},
)
}
@ -604,9 +604,9 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun settingsLanguages(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.TextPreference {
val value by unsortedPreferences.exhSettingsLanguages().collectAsState()
val value by exhPreferences.exhSettingsLanguages().collectAsState()
var dialogOpen by remember { mutableStateOf(false) }
if (dialogOpen) {
LanguagesDialog(
@ -614,7 +614,7 @@ object SettingsEhScreen : SearchableSettings {
initialValue = value,
onValueChange = {
dialogOpen = false
unsortedPreferences.exhSettingsLanguages().set(it)
exhPreferences.exhSettingsLanguages().set(it)
},
)
}
@ -770,9 +770,9 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun enabledCategories(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.TextPreference {
val value by unsortedPreferences.exhEnabledCategories().collectAsState()
val value by exhPreferences.exhEnabledCategories().collectAsState()
var dialogOpen by remember { mutableStateOf(false) }
if (dialogOpen) {
FrontPageCategoriesDialog(
@ -780,7 +780,7 @@ object SettingsEhScreen : SearchableSettings {
initialValue = value,
onValueChange = {
dialogOpen = false
unsortedPreferences.exhEnabledCategories().set(it)
exhPreferences.exhEnabledCategories().set(it)
},
)
}
@ -797,10 +797,10 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun watchedListDefaultState(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.SwitchPreference {
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.exhWatchedListDefaultState(),
preference = exhPreferences.exhWatchedListDefaultState(),
title = stringResource(SYMR.strings.watched_list_default),
subtitle = stringResource(SYMR.strings.watched_list_state_summary),
enabled = exhentaiEnabled,
@ -810,10 +810,10 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun imageQuality(
exhentaiEnabled: Boolean,
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.ListPreference<String> {
return Preference.PreferenceItem.ListPreference(
preference = unsortedPreferences.imageQuality(),
preference = exhPreferences.imageQuality(),
title = stringResource(SYMR.strings.eh_image_quality_summary),
subtitle = stringResource(SYMR.strings.eh_image_quality),
entries = persistentMapOf(
@ -829,18 +829,18 @@ object SettingsEhScreen : SearchableSettings {
}
@Composable
fun enhancedEhentaiView(unsortedPreferences: UnsortedPreferences): Preference.PreferenceItem.SwitchPreference {
fun enhancedEhentaiView(exhPreferences: ExhPreferences): Preference.PreferenceItem.SwitchPreference {
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.enhancedEHentaiView(),
preference = exhPreferences.enhancedEHentaiView(),
title = stringResource(SYMR.strings.pref_enhanced_e_hentai_view),
subtitle = stringResource(SYMR.strings.pref_enhanced_e_hentai_view_summary),
)
}
@Composable
fun readOnlySync(unsortedPreferences: UnsortedPreferences): Preference.PreferenceItem.SwitchPreference {
fun readOnlySync(exhPreferences: ExhPreferences): Preference.PreferenceItem.SwitchPreference {
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.exhReadOnlySync(),
preference = exhPreferences.exhReadOnlySync(),
title = stringResource(SYMR.strings.disable_favorites_uploading),
subtitle = stringResource(SYMR.strings.disable_favorites_uploading_summary),
)
@ -863,9 +863,9 @@ object SettingsEhScreen : SearchableSettings {
}
@Composable
fun lenientSync(unsortedPreferences: UnsortedPreferences): Preference.PreferenceItem.SwitchPreference {
fun lenientSync(exhPreferences: ExhPreferences): Preference.PreferenceItem.SwitchPreference {
return Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.exhLenientSync(),
preference = exhPreferences.exhLenientSync(),
title = stringResource(SYMR.strings.ignore_sync_errors),
subtitle = stringResource(SYMR.strings.ignore_sync_errors_summary),
)
@ -935,12 +935,12 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun updateCheckerFrequency(
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.ListPreference<Int> {
val value by unsortedPreferences.exhAutoUpdateFrequency().collectAsState()
val value by exhPreferences.exhAutoUpdateFrequency().collectAsState()
val context = LocalContext.current
return Preference.PreferenceItem.ListPreference(
preference = unsortedPreferences.exhAutoUpdateFrequency(),
preference = exhPreferences.exhAutoUpdateFrequency(),
title = stringResource(SYMR.strings.time_between_batches),
subtitle = if (value == 0) {
stringResource(SYMR.strings.time_between_batches_summary_1, stringResource(MR.strings.app_name))
@ -971,12 +971,12 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun autoUpdateRequirements(
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
): Preference.PreferenceItem.MultiSelectListPreference {
val value by unsortedPreferences.exhAutoUpdateRequirements().collectAsState()
val value by exhPreferences.exhAutoUpdateRequirements().collectAsState()
val context = LocalContext.current
return Preference.PreferenceItem.MultiSelectListPreference(
preference = unsortedPreferences.exhAutoUpdateRequirements(),
preference = exhPreferences.exhAutoUpdateRequirements(),
title = stringResource(SYMR.strings.auto_update_restrictions),
subtitle = remember(value) {
context.stringResource(
@ -1139,7 +1139,7 @@ object SettingsEhScreen : SearchableSettings {
@Composable
fun updaterStatistics(
unsortedPreferences: UnsortedPreferences,
exhPreferences: ExhPreferences,
getExhFavoriteMangaWithMetadata: GetExhFavoriteMangaWithMetadata,
getFlatMetadataById: GetFlatMetadataById,
): Preference.PreferenceItem.TextPreference {
@ -1150,7 +1150,7 @@ object SettingsEhScreen : SearchableSettings {
value = withIOContext {
try {
val stats =
unsortedPreferences.exhAutoUpdateStats().get().nullIfBlank()?.let {
exhPreferences.exhAutoUpdateStats().get().nullIfBlank()?.let {
Json.decodeFromString<EHentaiUpdaterStats>(it)
}

View File

@ -25,7 +25,6 @@ import kotlinx.collections.immutable.persistentListOf
import kotlinx.collections.immutable.persistentMapOf
import kotlinx.collections.immutable.toImmutableMap
import kotlinx.coroutines.launch
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.interactor.GetCategories
import tachiyomi.domain.category.interactor.ResetCategoryFlags
import tachiyomi.domain.category.model.Category
@ -59,9 +58,6 @@ object SettingsLibraryScreen : SearchableSettings {
val getCategories = remember { Injekt.get<GetCategories>() }
val libraryPreferences = remember { Injekt.get<LibraryPreferences>() }
val allCategories by getCategories.subscribe().collectAsState(initial = emptyList())
// SY -->
val unsortedPreferences = remember { Injekt.get<UnsortedPreferences>() }
// SY <--
return listOf(
getCategoriesGroup(LocalNavigator.currentOrThrow, allCategories, libraryPreferences),
@ -69,7 +65,6 @@ object SettingsLibraryScreen : SearchableSettings {
getBehaviorGroup(libraryPreferences),
// SY -->
getSortingCategory(LocalNavigator.currentOrThrow, libraryPreferences),
getMigrationCategory(unsortedPreferences),
// SY <--
)
}
@ -300,22 +295,5 @@ object SettingsLibraryScreen : SearchableSettings {
),
)
}
@Composable
fun getMigrationCategory(unsortedPreferences: UnsortedPreferences): Preference.PreferenceGroup {
val skipPreMigration by unsortedPreferences.skipPreMigration().collectAsState()
val migrationSources by unsortedPreferences.migrationSources().collectAsState()
return Preference.PreferenceGroup(
stringResource(SYMR.strings.migration),
enabled = skipPreMigration || migrationSources.isNotEmpty(),
preferenceItems = persistentListOf(
Preference.PreferenceItem.SwitchPreference(
preference = unsortedPreferences.skipPreMigration(),
title = stringResource(SYMR.strings.skip_pre_migration),
subtitle = stringResource(SYMR.strings.pref_skip_pre_migration_summary),
),
),
)
}
// SY <--
}

View File

@ -44,7 +44,6 @@ import logcat.LogPriority
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.MR
import tachiyomi.i18n.sy.SYMR
import tachiyomi.presentation.core.components.material.padding
@ -65,14 +64,13 @@ object SettingsMangadexScreen : SearchableSettings {
@Composable
override fun getPreferences(): List<Preference> {
val sourcePreferences: SourcePreferences = remember { Injekt.get() }
val unsortedPreferences: UnsortedPreferences = remember { Injekt.get() }
val trackPreferences: TrackPreferences = remember { Injekt.get() }
val mdex = remember { MdUtil.getEnabledMangaDex(unsortedPreferences, sourcePreferences) } ?: return emptyList()
val mdex = remember { MdUtil.getEnabledMangaDex(sourcePreferences) } ?: return emptyList()
return listOf(
loginPreference(mdex, trackPreferences),
preferredMangaDexId(unsortedPreferences, sourcePreferences),
syncMangaDexIntoThis(unsortedPreferences),
preferredMangaDexId(sourcePreferences),
syncMangaDexIntoThis(sourcePreferences),
syncLibraryToMangaDex(),
)
}
@ -174,11 +172,10 @@ object SettingsMangadexScreen : SearchableSettings {
@Composable
fun preferredMangaDexId(
unsortedPreferences: UnsortedPreferences,
sourcePreferences: SourcePreferences,
): Preference.PreferenceItem.ListPreference<String> {
return Preference.PreferenceItem.ListPreference(
preference = unsortedPreferences.preferredMangaDexId(),
preference = sourcePreferences.preferredMangaDexId(),
title = stringResource(SYMR.strings.mangadex_preffered_source),
subtitle = stringResource(SYMR.strings.mangadex_preffered_source_summary),
entries = MdUtil.getEnabledMangaDexs(sourcePreferences)
@ -250,7 +247,7 @@ object SettingsMangadexScreen : SearchableSettings {
}
@Composable
fun syncMangaDexIntoThis(unsortedPreferences: UnsortedPreferences): Preference.PreferenceItem.TextPreference {
fun syncMangaDexIntoThis(sourcePreferences: SourcePreferences): Preference.PreferenceItem.TextPreference {
val context = LocalContext.current
var dialogOpen by remember { mutableStateOf(false) }
if (dialogOpen) {
@ -258,7 +255,7 @@ object SettingsMangadexScreen : SearchableSettings {
onDismissRequest = { dialogOpen = false },
onSelectionConfirmed = { items ->
dialogOpen = false
unsortedPreferences.mangadexSyncToLibraryIndexes().set(
sourcePreferences.mangadexSyncToLibraryIndexes().set(
List(items.size) { index -> (index + 1).toString() }.toSet(),
)
LibraryUpdateJob.startNow(

View File

@ -227,13 +227,6 @@ object SettingsReaderScreen : SearchableSettings {
preference = readerPreferences.skipDupe(),
title = stringResource(MR.strings.pref_skip_dupe_chapters),
),
// SY -->
Preference.PreferenceItem.SwitchPreference(
preference = readerPreferences.markReadDupe(),
title = stringResource(SYMR.strings.pref_mark_read_dupe_chapters),
subtitle = stringResource(SYMR.strings.pref_mark_read_dupe_chapters_summary),
),
// SY <--
Preference.PreferenceItem.SwitchPreference(
preference = readerPreferences.alwaysShowChapterTransition(),
title = stringResource(MR.strings.pref_always_show_chapter_transition),

View File

@ -328,7 +328,7 @@ class App : Application(), DefaultLifecycleObserver, SingletonImageLoader.Factor
return super.generateFileName(
logLevel,
timestamp,
) + "-${BuildConfig.BUILD_TYPE}.log"
) + "-${BuildConfig.BUILD_TYPE}.txt"
}
}
flattener { timeMillis, level, tag, message ->

View File

@ -118,13 +118,15 @@ class MangaBackupCreator(
private fun Manga.toBackupManga(/* SY --> */customMangaInfo: CustomMangaInfo?/* SY <-- */) =
BackupManga(
url = this.url,
title = this.title,
artist = this.artist,
author = this.author,
description = this.description,
genre = this.genre.orEmpty(),
status = this.status.toInt(),
thumbnailUrl = this.thumbnailUrl,
// SY -->
title = this.ogTitle,
artist = this.ogArtist,
author = this.ogAuthor,
description = this.ogDescription,
genre = this.ogGenre.orEmpty(),
status = this.ogStatus.toInt(),
thumbnailUrl = this.ogThumbnailUrl,
// SY <--
favorite = this.favorite,
source = this.source,
dateAdded = this.dateAdded,

View File

@ -139,13 +139,15 @@ class MangaRestorer(
mangasQueries.update(
source = manga.source,
url = manga.url,
artist = manga.artist,
author = manga.author,
description = manga.description,
genre = manga.genre?.joinToString(separator = ", "),
title = manga.title,
status = manga.status,
thumbnailUrl = manga.thumbnailUrl,
// SY -->
artist = manga.ogArtist,
author = manga.ogAuthor,
description = manga.ogDescription,
genre = manga.ogGenre?.joinToString(separator = ", "),
title = manga.ogTitle,
status = manga.ogStatus,
thumbnailUrl = manga.ogThumbnailUrl,
// SY <--
favorite = manga.favorite,
lastUpdate = manga.lastUpdate,
nextUpdate = null,
@ -275,13 +277,15 @@ class MangaRestorer(
mangasQueries.insert(
source = manga.source,
url = manga.url,
artist = manga.artist,
author = manga.author,
description = manga.description,
genre = manga.genre,
title = manga.title,
status = manga.status,
thumbnailUrl = manga.thumbnailUrl,
// SY -->
artist = manga.ogArtist,
author = manga.ogAuthor,
description = manga.ogDescription,
genre = manga.ogGenre,
title = manga.ogTitle,
status = manga.ogStatus,
thumbnailUrl = manga.ogThumbnailUrl,
// SY <--
favorite = manga.favorite,
lastUpdate = manga.lastUpdate,
nextUpdate = 0L,
@ -458,6 +462,7 @@ class MangaRestorer(
}
// SY -->
/**
* Restore the categories from Json
*

View File

@ -291,6 +291,7 @@ class DownloadManager(
}
// SY -->
/**
* return the list of all manga folders
*/

View File

@ -120,6 +120,7 @@ class DownloadProvider(
}
// SY -->
/**
* Returns a list of all files in manga directory
*

View File

@ -23,6 +23,7 @@ import eu.kanade.domain.chapter.interactor.SyncChaptersWithSource
import eu.kanade.domain.manga.interactor.UpdateManga
import eu.kanade.domain.manga.model.copyFrom
import eu.kanade.domain.manga.model.toSManga
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.domain.sync.SyncPreferences
import eu.kanade.domain.track.model.toDbTrack
import eu.kanade.domain.track.model.toDomainTrack
@ -64,7 +65,6 @@ import tachiyomi.core.common.i18n.stringResource
import tachiyomi.core.common.preference.getAndSet
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.model.Category
import tachiyomi.domain.chapter.interactor.GetChaptersByMangaId
import tachiyomi.domain.chapter.model.Chapter
@ -558,11 +558,12 @@ class LibraryUpdateJob(private val context: Context, workerParams: WorkerParamet
}
// SY -->
/**
* filter all follows from Mangadex and only add reading or rereading manga to library
*/
private suspend fun syncFollows() = coroutineScope {
val preferences = Injekt.get<UnsortedPreferences>()
val preferences = Injekt.get<SourcePreferences>()
var count = 0
val mangaDex = MdUtil.getEnabledMangaDex(preferences, sourceManager = sourceManager)
?: return@coroutineScope
@ -734,6 +735,7 @@ class LibraryUpdateJob(private val context: Context, workerParams: WorkerParamet
private const val KEY_TARGET = "target"
// SY -->
/**
* Key for group to update.
*/

View File

@ -18,8 +18,6 @@ import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.domain.manga.model.Manga
import tachiyomi.i18n.MR
import tachiyomi.i18n.sy.SYMR
import uy.kohesive.injekt.Injekt
import uy.kohesive.injekt.api.get
import tachiyomi.domain.track.model.Track as DomainTrack
class MdList(id: Long) : BaseTracker(id, "MDList") {
@ -30,7 +28,7 @@ class MdList(id: Long) : BaseTracker(id, "MDList") {
.toImmutableList()
}
private val mdex by lazy { MdUtil.getEnabledMangaDex(Injekt.get()) }
private val mdex by lazy { MdUtil.getEnabledMangaDex() }
val interceptor = MangaDexAuthInterceptor(trackPreferences, this)

View File

@ -2,7 +2,7 @@ package eu.kanade.tachiyomi.di
import android.app.Application
import exh.pref.DelegateSourcePreferences
import tachiyomi.domain.UnsortedPreferences
import exh.source.ExhPreferences
import uy.kohesive.injekt.api.InjektRegistrar
class SYPreferenceModule(val application: Application) : InjektModule {
@ -15,7 +15,7 @@ class SYPreferenceModule(val application: Application) : InjektModule {
}
addSingletonFactory {
UnsortedPreferences(get())
ExhPreferences(get())
}
}
}

View File

@ -1,6 +1,7 @@
package eu.kanade.tachiyomi.source
import android.content.Context
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.tachiyomi.data.download.DownloadManager
import eu.kanade.tachiyomi.extension.ExtensionManager
import eu.kanade.tachiyomi.source.online.HttpSource
@ -19,6 +20,7 @@ import exh.source.EH_SOURCE_ID
import exh.source.EIGHTMUSES_SOURCE_ID
import exh.source.EXH_SOURCE_ID
import exh.source.EnhancedHttpSource
import exh.source.ExhPreferences
import exh.source.HBROWSE_SOURCE_ID
import exh.source.MERGED_SOURCE_ID
import exh.source.PURURIN_SOURCE_ID
@ -36,7 +38,6 @@ import kotlinx.coroutines.flow.combine
import kotlinx.coroutines.flow.map
import kotlinx.coroutines.launch
import kotlinx.coroutines.runBlocking
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.source.model.StubSource
import tachiyomi.domain.source.repository.StubSourceRepository
import tachiyomi.domain.source.service.SourceManager
@ -69,14 +70,15 @@ class AndroidSourceManager(
}
// SY -->
private val preferences: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
private val sourcePreferences: SourcePreferences by injectLazy()
// SY <--
init {
scope.launch {
extensionManager.installedExtensionsFlow
// SY -->
.combine(preferences.enableExhentai().changes()) { extensions, enableExhentai ->
.combine(exhPreferences.enableExhentai().changes()) { extensions, enableExhentai ->
extensions to enableExhentai
}
// SY <--
@ -88,7 +90,7 @@ class AndroidSourceManager(
Injekt.get(),
Injekt.get(),
// SY -->
preferences.allowLocalSourceHiddenFolders()::get,
sourcePreferences.allowLocalSourceHiddenFolders()::get,
// SY <--
),
),

View File

@ -44,6 +44,7 @@ import exh.metadata.metadata.EHentaiSearchMetadata.Companion.TAG_TYPE_WEAK
import exh.metadata.metadata.RaisedSearchMetadata.Companion.TAG_TYPE_VIRTUAL
import exh.metadata.metadata.RaisedSearchMetadata.Companion.toGenreString
import exh.metadata.metadata.base.RaisedTag
import exh.source.ExhPreferences
import exh.ui.login.EhLoginActivity
import exh.util.UriFilter
import exh.util.UriGroup
@ -84,7 +85,6 @@ import org.jsoup.nodes.TextNode
import rx.Observable
import tachiyomi.core.common.util.lang.runAsObservable
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.domain.UnsortedPreferences
import uy.kohesive.injekt.injectLazy
import java.io.ByteArrayOutputStream
import java.io.IOException
@ -117,7 +117,7 @@ class EHentai(
override val lang = "all"
override val supportsLatest = true
private val preferences: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
private val updateHelper: EHentaiUpdateHelper by injectLazy()
/**
@ -476,7 +476,7 @@ class EHentai(
}
private fun <T : MangasPage> T.checkValid(): MangasPage =
if (exh && mangas.isEmpty() && preferences.igneousVal().get().equals("mystery", true)) {
if (exh && mangas.isEmpty() && exhPreferences.igneousVal().get().equals("mystery", true)) {
throw Exception(
"Invalid igneous cookie, try re-logging or finding a correct one to input in the login menu",
)
@ -879,30 +879,30 @@ class EHentai(
}
fun spPref() = if (exh) {
preferences.exhSettingsProfile()
exhPreferences.exhSettingsProfile()
} else {
preferences.ehSettingsProfile()
exhPreferences.ehSettingsProfile()
}
private fun rawCookies(sp: Int): Map<String, String> {
val cookies: MutableMap<String, String> = mutableMapOf()
if (preferences.enableExhentai().get()) {
cookies[EhLoginActivity.MEMBER_ID_COOKIE] = preferences.memberIdVal().get()
cookies[EhLoginActivity.PASS_HASH_COOKIE] = preferences.passHashVal().get()
cookies[EhLoginActivity.IGNEOUS_COOKIE] = preferences.igneousVal().get()
if (exhPreferences.enableExhentai().get()) {
cookies[EhLoginActivity.MEMBER_ID_COOKIE] = exhPreferences.memberIdVal().get()
cookies[EhLoginActivity.PASS_HASH_COOKIE] = exhPreferences.passHashVal().get()
cookies[EhLoginActivity.IGNEOUS_COOKIE] = exhPreferences.igneousVal().get()
cookies["sp"] = sp.toString()
val sessionKey = preferences.exhSettingsKey().get()
val sessionKey = exhPreferences.exhSettingsKey().get()
if (sessionKey.isNotBlank()) {
cookies["sk"] = sessionKey
}
val sessionCookie = preferences.exhSessionCookie().get()
val sessionCookie = exhPreferences.exhSessionCookie().get()
if (sessionCookie.isNotBlank()) {
cookies["s"] = sessionCookie
}
val hathPerksCookie = preferences.exhHathPerksCookies().get()
val hathPerksCookie = exhPreferences.exhHathPerksCookies().get()
if (hathPerksCookie.isNotBlank()) {
cookies["hath_perks"] = hathPerksCookie
}
@ -949,7 +949,7 @@ class EHentai(
ToplistOptions(),
Filter.Separator(),
AutoCompleteTags(),
Watched(isEnabled = preferences.exhWatchedListDefaultState().get()),
Watched(isEnabled = exhPreferences.exhWatchedListDefaultState().get()),
GenreGroup(),
AdvancedGroup(),
ReverseFilter(),
@ -1360,7 +1360,7 @@ class EHentai(
private const val BLANK_PREVIEW_THUMB = "https://$THUMB_DOMAIN/g/$BLANK_THUMB"
private val MATCH_YEAR_REGEX = "^\\d{4}\$".toRegex()
private val MATCH_SEEK_REGEX = "^\\d{2,4}-\\d{1,2}".toRegex()
private val MATCH_SEEK_REGEX = "^\\d{2,4}-\\d{1,2}(-\\d{1,2})?".toRegex()
private val MATCH_JUMP_REGEX = "^\\d+(\$|d\$|w\$|m\$|y\$|-\$)".toRegex()
private const val EH_API_BASE = "https://api.e-hentai.org/api.php"

View File

@ -70,7 +70,9 @@ class NHentai(delegate: HttpSource, val context: Context) :
}
override suspend fun parseIntoMetadata(metadata: NHentaiSearchMetadata, input: Response) {
val json = GALLERY_JSON_REGEX.find(input.body.string())!!.groupValues[1].replace(
val body = input.body.string()
val server = MEDIA_SERVER_REGEX.find(body)?.groupValues?.get(1)?.toInt() ?: 1
val json = GALLERY_JSON_REGEX.find(body)!!.groupValues[1].replace(
UNICODE_ESCAPE_REGEX,
) { it.groupValues[1].toInt(radix = 16).toChar().toString() }
val jsonResponse = jsonParser.decodeFromString<JsonResponse>(json)
@ -84,6 +86,8 @@ class NHentai(delegate: HttpSource, val context: Context) :
mediaId = jsonResponse.mediaId
mediaServer = server
jsonResponse.title?.let { title ->
japaneseTitle = title.japanese
shortTitle = title.pretty
@ -190,16 +194,23 @@ class NHentai(delegate: HttpSource, val context: Context) :
return PagePreviewPage(
page,
metadata.pageImageTypes.mapIndexed { index, s ->
PagePreviewInfo(index + 1, imageUrl = thumbnailUrlFromType(metadata.mediaId!!, index + 1, s)!!)
PagePreviewInfo(
index + 1,
imageUrl = thumbnailUrlFromType(metadata.mediaId!!, metadata.mediaServer ?: 1, index + 1, s)!!,
)
},
false,
1,
)
}
private fun thumbnailUrlFromType(mediaId: String, page: Int, t: String) =
NHentaiSearchMetadata.typeToExtension(t)?.let {
"https://t1.nhentai.net/galleries/$mediaId/${page}t.$it"
private fun thumbnailUrlFromType(
mediaId: String,
mediaServer: Int,
page: Int,
t: String,
) = NHentaiSearchMetadata.typeToExtension(t)?.let {
"https://t$mediaServer.nhentai.net/galleries/$mediaId/${page}t.$it"
}
override suspend fun fetchPreviewImage(page: PagePreviewInfo, cacheControl: CacheControl?): Response {
@ -221,6 +232,7 @@ class NHentai(delegate: HttpSource, val context: Context) :
}
private val GALLERY_JSON_REGEX = Regex(".parse\\(\"(.*)\"\\);")
private val MEDIA_SERVER_REGEX = Regex("media_server\\s*:\\s*(\\d+)")
private val UNICODE_ESCAPE_REGEX = Regex("\\\\u([0-9a-fA-F]{4})")
private const val TITLE_PREF = "Display manga title as:"
}

View File

@ -13,13 +13,13 @@ import androidx.compose.runtime.rememberUpdatedState
import androidx.compose.ui.Modifier
import androidx.compose.ui.viewinterop.AndroidView
import androidx.core.view.isVisible
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.components.AdaptiveSheet
import eu.kanade.tachiyomi.databinding.MigrationBottomSheetBinding
import eu.kanade.tachiyomi.ui.browse.migration.MigrationFlags
import eu.kanade.tachiyomi.util.system.toast
import tachiyomi.core.common.preference.Preference
import tachiyomi.core.common.util.lang.toLong
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.sy.SYMR
import uy.kohesive.injekt.injectLazy
@ -45,7 +45,7 @@ fun MigrationBottomSheetDialog(
}
class MigrationBottomSheetDialogState(private val onStartMigration: State<(extraParam: String?) -> Unit>) {
private val preferences: UnsortedPreferences by injectLazy()
private val preferences: SourcePreferences by injectLazy()
/**
* Init general reader preferences.

View File

@ -10,14 +10,12 @@ import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.flow.update
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.source.service.SourceManager
import uy.kohesive.injekt.Injekt
import uy.kohesive.injekt.api.get
class PreMigrationScreenModel(
private val sourceManager: SourceManager = Injekt.get(),
private val prefs: UnsortedPreferences = Injekt.get(),
private val sourcePreferences: SourcePreferences = Injekt.get(),
) : ScreenModel {
@ -53,7 +51,7 @@ class PreMigrationScreenModel(
*/
private fun getEnabledSources(): List<MigrationSourceItem> {
val languages = sourcePreferences.enabledLanguages().get()
val sourcesSaved = prefs.migrationSources().get().split("/")
val sourcesSaved = sourcePreferences.migrationSources().get().split("/")
.mapNotNull { it.toLongOrNull() }
val disabledSources = sourcePreferences.disabledSources().get()
.mapNotNull { it.toLongOrNull() }
@ -134,6 +132,6 @@ class PreMigrationScreenModel(
?.joinToString("/") { it.source.id.toString() }
.orEmpty()
prefs.migrationSources().set(listOfSources)
sourcePreferences.migrationSources().set(listOfSources)
}
}

View File

@ -118,8 +118,7 @@ class MigrationListScreen(private val config: MigrationProcedureConfig) : Screen
)
val onDismissRequest = { screenModel.dialog.value = null }
when
(
when (
@Suppress("NAME_SHADOWING")
val dialog = dialog
) {

View File

@ -8,6 +8,7 @@ import eu.kanade.domain.chapter.interactor.SyncChaptersWithSource
import eu.kanade.domain.manga.interactor.UpdateManga
import eu.kanade.domain.manga.model.hasCustomCover
import eu.kanade.domain.manga.model.toSManga
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.tachiyomi.data.cache.CoverCache
import eu.kanade.tachiyomi.data.download.DownloadManager
import eu.kanade.tachiyomi.source.CatalogueSource
@ -38,14 +39,13 @@ import logcat.LogPriority
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.interactor.GetCategories
import tachiyomi.domain.category.interactor.SetMangaCategories
import tachiyomi.domain.chapter.interactor.GetChaptersByMangaId
import tachiyomi.domain.chapter.interactor.UpdateChapter
import tachiyomi.domain.chapter.model.Chapter
import tachiyomi.domain.chapter.model.ChapterUpdate
import tachiyomi.domain.history.interactor.GetHistoryByMangaId
import tachiyomi.domain.history.interactor.GetHistory
import tachiyomi.domain.history.interactor.UpsertHistory
import tachiyomi.domain.history.model.HistoryUpdate
import tachiyomi.domain.manga.interactor.GetManga
@ -64,7 +64,7 @@ import java.util.concurrent.atomic.AtomicInteger
class MigrationListScreenModel(
private val config: MigrationProcedureConfig,
private val preferences: UnsortedPreferences = Injekt.get(),
private val preferences: SourcePreferences = Injekt.get(),
private val sourceManager: SourceManager = Injekt.get(),
private val downloadManager: DownloadManager = Injekt.get(),
private val coverCache: CoverCache = Injekt.get(),
@ -75,7 +75,7 @@ class MigrationListScreenModel(
private val updateChapter: UpdateChapter = Injekt.get(),
private val getChaptersByMangaId: GetChaptersByMangaId = Injekt.get(),
private val getMergedReferencesById: GetMergedReferencesById = Injekt.get(),
private val getHistoryByMangaId: GetHistoryByMangaId = Injekt.get(),
private val getHistoryByMangaId: GetHistory = Injekt.get(),
private val upsertHistory: UpsertHistory = Injekt.get(),
private val getCategories: GetCategories = Injekt.get(),
private val setMangaCategories: SetMangaCategories = Injekt.get(),
@ -236,7 +236,7 @@ class MigrationListScreenModel(
try {
syncChaptersWithSource.await(chapters, localManga, source)
} catch (e: Exception) {
} catch (_: Exception) {
return@async2 null
}
manga.progress.value =
@ -248,7 +248,7 @@ class MigrationListScreenModel(
} catch (e: CancellationException) {
// Ignore cancellations
throw e
} catch (e: Exception) {
} catch (_: Exception) {
null
}
}
@ -283,7 +283,7 @@ class MigrationListScreenModel(
} catch (e: CancellationException) {
// Ignore cancellations
throw e
} catch (e: Exception) {
} catch (_: Exception) {
null
}
manga.progress.value = validSources.size to (index + 1)
@ -293,7 +293,7 @@ class MigrationListScreenModel(
null
}
}.await()
} catch (e: CancellationException) {
} catch (_: CancellationException) {
// Ignore canceled migrations
continue
}
@ -305,7 +305,7 @@ class MigrationListScreenModel(
} catch (e: CancellationException) {
// Ignore cancellations
throw e
} catch (e: Exception) {
} catch (_: Exception) {
}
}
@ -460,7 +460,7 @@ class MigrationListScreenModel(
val source = sourceManager.get(manga.source)!!
val chapters = source.getChapterList(localManga.toSManga())
syncChaptersWithSource.await(chapters, localManga, source)
} catch (e: Exception) {
} catch (_: Exception) {
return@async null
}
localManga
@ -473,7 +473,7 @@ class MigrationListScreenModel(
} catch (e: CancellationException) {
// Ignore cancellations
throw e
} catch (e: Exception) {
} catch (_: Exception) {
}
migratingManga.searchResult.value = SearchResult.Result(result.id)

View File

@ -8,13 +8,13 @@ import androidx.compose.ui.platform.LocalContext
import cafe.adriel.voyager.core.model.rememberScreenModel
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.browse.MigrateMangaScreen
import eu.kanade.presentation.util.Screen
import eu.kanade.tachiyomi.ui.browse.migration.advanced.design.PreMigrationScreen
import eu.kanade.tachiyomi.ui.manga.MangaScreen
import eu.kanade.tachiyomi.util.system.toast
import kotlinx.coroutines.flow.collectLatest
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.MR
import tachiyomi.presentation.core.screens.LoadingScreen
import uy.kohesive.injekt.Injekt
@ -44,7 +44,7 @@ data class MigrateMangaScreen(
onClickItem = {
// SY -->
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
listOf(it.id),
)

View File

@ -10,6 +10,7 @@ import cafe.adriel.voyager.core.model.rememberScreenModel
import cafe.adriel.voyager.core.screen.Screen
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.browse.MigrateSourceScreen
import eu.kanade.presentation.components.AppBar
import eu.kanade.presentation.components.TabContent
@ -19,7 +20,6 @@ import kotlinx.collections.immutable.persistentListOf
import kotlinx.coroutines.DelicateCoroutinesApi
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.manga.interactor.GetFavorites
import tachiyomi.i18n.MR
import tachiyomi.presentation.core.i18n.stringResource
@ -63,7 +63,7 @@ fun Screen.migrateSourceTab(): TabContent {
manga.asSequence().filter { it.source == source.id }.map { it.id }.toList()
withUIContext {
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
sourceMangas,
)

View File

@ -1,15 +0,0 @@
package eu.kanade.tachiyomi.ui.browse.migration.sources
import androidx.compose.runtime.Composable
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import eu.kanade.presentation.browse.BrowseTabWrapper
import eu.kanade.presentation.util.Screen
class MigrationSourcesScreen : Screen() {
@Composable
override fun Content() {
val navigator = LocalNavigator.currentOrThrow
BrowseTabWrapper(migrateSourceTab(), onBackPressed = navigator::pop)
}
}

View File

@ -36,6 +36,7 @@ import androidx.compose.ui.platform.LocalUriHandler
import cafe.adriel.voyager.core.model.rememberScreenModel
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.browse.BrowseSourceContent
import eu.kanade.presentation.browse.MissingSourceScreen
import eu.kanade.presentation.browse.components.BrowseSourceToolbar
@ -64,7 +65,6 @@ import kotlinx.coroutines.flow.receiveAsFlow
import mihon.presentation.core.util.collectAsLazyPagingItems
import tachiyomi.core.common.Constants
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.source.model.StubSource
import tachiyomi.i18n.MR
import tachiyomi.presentation.core.components.material.Scaffold
@ -327,7 +327,7 @@ data class BrowseSourceScreen(
onMigrate = {
// SY -->
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
it.id,
dialog.manga.id,

View File

@ -29,6 +29,7 @@ import eu.kanade.tachiyomi.source.online.MetadataSource
import eu.kanade.tachiyomi.source.online.all.MangaDex
import eu.kanade.tachiyomi.util.removeCovers
import exh.metadata.metadata.RaisedSearchMetadata
import exh.source.ExhPreferences
import exh.source.getMainSource
import exh.source.mangaDexSourceIds
import kotlinx.collections.immutable.ImmutableList
@ -55,7 +56,6 @@ import tachiyomi.core.common.preference.mapAsCheckboxState
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.core.common.util.lang.launchNonCancellable
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.interactor.GetCategories
import tachiyomi.domain.category.interactor.SetMangaCategories
import tachiyomi.domain.category.model.Category
@ -103,7 +103,7 @@ open class BrowseSourceScreenModel(
private val getIncognitoState: GetIncognitoState = Injekt.get(),
// SY -->
unsortedPreferences: UnsortedPreferences = Injekt.get(),
exhPreferences: ExhPreferences = Injekt.get(),
uiPreferences: UiPreferences = Injekt.get(),
private val getFlatMetadataById: GetFlatMetadataById = Injekt.get(),
private val deleteSavedSearchById: DeleteSavedSearchById = Injekt.get(),
@ -117,7 +117,7 @@ open class BrowseSourceScreenModel(
val source = sourceManager.getOrStub(sourceId)
// SY -->
val ehentaiBrowseDisplayMode by unsortedPreferences.enhancedEHentaiView().asState(screenModelScope)
val ehentaiBrowseDisplayMode by exhPreferences.enhancedEHentaiView().asState(screenModelScope)
val startExpanded by uiPreferences.expandFilters().asState(screenModelScope)

View File

@ -19,6 +19,7 @@ import cafe.adriel.voyager.navigator.currentOrThrow
import cafe.adriel.voyager.navigator.tab.LocalTabNavigator
import cafe.adriel.voyager.navigator.tab.TabOptions
import eu.kanade.core.preference.asState
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.domain.ui.UiPreferences
import eu.kanade.presentation.category.components.ChangeCategoryDialog
import eu.kanade.presentation.history.HistoryScreen
@ -36,7 +37,6 @@ import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.flow.collectLatest
import kotlinx.coroutines.flow.receiveAsFlow
import tachiyomi.core.common.i18n.stringResource
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.chapter.model.Chapter
import tachiyomi.i18n.MR
import tachiyomi.presentation.core.i18n.stringResource
@ -123,7 +123,7 @@ data object HistoryTab : Tab {
onMigrate = {
// SY -->
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
it.id,
dialog.manga.id,

View File

@ -1,6 +1,5 @@
package eu.kanade.tachiyomi.ui.home
import android.annotation.SuppressLint
import androidx.activity.compose.PredictiveBackHandler
import androidx.compose.animation.AnimatedContent
import androidx.compose.animation.AnimatedVisibility
@ -12,7 +11,8 @@ import androidx.compose.animation.togetherWith
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.RowScope
import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.windowInsetsPadding
import androidx.compose.foundation.layout.consumeWindowInsets
import androidx.compose.foundation.layout.padding
import androidx.compose.material3.Badge
import androidx.compose.material3.BadgedBox
import androidx.compose.material3.Icon
@ -30,15 +30,11 @@ import androidx.compose.runtime.produceState
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.runtime.setValue
import androidx.compose.runtime.staticCompositionLocalOf
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.semantics.contentDescription
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.text.style.TextOverflow
import androidx.compose.ui.unit.Density
import androidx.compose.ui.unit.LayoutDirection
import androidx.compose.ui.unit.dp
import androidx.compose.ui.util.fastFilter
import androidx.compose.ui.util.fastForEach
import androidx.compose.ui.util.lerp
@ -89,9 +85,6 @@ object HomeScreen : Screen() {
@Suppress("ConstPropertyName")
private const val TabNavigatorKey = "HomeTabs"
@SuppressLint("ComposeCompositionLocalUsage")
val LocalHomeScreenInsetsProvider = staticCompositionLocalOf { WindowInsets(0.dp) }
private val TABS = listOf(
LibraryTab,
UpdatesTab,
@ -154,50 +147,17 @@ object HomeScreen : Screen() {
}
}
},
contentWindowInsets = WindowInsets(0),
) { contentPadding ->
Box(
modifier = Modifier
.padding(contentPadding)
.consumeWindowInsets(contentPadding)
.graphicsLayer {
scaleX = scale
scaleY = scale
}
.windowInsetsPadding(
remember {
object : WindowInsets {
override fun getLeft(density: Density, layoutDirection: LayoutDirection): Int {
return with(density) {
contentPadding.calculateLeftPadding(layoutDirection).roundToPx()
}
}
override fun getRight(density: Density, layoutDirection: LayoutDirection): Int {
return with(density) {
contentPadding.calculateRightPadding(layoutDirection).roundToPx()
}
}
override fun getBottom(density: Density): Int = 0
override fun getTop(density: Density): Int = 0
}
},
),
) {
val insets = remember {
object : WindowInsets {
override fun getBottom(density: Density): Int {
return with(density) { contentPadding.calculateBottomPadding().roundToPx() }
}
override fun getTop(density: Density): Int {
return with(density) { contentPadding.calculateTopPadding().roundToPx() }
}
override fun getLeft(density: Density, layoutDirection: LayoutDirection): Int = 0
override fun getRight(density: Density, layoutDirection: LayoutDirection): Int = 0
}
}
AnimatedContent(
targetState = tabNavigator.current,
transitionSpec = {
@ -206,7 +166,6 @@ object HomeScreen : Screen() {
},
label = "tabContent",
) {
CompositionLocalProvider(LocalHomeScreenInsetsProvider provides insets) {
tabNavigator.saveableState(key = "currentTab", it) {
it.Content()
}
@ -214,7 +173,6 @@ object HomeScreen : Screen() {
}
}
}
}
val goToLibraryTab = { tabNavigator.current = LibraryTab }

View File

@ -48,6 +48,7 @@ import exh.search.QueryComponent
import exh.search.SearchEngine
import exh.search.Text
import exh.source.EH_SOURCE_ID
import exh.source.ExhPreferences
import exh.source.MERGED_SOURCE_ID
import exh.source.isEhBasedManga
import exh.source.isMetadataSource
@ -86,7 +87,6 @@ import tachiyomi.core.common.util.lang.compareToWithCollator
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.core.common.util.lang.launchNonCancellable
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.interactor.GetCategories
import tachiyomi.domain.category.interactor.SetMangaCategories
import tachiyomi.domain.category.model.Category
@ -144,7 +144,7 @@ class LibraryScreenModel(
private val downloadCache: DownloadCache = Injekt.get(),
private val trackerManager: TrackerManager = Injekt.get(),
// SY -->
private val unsortedPreferences: UnsortedPreferences = Injekt.get(),
private val exhPreferences: ExhPreferences = Injekt.get(),
private val sourcePreferences: SourcePreferences = Injekt.get(),
private val getMergedMangaById: GetMergedMangaById = Injekt.get(),
private val getTracks: GetTracks = Injekt.get(),
@ -260,9 +260,9 @@ class LibraryScreenModel(
// SY -->
combine(
unsortedPreferences.isHentaiEnabled().changes(),
exhPreferences.isHentaiEnabled().changes(),
sourcePreferences.disabledSources().changes(),
unsortedPreferences.enableExhentai().changes(),
exhPreferences.enableExhentai().changes(),
) { isHentaiEnabled, disabledSources, enableExhentai ->
isHentaiEnabled && (EH_SOURCE_ID.toString() !in disabledSources || enableExhentai)
}
@ -771,7 +771,7 @@ class LibraryScreenModel(
@OptIn(DelicateCoroutinesApi::class)
fun syncMangaToDex() {
launchIO {
MdUtil.getEnabledMangaDex(unsortedPreferences, sourcePreferences, sourceManager)?.let { mdex ->
MdUtil.getEnabledMangaDex(sourcePreferences, sourceManager)?.let { mdex ->
state.value.selection.fastFilter { it.manga.source in mangaDexSourceIds }.fastForEach { (manga) ->
mdex.updateFollowStatus(MdUtil.getMangaId(manga.url), FollowStatus.READING)
}
@ -1242,6 +1242,7 @@ class LibraryScreenModel(
}
// SY -->
/** Returns first unread chapter of a manga */
suspend fun getFirstUnread(manga: Manga): Chapter? {
return getNextChapters.await(manga.id).firstOrNull()
@ -1346,13 +1347,13 @@ class LibraryScreenModel(
}
fun onAcceptSyncWarning() {
unsortedPreferences.exhShowSyncIntro().set(false)
exhPreferences.exhShowSyncIntro().set(false)
}
fun openFavoritesSyncDialog() {
mutableState.update {
it.copy(
dialog = if (unsortedPreferences.exhShowSyncIntro().get()) {
dialog = if (exhPreferences.exhShowSyncIntro().get()) {
Dialog.SyncFavoritesWarning
} else {
Dialog.SyncFavoritesConfirm

View File

@ -28,6 +28,7 @@ import cafe.adriel.voyager.navigator.Navigator
import cafe.adriel.voyager.navigator.currentOrThrow
import cafe.adriel.voyager.navigator.tab.LocalTabNavigator
import cafe.adriel.voyager.navigator.tab.TabOptions
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.category.components.ChangeCategoryDialog
import eu.kanade.presentation.library.DeleteLibraryMangaDialog
import eu.kanade.presentation.library.LibrarySettingsDialog
@ -63,7 +64,6 @@ import kotlinx.coroutines.flow.receiveAsFlow
import kotlinx.coroutines.launch
import tachiyomi.core.common.i18n.stringResource
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.model.Category
import tachiyomi.domain.library.model.LibraryGroup
import tachiyomi.domain.library.model.LibraryManga
@ -201,7 +201,7 @@ data object LibraryTab : Tab {
screenModel.clearSelection()
if (selectedMangaIds.isNotEmpty()) {
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
selectedMangaIds,
)

View File

@ -89,6 +89,7 @@ import exh.log.DebugModeOverlay
import exh.source.BlacklistedSources
import exh.source.EH_SOURCE_ID
import exh.source.EXH_SOURCE_ID
import exh.source.ExhPreferences
import exh.syDebugVersion
import kotlinx.coroutines.channels.awaitClose
import kotlinx.coroutines.flow.callbackFlow
@ -103,7 +104,6 @@ import mihon.core.migration.Migrator
import tachiyomi.core.common.Constants
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.library.service.LibraryPreferences
import tachiyomi.domain.release.interactor.GetApplicationRelease
import tachiyomi.presentation.core.components.material.Scaffold
@ -117,7 +117,7 @@ class MainActivity : BaseActivity() {
private val preferences: BasePreferences by injectLazy()
// SY -->
private val unsortedPreferences: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
// SY <--
private val downloadCache: DownloadCache by injectLazy()
@ -222,8 +222,8 @@ class MainActivity : BaseActivity() {
// SY -->
initWhenIdle {
// Upload settings
if (unsortedPreferences.enableExhentai().get() &&
unsortedPreferences.exhShowSettingsUploadWarning().get()
if (exhPreferences.enableExhentai().get() &&
exhPreferences.exhShowSettingsUploadWarning().get()
) {
runExhConfigureDialog = true
}
@ -335,7 +335,7 @@ class MainActivity : BaseActivity() {
}
// SY -->
if (!unsortedPreferences.isHentaiEnabled().get()) {
if (!exhPreferences.isHentaiEnabled().get()) {
BlacklistedSources.HIDDEN_SOURCES += EH_SOURCE_ID
BlacklistedSources.HIDDEN_SOURCES += EXH_SOURCE_ID
}

View File

@ -27,6 +27,7 @@ import cafe.adriel.voyager.navigator.currentOrThrow
import com.google.android.material.dialog.MaterialAlertDialogBuilder
import eu.kanade.domain.manga.model.hasCustomCover
import eu.kanade.domain.manga.model.toSManga
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.category.components.ChangeCategoryDialog
import eu.kanade.presentation.components.NavigatorAdaptiveSheet
import eu.kanade.presentation.manga.ChapterSettingsDialog
@ -77,7 +78,6 @@ import tachiyomi.core.common.util.lang.launchUI
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.core.common.util.lang.withNonCancellableContext
import tachiyomi.core.common.util.system.logcat
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.chapter.model.Chapter
import tachiyomi.domain.manga.model.Manga
import tachiyomi.domain.source.service.SourceManager
@ -470,13 +470,14 @@ class MangaScreen(
}
// SY -->
/**
* Initiates source migration for the specific manga.
*/
private fun migrateManga(navigator: Navigator, manga: Manga, toMangaId: Long? = null) {
// SY -->
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
manga.id,
toMangaId,

View File

@ -184,8 +184,6 @@ class ReaderPreferences(
fun centerMarginType() = preferenceStore.getInt("center_margin_type", PagerConfig.CenterMarginType.NONE)
fun archiveReaderMode() = preferenceStore.getInt("archive_reader_mode", ArchiveReaderMode.LOAD_FROM_FILE)
fun markReadDupe() = preferenceStore.getBoolean("mark_read_dupe", false)
// SY <--
enum class FlashColor {

View File

@ -42,6 +42,7 @@ class PagerViewerAdapter(private val viewer: PagerViewer) : ViewPagerAdapter() {
var currentChapter: ReaderChapter? = null
// SY -->
/** Page used to start the shifted pages */
var pageToShift: ReaderPage? = null

View File

@ -13,7 +13,7 @@ import tachiyomi.domain.chapter.interactor.GetChaptersByMangaId
import tachiyomi.domain.chapter.model.Chapter
import tachiyomi.domain.chapter.model.ChapterUpdate
import tachiyomi.domain.chapter.repository.ChapterRepository
import tachiyomi.domain.history.interactor.GetHistoryByMangaId
import tachiyomi.domain.history.interactor.GetHistory
import tachiyomi.domain.history.interactor.RemoveHistory
import tachiyomi.domain.history.interactor.UpsertHistory
import tachiyomi.domain.history.model.History
@ -43,7 +43,7 @@ class EHentaiUpdateHelper(context: Context) {
private val chapterRepository: ChapterRepository by injectLazy()
private val upsertHistory: UpsertHistory by injectLazy()
private val removeHistory: RemoveHistory by injectLazy()
private val getHistoryByMangaId: GetHistoryByMangaId by injectLazy()
private val getHistoryByMangaId: GetHistory by injectLazy()
private val insertFavoriteEntryAlternative: InsertFavoriteEntryAlternative by injectLazy()
/**

View File

@ -27,14 +27,13 @@ import exh.debug.DebugToggles
import exh.eh.EHentaiUpdateWorkerConstants.UPDATES_PER_ITERATION
import exh.log.xLog
import exh.metadata.metadata.EHentaiSearchMetadata
import exh.source.ExhPreferences
import exh.util.cancellable
import kotlinx.coroutines.flow.asFlow
import kotlinx.coroutines.flow.mapNotNull
import kotlinx.coroutines.flow.toList
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
import tachiyomi.core.common.preference.getAndSet
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.chapter.interactor.GetChaptersByMangaId
import tachiyomi.domain.chapter.model.Chapter
import tachiyomi.domain.library.service.LibraryPreferences
@ -53,7 +52,7 @@ import kotlin.time.Duration.Companion.days
class EHentaiUpdateWorker(private val context: Context, workerParams: WorkerParameters) :
CoroutineWorker(context, workerParams) {
private val preferences: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
private val libraryPreferences: LibraryPreferences by injectLazy()
private val sourceManager: SourceManager by injectLazy()
private val updateHelper: EHentaiUpdateHelper by injectLazy()
@ -70,7 +69,7 @@ class EHentaiUpdateWorker(private val context: Context, workerParams: WorkerPara
override suspend fun doWork(): Result {
return try {
if (requiresWifiConnection(preferences) && !context.isConnectedToWifi()) {
if (requiresWifiConnection(exhPreferences) && !context.isConnectedToWifi()) {
Result.success() // retry again later
} else {
setForegroundSafely()
@ -215,7 +214,7 @@ class EHentaiUpdateWorker(private val context: Context, workerParams: WorkerPara
updatedThisIteration++
}
} finally {
preferences.exhAutoUpdateStats().set(
exhPreferences.exhAutoUpdateStats().set(
Json.encodeToString(
EHentaiUpdaterStats(
startTime,
@ -279,10 +278,10 @@ class EHentaiUpdateWorker(private val context: Context, workerParams: WorkerPara
}
fun scheduleBackground(context: Context, prefInterval: Int? = null, prefRestrictions: Set<String>? = null) {
val preferences = Injekt.get<UnsortedPreferences>()
val interval = prefInterval ?: preferences.exhAutoUpdateFrequency().get()
val exhPreferences = Injekt.get<ExhPreferences>()
val interval = prefInterval ?: exhPreferences.exhAutoUpdateFrequency().get()
if (interval > 0) {
val restrictions = prefRestrictions ?: preferences.exhAutoUpdateRequirements().get()
val restrictions = prefRestrictions ?: exhPreferences.exhAutoUpdateRequirements().get()
val acRestriction = DEVICE_CHARGING in restrictions
val constraints = Constraints.Builder()
@ -312,8 +311,8 @@ class EHentaiUpdateWorker(private val context: Context, workerParams: WorkerPara
}
}
fun requiresWifiConnection(preferences: UnsortedPreferences): Boolean {
val restrictions = preferences.exhAutoUpdateRequirements().get()
fun requiresWifiConnection(exhPreferences: ExhPreferences): Boolean {
val restrictions = exhPreferences.exhAutoUpdateRequirements().get()
return DEVICE_ONLY_ON_WIFI in restrictions
}
}

View File

@ -14,6 +14,7 @@ import exh.eh.EHentaiUpdateWorker
import exh.log.xLog
import exh.source.EH_SOURCE_ID
import exh.source.EXH_SOURCE_ID
import exh.source.ExhPreferences
import exh.source.isEhBasedManga
import exh.util.ThrottleManager
import exh.util.createPartialWakeLock
@ -29,7 +30,6 @@ import okhttp3.Request
import tachiyomi.core.common.i18n.stringResource
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.core.common.util.lang.withUIContext
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.category.interactor.CreateCategoryWithName
import tachiyomi.domain.category.interactor.GetCategories
import tachiyomi.domain.category.interactor.SetMangaCategories
@ -57,7 +57,7 @@ class FavoritesSyncHelper(val context: Context) {
private val createCategoryWithName: CreateCategoryWithName by injectLazy()
private val updateCategory: UpdateCategory by injectLazy()
private val prefs: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
private val exh by lazy {
Injekt.get<SourceManager>().get(EXH_SOURCE_ID) as? EHentai
@ -90,7 +90,7 @@ class FavoritesSyncHelper(val context: Context) {
private suspend fun beginSync() {
// Check if logged in
if (!prefs.enableExhentai().get()) {
if (!exhPreferences.enableExhentai().get()) {
status.value = FavoritesSyncStatus.SyncError.NotLoggedInSyncError
return
}
@ -138,7 +138,7 @@ class FavoritesSyncHelper(val context: Context) {
status.value = FavoritesSyncStatus.Processing.CalculatingRemoteChanges
val remoteChanges = storage.getChangedRemoteEntries(favorites.first)
val localChanges = if (prefs.exhReadOnlySync().get()) {
val localChanges = if (exhPreferences.exhReadOnlySync().get()) {
null // Do not build local changes if they are not going to be applied
} else {
status.value = FavoritesSyncStatus.Processing.CalculatingLocalChanges
@ -238,7 +238,7 @@ class FavoritesSyncHelper(val context: Context) {
gallery.gid,
)
if (prefs.exhLenientSync().get()) {
if (exhPreferences.exhLenientSync().get()) {
errorList += error
} else {
status.value = error
@ -289,7 +289,7 @@ class FavoritesSyncHelper(val context: Context) {
)
if (!explicitlyRetryExhRequest(10, request)) {
if (prefs.exhLenientSync().get()) {
if (exhPreferences.exhLenientSync().get()) {
errorList += FavoritesSyncStatus.SyncError.GallerySyncError.UnableToDeleteFromRemote
} else {
status.value = FavoritesSyncStatus.SyncError.GallerySyncError.UnableToDeleteFromRemote
@ -392,7 +392,7 @@ class FavoritesSyncHelper(val context: Context) {
)
}
if (prefs.exhLenientSync().get()) {
if (exhPreferences.exhLenientSync().get()) {
errorList += error
} else {
status.value = error

View File

@ -16,14 +16,16 @@ class MangaDexLoginActivity : BaseOAuthLoginActivity() {
val code = data?.getQueryParameter("code")
if (code != null) {
lifecycleScope.launchIO {
Injekt.get<SourceManager>().isInitialized.first { it }
MdUtil.getEnabledMangaDex(Injekt.get())?.login(code)
val sourceManager = Injekt.get<SourceManager>()
sourceManager.isInitialized.first { it }
MdUtil.getEnabledMangaDex(sourceManager = sourceManager)?.login(code)
returnToSettings()
}
} else {
lifecycleScope.launchIO {
Injekt.get<SourceManager>().isInitialized.first { it }
MdUtil.getEnabledMangaDex(Injekt.get())?.logout()
val sourceManager = Injekt.get<SourceManager>()
sourceManager.isInitialized.first { it }
MdUtil.getEnabledMangaDex(sourceManager = sourceManager)?.logout()
returnToSettings()
}
}

View File

@ -13,6 +13,7 @@ import androidx.compose.ui.platform.LocalHapticFeedback
import cafe.adriel.voyager.core.model.rememberScreenModel
import cafe.adriel.voyager.navigator.LocalNavigator
import cafe.adriel.voyager.navigator.currentOrThrow
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.browse.BrowseSourceContent
import eu.kanade.presentation.browse.components.BrowseSourceSimpleToolbar
import eu.kanade.presentation.browse.components.RemoveMangaDialog
@ -26,7 +27,6 @@ import eu.kanade.tachiyomi.ui.manga.MangaScreen
import exh.ui.ifSourcesLoaded
import mihon.presentation.core.util.collectAsLazyPagingItems
import tachiyomi.core.common.util.lang.launchIO
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.sy.SYMR
import tachiyomi.presentation.core.components.material.Scaffold
import tachiyomi.presentation.core.i18n.stringResource
@ -109,7 +109,7 @@ class MangaDexFollowsScreen(private val sourceId: Long) : Screen() {
onOpenManga = { navigator.push(MangaScreen(it.id)) },
onMigrate = {
PreMigrationScreen.navigateToMigration(
Injekt.get<UnsortedPreferences>().skipPreMigration().get(),
Injekt.get<SourcePreferences>().skipPreMigration().get(),
navigator,
it.id,
dialog.manga.id,

View File

@ -17,7 +17,6 @@ import exh.source.getMainSource
import exh.util.dropBlank
import exh.util.floor
import exh.util.nullIfZero
import kotlinx.serialization.encodeToString
import kotlinx.serialization.json.Json
import okhttp3.FormBody
import okhttp3.Headers
@ -26,7 +25,6 @@ import okhttp3.Request
import okhttp3.RequestBody
import okhttp3.RequestBody.Companion.toRequestBody
import org.jsoup.parser.Parser
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.source.service.SourceManager
import uy.kohesive.injekt.Injekt
import uy.kohesive.injekt.api.get
@ -232,9 +230,9 @@ class MdUtil {
return codeVerifier ?: PkceUtil.generateCodeVerifier().also { codeVerifier = it }
}
fun getEnabledMangaDex(preferences: UnsortedPreferences, sourcePreferences: SourcePreferences = Injekt.get(), sourceManager: SourceManager = Injekt.get()): MangaDex? {
fun getEnabledMangaDex(sourcePreferences: SourcePreferences = Injekt.get(), sourceManager: SourceManager = Injekt.get()): MangaDex? {
return getEnabledMangaDexs(sourcePreferences, sourceManager).let { mangadexs ->
preferences.preferredMangaDexId().get().toLongOrNull()?.nullIfZero()
sourcePreferences.preferredMangaDexId().get().toLongOrNull()?.nullIfZero()
?.let { preferredMangaDexId ->
mangadexs.firstOrNull { it.id == preferredMangaDexId }
}

View File

@ -6,9 +6,9 @@ import androidx.compose.runtime.Composable
import androidx.compose.runtime.remember
import androidx.compose.ui.Modifier
import androidx.compose.ui.viewinterop.AndroidView
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.presentation.components.AdaptiveSheet
import eu.kanade.tachiyomi.databinding.RecommendationSearchBottomSheetBinding
import tachiyomi.domain.UnsortedPreferences
import uy.kohesive.injekt.injectLazy
@Composable
@ -30,7 +30,7 @@ fun RecommendationSearchBottomSheetDialog(
}
class RecommendationSearchBottomSheetDialogState(private val onSearchRequest: () -> Unit) {
private val preferences: UnsortedPreferences by injectLazy()
private val preferences: SourcePreferences by injectLazy()
fun initPreferences(binding: RecommendationSearchBottomSheetBinding) {
val flags = preferences.recommendationSearchFlags().get()

View File

@ -6,6 +6,7 @@ import android.os.PowerManager
import androidx.annotation.StringRes
import androidx.core.net.toUri
import eu.kanade.domain.manga.model.toSManga
import eu.kanade.domain.source.service.SourcePreferences
import eu.kanade.tachiyomi.source.CatalogueSource
import eu.kanade.tachiyomi.source.model.SManga
import exh.log.xLog
@ -27,7 +28,6 @@ import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.launch
import mihon.domain.manga.model.toDomainManga
import tachiyomi.data.source.NoResultsException
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.library.model.LibraryManga
import tachiyomi.domain.manga.interactor.GetLibraryManga
import tachiyomi.domain.manga.interactor.NetworkToLocalManga
@ -47,7 +47,7 @@ class RecommendationSearchHelper(val context: Context) {
private val getTracks: GetTracks by injectLazy()
private val networkToLocalManga: NetworkToLocalManga by injectLazy()
private val sourceManager: SourceManager by injectLazy()
private val prefs: UnsortedPreferences by injectLazy()
private val preferences: SourcePreferences by injectLazy()
private var wifiLock: WifiManager.WifiLock? = null
private var wakeLock: PowerManager.WakeLock? = null
@ -70,7 +70,7 @@ class RecommendationSearchHelper(val context: Context) {
}
private suspend fun beginSearch(mangaList: List<Manga>) {
val flags = prefs.recommendationSearchFlags().get()
val flags = preferences.recommendationSearchFlags().get()
val libraryManga = getLibraryManga.await()
val tracks = getTracks.await()
@ -192,7 +192,7 @@ class RecommendationSearchHelper(val context: Context) {
libraryManga: List<LibraryManga>,
tracks: List<Track>,
): List<SManga> {
val flags = prefs.recommendationSearchFlags().get()
val flags = preferences.recommendationSearchFlags().get()
if (!SearchFlags.hasHideLibraryResults(flags)) {
return this

View File

@ -40,8 +40,10 @@ fun RecommendationSearchProgressDialog(
val context = LocalContext.current
val currentView = LocalView.current
DisposableEffect(Unit) {
DisposableEffect(status) {
if (status != SearchStatus.Idle) {
currentView.keepScreenOn = true
}
onDispose {
currentView.keepScreenOn = false
}

View File

@ -8,19 +8,19 @@ import exh.log.maybeInjectEHLogger
import exh.log.xLogD
import exh.source.EH_SOURCE_ID
import exh.source.EXH_SOURCE_ID
import exh.source.ExhPreferences
import okhttp3.FormBody
import okhttp3.OkHttpClient
import okhttp3.Request
import tachiyomi.core.common.i18n.stringResource
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.domain.source.service.SourceManager
import tachiyomi.i18n.sy.SYMR
import uy.kohesive.injekt.injectLazy
import java.util.Locale
class EHConfigurator(val context: Context) {
private val prefs: UnsortedPreferences by injectLazy()
private val sources: SourceManager by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
private val sourceManager: SourceManager by injectLazy()
private val configuratorClient = OkHttpClient.Builder()
.maybeInjectEHLogger()
@ -52,8 +52,8 @@ class EHConfigurator(val context: Context) {
private val EHentai.uconfigUrl get() = baseUrl + UCONFIG_URL
suspend fun configureAll() {
val ehSource = sources.get(EH_SOURCE_ID) as EHentai
val exhSource = sources.get(EXH_SOURCE_ID) as EHentai
val ehSource = sourceManager.get(EH_SOURCE_ID) as EHentai
val exhSource = sourceManager.get(EXH_SOURCE_ID) as EHentai
// Get hath perks
val perksPage = configuratorClient.newCall(
@ -146,13 +146,13 @@ class EHConfigurator(val context: Context) {
}?.removePrefix("hath_perks=")?.substringBefore(';')
if (keyCookie != null) {
prefs.exhSettingsKey().set(keyCookie)
exhPreferences.exhSettingsKey().set(keyCookie)
}
if (sessionCookie != null) {
prefs.exhSessionCookie().set(sessionCookie)
exhPreferences.exhSessionCookie().set(sessionCookie)
}
if (hathPerksCookie != null) {
prefs.exhHathPerksCookies().set(hathPerksCookie)
exhPreferences.exhHathPerksCookies().set(hathPerksCookie)
}
}

View File

@ -1,18 +1,18 @@
package exh.uconfig
import exh.source.ExhPreferences
import okhttp3.FormBody
import tachiyomi.domain.UnsortedPreferences
import uy.kohesive.injekt.injectLazy
import java.util.Locale
class EhUConfigBuilder {
private val preferences: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
fun build(hathPerks: EHHathPerksResponse): FormBody {
val configItems = mutableListOf<ConfigItem>()
configItems += when (
preferences.imageQuality()
exhPreferences.imageQuality()
.get()
.lowercase(Locale.getDefault())
) {
@ -25,19 +25,19 @@ class EhUConfigBuilder {
else -> Entry.ImageSize.AUTO
}
configItems += when (preferences.useHentaiAtHome().get()) {
configItems += when (exhPreferences.useHentaiAtHome().get()) {
2 -> Entry.UseHentaiAtHome.NO
1 -> Entry.UseHentaiAtHome.DEFAULTONLY
else -> Entry.UseHentaiAtHome.ANY
}
configItems += if (preferences.useJapaneseTitle().get()) {
configItems += if (exhPreferences.useJapaneseTitle().get()) {
Entry.TitleDisplayLanguage.JAPANESE
} else {
Entry.TitleDisplayLanguage.DEFAULT
}
configItems += if (preferences.exhUseOriginalImages().get()) {
configItems += if (exhPreferences.exhUseOriginalImages().get()) {
Entry.UseOriginalImages.YES
} else {
Entry.UseOriginalImages.NO
@ -61,13 +61,13 @@ class EhUConfigBuilder {
configItems += Entry.UseMPV()
configItems += Entry.ShowPopularRightNowPane()
configItems += Entry.TagFilteringThreshold(preferences.ehTagFilterValue().get())
configItems += Entry.TagWatchingThreshold(preferences.ehTagWatchingValue().get())
configItems += Entry.TagFilteringThreshold(exhPreferences.ehTagFilterValue().get())
configItems += Entry.TagWatchingThreshold(exhPreferences.ehTagWatchingValue().get())
configItems += Entry.LanguageSystem().getLanguages(preferences.exhSettingsLanguages().get().split("\n"))
configItems += Entry.LanguageSystem().getLanguages(exhPreferences.exhSettingsLanguages().get().split("\n"))
configItems += Entry.Categories().categoryConfigs(
preferences.exhEnabledCategories().get().split(",").map {
exhPreferences.exhEnabledCategories().get().split(",").map {
it.toBoolean()
},
)

View File

@ -6,6 +6,7 @@ import cafe.adriel.voyager.core.model.screenModelScope
import exh.GalleryAddEvent
import exh.GalleryAdder
import exh.log.xLogE
import exh.source.ExhPreferences
import exh.util.trimOrNull
import kotlinx.coroutines.CoroutineExceptionHandler
import kotlinx.coroutines.Dispatchers
@ -14,13 +15,12 @@ import kotlinx.coroutines.flow.update
import kotlinx.coroutines.launch
import tachiyomi.core.common.i18n.stringResource
import tachiyomi.core.common.util.lang.withIOContext
import tachiyomi.domain.UnsortedPreferences
import tachiyomi.i18n.sy.SYMR
import uy.kohesive.injekt.Injekt
import uy.kohesive.injekt.api.get
class BatchAddScreenModel(
private val unsortedPreferences: UnsortedPreferences = Injekt.get(),
private val exhPreferences: ExhPreferences = Injekt.get(),
) : StateScreenModel<BatchAddState>(BatchAddState()) {
private val galleryAdder by lazy { GalleryAdder() }
@ -37,7 +37,7 @@ class BatchAddScreenModel(
private fun addGalleries(context: Context, galleries: String) {
val splitGalleries = if (ehVisitedRegex.containsMatchIn(galleries)) {
val url = if (unsortedPreferences.enableExhentai().get()) {
val url = if (exhPreferences.enableExhentai().get()) {
"https://exhentai.org/g/"
} else {
"https://e-hentai.org/g/"

View File

@ -21,7 +21,7 @@ import eu.kanade.tachiyomi.util.system.WebViewUtil
import eu.kanade.tachiyomi.util.system.toast
import eu.kanade.tachiyomi.util.view.setComposeContent
import exh.log.xLogD
import tachiyomi.domain.UnsortedPreferences
import exh.source.ExhPreferences
import tachiyomi.i18n.MR
import uy.kohesive.injekt.injectLazy
import java.net.HttpCookie
@ -31,7 +31,7 @@ import java.util.Locale
* LoginController
*/
class EhLoginActivity : BaseActivity() {
private val preferenceManager: UnsortedPreferences by injectLazy()
private val exhPreferences: ExhPreferences by injectLazy()
override fun onCreate(savedInstanceState: Bundle?) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.UPSIDE_DOWN_CAKE) {
@ -106,7 +106,7 @@ class EhLoginActivity : BaseActivity() {
} else if (parsedUrl.host.equals("exhentai.org", ignoreCase = true)) {
// At ExHentai, check that everything worked out...
if (applyExHentaiCookies(url, customIgneous)) {
preferenceManager.enableExhentai().set(true)
exhPreferences.enableExhentai().set(true)
setResult(RESULT_OK)
finish()
}
@ -155,9 +155,9 @@ class EhLoginActivity : BaseActivity() {
if (memberId == null || passHash == null || igneous == null) return false
// Update prefs
preferenceManager.memberIdVal().set(memberId!!)
preferenceManager.passHashVal().set(passHash!!)
preferenceManager.igneousVal().set(igneous!!)
exhPreferences.memberIdVal().set(memberId!!)
exhPreferences.passHashVal().set(passHash!!)
exhPreferences.igneousVal().set(igneous!!)
return true
}

View File

@ -50,8 +50,7 @@ class MetadataViewScreen(private val mangaId: Long, private val sourceId: Long)
)
},
) { paddingValues ->
when
(
when (
@Suppress("NAME_SHADOWING")
val state = state
) {

View File

@ -46,4 +46,5 @@ val migrations: List<Migration>
MoveEncryptionSettingsToAppStateMigration(),
TrustExtensionRepositoryMigration(),
CategoryPreferencesCleanupMigration(),
RemoveDuplicateReaderPreferenceMigration(),
)

View File

@ -0,0 +1,26 @@
package mihon.core.migration.migrations
import android.content.SharedPreferences
import androidx.core.content.edit
import mihon.core.migration.Migration
import mihon.core.migration.MigrationContext
import tachiyomi.core.common.util.lang.withIOContext
class RemoveDuplicateReaderPreferenceMigration : Migration {
override val version: Float = 75f
override suspend fun invoke(migrationContext: MigrationContext): Boolean = withIOContext {
val prefs = migrationContext.get<SharedPreferences>() ?: return@withIOContext false
if (prefs.getBoolean("mark_read_dupe", false)) {
val readPrefSet = prefs.getStringSet("mark_duplicate_read_chapter_read", emptySet())?.toMutableSet()
readPrefSet?.add("existing")
prefs.edit {
putStringSet("mark_duplicate_read_chapter_read", readPrefSet)
remove("mark_read_dupe")
}
}
return@withIOContext true
}
}

View File

@ -1,19 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
android:color="?attr/colorControlHighlight">
<item>
<selector>
<item android:state_selected="true">
<color android:color="?attr/colorControlHighlight" />
</item>
<item android:state_activated="true">
<color android:color="?attr/colorControlHighlight" />
</item>
<item>
<color android:color="?android:attr/colorBackground" />
</item>
</selector>
</item>
</ripple>

View File

@ -1,10 +1,15 @@
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
<com.google.android.material.card.MaterialCardView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@drawable/list_item_selector_background">
app:cardBackgroundColor="?android:attr/colorBackground"
app:cardElevation="0dp"
app:cardForegroundColor="@color/draggable_card_foreground">
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<ImageView
android:id="@+id/image"
@ -15,7 +20,7 @@
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:srcCompat="@mipmap/ic_launcher_round" />
app:srcCompat="@drawable/anim_browse_enter" />
<TextView
android:id="@+id/title"
@ -43,4 +48,5 @@
app:srcCompat="@drawable/ic_drag_handle_24dp"
app:tint="?android:attr/textColorHint" />
</androidx.constraintlayout.widget.ConstraintLayout>
</androidx.constraintlayout.widget.ConstraintLayout>
</com.google.android.material.card.MaterialCardView>

View File

@ -206,6 +206,7 @@ object ImageUtil {
LEFT,
}
// SY -->
/**
* Split the image into left and right parts, then merge them into a
* new image with added center padding scaled relative to the height of the display view

View File

@ -89,9 +89,5 @@ class HistoryRepositoryImpl(
logcat(LogPriority.ERROR, throwable = e)
}
}
override suspend fun getByMangaId(mangaId: Long): List<History> {
return handler.awaitList { historyQueries.getHistoryByMangaId(mangaId, HistoryMapper::mapHistory) }
}
// SY <--
}

View File

@ -1,35 +1,16 @@
package tachiyomi.domain
package exh.source
import tachiyomi.core.common.preference.Preference
import tachiyomi.core.common.preference.PreferenceStore
class UnsortedPreferences(
class ExhPreferences(
private val preferenceStore: PreferenceStore,
) {
// SY -->
fun migrateFlags() = preferenceStore.getInt("migrate_flags", Int.MAX_VALUE)
fun defaultMangaOrder() = preferenceStore.getString("default_manga_order", "")
fun migrationSources() = preferenceStore.getString("migrate_sources", "")
fun smartMigration() = preferenceStore.getBoolean("smart_migrate", false)
fun useSourceWithMost() = preferenceStore.getBoolean("use_source_with_most", false)
fun skipPreMigration() = preferenceStore.getBoolean(Preference.appStateKey("skip_pre_migration"), false)
fun hideNotFoundMigration() = preferenceStore.getBoolean("hide_not_found_migration", false)
fun showOnlyUpdatesMigration() = preferenceStore.getBoolean("show_only_updates_migration", false)
fun recommendationSearchFlags() = preferenceStore.getInt("rec_search_flags", Int.MAX_VALUE)
fun isHentaiEnabled() = preferenceStore.getBoolean("eh_is_hentai_enabled", true)
fun enableExhentai() = preferenceStore.getBoolean(Preference.privateKey("enable_exhentai"), false)
fun enableExhentai() = preferenceStore.getBoolean(Preference.Companion.privateKey("enable_exhentai"), false)
fun imageQuality() = preferenceStore.getString("ehentai_quality", "auto")
@ -44,15 +25,15 @@ class UnsortedPreferences(
fun ehTagWatchingValue() = preferenceStore.getInt("eh_tag_watching_value", 0)
// EH Cookies
fun memberIdVal() = preferenceStore.getString(Preference.privateKey("eh_ipb_member_id"), "")
fun memberIdVal() = preferenceStore.getString(Preference.Companion.privateKey("eh_ipb_member_id"), "")
fun passHashVal() = preferenceStore.getString(Preference.privateKey("eh_ipb_pass_hash"), "")
fun igneousVal() = preferenceStore.getString(Preference.privateKey("eh_igneous"), "")
fun ehSettingsProfile() = preferenceStore.getInt(Preference.privateKey("eh_ehSettingsProfile"), -1)
fun exhSettingsProfile() = preferenceStore.getInt(Preference.privateKey("eh_exhSettingsProfile"), -1)
fun exhSettingsKey() = preferenceStore.getString(Preference.privateKey("eh_settingsKey"), "")
fun exhSessionCookie() = preferenceStore.getString(Preference.privateKey("eh_sessionCookie"), "")
fun exhHathPerksCookies() = preferenceStore.getString(Preference.privateKey("eh_hathPerksCookie"), "")
fun passHashVal() = preferenceStore.getString(Preference.Companion.privateKey("eh_ipb_pass_hash"), "")
fun igneousVal() = preferenceStore.getString(Preference.Companion.privateKey("eh_igneous"), "")
fun ehSettingsProfile() = preferenceStore.getInt(Preference.Companion.privateKey("eh_ehSettingsProfile"), -1)
fun exhSettingsProfile() = preferenceStore.getInt(Preference.Companion.privateKey("eh_exhSettingsProfile"), -1)
fun exhSettingsKey() = preferenceStore.getString(Preference.Companion.privateKey("eh_settingsKey"), "")
fun exhSessionCookie() = preferenceStore.getString(Preference.Companion.privateKey("eh_sessionCookie"), "")
fun exhHathPerksCookies() = preferenceStore.getString(Preference.Companion.privateKey("eh_hathPerksCookie"), "")
fun exhShowSyncIntro() = preferenceStore.getBoolean("eh_show_sync_intro", true)
@ -68,7 +49,7 @@ class UnsortedPreferences(
fun exhAutoUpdateRequirements() = preferenceStore.getStringSet("eh_auto_update_restrictions", emptySet())
fun exhAutoUpdateStats() = preferenceStore.getString(Preference.appStateKey("eh_auto_update_stats"), "")
fun exhAutoUpdateStats() = preferenceStore.getString(Preference.Companion.appStateKey("eh_auto_update_stats"), "")
fun exhWatchedListDefaultState() = preferenceStore.getBoolean("eh_watched_list_default_state", false)
@ -86,13 +67,4 @@ class UnsortedPreferences(
)
fun enhancedEHentaiView() = preferenceStore.getBoolean("enhanced_e_hentai_view", true)
fun preferredMangaDexId() = preferenceStore.getString("preferred_mangaDex_id", "0")
fun mangadexSyncToLibraryIndexes() = preferenceStore.getStringSet(
"pref_mangadex_sync_to_library_indexes",
emptySet(),
)
fun allowLocalSourceHiddenFolders() = preferenceStore.getBoolean("allow_local_source_hidden_folders", false)
}

View File

@ -1,13 +0,0 @@
package tachiyomi.domain.history.interactor
import tachiyomi.domain.history.model.History
import tachiyomi.domain.history.repository.HistoryRepository
class GetHistoryByMangaId(
private val repository: HistoryRepository,
) {
suspend fun await(mangaId: Long): List<History> {
return repository.getByMangaId(mangaId)
}
}

View File

@ -25,7 +25,5 @@ interface HistoryRepository {
// SY -->
suspend fun upsertHistory(historyUpdates: List<HistoryUpdate>)
suspend fun getByMangaId(mangaId: Long): List<History>
// SY <--
}

View File

@ -1,5 +1,5 @@
[versions]
compose-bom = "2025.05.00"
compose-bom = "2025.05.01"
[libraries]
activity = "androidx.activity:activity-compose:1.10.1"

View File

@ -1,14 +1,14 @@
[versions]
kotlin_version = "2.1.20"
kotlin_version = "2.1.21"
serialization_version = "1.8.1"
xml_serialization_version = "0.91.0"
xml_serialization_version = "0.91.1"
[libraries]
reflect = { module = "org.jetbrains.kotlin:kotlin-reflect", version.ref = "kotlin_version" }
gradle = { module = "org.jetbrains.kotlin:kotlin-gradle-plugin", version.ref = "kotlin_version" }
compose-compiler-gradle = { module = "org.jetbrains.kotlin:compose-compiler-gradle-plugin", version.ref = "kotlin_version" }
immutables = { module = "org.jetbrains.kotlinx:kotlinx-collections-immutable", version = "0.3.8" }
immutables = { module = "org.jetbrains.kotlinx:kotlinx-collections-immutable", version = "0.4.0" }
coroutines-bom = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-bom", version = "1.10.2" }
coroutines-core = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-core" }

View File

@ -8,7 +8,7 @@ sqldelight = "2.0.2"
sqlite = "2.5.1"
voyager = "1.1.0-beta03"
spotless = "7.0.3"
ktlint-core = "1.5.0"
ktlint-core = "1.6.0"
firebase-bom = "33.13.0"
markdown = "0.34.0"
@ -42,7 +42,7 @@ preferencektx = "androidx.preference:preference-ktx:1.2.1"
injekt = "com.github.null2264:injekt-koin:ee267b2e27"
coil-bom = { module = "io.coil-kt.coil3:coil-bom", version = "3.1.0" }
coil-bom = { module = "io.coil-kt.coil3:coil-bom", version = "3.2.0" }
coil-core = { module = "io.coil-kt.coil3:coil" }
coil-gif = { module = "io.coil-kt.coil3:coil-gif" }
coil-compose = { module = "io.coil-kt.coil3:coil-compose" }

View File

@ -10,7 +10,7 @@ composeRatingbar = "com.github.a914-gowtham:compose-ratingbar:1.2.3"
versionsx = "com.github.ben-manes:gradle-versions-plugin:0.51.0"
sqlcipher = "net.zetetic:sqlcipher-android:4.8.0"
sqlcipher = "net.zetetic:sqlcipher-android:4.9.0"
exifinterface = "androidx.exifinterface:exifinterface:1.3.7"

View File

@ -1,6 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.14-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.14.1-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME

View File

@ -80,4 +80,60 @@
<item quantity="many">منذُ %1$d دقيقة</item>
<item quantity="other">منذُ %1$d دقيقة</item>
</plurals>
<plurals name="pref_tag_sorting_desc">
<item quantity="zero">العلامات في هذه القائمة . تعطيك خيار الترتيب حسب الأولوية في هذه القائمة، مما يعني أن المدخلات سيتم توزيعها حسب اختيارك</item>
<item quantity="one">هاذا الخيار يعطيك إمكانية فرز المدخلات في هذه القائمة حسب اختيارك</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
<plurals name="num_lock_times">
<item quantity="zero">وقت الإنغلاق</item>
<item quantity="one">‬وقت الإغلاق</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
<plurals name="migrate_entry">
<item quantity="zero">ترحيل ....... المدخل؟</item>
<item quantity="one">نقل ...... المدخلات؟</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
<plurals name="humanize_month">
<item quantity="zero">%1$d شهر مضى</item>
<item quantity="one">%1$dشهور مضت</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
<plurals name="browse_language_and_pages">
<item quantity="zero">....،.... الصفحة</item>
<item quantity="one">.....،... الصفحات</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
<plurals name="humanize_year">
<item quantity="zero">...... سنة مضت</item>
<item quantity="one">..... سنوات مضت</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
<plurals name="humanize_week">
<item quantity="zero">"%1$d اسبوع الفائت"</item>
<item quantity="one">%1$d اسابيع الماضية</item>
<item quantity="two"></item>
<item quantity="few"></item>
<item quantity="many"></item>
<item quantity="other"></item>
</plurals>
</resources>

View File

@ -537,4 +537,71 @@
<string name="favorites_sync_processing_throttle">٪1$s\n\nيتم اختناق المزامنة حاليا (لتجنب حظرها من ExHentai) وقد يستغرق وقتا طويلا حتى يكتمل.</string>
<string name="favorites_sync_notes">ملاحظات مزامنة المفضلة الهامة</string>
<string name="eh_batch_add_finish">إنهاء</string>
<string name="favorites_sync_failed_to_add_to_local_error">\'%1$s\'%2$s</string>
<string name="rating9">رائع</string>
<string name="relation_alternate_story">قصة بديلة</string>
<string name="similar_titles">عناوين متشابهة</string>
<string name="mangadex_preffered_source">مصدر MangaDex المفضل</string>
<string name="mangadex_sync_follows_to_library">مزامنة مدخلات MangaDex في مكتبتك</string>
<string name="rating6">حسنا</string>
<string name="mangadex_push_favorites_to_mangadex">مزامنة إدخالات المكتبة مع MangaDex</string>
<string name="similar">مشابه ل%1$s</string>
<string name="relation_same_franchise">نفس الامتياز</string>
<string name="humanize_fallback">لحظات مضت</string>
<string name="random">عشوائي</string>
<string name="western">غرب</string>
<string name="could_not_open_entry">لا يمكن فتح هادا الإدخال:\n\n%1$s</string>
<string name="relation_based_on">مبني على</string>
<string name="relation_adapted_from">مأخود من</string>
<string name="game_cg">لعبة</string>
<string name="total_ratings">التقييم الكلي</string>
<string name="fetch_chapter_updates">البحث عن تحديثات الفصول</string>
<string name="no_dedupe">لا تكرار</string>
<string name="deduplication_mode">وضع إزالة التكرار:</string>
<string name="mangadex_add_to_follows">اضافة تتبع ل MangaDex</string>
<string name="mangadex_preffered_source_summary">قم بتعيين مصدر MangaDex الذي اخترته، وسيتم استخدامه للتتبع ومجموعة من الميزات الأخرى في التطبيق</string>
<string name="mangadex_sync_follows_to_library_summary">نقل إدخالات MangaDex إلى مكتبتك إذا لم تتم إضافتها بالفعل.</string>
<string name="mangadex_follows">متابعة MangaDex</string>
<string name="alt_titles">عناوين بديلة</string>
<string name="community_recommendations">اقتراحات المجتمع</string>
<string name="relation_similar">مشابه</string>
<string name="relation_shared_universe">كون مشترك</string>
<string name="relation_colored">ملون</string>
<string name="include_all_read_entries">يتضمن كل ما تم قرائته</string>
<string name="scan_qr_code">امسح الرمز</string>
<string name="error_with_reason">خطأ:%1$s</string>
<string name="launching_app">فتح التطبيق…</string>
<string name="rating8">رائع</string>
<string name="page_preview_page_go_to">ادخل إلى</string>
<string name="rating2">مؤلم</string>
<string name="no_rating">لا تقييم</string>
<string name="artist_cg">‬الفنان</string>
<string name="genre">النوع</string>
<string name="merged_toggle_download_chapters_error">خطأ في تنزيل الفصول</string>
<string name="merged_references_invalid">اندماج المراجع غير صالح</string>
<string name="dedupe_priority">إزالة التكرار حسب الأولوية</string>
<string name="allow_deduplication">سماح بالتكرار:</string>
<string name="dedupe_highest_chapter">اضهار المصدر صاحب أعلى عدد من الفصول</string>
<string name="dedupe_most_chapters">اضهار المصدر مع اكثر الفصول</string>
<string name="relation_preserialization">التسلسل المسبق</string>
<string name="rating0">كارثة</string>
<string name="deduplication_entry_info">معلومات عن الإدخال:</string>
<string name="merged_chapter_updates_error">خطأ تبديل تحديثات الفصل</string>
<string name="ignore_non_library_entries">تجاهل المدخلات التي لا تنتمي إلى الكتبة</string>
<string name="md_follows_unfollowed">إزالة المتابعة</string>
<string name="rating7">جيد</string>
<string name="loading_entry">جاري التحميل…</string>
<string name="rating4">سيئ</string>
<string name="page_previews">الصفحة السابقة</string>
<string name="misc">موسيقى</string>
<string name="video">‬فيديو</string>
<string name="more_info">المزيد من المعلومات</string>
<string name="alt_title">عنوان اضافي</string>
<string name="relation_side_story">قصة جانبية</string>
<string name="relation_main_story">القصة الأساسية</string>
<string name="relation_monochrome">أحادي اللون</string>
<string name="relation_sequel">تتمة</string>
<string name="relation_prequel">مقدمة</string>
<string name="relation_alternate_version">النسخ البديلة</string>
<string name="relation_serialization">التسلسل</string>
</resources>

View File

@ -628,4 +628,5 @@
<string name="rec_hide_library_entries">Ocultar elementos que ya estén en la biblioteca</string>
<string name="pref_tracker_resolve_using_source_metadata_summary">Encuentra el título automáticamente si la fuente ya enlaza con el servicio de seguimiento. De momento solo funciona en MangaDex</string>
<string name="pref_tracker_resolve_using_source_metadata">Elegir títulos a través de los metadatos de la fuente</string>
<string name="scan_qr_code">Escanear un código QR</string>
</resources>

View File

@ -646,4 +646,5 @@
<string name="rec_processing_state">Pinoprosesong entry %1$d ng %2$d</string>
<string name="rec_collecting">Nangongolekta ng mga rekomendasyon</string>
<string name="rec_initializing">Sinisimulan</string>
<string name="scan_qr_code">Mag-scan ng QR code</string>
</resources>

View File

@ -159,7 +159,7 @@
<string name="library_group_updates_all_but_ungrouped">Jalankan pembaruan global hanya untuk yang tidak dikelompokkan, pembaruan kategori untuk yang lainnya</string>
<string name="library_group_updates_all">Hanya jalankan pembaruan kategori</string>
<!-- Browse settings -->
<string name="pref_source_source_filtering">Filter Sumber dalam kategori</string>
<string name="pref_source_source_filtering">Filter sumber dalam kategori</string>
<string name="pref_source_source_filtering_summery">Saring sumber-sumber yang ada dalam kategori, agar sumber-sumber tersebut tidak dimasukkan ke dalam kategori bahasa jika berada dalam suatu kategori</string>
<string name="pref_source_navigation">Ganti tombol Terbaru</string>
<string name="pref_source_navigation_summery">Ganti tombol Terbaru dengan tampilan penelusuran khusus yang mencakup bab terbaru dan daftar manga</string>
@ -539,7 +539,7 @@
<string name="pref_library_mark_duplicate_chapters">Tandai bagian baru yang sudah terbaca sebagai terbaca</string>
<string name="update_3hour">Setiap 3 jam</string>
<string name="label_triggers">Pemicu</string>
<string name="sync_complete">Berhasil Menyinkronkan perpustakaan</string>
<string name="sync_complete">Berhasil menyinkronkan perpustakaan</string>
<string name="label_sync">Sinkronisasi</string>
<string name="pref_sync_host">Host</string>
<string name="pref_sync_host_summ">Masukkan alamat host untuk menyinkronkan perpustakaan Anda</string>
@ -668,4 +668,5 @@
<string name="rec_processing_state">Memproses entri %1$d dari %2$d</string>
<string name="rec_collecting">Mengumpulkan rekomendasi</string>
<string name="rec_initializing">Inisialisasi</string>
<string name="scan_qr_code">Pindai kode QR</string>
</resources>

View File

@ -142,7 +142,7 @@
<string name="wsrv">wsrv.nl</string>
<string name="bandwidth_data_saver_server">Bandwidth Hero Proxy Server</string>
<string name="data_saver_server_summary">ここに Bandwidth Hero Proxy server のurlを入力して下さい</string>
<string name="clear_db_exclude_read">既読の章がある作品を保留</string>
<string name="clear_db_exclude_read">既読の章がある作品は保持</string>
<!-- Log Level -->
<string name="log_minimal">最小</string>
<string name="log_extra">最大</string>

View File

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<plurals name="cleanup_done">
<item quantity="other">ရှင်းလင်းမှုပြီးပါပြီ။ %d ဖိုင်တွဲကို ဖယ်ရှားခဲ့သည်။</item>
</plurals>
</resources>

View File

@ -42,4 +42,5 @@
<string name="tag_filtering_threshhold_error">-9999 र 0 को बीचमा हुनुपर्छ!</string>
<string name="artist">कलाकार</string>
<string name="author">लेखक</string>
<string name="clear_db_exclude_read">अध्याय पढिएका इन्ट्रीहरू राख्नुहोस्</string>
</resources>

View File

@ -634,4 +634,22 @@
<string name="delete_tag">Excluir tag</string>
<string name="too_many_in_feed">Muitas fontes no seu feed, não é possível adicionar mais de 10</string>
<string name="action_stop">Parar</string>
<string name="rec_services_to_search">Serviços de recomendação para busca</string>
<string name="rec_hide_library_entries">Ocultar resultados já existentes em sua biblioteca</string>
<string name="scan_qr_code">Escanear um código QR</string>
<string name="rec_search">Encontre recomendações comuns</string>
<string name="rec_group_source">Recomendações de fontes</string>
<string name="rec_group_tracker">Recomendações do rastreador</string>
<string name="rec_common_recommendations">Recomendações comuns</string>
<string name="rec_search_short">Encontre recomendações</string>
<string name="rec_error_title">Falha na busca</string>
<string name="rec_error_string">Ocorreu um erro durante o processo de busca: %1$s</string>
<string name="rec_collecting">Coletando recomendações</string>
<string name="rec_initializing">Inicializando</string>
<string name="similar_titles">Títulos similares</string>
<string name="relation_sequel">Sequência</string>
<string name="feed">Feed</string>
<string name="rec_no_results">Nenhuma recomendação encontrada</string>
<string name="failed_merge">Falha ao mesclar a entrada: %1$s</string>
<string name="select_tracker">Selecione um rastreador</string>
</resources>

View File

@ -261,7 +261,7 @@
<string name="download_threads">Потоки загрузки</string>
<string name="download_threads_summary">Более высокие значения могут значительно ускорить загрузку изображений, но также могут спровоцировать блокировку источников для TachiyomiSY. Рекомендуемое значение - 2 или 3. Текущее значение: %s</string>
<string name="aggressively_load_pages">Агрессивная загрузка страниц</string>
<string name="aggressively_load_pages_summary">Медленно загружать всю главу во время чтения вместо загрузки в текущий момент просматреваемых страниц</string>
<string name="aggressively_load_pages_summary">Медленно загружать всю главу во время чтения вместо загрузки в текущий момент просматреваемых страниц.</string>
<string name="skip_queue_on_retry">Пропускать очередь при повторной попытке</string>
<string name="skip_queue_on_retry_summary">Обычно нажатие кнопки «Повторить» при неудачной загрузке будет ждать, пока загрузчик закончит загрузку последней страницы, прежде чем начать перезагрузку неудачной страницы. Включение этого режима заставит загрузчик немедленно начать перезагрузку неудачной страницы, как только будет нажата кнопка «Повторить».</string>
<string name="reader_preload_amount">Количество страниц с предзагрузкой</string>
@ -671,7 +671,7 @@
<string name="alt_titles">Альт. названия</string>
<string name="select_tracker">Выбрать сервис отслеживания</string>
<string name="fill_from_tracker">Заполнить из сервиса</string>
<string name="entry_not_tracked">Введённая запись не является сервисом отслеживания</string>
<string name="entry_not_tracked">Введённая запись не является сервисом отслеживания.</string>
<string name="favorites_sync_unable_to_add_to_remote">Невозможно добавить галерею на удалённый сервер: \'%1$s\' (GID: %2$s)!</string>
<string name="similar_titles">Похожие имена</string>
<string name="rec_hide_library_entries">Скрыть серии которые находятся в библиотеке</string>
@ -689,4 +689,5 @@
<string name="rec_search">Найти общие рекомендации</string>
<string name="rec_initializing">Идёт подготовка</string>
<string name="rec_common_recommendations">Общие рекомендации</string>
<string name="scan_qr_code">Сканировать QR-код</string>
</resources>

View File

@ -62,7 +62,7 @@
<string name="pref_enhanced_e_hentai_view_summary">E/ExHentai için gelişmiş arama menüsü modunu açın/kapatın</string>
<string name="favorites_sync">E-Hentai Favorileri eşitleme</string>
<string name="disable_favorites_uploading">Favorilerin gönderilmesini kapat</string>
<string name="disable_favorites_uploading_summary">Favoriler yalnızca ExHentai üzerinden indirilir. Uygulama favorilere yapılan değişiklikler gönderilmeyecektir. ExHentai üzerinde favorilerin yanlışlıkla kaybolmasını önler. Silinenlerin yine de indirileceğini unutmayın (ExHentai üzerinde bir favoriyi silersemiz uygulamada da silinecektir).</string>
<string name="disable_favorites_uploading_summary">Favoriler yalnızca ExHentai üzerinden indirilir. Uygulamada favorilere yapılan değişiklikler gönderilmeyecektir. ExHentai üzerinde favorilerin yanlışlıkla kaybolmasını önler. Silinenlerin yine de indirileceğini unutmayın (ExHentai üzerinde bir favoriyi silerseniz uygulamada da silinecektir).</string>
<string name="show_favorite_sync_notes">Favorilerin eşitleme notlarını göster</string>
<string name="show_favorite_sync_notes_summary">Favori eşitleme özelliği ile ilgili çeşitli bilgiler gösterir</string>
<string name="please_login">Lütfen giriş yapın!</string>
@ -112,7 +112,7 @@
<string name="log_level_summary">Bunu değiştirmek uygulama performansını etkileyebilir. Değiştirdikten sonra uygulamayı yeniden başlatın. Şu anki değer: %s</string>
<string name="enable_source_blacklist">Kaynak kara listesini etkinleştir</string>
<string name="enable_source_blacklist_summary">%1$s ile uyumsuz uzantıları/kaynakları gizle. Değiştirdikten sonra uygulamayı yeniden başlatın.</string>
<string name="open_debug_menu_summary"><![CDATA[NE YAPTIĞINIZI BİLMİYORSANIZ BU MENÜYE DOKUNMAYIN! <font color=\'red\'>KİTAPLIPINIZI KULLANILMAZ YAPABİLİR!</font>]]></string>
<string name="open_debug_menu_summary"><![CDATA[NE YAPTIĞINIZI BİLMİYORSANIZ BU MENÜYE DOKUNMAYIN! <font color=\'red\'>KİTAPLIĞINIZI KULLANILMAZ YAPABİLİR!</font>]]></string>
<string name="starting_cleanup">Temizleme başlatılıyor</string>
<string name="delete_unused_chapters">Var olmayan, yarım yüklenmiş veya okunmuş bölümleri silin</string>
<string name="no_folders_to_cleanup">Temizlenecek klasör yok</string>
@ -261,7 +261,7 @@
<string name="reader_preload_amount_16_pages">16 sayfa</string>
<string name="reader_preload_amount_20_pages">20 sayfa</string>
<string name="reader_cache_size">Okuyucu önbellek boyutu</string>
<string name="reader_cache_size_summary">Okurken cihazda kaydedilecek görsel sayısı. Daha yüksek değerler daha rahat bir okuma deneyimi sağlar ancak kullanılan disk alanını artırır</string>
<string name="reader_cache_size_summary">Okurken cihazda kaydedilecek görsel miktarı. Daha yüksek değerler daha rahat bir okuma deneyimi sağlar ancak kullanılan disk alanını artırır</string>
<string name="preserve_reading_position">Okunmuş girdilerde okuma konumunu koru</string>
<string name="auto_webtoon_mode">Otomatik Webtoon Modu</string>
<string name="auto_webtoon_mode_summary">Muhtemelen uzun şerit formatını kullandığı algılanan girdiler için otomatik webtoon modunu kullan</string>
@ -619,4 +619,5 @@
<string name="rec_processing_state">%2$d girdiden %1$d. girdi işleniyor</string>
<string name="rec_collecting">Öneriler toplanıyor</string>
<string name="rec_initializing">Başlatılıyor</string>
<string name="scan_qr_code">QR kod tarayın</string>
</resources>

View File

@ -39,7 +39,7 @@ dependencyResolutionManagement {
}
plugins {
id("org.gradle.toolchains.foojay-resolver-convention") version "0.10.0"
id("org.gradle.toolchains.foojay-resolver-convention") version "1.0.0"
}
enableFeaturePreview("TYPESAFE_PROJECT_ACCESSORS")

View File

@ -28,6 +28,7 @@ class NHentaiSearchMetadata : RaisedSearchMetadata() {
var favoritesCount: Long? = null
var mediaId: String? = null
var mediaServer: Int? = null
var japaneseTitle by titleDelegate(TITLE_TYPE_JAPANESE)
var englishTitle by titleDelegate(TITLE_TYPE_ENGLISH)
@ -46,7 +47,7 @@ class NHentaiSearchMetadata : RaisedSearchMetadata() {
val cover = if (mediaId != null) {
typeToExtension(coverImageType)?.let {
"https://t1.nhentai.net/galleries/$mediaId/cover.$it"
"https://t${mediaServer ?: 1}.nhentai.net/galleries/$mediaId/cover.$it"
}
} else {
null