Updated on 2026-08-14
This commit is contained in:
parent
15ba41b158
commit
df7e72f527
9 changed files with 26 additions and 49 deletions
|
|
@ -33,7 +33,7 @@ internal class SendStateFactory(
|
|||
private val userWalletProvider: Provider<UserWallet>,
|
||||
private val appCurrencyProvider: Provider<AppCurrency>,
|
||||
private val cryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus?>,
|
||||
private val isTapHelpPreviewEnabledProvider: Provider<Boolean>,
|
||||
private val validateWalletMemoUseCase: ValidateWalletMemoUseCase,
|
||||
private val getExplorerTransactionUrlUseCase: GetExplorerTransactionUrlUseCase,
|
||||
|
|
|
|||
|
|
@ -13,10 +13,10 @@ import com.tangem.utils.converter.Converter
|
|||
internal class FeeConverter(
|
||||
private val clickIntents: SendClickIntents,
|
||||
private val appCurrencyProvider: Provider<AppCurrency>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus?>,
|
||||
) : Converter<FeeSelectorState.Content, Fee> {
|
||||
|
||||
private val ethereumCustomFeeConverter by lazy {
|
||||
private val ethereumCustomFeeConverter by lazy(LazyThreadSafetyMode.NONE) {
|
||||
EthereumCustomFeeConverter(
|
||||
clickIntents = clickIntents,
|
||||
appCurrencyProvider = appCurrencyProvider,
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ import kotlinx.collections.immutable.persistentListOf
|
|||
internal class FeeStateFactory(
|
||||
private val clickIntents: SendClickIntents,
|
||||
private val currentStateProvider: Provider<SendUiState>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus?>,
|
||||
private val appCurrencyProvider: Provider<AppCurrency>,
|
||||
private val isFeeApproximateUseCase: IsFeeApproximateUseCase,
|
||||
) {
|
||||
|
|
@ -153,7 +153,7 @@ internal class FeeStateFactory(
|
|||
}
|
||||
|
||||
private fun isFeeApproximate(fee: Fee): Boolean {
|
||||
val cryptoCurrencyStatus = feeCryptoCurrencyStatusProvider()
|
||||
val cryptoCurrencyStatus = feeCryptoCurrencyStatusProvider() ?: return false
|
||||
return isFeeApproximateUseCase(
|
||||
networkId = cryptoCurrencyStatus.currency.network.id,
|
||||
amountType = fee.amount.type,
|
||||
|
|
|
|||
|
|
@ -14,10 +14,10 @@ import kotlinx.collections.immutable.persistentListOf
|
|||
internal class SendFeeCustomFieldConverter(
|
||||
private val clickIntents: SendClickIntents,
|
||||
private val appCurrencyProvider: Provider<AppCurrency>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus?>,
|
||||
) : Converter<Fee, ImmutableList<SendTextField.CustomFee>> {
|
||||
|
||||
private val ethereumCustomFeeConverter by lazy {
|
||||
private val ethereumCustomFeeConverter by lazy(LazyThreadSafetyMode.NONE) {
|
||||
EthereumCustomFeeConverter(
|
||||
clickIntents = clickIntents,
|
||||
appCurrencyProvider = appCurrencyProvider,
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ import kotlinx.collections.immutable.persistentListOf
|
|||
|
||||
internal class SendFeeStateConverter(
|
||||
private val appCurrencyProvider: Provider<AppCurrency>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus?>,
|
||||
) : Converter<Unit, SendStates.FeeState> {
|
||||
|
||||
override fun convert(value: Unit): SendStates.FeeState {
|
||||
|
|
@ -17,7 +17,7 @@ internal class SendFeeStateConverter(
|
|||
feeSelectorState = FeeSelectorState.Error,
|
||||
fee = null,
|
||||
notifications = persistentListOf(),
|
||||
rate = feeCryptoCurrencyStatusProvider().value.fiatRate,
|
||||
rate = feeCryptoCurrencyStatusProvider()?.value?.fiatRate,
|
||||
appCurrency = appCurrencyProvider(),
|
||||
isFeeApproximate = false,
|
||||
isCustomSelected = false,
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ import java.math.RoundingMode
|
|||
internal class EthereumCustomFeeConverter(
|
||||
private val clickIntents: SendClickIntents,
|
||||
private val appCurrencyProvider: Provider<AppCurrency>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus>,
|
||||
private val feeCryptoCurrencyStatusProvider: Provider<CryptoCurrencyStatus?>,
|
||||
) : Converter<Fee.Ethereum, ImmutableList<SendTextField.CustomFee>> {
|
||||
|
||||
override fun convert(value: Fee.Ethereum): ImmutableList<SendTextField.CustomFee> {
|
||||
|
|
@ -49,8 +49,8 @@ internal class EthereumCustomFeeConverter(
|
|||
keyboardActions = KeyboardActions(),
|
||||
),
|
||||
SendTextField.CustomFee(
|
||||
value = value.gasPrice.toString(),
|
||||
decimals = GAS_DECIMALS,
|
||||
value = value.gasPrice.toBigDecimal().movePointLeft(GIGA_DECIMALS).toString(),
|
||||
decimals = GIGA_DECIMALS,
|
||||
symbol = ETHEREUM_GAS_UNIT,
|
||||
title = resourceReference(R.string.send_gas_price),
|
||||
footer = resourceReference(R.string.send_gas_price_footer),
|
||||
|
|
@ -105,7 +105,7 @@ internal class EthereumCustomFeeConverter(
|
|||
|
||||
private fun getFeeFormatted(fee: BigDecimal?): TextReference {
|
||||
val appCurrency = appCurrencyProvider()
|
||||
val rate = feeCryptoCurrencyStatusProvider().value.fiatRate
|
||||
val rate = feeCryptoCurrencyStatusProvider()?.value?.fiatRate
|
||||
val fiatFee = rate?.let { fee?.multiply(it) }
|
||||
return stringReference(
|
||||
BigDecimalFormatter.formatFiatAmount(
|
||||
|
|
@ -118,7 +118,7 @@ internal class EthereumCustomFeeConverter(
|
|||
|
||||
private fun checkExceedBalance(feeAmount: BigDecimal?): Boolean {
|
||||
val cryptoCurrencyStatus = feeCryptoCurrencyStatusProvider()
|
||||
val currencyCryptoAmount = cryptoCurrencyStatus.value.amount ?: BigDecimal.ZERO
|
||||
val currencyCryptoAmount = cryptoCurrencyStatus?.value?.amount ?: BigDecimal.ZERO
|
||||
|
||||
return feeAmount == null || feeAmount.isZero() || feeAmount > currencyCryptoAmount
|
||||
}
|
||||
|
|
@ -134,9 +134,9 @@ internal class EthereumCustomFeeConverter(
|
|||
setEmpty(GAS_PRICE)
|
||||
} else {
|
||||
val newFeeAmountDecimal = value.parseToBigDecimal(this[FEE_AMOUNT].decimals)
|
||||
val newFeeAmount = newFeeAmountDecimal.movePointRight(this[FEE_AMOUNT].decimals)
|
||||
val newGasPrice = newFeeAmount.divide(gasLimit, GAS_DECIMALS, RoundingMode.HALF_UP)
|
||||
set(GAS_PRICE, this[GAS_PRICE].copy(value = newGasPrice.parseBigDecimal(GAS_DECIMALS)))
|
||||
val newFeeAmount = newFeeAmountDecimal.movePointRight(this[GAS_PRICE].decimals) // from ETH to GWEI
|
||||
val newGasPrice = newFeeAmount.divide(gasLimit, this[GAS_PRICE].decimals, RoundingMode.HALF_UP)
|
||||
set(GAS_PRICE, this[GAS_PRICE].copy(value = newGasPrice.parseBigDecimal(this[GAS_PRICE].decimals)))
|
||||
set(
|
||||
index,
|
||||
this[index].copy(
|
||||
|
|
@ -154,8 +154,8 @@ internal class EthereumCustomFeeConverter(
|
|||
setEmpty(GAS_PRICE)
|
||||
} else {
|
||||
val newGasPrice = value.parseToBigDecimal(this[GAS_PRICE].decimals)
|
||||
.movePointLeft(this[GAS_PRICE].decimals)
|
||||
val newFeeAmount = (gasLimit * newGasPrice).movePointLeft(this[FEE_AMOUNT].decimals)
|
||||
.movePointLeft(this[GAS_PRICE].decimals) // from GWEI to ETH
|
||||
val newFeeAmount = gasLimit * newGasPrice
|
||||
set(
|
||||
FEE_AMOUNT,
|
||||
this[FEE_AMOUNT].copy(
|
||||
|
|
@ -174,7 +174,7 @@ internal class EthereumCustomFeeConverter(
|
|||
} else {
|
||||
val newGasLimit = value.parseToBigDecimal(this[GAS_LIMIT].decimals)
|
||||
val gasPrice = this[GAS_PRICE].value.parseToBigDecimal(this[GAS_PRICE].decimals)
|
||||
.movePointLeft(this[FEE_AMOUNT].decimals)
|
||||
.movePointLeft(this[GAS_PRICE].decimals) // from GWEI to ETH
|
||||
val newFeeAmount = newGasLimit * gasPrice
|
||||
set(
|
||||
FEE_AMOUNT,
|
||||
|
|
@ -198,6 +198,7 @@ internal class EthereumCustomFeeConverter(
|
|||
|
||||
companion object {
|
||||
private const val ETHEREUM_GAS_UNIT = "GWEI"
|
||||
private const val GIGA_DECIMALS = 9
|
||||
private const val FEE_AMOUNT = 0
|
||||
private const val GAS_PRICE = 1
|
||||
private const val GAS_LIMIT = 2
|
||||
|
|
|
|||
|
|
@ -140,7 +140,7 @@ private fun SendingText(uiState: SendUiState, isVisible: Boolean, modifier: Modi
|
|||
val feeState = uiState.feeState
|
||||
val fiatRate = feeState?.rate
|
||||
val fiatAmount = amountState?.amountTextField?.fiatAmount
|
||||
val feeFiat = feeState?.fee?.amount?.value?.multiply(fiatRate)
|
||||
val feeFiat = fiatRate?.let { feeState.fee?.amount?.value?.multiply(it) }
|
||||
val sendingFiat = feeFiat?.let { fiatAmount?.value?.plus(it) }
|
||||
|
||||
if (feeFiat != null && sendingFiat != null) {
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@ import androidx.compose.foundation.background
|
|||
import androidx.compose.foundation.clickable
|
||||
import androidx.compose.foundation.layout.*
|
||||
import androidx.compose.foundation.shape.RoundedCornerShape
|
||||
import androidx.compose.material3.HorizontalDivider
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Alignment
|
||||
|
|
@ -41,7 +40,6 @@ internal fun RecipientBlock(
|
|||
.padding(TangemTheme.dimens.spacing12),
|
||||
) {
|
||||
AddressBlock(recipientState.addressTextField)
|
||||
MemoBlock(recipientState.memoTextField)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -72,28 +70,6 @@ private fun AddressBlock(address: SendTextField.RecipientAddress) {
|
|||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
private fun MemoBlock(memo: SendTextField.RecipientMemo?) {
|
||||
val showMemo = memo != null && memo.value.isNotBlank()
|
||||
if (showMemo) {
|
||||
HorizontalDivider(
|
||||
color = TangemTheme.colors.stroke.primary,
|
||||
modifier = Modifier.padding(vertical = TangemTheme.dimens.spacing12),
|
||||
)
|
||||
Text(
|
||||
text = memo?.label?.resolveReference().orEmpty(),
|
||||
style = TangemTheme.typography.caption2,
|
||||
color = TangemTheme.colors.text.secondary,
|
||||
)
|
||||
Text(
|
||||
text = memo?.value.orEmpty(),
|
||||
style = TangemTheme.typography.body2,
|
||||
color = TangemTheme.colors.text.primary1,
|
||||
modifier = Modifier.padding(top = TangemTheme.dimens.spacing8),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
// region Preview
|
||||
@Preview
|
||||
@Composable
|
||||
|
|
|
|||
|
|
@ -184,7 +184,7 @@ internal class SendViewModel @Inject constructor(
|
|||
private var isTapHelpPreviewEnabled: Boolean = false
|
||||
private var coinCryptoCurrencyStatus: CryptoCurrencyStatus by Delegates.notNull()
|
||||
private var cryptoCurrencyStatus: CryptoCurrencyStatus by Delegates.notNull()
|
||||
private var feeCryptoCurrencyStatus: CryptoCurrencyStatus by Delegates.notNull()
|
||||
private var feeCryptoCurrencyStatus: CryptoCurrencyStatus? = null
|
||||
|
||||
private var balanceJobHolder = JobHolder()
|
||||
private var balanceHidingJobHolder = JobHolder()
|
||||
|
|
@ -328,12 +328,12 @@ internal class SendViewModel @Inject constructor(
|
|||
private suspend fun getFeeCurrencyStatusSync(
|
||||
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||
isMultiCurrency: Boolean,
|
||||
): CryptoCurrencyStatus {
|
||||
): CryptoCurrencyStatus? {
|
||||
return if (isMultiCurrency) {
|
||||
getFeePaidCryptoCurrencyStatusSyncUseCase(
|
||||
userWalletId = userWalletId,
|
||||
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||
).getOrNull() ?: error("Fee currency is unreachable")
|
||||
).getOrNull()
|
||||
} else {
|
||||
cryptoCurrencyStatus
|
||||
}
|
||||
|
|
@ -354,7 +354,7 @@ internal class SendViewModel @Inject constructor(
|
|||
private fun onDataLoaded(
|
||||
currencyStatus: CryptoCurrencyStatus,
|
||||
coinCurrencyStatus: CryptoCurrencyStatus,
|
||||
feeCurrencyStatus: CryptoCurrencyStatus,
|
||||
feeCurrencyStatus: CryptoCurrencyStatus?,
|
||||
) {
|
||||
cryptoCurrencyStatus = currencyStatus
|
||||
coinCryptoCurrencyStatus = coinCurrencyStatus
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue