Updated on 2026-08-14

This commit is contained in:
Tangem 2022-08-19 01:38:31 +03:00
parent cf692a7cd6
commit 6bcd70c978
11 changed files with 78 additions and 34 deletions

View file

@ -0,0 +1,8 @@
package com.tangem.tap.common.feature
/**
[REDACTED_AUTHOR]
*/
interface Feature {
fun featureIsSwitchedOn():Boolean
}

View file

@ -51,21 +51,15 @@ data class WalletState(
// if you do not delegate - the application crashes on startup,
// because twinCardsState has not been created yet
val twinCardsState: TwinCardsState by ReadOnlyProperty<Any, TwinCardsState> { thisRef, property ->
val twinCardsState: TwinCardsState by ReadOnlyProperty<Any, TwinCardsState> { _, _ ->
store.state.twinCardsState
}
val isTangemTwins: Boolean
get() = store.state.globalState.scanResponse?.isTangemTwins() == true
val primaryWallet: WalletData? = wallets.firstOrNull()
?.walletsData?.firstOrNull()
val primaryWalletManager: WalletManager? =
if (wallets.isNotEmpty()) wallets[0].walletManager else null
val shouldShowDetails: Boolean =
primaryWallet?.currencyData?.status != BalanceStatus.EmptyCard &&
primaryWallet?.currencyData?.status != BalanceStatus.UnknownBlockchain
val isExchangeServiceFeatureOn: Boolean
get() = store.state.globalState.exchangeManager.featureIsSwitchedOn()
val blockchains: List<Blockchain>
get() = wallets.mapNotNull { it.walletManager?.wallet?.blockchain }
@ -79,6 +73,14 @@ data class WalletState(
val walletManagers: List<WalletManager>
get() = wallets.mapNotNull { it.walletManager }
val primaryWallet: WalletData? = wallets.firstOrNull()?.walletsData?.firstOrNull()
val primaryWalletManager: WalletManager? = if (wallets.isNotEmpty()) wallets[0].walletManager else null
val shouldShowDetails: Boolean =
primaryWallet?.currencyData?.status != BalanceStatus.EmptyCard &&
primaryWallet?.currencyData?.status != BalanceStatus.UnknownBlockchain
fun getWalletManager(currency: Currency?): WalletManager? {
if (currency?.blockchain == null) return null
return getWalletStore(currency)?.walletManager

View file

@ -30,7 +30,6 @@ import com.tangem.tap.features.wallet.redux.WalletState
import com.tangem.tap.features.wallet.redux.WalletStore
import com.tangem.tap.features.wallet.ui.BalanceStatus
import com.tangem.tap.features.wallet.ui.BalanceWidgetData
import com.tangem.tap.store
import org.rekotlin.Action
import java.math.BigDecimal
@ -48,7 +47,6 @@ private fun internalReduce(action: Action, state: AppState): WalletState {
if (action !is WalletAction) return state.walletState
val exchangeManager = store.state.globalState.exchangeManager
var newState = state.walletState
when (action) {

View file

@ -140,7 +140,7 @@ class WalletDetailsFragment : Fragment(R.layout.fragment_wallet_details),
setupAddressCard(selectedWallet)
setupNoInternetHandling(state)
setupBalanceData(selectedWallet.currencyData)
setupButtons(selectedWallet)
setupButtons(selectedWallet, state.isExchangeServiceFeatureOn)
handleCurrencyIcon(selectedWallet)
handleWarnings(selectedWallet)
@ -186,7 +186,7 @@ class WalletDetailsFragment : Fragment(R.layout.fragment_wallet_details),
)
}
private fun setupButtons(selectedWallet: WalletData) = with(binding) {
private fun setupButtons(selectedWallet: WalletData, isExchangeServiceFeatureOn: Boolean) = with(binding) {
lWalletDetails.btnCopy.setOnClickListener {
selectedWallet.walletAddresses?.selectedAddress?.address?.let { addressString ->
store.dispatch(WalletAction.CopyAddress(addressString, requireContext()))
@ -199,6 +199,7 @@ class WalletDetailsFragment : Fragment(R.layout.fragment_wallet_details),
}
rowButtons.updateButtonsVisibility(
exchangeServiceFeatureOn = isExchangeServiceFeatureOn,
buyAllowed = selectedWallet.isAvailableToBuy,
sellAllowed = selectedWallet.isAvailableToSell,
sendAllowed = selectedWallet.mainButton.enabled,

View file

@ -35,14 +35,21 @@ internal class WalletDetailsButtonsRow @JvmOverloads constructor(
}
fun updateButtonsVisibility(
exchangeServiceFeatureOn: Boolean,
buyAllowed: Boolean,
sellAllowed: Boolean,
sendAllowed: Boolean,
) = with(binding) {
btnBuy.isVisible = (buyAllowed && !sellAllowed) || (!buyAllowed && !sellAllowed)
btnBuy.isEnabled = buyAllowed
btnSell.isVisible = !buyAllowed && sellAllowed
btnTrade.isVisible = buyAllowed && sellAllowed
if (exchangeServiceFeatureOn) {
btnBuy.isVisible = (buyAllowed && !sellAllowed) || (!buyAllowed && !sellAllowed)
btnBuy.isEnabled = buyAllowed
btnSell.isVisible = !buyAllowed && sellAllowed
btnTrade.isVisible = buyAllowed && sellAllowed
} else {
btnBuy.isVisible = false
btnSell.isVisible = false
btnTrade.isVisible = false
}
btnSend.isEnabled = sendAllowed
}
}

View file

@ -58,7 +58,7 @@ class SingleWalletView : WalletView() {
state.primaryWallet ?: return
setupTwinCards(state.twinCardsState, binding)
setupButtons(state.primaryWallet, binding)
setupButtons(state.primaryWallet, binding, state.isExchangeServiceFeatureOn)
setupAddressCard(state.primaryWallet, binding)
showPendingTransactionsIfPresent(state.primaryWallet.pendingTransactions)
setupBalance(state, state.primaryWallet)
@ -97,18 +97,23 @@ class SingleWalletView : WalletView() {
}
}
private fun setupButtons(state: WalletData, binding: FragmentWalletBinding) = with(binding) {
setupRowButtons(state, rowButtons)
private fun setupButtons(
walletData: WalletData,
binding: FragmentWalletBinding,
isExchangeServiceFeatureEnabled: Boolean,
) = with(binding) {
setupRowButtons(walletData, rowButtons, isExchangeServiceFeatureEnabled)
lAddress.btnCopy.setOnClickListener {
state.walletAddresses?.selectedAddress?.address?.let { addressString ->
walletData.walletAddresses?.selectedAddress?.address?.let { addressString ->
store.dispatch(WalletAction.CopyAddress(addressString, fragment!!.requireContext()))
}
}
lAddress.btnShowQr.setOnClickListener {
state.walletAddresses?.selectedAddress?.let { selectedAddress ->
walletData.walletAddresses?.selectedAddress?.let { selectedAddress ->
store.dispatch(
WalletAction.DialogAction.QrCode(
currency = state.currency,
currency = walletData.currency,
selectedAddress = selectedAddress,
),
)
@ -116,11 +121,16 @@ class SingleWalletView : WalletView() {
}
}
private fun setupRowButtons(state: WalletData, rowButtons: WalletDetailsButtonsRow) {
private fun setupRowButtons(
walletData: WalletData,
rowButtons: WalletDetailsButtonsRow,
isExchangeServiceFeatureEnabled: Boolean,
) {
rowButtons.updateButtonsVisibility(
buyAllowed = state.isAvailableToBuy,
sellAllowed = state.isAvailableToSell,
sendAllowed = state.mainButton.enabled,
exchangeServiceFeatureOn = isExchangeServiceFeatureEnabled,
buyAllowed = walletData.isAvailableToBuy,
sellAllowed = walletData.isAvailableToSell,
sendAllowed = walletData.mainButton.enabled,
)
rowButtons.onBuyClick = { store.dispatch(WalletAction.TradeCryptoAction.Buy()) }
@ -128,7 +138,7 @@ class SingleWalletView : WalletView() {
rowButtons.onTradeClick = { store.dispatch(WalletAction.DialogAction.ChooseTradeActionDialog) }
rowButtons.onSendClick = {
when (state.mainButton) {
when (walletData.mainButton) {
is WalletMainButton.SendButton -> store.dispatch(WalletAction.Send())
is WalletMainButton.CreateWalletButton -> store.dispatch(WalletAction.CreateWallet)
}

View file

@ -12,6 +12,12 @@ class CardExchangeRules(
val cardProvider: () -> Card?,
) : ExchangeRules {
override fun featureIsSwitchedOn(): Boolean {
val card = cardProvider() ?: return false
return !card.isStart2Coin
}
override fun isBuyAllowed(): Boolean {
val card = cardProvider() ?: return false

View file

@ -26,6 +26,8 @@ class CurrencyExchangeManager(
private val primaryRules: ExchangeRules,
) : ExchangeService, ExchangeUrlBuilder {
override fun featureIsSwitchedOn(): Boolean = primaryRules.featureIsSwitchedOn()
override suspend fun update() {
buyService.update()
sellService.update()

View file

@ -1,13 +1,22 @@
package com.tangem.tap.network.exchangeServices
import com.tangem.blockchain.common.Blockchain
import com.tangem.tap.common.feature.Feature
import com.tangem.tap.features.wallet.models.Currency
interface ExchangeService: ExchangeRules {
interface Exchanger {
fun isBuyAllowed(): Boolean
fun isSellAllowed(): Boolean
fun availableForBuy(currency: Currency):Boolean
fun availableForSell(currency: Currency):Boolean
}
interface ExchangeService: Feature, Exchanger {
suspend fun update()
companion object {
fun dummy(): ExchangeService = object : ExchangeService {
override fun featureIsSwitchedOn(): Boolean = false
override suspend fun update() {}
override fun isBuyAllowed(): Boolean = false
override fun isSellAllowed(): Boolean = false
@ -17,14 +26,11 @@ interface ExchangeService: ExchangeRules {
}
}
interface ExchangeRules {
fun isBuyAllowed(): Boolean
fun isSellAllowed(): Boolean
fun availableForBuy(currency: Currency):Boolean
fun availableForSell(currency: Currency):Boolean
interface ExchangeRules: Feature, Exchanger {
companion object {
fun dummy(): ExchangeRules = object : ExchangeRules {
override fun featureIsSwitchedOn(): Boolean = false
override fun isBuyAllowed(): Boolean = false
override fun isSellAllowed(): Boolean = false
override fun availableForBuy(currency: Currency): Boolean = false

View file

@ -28,6 +28,8 @@ class MercuryoService(
private val blockchainsAvailableToBuy = mutableListOf<Blockchain>()
private val tokensAvailableToBy = mutableMapOf<String, MutableList<Blockchain>>()
override fun featureIsSwitchedOn(): Boolean = true
override suspend fun update() {
when (val result = performRequest { api.currencies(apiVersion) }) {
is Result.Success -> {

View file

@ -29,6 +29,8 @@ class MoonPayService(
private var status: MoonPayStatus? = null
override fun featureIsSwitchedOn(): Boolean = true
override suspend fun update() {
withIOContext {
performRequest {