Определите правильный тип - PullRequest
0 голосов
/ 02 февраля 2020

В моем приложении довольно много переменных, которые зависят от нескольких других LiveData, поэтому я использую это:

class TripleLiveData<A, B, C>(
    private val first: LiveData<A?>,
    private val second: LiveData<B?>,
    private val third: LiveData<C?>
) : MediatorLiveData<Triple<A?, B?, C?>>() {
    init {
        addSource(first) { setValue(Triple(first.value, second.value, third.value)) }
        addSource(second) { setValue(Triple(first.value, second.value, third.value)) }
        addSource(third) { setValue(Triple(first.value, second.value, third.value)) }
    }
}
private val tokensRequired = TripleLiveData(stitchedScreenshot, shareType, expiryIntention).switchMap {
    liveData {
        val stitchedScreenshotReference = it.first?.reference
        val shareType = it.second
        val expiryIntention = it.third

        if (screenshotReference == null || shareType == null || expiryIntention == null) return@liveData

        emit(null)
        emit(getTokensRequired(screenshotReference, shareType, expiryIntention))
    }
}

Есть некоторые блоки кода, которые делают то же самое: проверьте, все ли значения не ноль и, если так, испускают значение. Я хотел бы абстрагироваться от этого.

Я сделал это следующим образом:

class TripleLiveData<A, B, C>(
    private val first: LiveData<A?>,
    private val second: LiveData<B?>,
    private val third: LiveData<C?>
) : MediatorLiveData<Triple<A?, B?, C?>>() {
    init {
        addSource(first) { setValue(Triple(first.value, second.value, third.value)) }
        addSource(second) { setValue(Triple(first.value, second.value, third.value)) }
        addSource(third) { setValue(Triple(first.value, second.value, third.value)) }
    }

    fun <T> switchLiveMap(action: suspend LiveDataScope<T>.(A, B, C) -> Unit) =
        switchMap {
            liveData<T> {
                val first = it.first
                val second = it.second
                val third = it.third

                if (first == null || second == null || third == null) return@liveData

                action(first, second, third)
            }
        }
}
private val tokensRequired = TripleLiveData(
    stitchedScreenshot,
    shareType,
    expiryIntention
).switchLiveMap<Int?> { stitchedScreenshot, shareType, expiryIntention ->
    emit(null)
    emit(getTokensRequired(stitchedScreenshot.reference, shareType, expiryIntention))
}

Однако: switchLiveMap не может вывести его тип, который будет испущен , <Int?> должен быть объявлен. Куда мне положить мой <T>, чтобы он больше не нужен?

...