Как избежать loadIntent() каждый раз при запуске фрагмента
При использовании mosby-Mvi,
Следующий код работает нормально - срабатывает только один раз при создании фрагмента.
override fun loadIntent(): Observable<Unit> {
return Observable.just(Unit)
}
Следующий код работает неожиданно - срабатывает каждый раз, когда активность просыпается из фона.
override fun loadIntent(): Observable<Unit> {
return Observable.just(Unit).mergeWith(RxView.clicks(error).map { Unit })
}
Это почему?
1 ответ
Это контракт RxJava, который уважает Мосби.
В первом примере происходит следующее:
override fun loadIntent(): Observable<Unit> {
return Observable.just(Unit)
}
Затем в ведущем вы делаете что-то вроде:
intent(YourView::loadIntent)
Это в основном подписывается на loadIntent()
который Observable.just(Unit)
Затем следующие обратные вызовы RxJava запускаются внутри intent(YourView::loadIntent)
:
--> onNext(Unit)
--> onComplete()
Так что ваши intent(YourView::loadIntent)
достиг onComplete()
состояние, которое означает, что любые будущие выбросы будут просто игнорироваться (это контракт RxJava). Таким образом, "магия", почему это намерение только вызывает, заключается в том, что в вашем докладчике он достигает onComplete()
,
Во втором примере:
override fun loadIntent(): Observable<Unit> {
return Observable.just(Unit).mergeWith(RxView.clicks(error).map { Unit })
}
Что нужно отметить здесь mergeWith()
оператор. "Проблема" здесь в том, что mergeWith()
только завершает (и звонит onComplete()
) если оба Observable.just(Unit)
а также RxView.clicks(error)
индивидуально достичь onComplete
, В то время как Observable.just(Unit)
достигает onComplete(), как уже обсуждалось в предыдущем фрагменте кода, RxView.clicks(error)
никогда не достигает onComplete()
и вот почему mergeWith()
никогда не достигает onComplete()
и именно поэтому при воссоздании фрагмента (например, изменения ориентации экрана) это намерение срабатывает снова.
Я бы порекомендовал сделать mergeWith()
в своем докладчике и разделить его на две части: loadIntnent()
а также retryLoadingOnErrorIntent()
,