как избежать повторения повторенияOnLifecycle снова и снова при возобновлении фрагмента

как я могу избежать повторного выполнения кода collect{} при возвращении к фрагменту.

ViewModel класс

          private val _commitResult = MutableStateFlow<Map<String, Any>>(mapOf())
    val commitResult: StateFlow<Map<String, Any>> = _commitResult
Fragment code like this:

    viewLifecycleOwner.lifecycleScope.launch {
            viewLifecycleOwner.repeatOnLifecycle(Lifecycle.State.STARTED){
                viewModel.commitResult.collect { data ->
                    Logger.i("commitResult $data")
                    //navigate to another fragment
                }
            }
        }

когда я сначала меняю значение _commitResult в viewModel, переход к другому фрагменту работает нормально. к сожалению, когда я вернусь к фрагменту. collect{ // navigate to another fragment} снова изгоню.

Я знаю, когда вернусь к фрагменту. onCreateView, и viewModel выдаст хранилище данных раньше, поэтому collect { // navigate to another fragment}извинить. Как мне этого избежать?

так же, как LiveData, я использую Event, чтобы исправить это с помощью LiveData.

      open class Event<out T>(private val content: T) {

var hasBeenHandled = false
    private set // Allow external read but not write

/**
 * Returns the content and prevents its use again.
 */
fun getContentIfNotHandled(): T? {
    return if (hasBeenHandled) {
        null
    } else {
        hasBeenHandled = true
        content
    }
}

/**
 * Returns the content, even if it's already been handled.
 */
fun peekContent(): T = content
}

как я могу справиться с этим с помощью Stateflow? на самом деле мне не нравится, когда Event<.> обрабатывает это, я неправильно использую поток состояний? как я могу это исправить? Если кто может помочь, заранее спасибо.

1 ответ

StateFlow сохраняет свое состояние, поэтому я бы предложил:

А) Использование SharedFlow. https://kotlin.github.io/kotlinx.coroutines/kotlinx-coroutines-core/kotlinx.coroutines.flow/-shared-flow/

B) Используйте шаблон, в котором вы обрабатываете отклонение событий

      class Vm: ViewModel() {
  
  private val mEvent = MutableStateFlow<MyResult?>(null)
  val event = mEvent.asStateFlow()

  fun dismissEvent() {
    mEvent.value = null
  }

}

class Frag: Fragment() {
  override fun onViewCreated() {
     vm.event.collect {
       navigate()
       vm.dismissEvent()
     }
  }
}
Другие вопросы по тегам