Ensure PageLoader cache sync
This commit is contained in:
1 parent
eff5467ccf
commit
e8c4b9ab78
4 files changed
+31
-34
No files matched your search
@@ -60,6 +60,7 @@ import com.hippo.ehviewer.util.AppConfig
|
||||
import com.hippo.ehviewer.util.CrashHandler
|
||||
import com.hippo.ehviewer.util.FavouriteStatusRouter
|
||||
import com.hippo.ehviewer.util.FileUtils
|
||||
import com.hippo.ehviewer.util.OSUtils
|
||||
import com.hippo.ehviewer.util.isAtLeastO
|
||||
import com.hippo.ehviewer.util.isAtLeastP
|
||||
import com.hippo.ehviewer.util.isAtLeastS
|
||||
@@ -107,7 +108,8 @@ class EhApplication :
|
||||
launchUI { FavouriteStatusRouter.collect { (gid, slot) -> detailCache[gid]?.favoriteSlot = slot } }
|
||||
launch { EhTagDatabase }
|
||||
launch { EhDB }
|
||||
dataStateFlow.value
|
||||
launchIO { dataStateFlow.value }
|
||||
launchIO { OSUtils.totalMemory }
|
||||
launch {
|
||||
if (DownloadManager.labelList.isNotEmpty() && Settings.downloadFilterMode.key !in Settings.prefs) {
|
||||
Settings.downloadFilterMode.value = DownloadsFilterMode.CUSTOM.flag
|
||||
@@ -118,13 +120,9 @@ class EhApplication :
|
||||
FileUtils.cleanupDirectory(AppConfig.externalCrashDir)
|
||||
FileUtils.cleanupDirectory(AppConfig.externalParseErrorDir)
|
||||
}
|
||||
launch {
|
||||
cleanupDownload()
|
||||
}
|
||||
launch { cleanupDownload() }
|
||||
if (Settings.requestNews) {
|
||||
launch {
|
||||
checkDawn()
|
||||
}
|
||||
launch { checkDawn() }
|
||||
}
|
||||
}
|
||||
if (BuildConfig.DEBUG) {
|
||||
|
||||
@@ -13,6 +13,7 @@ import com.hippo.ehviewer.Settings
|
||||
import com.hippo.ehviewer.image.hasQrCode
|
||||
import eu.kanade.tachiyomi.util.system.logcat
|
||||
import moe.tarsin.coroutines.runSuspendCatching
|
||||
import moe.tarsin.kt.sync
|
||||
|
||||
private val detectQrCodeKey = Extras.Key(default = false)
|
||||
|
||||
@@ -33,7 +34,7 @@ object QrCodeInterceptor : Interceptor {
|
||||
if (image is BitmapImageWithExtraInfo) {
|
||||
fun compute() = runSuspendCatching { hasQrCode(image.image.bitmap) }.onFailure { logcat(it) }.getOrThrow()
|
||||
val hasQrCode = when (val key = result.memoryCacheKey) {
|
||||
is MemoryCache.Key -> synchronized(cache) { cache[key] } ?: compute().also { synchronized(cache) { cache[key] = it } }
|
||||
is MemoryCache.Key -> cache.sync { cache[key] } ?: compute().also { cache.sync { cache[key] = it } }
|
||||
null -> compute()
|
||||
}
|
||||
val new = image.copy(hasQrCode = hasQrCode)
|
||||
|
||||
@@ -6,32 +6,30 @@ import com.hippo.ehviewer.Settings
|
||||
import com.hippo.ehviewer.image.Image
|
||||
import com.hippo.ehviewer.util.OSUtils
|
||||
import com.hippo.ehviewer.util.isAtLeastO
|
||||
import eu.kanade.tachiyomi.util.lang.withIOContext
|
||||
import kotlinx.coroutines.flow.MutableStateFlow
|
||||
import kotlinx.coroutines.flow.update
|
||||
import moe.tarsin.kt.sync
|
||||
|
||||
private const val MAX_CACHE_SIZE = 512 * 1024 * 1024
|
||||
private const val MIN_CACHE_SIZE = 128 * 1024 * 1024
|
||||
|
||||
abstract class PageLoader {
|
||||
private val cache by lazy {
|
||||
SieveCache<Int, Image>(
|
||||
maxSize = if (isAtLeastO) {
|
||||
(OSUtils.totalMemory / 16).toInt().coerceIn(MIN_CACHE_SIZE, MAX_CACHE_SIZE)
|
||||
private val cache = SieveCache<Int, Image>(
|
||||
maxSize = if (isAtLeastO) {
|
||||
(OSUtils.totalMemory / 16).toInt().coerceIn(MIN_CACHE_SIZE, MAX_CACHE_SIZE)
|
||||
} else {
|
||||
(OSUtils.appMaxMemory / 3 * 2).toInt()
|
||||
},
|
||||
sizeOf = { _, v -> v.allocationSize.toInt() },
|
||||
onEntryRemoved = { k, o, n, _ ->
|
||||
if (o.isRecyclable) {
|
||||
n ?: notifyPageWait(k)
|
||||
o.recycle()
|
||||
} else {
|
||||
(OSUtils.appMaxMemory / 3 * 2).toInt()
|
||||
},
|
||||
sizeOf = { _, v -> v.allocationSize.toInt() },
|
||||
onEntryRemoved = { k, o, n, _ ->
|
||||
if (o.isRecyclable) {
|
||||
n ?: notifyPageWait(k)
|
||||
o.recycle()
|
||||
} else {
|
||||
o.isRecyclable = true
|
||||
}
|
||||
},
|
||||
)
|
||||
}
|
||||
o.isRecyclable = true
|
||||
}
|
||||
},
|
||||
)
|
||||
|
||||
val pages by lazy {
|
||||
check(size > 0)
|
||||
@@ -41,10 +39,7 @@ abstract class PageLoader {
|
||||
private val prefetchPageCount = Settings.preloadImage
|
||||
|
||||
@CallSuper
|
||||
open suspend fun awaitReady(): Boolean {
|
||||
withIOContext { cache }
|
||||
return true
|
||||
}
|
||||
open suspend fun awaitReady() = true
|
||||
|
||||
abstract val isReady: Boolean
|
||||
|
||||
@@ -53,11 +48,11 @@ abstract class PageLoader {
|
||||
|
||||
@CallSuper
|
||||
open fun stop() {
|
||||
cache.evictAll()
|
||||
cache.sync { evictAll() }
|
||||
}
|
||||
|
||||
fun restart() {
|
||||
cache.evictAll()
|
||||
cache.sync { evictAll() }
|
||||
pages.forEach(Page::reset)
|
||||
}
|
||||
|
||||
@@ -66,7 +61,7 @@ abstract class PageLoader {
|
||||
private var lastRequestIndex = -1
|
||||
|
||||
fun request(index: Int) {
|
||||
val image = cache[index]
|
||||
val image = cache.sync { cache[index] }
|
||||
if (image != null) {
|
||||
notifyPageSucceed(index, image, false)
|
||||
} else {
|
||||
@@ -125,7 +120,7 @@ abstract class PageLoader {
|
||||
|
||||
fun notifyPageSucceed(index: Int, image: Image, replaceCache: Boolean = true) {
|
||||
if (replaceCache) {
|
||||
cache.put(index, image)
|
||||
cache.sync { cache[index] = image }
|
||||
}
|
||||
pages[index].statusFlow.update { if (image.hasQrCode) PageStatus.Blocked(image) else PageStatus.Ready(image) }
|
||||
}
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
package moe.tarsin.kt
|
||||
|
||||
inline fun <T : Any, R> T.sync(block: T.() -> R) = synchronized(this) { block(this) }
|
||||
Reference in new issue
Block a user