HapeLee 5 месяцев назад
Родитель
Сommit
8d12e03113
1 измененных файлов с 13 добавлено и 3 удалено
  1. 13 3
      app/src/main/java/io/legado/app/ui/config/PrefDelegate.kt

+ 13 - 3
app/src/main/java/io/legado/app/ui/config/PrefDelegate.kt

@@ -19,6 +19,7 @@ import io.legado.app.utils.putPrefStringSync
 import io.legado.app.help.config.DsSync
 import androidx.datastore.preferences.core.*
 import io.legado.app.data.repository.dataStore
+import kotlinx.coroutines.CompletableDeferred
 import kotlinx.coroutines.CoroutineScope
 import kotlinx.coroutines.Dispatchers
 import kotlinx.coroutines.Job
@@ -28,6 +29,7 @@ import kotlinx.coroutines.flow.distinctUntilChanged
 import kotlinx.coroutines.flow.first
 import kotlinx.coroutines.flow.map
 import kotlinx.coroutines.launch
+import kotlinx.coroutines.withContext
 import splitties.init.appCtx
 import java.io.IOException
 import kotlin.properties.ReadWriteProperty
@@ -35,11 +37,13 @@ import kotlin.reflect.KProperty
 
 interface PrefDelegate<T> : ReadWriteProperty<Any?, T> {
     val state: State<T>
+    val ready: CompletableDeferred<Unit>
     fun dispose()
 }
 
 class PrefStateDelegate<T>(private val delegate: PrefDelegate<T>) : ReadWriteProperty<Any?, T> by delegate {
     val state: State<T> get() = delegate.state
+    val ready: CompletableDeferred<Unit> get() = delegate.ready
 }
 
 fun <T> prefDelegate(
@@ -54,14 +58,19 @@ fun <T> prefDelegate(
         override val state: State<T> get() = _value
         private val scope = CoroutineScope(Dispatchers.IO)
         private var dsObserverJob: Job? = null
+        override val ready = CompletableDeferred<Unit>()
 
         init {
             // 从 DataStore 读取初始值(DS 为唯一读取源)
+            // 在 IO 线程读取,切换到 Main 线程更新 MutableState,确保 snapshotFlow 能检测到变化
             scope.launch {
                 val dsValue = readFromDs()
                 if (dsValue != null) {
-                    _value.value = dsValue
+                    withContext(Dispatchers.Main) {
+                        _value.value = dsValue
+                    }
                 }
+                ready.complete(Unit)
             }
             // 观察 DataStore 变化,用于跨实例同步
             dsObserverJob = scope.launch {
@@ -91,7 +100,9 @@ fun <T> prefDelegate(
                     .distinctUntilChanged()
                     .collect { dsValue ->
                         if (dsValue != null && _value.value != dsValue) {
-                            _value.value = dsValue
+                            withContext(Dispatchers.Main) {
+                                _value.value = dsValue
+                            }
                             onValueChange?.invoke(dsValue)
                         }
                     }
@@ -126,7 +137,6 @@ fun <T> prefDelegate(
                     is Float -> appCtx.putPrefFloat(key, value)
                 }
                 // 同步写入 DataStore,确保持久化后再返回
-                // 异常不阻断流程:SP 已写入,readFromDs() 会回退到 SP 读取
                 runCatching {
                     runBlocking(Dispatchers.IO) {
                         when (value) {