Updated on 2026-08-14
This commit is contained in:
parent
895af6c0a6
commit
b2726d153c
28 changed files with 197 additions and 40 deletions
|
|
@ -186,7 +186,6 @@ internal class DefaultNetworksRepository(
|
|||
is UpdateWalletManagerResult.NoAccount,
|
||||
-> Unit
|
||||
is UpdateWalletManagerResult.Unreachable,
|
||||
is UpdateWalletManagerResult.UnreachableWithoutAddresses,
|
||||
is UpdateWalletManagerResult.MissedDerivation,
|
||||
-> {
|
||||
Timber.w(
|
||||
|
|
|
|||
|
|
@ -19,9 +19,8 @@ internal class NetworkStatusFactory {
|
|||
network = network,
|
||||
value = when (result) {
|
||||
is UpdateWalletManagerResult.MissedDerivation -> NetworkStatus.MissedDerivation
|
||||
is UpdateWalletManagerResult.UnreachableWithoutAddresses -> NetworkStatus.UnreachableWithoutAddresses
|
||||
is UpdateWalletManagerResult.Unreachable -> NetworkStatus.Unreachable(
|
||||
address = getNetworkAddress(result.selectedAddress, result.addresses),
|
||||
address = getNetworkAddressOrNull(result.selectedAddress, result.addresses),
|
||||
)
|
||||
is UpdateWalletManagerResult.NoAccount -> NetworkStatus.NoAccount(
|
||||
address = getNetworkAddress(result.selectedAddress, result.addresses),
|
||||
|
|
@ -96,6 +95,14 @@ internal class NetworkStatusFactory {
|
|||
return transactions.mapTo(hashSetOf()) { it.txHistoryItem }
|
||||
}
|
||||
|
||||
private fun getNetworkAddressOrNull(selectedAddress: String?, availableAddresses: Set<Address>?): NetworkAddress? {
|
||||
if (selectedAddress == null || availableAddresses == null) {
|
||||
return null
|
||||
}
|
||||
|
||||
return getNetworkAddress(selectedAddress, availableAddresses)
|
||||
}
|
||||
|
||||
private fun getNetworkAddress(selectedAddress: String, availableAddresses: Set<Address>): NetworkAddress {
|
||||
val defaultAddress = availableAddresses
|
||||
.firstOrNull { it.value == selectedAddress }
|
||||
|
|
|
|||
|
|
@ -132,7 +132,7 @@ class DefaultWalletManagersFacade(
|
|||
val walletManager = getOrCreateWalletManager(userWalletId, blockchain, derivationPath)
|
||||
if (walletManager == null || blockchain == Blockchain.Unknown) {
|
||||
Timber.w("Unable to get a wallet manager for blockchain: $blockchain")
|
||||
return UpdateWalletManagerResult.UnreachableWithoutAddresses
|
||||
return UpdateWalletManagerResult.Unreachable()
|
||||
}
|
||||
|
||||
return getLastWalletManagerResult(walletManager)
|
||||
|
|
@ -246,7 +246,7 @@ class DefaultWalletManagersFacade(
|
|||
)
|
||||
if (walletManager == null || blockchain == Blockchain.Unknown) {
|
||||
Timber.w("Unable to create or find a wallet manager for blockchain: $blockchain")
|
||||
return UpdateWalletManagerResult.UnreachableWithoutAddresses
|
||||
return UpdateWalletManagerResult.Unreachable()
|
||||
}
|
||||
|
||||
updateWalletManagerTokensIfNeeded(walletManager, extraTokens)
|
||||
|
|
|
|||
|
|
@ -6,11 +6,9 @@ sealed class UpdateWalletManagerResult {
|
|||
|
||||
object MissedDerivation : UpdateWalletManagerResult()
|
||||
|
||||
object UnreachableWithoutAddresses : UpdateWalletManagerResult()
|
||||
|
||||
data class Unreachable(
|
||||
val selectedAddress: String,
|
||||
val addresses: Set<Address>,
|
||||
val selectedAddress: String? = null,
|
||||
val addresses: Set<Address>? = null,
|
||||
) : UpdateWalletManagerResult()
|
||||
|
||||
data class Verified(
|
||||
|
|
|
|||
|
|
@ -50,8 +50,6 @@ data class CryptoCurrencyStatus(
|
|||
/** Represents the Loading state of a cryptocurrency, typically while fetching its details. */
|
||||
object Loading : Status(isError = false)
|
||||
|
||||
object UnreachableWithoutAddresses : Status(isError = true)
|
||||
|
||||
/**
|
||||
* Represents a state where the cryptocurrency is not reachable.
|
||||
*
|
||||
|
|
@ -62,7 +60,7 @@ data class CryptoCurrencyStatus(
|
|||
data class Unreachable(
|
||||
override val priceChange: BigDecimal?,
|
||||
override val fiatRate: BigDecimal?,
|
||||
override val networkAddress: NetworkAddress,
|
||||
override val networkAddress: NetworkAddress?,
|
||||
) : Status(isError = true)
|
||||
|
||||
/** Represents a state where the cryptocurrency's network amount not found. */
|
||||
|
|
|
|||
|
|
@ -21,14 +21,12 @@ data class NetworkStatus(
|
|||
*/
|
||||
sealed class Status
|
||||
|
||||
object UnreachableWithoutAddresses : Status()
|
||||
|
||||
/**
|
||||
* Represents the state where the network is unreachable.
|
||||
*
|
||||
* @property address Network addresses.
|
||||
*/
|
||||
data class Unreachable(val address: NetworkAddress) : Status()
|
||||
data class Unreachable(val address: NetworkAddress?) : Status()
|
||||
|
||||
/**
|
||||
* Represents the state where a derivation has been missed.
|
||||
|
|
|
|||
|
|
@ -16,7 +16,6 @@ internal class CurrencyStatusOperations(
|
|||
return when (val status = networkStatus?.value) {
|
||||
null -> CryptoCurrencyStatus.Loading
|
||||
is NetworkStatus.MissedDerivation -> createMissedDerivationStatus()
|
||||
is NetworkStatus.UnreachableWithoutAddresses -> CryptoCurrencyStatus.UnreachableWithoutAddresses
|
||||
is NetworkStatus.Unreachable -> createUnreachableStatus(status)
|
||||
is NetworkStatus.NoAccount -> createNoAccountStatus(status)
|
||||
is NetworkStatus.Verified -> createStatus(status)
|
||||
|
|
|
|||
|
|
@ -22,7 +22,6 @@ internal class TokenListFiatBalanceOperations(
|
|||
}
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
is CryptoCurrencyStatus.NoAmount,
|
||||
is CryptoCurrencyStatus.NoQuote,
|
||||
-> {
|
||||
|
|
|
|||
|
|
@ -45,7 +45,7 @@ internal object MockNetworks {
|
|||
|
||||
val networkStatus1 = NetworkStatus(
|
||||
network = network1,
|
||||
value = NetworkStatus.UnreachableWithoutAddresses,
|
||||
value = NetworkStatus.Unreachable(address = null),
|
||||
)
|
||||
|
||||
val networkStatus2 = NetworkStatus(
|
||||
|
|
|
|||
|
|
@ -0,0 +1,27 @@
|
|||
package com.tangem.feature.tokendetails.presentation.tokendetails.analytics
|
||||
|
||||
import com.tangem.core.analytics.models.AnalyticsEvent
|
||||
import com.tangem.domain.tokens.model.CryptoCurrency
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.analytics.utils.toAnalyticsParams
|
||||
|
||||
internal open class TokenDetailsAnalyticsEvent(
|
||||
event: String,
|
||||
params: Map<String, String> = mapOf(),
|
||||
) : AnalyticsEvent(category = "Token", event, params) {
|
||||
|
||||
open class Notice(
|
||||
event: String,
|
||||
params: Map<String, String> = mapOf(),
|
||||
) : TokenDetailsAnalyticsEvent(event = "Notice - $event", params) {
|
||||
|
||||
class NetworkUnreachable(currency: CryptoCurrency) : Notice(
|
||||
event = "Network Unreachable",
|
||||
params = currency.toAnalyticsParams(),
|
||||
)
|
||||
|
||||
class NotEnoughFee(currency: CryptoCurrency) : Notice(
|
||||
event = "Not Enough Fee",
|
||||
params = currency.toAnalyticsParams(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,38 @@
|
|||
package com.tangem.feature.tokendetails.presentation.tokendetails.analytics
|
||||
|
||||
import arrow.core.Either
|
||||
import arrow.core.getOrElse
|
||||
import com.tangem.core.analytics.api.AnalyticsEventHandler
|
||||
import com.tangem.core.analytics.models.AnalyticsEvent
|
||||
import com.tangem.domain.tokens.error.CurrencyStatusError
|
||||
import com.tangem.domain.tokens.model.CryptoCurrencyStatus
|
||||
|
||||
internal class TokenDetailsCurrencyStatusAnalyticsSender(
|
||||
private val analyticsEventHandler: AnalyticsEventHandler,
|
||||
) {
|
||||
|
||||
fun send(maybeCurrencyStatus: Either<CurrencyStatusError, CryptoCurrencyStatus>) {
|
||||
val currencyStatus = maybeCurrencyStatus.getOrElse { return }
|
||||
val event = getEvent(currencyStatus)
|
||||
|
||||
if (event != null) {
|
||||
analyticsEventHandler.send(event)
|
||||
}
|
||||
}
|
||||
|
||||
private fun getEvent(currencyStatus: CryptoCurrencyStatus): AnalyticsEvent? {
|
||||
return when (currencyStatus.value) {
|
||||
is CryptoCurrencyStatus.Custom,
|
||||
is CryptoCurrencyStatus.Loaded,
|
||||
is CryptoCurrencyStatus.Loading,
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.NoAccount,
|
||||
is CryptoCurrencyStatus.NoAmount,
|
||||
is CryptoCurrencyStatus.NoQuote,
|
||||
-> null
|
||||
is CryptoCurrencyStatus.Unreachable -> TokenDetailsAnalyticsEvent.Notice.NetworkUnreachable(
|
||||
currency = currencyStatus.currency,
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,45 @@
|
|||
package com.tangem.feature.tokendetails.presentation.tokendetails.analytics
|
||||
|
||||
import com.tangem.core.analytics.api.AnalyticsEventHandler
|
||||
import com.tangem.core.analytics.models.AnalyticsEvent
|
||||
import com.tangem.domain.tokens.model.CryptoCurrency
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.state.TokenDetailsState
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.state.components.TokenDetailsNotification
|
||||
|
||||
internal class TokenDetailsNotificationsAnalyticsSender(
|
||||
private val cryptoCurrency: CryptoCurrency,
|
||||
private val analyticsEventHandler: AnalyticsEventHandler,
|
||||
) {
|
||||
|
||||
fun send(displayedUiState: TokenDetailsState, newNotifications: List<TokenDetailsNotification>) {
|
||||
if (newNotifications.isEmpty()) return
|
||||
if (displayedUiState.pullToRefreshConfig.isRefreshing) return
|
||||
|
||||
val eventsFromNewWarnings = getEvents(newNotifications)
|
||||
val eventsFromDisplayedWarnings = getEvents(displayedUiState.notifications)
|
||||
val eventsToSend = eventsFromNewWarnings.filter { it !in eventsFromDisplayedWarnings }
|
||||
|
||||
eventsToSend.forEach { event ->
|
||||
analyticsEventHandler.send(event)
|
||||
}
|
||||
}
|
||||
|
||||
private fun getEvents(notifications: List<TokenDetailsNotification>): Set<AnalyticsEvent> {
|
||||
return notifications.mapNotNullTo(mutableSetOf(), ::getEvent)
|
||||
}
|
||||
|
||||
private fun getEvent(notification: TokenDetailsNotification): AnalyticsEvent? {
|
||||
return when (notification) {
|
||||
is TokenDetailsNotification.NetworkFee -> TokenDetailsAnalyticsEvent.Notice.NotEnoughFee(
|
||||
currency = cryptoCurrency,
|
||||
)
|
||||
is TokenDetailsNotification.NetworksUnreachable,
|
||||
is TokenDetailsNotification.ExistentialDeposit,
|
||||
is TokenDetailsNotification.HasPendingTransactions,
|
||||
is TokenDetailsNotification.NetworksNoAccount,
|
||||
is TokenDetailsNotification.RentInfo,
|
||||
is TokenDetailsNotification.SwapPromo,
|
||||
-> null
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
package com.tangem.feature.tokendetails.presentation.tokendetails.analytics.utils
|
||||
|
||||
import com.tangem.domain.tokens.model.CryptoCurrency
|
||||
|
||||
internal fun CryptoCurrency.toAnalyticsParams(): Map<String, String> {
|
||||
return mapOf(
|
||||
"Token" to symbol,
|
||||
"Blockchain" to network.currencySymbol,
|
||||
)
|
||||
}
|
||||
|
|
@ -78,7 +78,6 @@ internal class TokenDetailsLoadedBalanceConverter(
|
|||
is CryptoCurrencyStatus.Loading -> TokenDetailsBalanceBlockState.Loading(currentState.actionButtons)
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
is CryptoCurrencyStatus.NoAmount,
|
||||
-> TokenDetailsBalanceBlockState.Error(currentState.actionButtons)
|
||||
}
|
||||
|
|
@ -102,7 +101,6 @@ internal class TokenDetailsLoadedBalanceConverter(
|
|||
is CryptoCurrencyStatus.Custom,
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
is CryptoCurrencyStatus.NoAmount,
|
||||
-> status.toContentConfig(currencySymbol)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -40,6 +40,8 @@ import com.tangem.domain.wallets.usecase.GetUserWalletUseCase
|
|||
import com.tangem.feature.swap.domain.SwapTransactionRepository
|
||||
import com.tangem.feature.swap.domain.api.SwapRepository
|
||||
import com.tangem.feature.tokendetails.presentation.router.InnerTokenDetailsRouter
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.analytics.TokenDetailsCurrencyStatusAnalyticsSender
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.analytics.TokenDetailsNotificationsAnalyticsSender
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.state.SwapTransactionsState
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.state.TokenDetailsState
|
||||
import com.tangem.feature.tokendetails.presentation.tokendetails.state.factory.TokenDetailsStateFactory
|
||||
|
|
@ -57,7 +59,6 @@ import kotlinx.coroutines.launch
|
|||
import timber.log.Timber
|
||||
import java.math.BigDecimal
|
||||
import javax.inject.Inject
|
||||
import kotlin.properties.Delegates
|
||||
|
||||
@Suppress("LongParameterList", "LargeClass", "TooManyFunctions")
|
||||
@HiltViewModel
|
||||
|
|
@ -95,7 +96,7 @@ internal class TokenDetailsViewModel @Inject constructor(
|
|||
private val cryptoCurrency: CryptoCurrency = savedStateHandle[TokenDetailsRouter.CRYPTO_CURRENCY_KEY]
|
||||
?: error("This screen can't open without `CryptoCurrency`")
|
||||
|
||||
var router by Delegates.notNull<InnerTokenDetailsRouter>()
|
||||
lateinit var router: InnerTokenDetailsRouter
|
||||
|
||||
private val marketPriceJobHolder = JobHolder()
|
||||
private val refreshStateJobHolder = JobHolder()
|
||||
|
|
@ -115,7 +116,7 @@ internal class TokenDetailsViewModel @Inject constructor(
|
|||
decimals = cryptoCurrency.decimals,
|
||||
)
|
||||
|
||||
private val exchangeStatusFactory by lazy {
|
||||
private val exchangeStatusFactory by lazy(mode = LazyThreadSafetyMode.NONE) {
|
||||
ExchangeStatusFactory(
|
||||
swapTransactionRepository = swapTransactionRepository,
|
||||
swapRepository = swapRepository,
|
||||
|
|
@ -132,6 +133,17 @@ internal class TokenDetailsViewModel @Inject constructor(
|
|||
)
|
||||
}
|
||||
|
||||
private val notificationsAnalyticsSender by lazy(mode = LazyThreadSafetyMode.NONE) {
|
||||
TokenDetailsNotificationsAnalyticsSender(
|
||||
cryptoCurrency = cryptoCurrency,
|
||||
analyticsEventHandler = analyticsEventsHandler,
|
||||
)
|
||||
}
|
||||
|
||||
private val currencyStatusAnalyticsSender by lazy(mode = LazyThreadSafetyMode.NONE) {
|
||||
TokenDetailsCurrencyStatusAnalyticsSender(analyticsEventsHandler)
|
||||
}
|
||||
|
||||
var uiState: TokenDetailsState by mutableStateOf(stateFactory.getInitialState(cryptoCurrency))
|
||||
private set
|
||||
|
||||
|
|
@ -188,7 +200,11 @@ internal class TokenDetailsViewModel @Inject constructor(
|
|||
isSingleWalletWithTokens = wallet.scanResponse.cardTypesResolver.isSingleWalletWithToken(),
|
||||
)
|
||||
.distinctUntilChanged()
|
||||
.onEach { uiState = stateFactory.getStateWithNotifications(it) }
|
||||
.onEach {
|
||||
val updatedState = stateFactory.getStateWithNotifications(it)
|
||||
notificationsAnalyticsSender.send(uiState, updatedState.notifications)
|
||||
uiState = updatedState
|
||||
}
|
||||
.launchIn(viewModelScope)
|
||||
.saveIn(warningsJobHolder)
|
||||
}
|
||||
|
|
@ -203,13 +219,14 @@ internal class TokenDetailsViewModel @Inject constructor(
|
|||
isSingleWalletWithTokens = wallet.scanResponse.cardTypesResolver.isSingleWalletWithToken(),
|
||||
)
|
||||
.distinctUntilChanged()
|
||||
.onEach { either ->
|
||||
uiState = stateFactory.getCurrencyLoadedBalanceState(either)
|
||||
either.onRight { status ->
|
||||
.onEach { maybeCurrencyStatus ->
|
||||
uiState = stateFactory.getCurrencyLoadedBalanceState(maybeCurrencyStatus)
|
||||
maybeCurrencyStatus.onRight { status ->
|
||||
cryptoCurrencyStatus = status
|
||||
updateButtons(userWalletId = userWalletId, currencyStatus = status)
|
||||
updateWarnings(status)
|
||||
}
|
||||
currencyStatusAnalyticsSender.send(maybeCurrencyStatus)
|
||||
}
|
||||
.flowOn(dispatchers.io)
|
||||
.launchIn(viewModelScope)
|
||||
|
|
|
|||
|
|
@ -56,6 +56,7 @@ internal class DefaultWalletRouter(
|
|||
if (walletFeatureToggles.isWalletsScrollingPreviewEnabled) {
|
||||
val viewModel = hiltViewModel<WalletViewModelV2>().apply {
|
||||
setWalletRouter(router = this@DefaultWalletRouter)
|
||||
subscribeToLifecycle(LocalLifecycleOwner.current)
|
||||
}
|
||||
|
||||
WalletScreenV2(state = viewModel.uiState.collectAsStateWithLifecycle().value)
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ import com.tangem.domain.wallets.models.UserWallet
|
|||
import com.tangem.feature.wallet.presentation.wallet.analytics.WalletScreenAnalyticsEvent.Basic
|
||||
import com.tangem.feature.wallet.presentation.wallet.analytics.WalletScreenAnalyticsEvent.MainScreen
|
||||
import com.tangem.feature.wallet.presentation.wallet.state2.model.WalletState
|
||||
import com.tangem.feature.wallet.presentation.wallet.utils.ScreenLifecycleProvider
|
||||
import dagger.hilt.android.scopes.ViewModelScoped
|
||||
import java.math.BigDecimal
|
||||
import javax.inject.Inject
|
||||
|
|
@ -20,9 +21,11 @@ import javax.inject.Inject
|
|||
internal class TokenListAnalyticsSender @Inject constructor(
|
||||
private val analyticsEventHandler: AnalyticsEventHandler,
|
||||
private val checkIsWalletToppedUpUseCase: CheckIsWalletToppedUpUseCase,
|
||||
private val screenLifecycleProvider: ScreenLifecycleProvider,
|
||||
) {
|
||||
|
||||
suspend fun send(displayedUiState: WalletState?, userWallet: UserWallet, tokenList: TokenList) {
|
||||
if (screenLifecycleProvider.isBackground) return
|
||||
if (displayedUiState == null || displayedUiState.pullToRefreshConfig.isRefreshing) return
|
||||
if (tokenList.totalFiatBalance is TokenList.FiatBalance.Loading) return
|
||||
|
||||
|
|
@ -117,8 +120,7 @@ internal class TokenListAnalyticsSender @Inject constructor(
|
|||
|
||||
private fun sendUnreachableNetworksEventIfNeeded(currenciesStatuses: List<CryptoCurrencyStatus>) {
|
||||
val hasUnreachableCurrencies = currenciesStatuses.any {
|
||||
it.value is CryptoCurrencyStatus.Unreachable ||
|
||||
it.value is CryptoCurrencyStatus.UnreachableWithoutAddresses
|
||||
it.value is CryptoCurrencyStatus.Unreachable
|
||||
}
|
||||
|
||||
if (hasUnreachableCurrencies) {
|
||||
|
|
|
|||
|
|
@ -5,15 +5,18 @@ import com.tangem.core.analytics.models.AnalyticsEvent
|
|||
import com.tangem.feature.wallet.presentation.wallet.analytics.WalletScreenAnalyticsEvent.MainScreen
|
||||
import com.tangem.feature.wallet.presentation.wallet.state.components.WalletNotification
|
||||
import com.tangem.feature.wallet.presentation.wallet.state2.model.WalletState
|
||||
import com.tangem.feature.wallet.presentation.wallet.utils.ScreenLifecycleProvider
|
||||
import dagger.hilt.android.scopes.ViewModelScoped
|
||||
import javax.inject.Inject
|
||||
|
||||
@ViewModelScoped
|
||||
internal class WalletWarningsAnalyticsSender @Inject constructor(
|
||||
private val analyticsEventHandler: AnalyticsEventHandler,
|
||||
private val screenLifecycleProvider: ScreenLifecycleProvider,
|
||||
) {
|
||||
|
||||
fun send(displayedUiState: WalletState?, newWarnings: List<WalletNotification>) {
|
||||
if (screenLifecycleProvider.isBackground) return
|
||||
if (newWarnings.isEmpty()) return
|
||||
if (displayedUiState == null || displayedUiState.pullToRefreshConfig.isRefreshing) return
|
||||
|
||||
|
|
|
|||
|
|
@ -73,7 +73,6 @@ internal class WalletSingleCurrencyLoadedBalanceConverter(
|
|||
is CryptoCurrencyStatus.Custom,
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
is CryptoCurrencyStatus.NoQuote,
|
||||
-> MarketPriceBlockState.Error(currencySymbol)
|
||||
}
|
||||
|
|
@ -117,7 +116,6 @@ internal class WalletSingleCurrencyLoadedBalanceConverter(
|
|||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Custom,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
-> {
|
||||
WalletCardState.Error(
|
||||
id = selectedWallet.id,
|
||||
|
|
|
|||
|
|
@ -21,7 +21,6 @@ internal class SingleWalletCardStateConverter(
|
|||
is CryptoCurrencyStatus.Custom,
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
-> value.toErrorState()
|
||||
is CryptoCurrencyStatus.NoQuote,
|
||||
is CryptoCurrencyStatus.Loaded,
|
||||
|
|
|
|||
|
|
@ -25,7 +25,6 @@ internal class SingleWalletMarketPriceConverter(
|
|||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.NoQuote,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
-> MarketPriceBlockState.Error(value.currencySymbol)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,7 +28,6 @@ internal class TokenItemStateConverter(
|
|||
-> value.mapToTokenItemState()
|
||||
is CryptoCurrencyStatus.MissedDerivation -> value.mapToNoAddressTokenItemState()
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
is CryptoCurrencyStatus.NoAmount,
|
||||
-> value.mapToUnreachableTokenItemState()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -22,7 +22,6 @@ internal class VisaWalletCardStateConverter(
|
|||
is CryptoCurrencyStatus.Custom,
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
-> value.toErrorState()
|
||||
is CryptoCurrencyStatus.NoQuote,
|
||||
is CryptoCurrencyStatus.Loaded,
|
||||
|
|
|
|||
|
|
@ -73,7 +73,6 @@ internal class PrimaryCurrencySubscriber(
|
|||
-> createCardBalanceState(fiatAmount)
|
||||
is CryptoCurrencyStatus.NoQuote -> AnalyticsParam.CardBalanceState.NoRate
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
-> AnalyticsParam.CardBalanceState.BlockchainError
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Loading,
|
||||
|
|
|
|||
|
|
@ -28,7 +28,6 @@ internal class CryptoCurrencyStatusToTokenItemConverter(
|
|||
-> value.mapToTokenItemState()
|
||||
is CryptoCurrencyStatus.MissedDerivation -> value.mapToNoAddressTokenItemState()
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
is CryptoCurrencyStatus.NoAmount,
|
||||
-> value.mapToUnreachableTokenItemState()
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,21 @@
|
|||
package com.tangem.feature.wallet.presentation.wallet.utils
|
||||
|
||||
import androidx.lifecycle.DefaultLifecycleObserver
|
||||
import androidx.lifecycle.LifecycleOwner
|
||||
import dagger.hilt.android.scopes.ViewModelScoped
|
||||
import javax.inject.Inject
|
||||
|
||||
@ViewModelScoped
|
||||
internal class ScreenLifecycleProvider @Inject constructor() : DefaultLifecycleObserver {
|
||||
|
||||
var isBackground: Boolean = true
|
||||
private set
|
||||
|
||||
override fun onResume(owner: LifecycleOwner) {
|
||||
isBackground = false
|
||||
}
|
||||
|
||||
override fun onPause(owner: LifecycleOwner) {
|
||||
isBackground = true
|
||||
}
|
||||
}
|
||||
|
|
@ -1231,7 +1231,6 @@ internal class WalletViewModel @Inject constructor(
|
|||
}
|
||||
is CryptoCurrencyStatus.NoQuote -> AnalyticsParam.CardBalanceState.NoRate
|
||||
is CryptoCurrencyStatus.Unreachable,
|
||||
is CryptoCurrencyStatus.UnreachableWithoutAddresses,
|
||||
-> AnalyticsParam.CardBalanceState.BlockchainError
|
||||
is CryptoCurrencyStatus.MissedDerivation,
|
||||
is CryptoCurrencyStatus.Loading,
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
package com.tangem.feature.wallet.presentation.wallet.viewmodels
|
||||
|
||||
import androidx.lifecycle.LifecycleOwner
|
||||
import androidx.lifecycle.ViewModel
|
||||
import androidx.lifecycle.viewModelScope
|
||||
import com.tangem.core.analytics.api.AnalyticsEventHandler
|
||||
|
|
@ -21,6 +22,7 @@ import com.tangem.feature.wallet.presentation.wallet.state2.WalletStateControlle
|
|||
import com.tangem.feature.wallet.presentation.wallet.state2.model.WalletScreenState
|
||||
import com.tangem.feature.wallet.presentation.wallet.state2.transformers.*
|
||||
import com.tangem.feature.wallet.presentation.wallet.state2.utils.WalletEventSender
|
||||
import com.tangem.feature.wallet.presentation.wallet.utils.ScreenLifecycleProvider
|
||||
import com.tangem.feature.wallet.presentation.wallet.viewmodels.intents.WalletClickIntentsV2
|
||||
import com.tangem.utils.Provider
|
||||
import com.tangem.utils.coroutines.CoroutineDispatcherProvider
|
||||
|
|
@ -33,7 +35,6 @@ import kotlinx.coroutines.launch
|
|||
import kotlinx.coroutines.withContext
|
||||
import timber.log.Timber
|
||||
import javax.inject.Inject
|
||||
import kotlin.properties.Delegates
|
||||
|
||||
@Suppress("LongParameterList")
|
||||
@HiltViewModel
|
||||
|
|
@ -53,11 +54,12 @@ internal class WalletViewModelV2 @Inject constructor(
|
|||
analyticsEventsHandler: AnalyticsEventHandler,
|
||||
private val dispatchers: CoroutineDispatcherProvider,
|
||||
private val reduxStateHolder: ReduxStateHolder,
|
||||
private val screenLifecycleProvider: ScreenLifecycleProvider,
|
||||
) : ViewModel() {
|
||||
|
||||
val uiState: StateFlow<WalletScreenState> = stateHolder.uiState
|
||||
|
||||
private var router: InnerWalletRouter by Delegates.notNull()
|
||||
private lateinit var router: InnerWalletRouter
|
||||
private var walletsUpdateJobHolder: JobHolder = JobHolder()
|
||||
|
||||
init {
|
||||
|
|
@ -75,6 +77,10 @@ internal class WalletViewModelV2 @Inject constructor(
|
|||
clickIntents.initialize(router, viewModelScope)
|
||||
}
|
||||
|
||||
fun subscribeToLifecycle(lifecycleOwner: LifecycleOwner) {
|
||||
lifecycleOwner.lifecycle.addObserver(screenLifecycleProvider)
|
||||
}
|
||||
|
||||
override fun onCleared() {
|
||||
super.onCleared()
|
||||
stateHolder.clear()
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue