From d69456dfd0dc2c85173e519dbf7c83a277d9eca9 Mon Sep 17 00:00:00 2001 From: johan12345 Date: Sun, 11 Sep 2022 19:14:12 +0200 Subject: [PATCH] fix more issues switching the data source, esp. on Android Auto --- .../java/net/vonforst/evmap/auto/MapScreen.kt | 17 ++++++---- .../evmap/storage/ChargeLocationsDao.kt | 32 +++++++++---------- .../evmap/storage/GEReferenceDataDao.kt | 1 + .../evmap/storage/OCMReferenceDataDao.kt | 1 + 4 files changed, 28 insertions(+), 23 deletions(-) diff --git a/app/src/google/java/net/vonforst/evmap/auto/MapScreen.kt b/app/src/google/java/net/vonforst/evmap/auto/MapScreen.kt index 91792839..aae6128a 100644 --- a/app/src/google/java/net/vonforst/evmap/auto/MapScreen.kt +++ b/app/src/google/java/net/vonforst/evmap/auto/MapScreen.kt @@ -13,7 +13,10 @@ import androidx.car.app.hardware.info.EnergyLevel import androidx.car.app.model.* import androidx.core.content.ContextCompat import androidx.core.graphics.drawable.IconCompat -import androidx.lifecycle.* +import androidx.lifecycle.DefaultLifecycleObserver +import androidx.lifecycle.LifecycleOwner +import androidx.lifecycle.MutableLiveData +import androidx.lifecycle.lifecycleScope import com.car2go.maps.model.LatLng import kotlinx.coroutines.* import net.vonforst.evmap.BuildConfig @@ -30,6 +33,7 @@ import net.vonforst.evmap.storage.PreferenceDataSource import net.vonforst.evmap.ui.availabilityText import net.vonforst.evmap.ui.getMarkerTint import net.vonforst.evmap.utils.distanceBetween +import net.vonforst.evmap.viewmodel.await import net.vonforst.evmap.viewmodel.awaitFinished import net.vonforst.evmap.viewmodel.filtersWithValue import net.vonforst.evmap.viewmodel.getFilterValues @@ -173,7 +177,9 @@ class MapScreen(ctx: CarContext, val session: EVMapSession) : ).setTint(CarColor.DEFAULT).build() ) .setOnClickListener { - screenManager.push(SettingsScreen(carContext)) + screenManager.pushForResult(SettingsScreen(carContext)) { + repo.api.value = createApi(prefs.dataSource, carContext) + } session.mapScreen = null } .build()) @@ -308,7 +314,6 @@ class MapScreen(ctx: CarContext, val session: EVMapSession) : private fun loadChargers() { val location = location ?: return - val filters = filtersWithValue.value ?: return val searchLocation = prefs.placeSearchResultAndroidAuto ?: LatLng.fromLocation(location) @@ -316,6 +321,8 @@ class MapScreen(ctx: CarContext, val session: EVMapSession) : updateCoroutine = lifecycleScope.launch { try { + val filters = filtersWithValue.await() + // load chargers if (filterStatus.value == FILTERS_FAVORITES) { chargers = @@ -373,9 +380,7 @@ class MapScreen(ctx: CarContext, val session: EVMapSession) : // Reloading chargers in onStart does not seem to count towards content limit. // So let's do this so the user gets fresh chargers when re-entering the app. invalidate() - filtersWithValue.observe(this@MapScreen) { - loadChargers() - } + loadChargers() } private fun setupListeners() { diff --git a/app/src/main/java/net/vonforst/evmap/storage/ChargeLocationsDao.kt b/app/src/main/java/net/vonforst/evmap/storage/ChargeLocationsDao.kt index 1a347de0..7771afc0 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/ChargeLocationsDao.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/ChargeLocationsDao.kt @@ -13,10 +13,7 @@ import net.vonforst.evmap.api.StringProvider import net.vonforst.evmap.api.goingelectric.GEReferenceData import net.vonforst.evmap.api.goingelectric.GoingElectricApiWrapper import net.vonforst.evmap.api.openchargemap.OpenChargeMapApiWrapper -import net.vonforst.evmap.model.ChargeLocation -import net.vonforst.evmap.model.ChargepointListItem -import net.vonforst.evmap.model.FilterValues -import net.vonforst.evmap.model.ReferenceData +import net.vonforst.evmap.model.* import net.vonforst.evmap.viewmodel.Resource import net.vonforst.evmap.viewmodel.await @@ -39,7 +36,7 @@ class ChargeLocationsRepository( ) { val api = MutableLiveData>().apply { value = api } - private val apiAndReferenceData = this.api.switchMap { api -> + val referenceData = this.api.switchMap { api -> when (api) { is GoingElectricApiWrapper -> { GEReferenceDataRepository( @@ -47,7 +44,7 @@ class ChargeLocationsRepository( scope, db.geReferenceDataDao(), prefs - ).getReferenceData().map { api to it } + ).getReferenceData() } is OpenChargeMapApiWrapper -> { OCMReferenceDataRepository( @@ -55,14 +52,13 @@ class ChargeLocationsRepository( scope, db.ocmReferenceDataDao(), prefs - ).getReferenceData().map { api to it } + ).getReferenceData() } else -> { throw RuntimeException("no reference data implemented") } } } - val referenceData = apiAndReferenceData.map { it.second } private val chargeLocationsDao = db.chargeLocationsDao() @@ -72,8 +68,8 @@ class ChargeLocationsRepository( filters: FilterValues? ): LiveData>> { return liveData { - val (api, refData) = apiAndReferenceData.await() - val result = api.getChargepoints(refData, bounds, zoom, filters) + val refData = referenceData.await() + val result = api.value!!.getChargepoints(refData, bounds, zoom, filters) emit(result) } @@ -86,8 +82,8 @@ class ChargeLocationsRepository( filters: FilterValues? ): LiveData>> { return liveData { - val (api, refData) = apiAndReferenceData.await() - val result = api.getChargepointsRadius(refData, location, radius, zoom, filters) + val refData = referenceData.await() + val result = api.value!!.getChargepointsRadius(refData, location, radius, zoom, filters) emit(result) } @@ -97,18 +93,20 @@ class ChargeLocationsRepository( id: Long ): LiveData> { return liveData { - val (api, refData) = apiAndReferenceData.await() - val result = api.getChargepointDetail(refData, id) + val refData = referenceData.await() + val result = api.value!!.getChargepointDetail(refData, id) emit(result) } } - fun getFilters(sp: StringProvider) = apiAndReferenceData.map { (api, refData) -> - api.getFilters(refData, sp) + fun getFilters(sp: StringProvider) = MediatorLiveData>>().apply { + addSource(referenceData) { refData: ReferenceData? -> + refData?.let { value = api.value!!.getFilters(refData, sp) } + } } val chargeCardMap by lazy { - apiAndReferenceData.map { (_, refData) -> + referenceData.map { refData: ReferenceData? -> if (refData is GEReferenceData) { refData.chargecards.associate { it.id to it.convert() diff --git a/app/src/main/java/net/vonforst/evmap/storage/GEReferenceDataDao.kt b/app/src/main/java/net/vonforst/evmap/storage/GEReferenceDataDao.kt index 41d50194..d7949160 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/GEReferenceDataDao.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/GEReferenceDataDao.kt @@ -87,6 +87,7 @@ class GEReferenceDataRepository( val networks = dao.getAllNetworks() val chargeCards = dao.getAllChargeCards() return MediatorLiveData().apply { + value = null listOf(chargeCards, networks, plugs).map { source -> addSource(source) { _ -> val p = plugs.value ?: return@addSource diff --git a/app/src/main/java/net/vonforst/evmap/storage/OCMReferenceDataDao.kt b/app/src/main/java/net/vonforst/evmap/storage/OCMReferenceDataDao.kt index 419a0d3c..eefa3e04 100644 --- a/app/src/main/java/net/vonforst/evmap/storage/OCMReferenceDataDao.kt +++ b/app/src/main/java/net/vonforst/evmap/storage/OCMReferenceDataDao.kt @@ -79,6 +79,7 @@ class OCMReferenceDataRepository( val countries = dao.getAllCountries() val operators = dao.getAllOperators() return MediatorLiveData().apply { + value = null listOf(countries, connectionTypes, operators).map { source -> addSource(source) { _ -> val ct = connectionTypes.value