@@ -293,7 +293,7 @@ class AppViewModel @Inject constructor(
293293
294294 SendEvent .SpeedAndFee -> setSendEffect(SendEffect .NavigateToFee )
295295 SendEvent .SwipeToPay -> onSwipeToPay()
296- SendEvent .ConfirmAmountWarning -> onConfirmAmountWarning()
296+ is SendEvent .ConfirmAmountWarning -> onConfirmAmountWarning(it.warning )
297297 SendEvent .DismissAmountWarning -> onDismissAmountWarning()
298298 SendEvent .PayConfirmed -> onConfirmPay()
299299 SendEvent .BackToAmount -> setSendEffect(SendEffect .PopBack (SendRoute .Amount ))
@@ -818,29 +818,36 @@ class AppViewModel @Inject constructor(
818818 val amount = _sendUiState .value.amount
819819
820820 handleSanityChecks(amount)
821- if (_sendUiState .value.showAmountWarningDialog != null ) return @launch // await for dialog UI interaction
821+ if (_sendUiState .value.showSanityWarningDialog != null ) return @launch // await for dialog UI interaction
822822
823823 _sendUiState .update { it.copy(shouldConfirmPay = true ) }
824824 }
825825 }
826826
827827 private suspend fun handleSanityChecks (amountSats : ULong ) {
828- if (_sendUiState .value.showAmountWarningDialog != null ) return
828+ if (_sendUiState .value.showSanityWarningDialog != null ) return
829829
830830 val settings = settingsStore.data.first()
831- val amountInUsd = currencyRepo.convertSatsToFiat(amountSats.toLong(), " USD" ).getOrNull() ? : return
832- if (amountInUsd.value > BigDecimal (SEND_AMOUNT_WARNING_THRESHOLD ) && settings.enableSendAmountWarning) {
831+
832+ if (
833+ amountSats > BigDecimal .valueOf(walletRepo.balanceState.value.totalSats.toLong())
834+ .times(BigDecimal (MAX_BALANCE_FRACTION )).toLong().toUInt() &&
835+ SanityWarning .OVER_HALF_BALANCE !in _sendUiState .value.confirmedWarnings
836+ ) {
833837 _sendUiState .update {
834- it.copy(showAmountWarningDialog = AmountWarning . VALUE_OVER_100_USD )
838+ it.copy(showSanityWarningDialog = SanityWarning . OVER_HALF_BALANCE )
835839 }
836840 return
837841 }
838842
839- if (amountSats > BigDecimal .valueOf(walletRepo.balanceState.value.totalSats.toLong())
840- .times(BigDecimal (0.5 )).toLong().toUInt()
843+ val amountInUsd = currencyRepo.convertSatsToFiat(amountSats.toLong(), " USD" ).getOrNull() ? : return
844+ if (
845+ amountInUsd.value > BigDecimal (SEND_AMOUNT_WARNING_THRESHOLD ) &&
846+ settings.enableSendAmountWarning &&
847+ SanityWarning .VALUE_OVER_100_USD !in _sendUiState .value.confirmedWarnings
841848 ) {
842849 _sendUiState .update {
843- it.copy(showAmountWarningDialog = AmountWarning . OVER_HALF_BALANCE )
850+ it.copy(showSanityWarningDialog = SanityWarning . VALUE_OVER_100_USD )
844851 }
845852 return
846853 }
@@ -854,25 +861,31 @@ class AppViewModel @Inject constructor(
854861 utxosToSpend = _sendUiState .value.selectedUtxos,
855862 ).getOrNull() ? : return
856863
857- if (totalFee > BigDecimal .valueOf(amountSats.toLong())
858- .times(BigDecimal (0.5 )).toLong().toUInt()
864+ if (
865+ totalFee > BigDecimal .valueOf(
866+ amountSats.toLong()
867+ ).times(BigDecimal (MAX_FEE_AMOUNT_RATIO )).toLong().toUInt() &&
868+ SanityWarning .FEE_OVER_HALF_VALUE !in _sendUiState .value.confirmedWarnings
859869 ) {
860870 _sendUiState .update {
861- it.copy(showAmountWarningDialog = AmountWarning .FEE_OVER_HALF_VALUE )
871+ it.copy(showSanityWarningDialog = SanityWarning .FEE_OVER_HALF_VALUE )
862872 }
863873 return
864874 }
865875
866- val feeInUsd = currencyRepo.convertSatsToFiat(amountSats.toLong(), " USD" ).getOrNull() ? : return
867- if (feeInUsd.value > BigDecimal (10 )) {
876+ val feeInUsd = currencyRepo.convertSatsToFiat(totalFee.toLong(), " USD" ).getOrNull() ? : return
877+ if (
878+ feeInUsd.value > BigDecimal (TEN_USD ) &&
879+ SanityWarning .FEE_OVER_10_USD !in _sendUiState .value.confirmedWarnings
880+ ) {
868881 _sendUiState .update {
869- it.copy(showAmountWarningDialog = AmountWarning .FEE_OVER_10_USD )
882+ it.copy(showSanityWarningDialog = SanityWarning .FEE_OVER_10_USD )
870883 }
871884 return
872885 }
873886
874887 _sendUiState .update {
875- it.copy(showAmountWarningDialog = null )
888+ it.copy(showSanityWarningDialog = null )
876889 }
877890 }
878891
@@ -1401,20 +1414,21 @@ class AppViewModel @Inject constructor(
14011414 }
14021415 }
14031416
1404- private fun onConfirmAmountWarning () {
1417+ private fun onConfirmAmountWarning (warning : SanityWarning ) {
14051418 viewModelScope.launch {
14061419 _sendUiState .update {
14071420 it.copy(
1408- showAmountWarningDialog = null ,
1409- shouldConfirmPay = true ,
1421+ showSanityWarningDialog = null ,
1422+ confirmedWarnings = it.confirmedWarnings + warning
14101423 )
14111424 }
14121425 }
1426+ onSwipeToPay()
14131427 }
14141428
14151429 private fun onDismissAmountWarning () {
14161430 _sendUiState .update {
1417- it.copy(showAmountWarningDialog = null )
1431+ it.copy(showSanityWarningDialog = null )
14181432 }
14191433 }
14201434
@@ -1434,6 +1448,9 @@ class AppViewModel @Inject constructor(
14341448 companion object {
14351449 private const val TAG = " AppViewModel"
14361450 private const val SEND_AMOUNT_WARNING_THRESHOLD = 100.0
1451+ private const val TEN_USD = 10
1452+ private const val MAX_BALANCE_FRACTION = 0.5
1453+ private const val MAX_FEE_AMOUNT_RATIO = 0.5
14371454 }
14381455}
14391456
@@ -1450,7 +1467,8 @@ data class SendUiState(
14501467 val payMethod : SendMethod = SendMethod .ONCHAIN ,
14511468 val selectedTags : List <String > = listOf(),
14521469 val decodedInvoice : LightningInvoice ? = null ,
1453- val showAmountWarningDialog : AmountWarning ? = null ,
1470+ val showSanityWarningDialog : SanityWarning ? = null ,
1471+ val confirmedWarnings : List <SanityWarning > = listOf(),
14541472 val shouldConfirmPay : Boolean = false ,
14551473 val selectedUtxos : List <SpendableUtxo >? = null ,
14561474 val lnurl : LnurlParams ? = null ,
@@ -1462,7 +1480,7 @@ data class SendUiState(
14621480 val fees : Map <FeeRate , Long > = emptyMap(),
14631481)
14641482
1465- enum class AmountWarning (@StringRes val message : Int , val testTag : String ) {
1483+ enum class SanityWarning (@StringRes val message : Int , val testTag : String ) {
14661484 VALUE_OVER_100_USD (R .string.wallet__send_dialog1, " SendDialog1" ),
14671485 OVER_HALF_BALANCE (R .string.wallet__send_dialog2, " SendDialog2" ),
14681486 FEE_OVER_HALF_VALUE (R .string.wallet__send_dialog3, " SendDialog3" ),
@@ -1513,7 +1531,7 @@ sealed interface SendEvent {
15131531 data object SwipeToPay : SendEvent
15141532 data object SpeedAndFee : SendEvent
15151533 data object PaymentMethodSwitch : SendEvent
1516- data object ConfirmAmountWarning : SendEvent
1534+ data class ConfirmAmountWarning ( val warning : SanityWarning ) : SendEvent
15171535 data object DismissAmountWarning : SendEvent
15181536 data object PayConfirmed : SendEvent
15191537 data object BackToAmount : SendEvent
0 commit comments