Updated on 2026-08-14

This commit is contained in:
Tangem 2022-10-28 17:24:13 +05:00
commit f05063eed2
12 changed files with 90 additions and 64 deletions

View file

@ -6,7 +6,7 @@ import com.tangem.operations.backup.BackupService
/**
[REDACTED_AUTHOR]
*/
fun BackupService.primaryCardIsSaltPay(): Boolean {
fun BackupService.primaryCardIsSaltPayVisa(): Boolean {
return primaryCardId?.slice(0..3)?.let {
SaltPayWorkaround.isVisaBatchId(it)
} ?: false

View file

@ -6,6 +6,7 @@ import android.webkit.WebView
[REDACTED_AUTHOR]
*/
fun WebView.configureSettings() {
resumeTimers()
settings.apply {
javaScriptEnabled = true
domStorageEnabled = true
@ -15,5 +16,4 @@ fun WebView.configureSettings() {
fun WebView.stop() {
stopLoading()
pauseTimers()
destroy()
}

View file

@ -140,7 +140,10 @@ private fun handleAction(action: Action, appState: () -> AppState?, dispatch: Di
secretKey = moonPaySecretKey,
logEnabled = LogConfig.network.moonPayService,
)
val cardProvider = { store.state.globalState.scanResponse?.card }
val cardProvider = {
store.state.globalState.scanResponse?.card
?: store.state.globalState.onboardingState.onboardingManager?.scanResponse?.card
}
val exchangeManager = CurrencyExchangeManager(
buyService = buyService,

View file

@ -25,7 +25,7 @@ class DetailsViewModel(private val store: Store<AppState>) {
SettingsElement.WalletConnect -> {
if (state.scanResponse?.card?.isMultiwalletAllowed == true) it else null
}
SettingsElement.Chat -> if (state.scanResponse?.card?.isSaltPay != true) it else null
SettingsElement.SendFeedback -> if (state.scanResponse?.card?.isSaltPay != true) it else null
SettingsElement.LinkMoreCards -> {
// if (state.createBackupAllowed) it else null
// TODO: SaltPay: temporary excluding backup process for Visa cards

View file

@ -1,11 +1,14 @@
package com.tangem.tap.features.home.redux
import com.tangem.common.card.Card
import com.tangem.common.core.TangemError
import com.tangem.common.services.Result
import com.tangem.domain.common.ScanResponse
import com.tangem.domain.common.extensions.withIOContext
import com.tangem.domain.common.extensions.withMainContext
import com.tangem.operations.backup.BackupService
import com.tangem.tap.DELAY_SDK_DIALOG_CLOSE
import com.tangem.tap.backupService
import com.tangem.tap.common.analytics.Analytics
import com.tangem.tap.common.analytics.AnalyticsEventAnOld
import com.tangem.tap.common.analytics.AnalyticsParamAnOld
@ -15,6 +18,7 @@ import com.tangem.tap.common.entities.IndeterminateProgressButton
import com.tangem.tap.common.extensions.dispatchDialogShow
import com.tangem.tap.common.extensions.dispatchOpenUrl
import com.tangem.tap.common.extensions.onCardScanned
import com.tangem.tap.common.extensions.primaryCardIsSaltPayVisa
import com.tangem.tap.common.postUiDelayBg
import com.tangem.tap.common.redux.AppDialog
import com.tangem.tap.common.redux.AppState
@ -84,6 +88,7 @@ private fun handleHomeAction(appState: () -> AppState?, action: Action, dispatch
onSuccess = { scanResponse ->
store.dispatch(HomeAction.ScanInProgress(false))
checkForUnfinishedBackupForSaltPay(
backupService = backupService,
scanResponse = scanResponse,
nextHandler = {
showDisclaimerIfNeed(
@ -116,13 +121,23 @@ private fun handleHomeAction(appState: () -> AppState?, action: Action, dispatch
* see BackupAction.CheckForUnfinishedBackup
* If user touches card other than Visa SaltPay - show dialog and block next processing
*/
private fun checkForUnfinishedBackupForSaltPay(scanResponse: ScanResponse, nextHandler: (ScanResponse) -> Unit) {
if (BackupAction.hasSaltPayUnfinishedBackup()) {
if (scanResponse.isSaltPayVisa()) {
nextHandler(scanResponse)
} else {
showSaltPayTapVisaLogoCardDialog()
}
private fun checkForUnfinishedBackupForSaltPay(
backupService: BackupService,
scanResponse: ScanResponse,
nextHandler: (ScanResponse) -> Unit,
) {
if (!backupService.hasIncompletedBackup || !backupService.primaryCardIsSaltPayVisa()) {
nextHandler(scanResponse)
return
}
fun isTheSamePrimaryCard(card: Card): Boolean {
return backupService.primaryCardId?.let { it == card.cardId } ?: false
}
if (scanResponse.isSaltPayWallet() || !isTheSamePrimaryCard(scanResponse.card)) {
changeButtonState(ButtonState.ENABLED)
showSaltPayTapVisaLogoCardDialog()
} else {
nextHandler(scanResponse)
}

View file

@ -7,6 +7,7 @@ import com.tangem.tap.features.onboarding.products.wallet.saltPay.SaltPayActivat
import com.tangem.tap.features.onboarding.products.wallet.saltPay.message.SaltPayActivationError
import com.tangem.tap.features.onboarding.products.wallet.saltPay.redux.SaltPayActivationStep
import com.tangem.tap.features.onboarding.products.wallet.saltPay.redux.update
import com.tangem.tap.preferencesStorage
/**
[REDACTED_AUTHOR]
@ -19,10 +20,16 @@ class OnboardingSaltPayHelper {
manager: SaltPayActivationManager,
): Result<Boolean> {
return try {
val updatedStep = manager.update(SaltPayActivationStep.None, null).successOr { return it }
val isRegistrationCase = updatedStep != SaltPayActivationStep.Finished
var updatedStep = manager.update(SaltPayActivationStep.None, null).successOr { return it }
val cardStorage = preferencesStorage.usedCardsPrefStorage
val activationIsFinished = cardStorage.isActivationFinished(scanResponse.card.cardId)
if (updatedStep == SaltPayActivationStep.Success && activationIsFinished) {
updatedStep = SaltPayActivationStep.Finished
}
val isActivationCase = updatedStep != SaltPayActivationStep.Finished
val isBackupCase = scanResponse.card.backupStatus?.isActive == false
Result.Success(isRegistrationCase || isBackupCase)
Result.Success(isActivationCase || isBackupCase)
} catch (ex: Exception) {
Result.Failure(ex)
} catch (error: SaltPayActivationError) {

View file

@ -1,8 +1,6 @@
package com.tangem.tap.features.onboarding.products.wallet.redux
import android.graphics.Bitmap
import com.tangem.tap.backupService
import com.tangem.tap.common.extensions.primaryCardIsSaltPay
import org.rekotlin.Action
sealed class OnboardingWalletAction : Action {
@ -70,10 +68,4 @@ sealed class BackupAction : Action {
object DiscardBackup : BackupAction()
object DiscardSavedBackup : BackupAction()
object ResumeFoundUnfinishedBackup : BackupAction()
companion object {
fun hasSaltPayUnfinishedBackup(): Boolean {
return backupService.hasIncompletedBackup && backupService.primaryCardIsSaltPay()
}
}
}

View file

@ -13,7 +13,7 @@ import com.tangem.tap.common.analytics.Analytics
import com.tangem.tap.common.analytics.events.Onboarding
import com.tangem.tap.common.extensions.dispatchDialogShow
import com.tangem.tap.common.extensions.dispatchOnMain
import com.tangem.tap.common.extensions.primaryCardIsSaltPay
import com.tangem.tap.common.extensions.primaryCardIsSaltPayVisa
import com.tangem.tap.common.redux.AppState
import com.tangem.tap.common.redux.global.GlobalAction
import com.tangem.tap.common.redux.navigation.AppScreen
@ -328,7 +328,7 @@ private fun handleBackupAction(appState: () -> AppState?, action: BackupAction)
backupService.discardSavedBackup()
}
is BackupAction.CheckForUnfinishedBackup -> {
if (backupService.hasIncompletedBackup && !backupService.primaryCardIsSaltPay()) {
if (backupService.hasIncompletedBackup && !backupService.primaryCardIsSaltPayVisa()) {
store.dispatch(GlobalAction.ShowDialog(BackupDialog.UnfinishedBackupFound))
}
}

View file

@ -76,7 +76,7 @@ private class BackupReducer {
is BackupAction.IntroduceBackup -> BackupState(
backupStep = BackupStep.InitBackup,
maxBackupCards = if (isSaltPay) 1 else 2,
canSkipBackup = !isSaltPay,
canSkipBackup = state.canSkipBackup,
)
BackupAction.StartAddingPrimaryCard -> state.copy(backupStep = BackupStep.ScanOriginCard)
BackupAction.StartAddingBackupCards -> {

View file

@ -300,12 +300,17 @@ private fun determineStep(
amountToClaim: Amount?,
response: RegistrationResponse.Item,
): SaltPayActivationStep {
fun getStepBaseOnAmountToClaim(amount: Amount?): SaltPayActivationStep = when (amount) {
null -> SaltPayActivationStep.Success
else -> SaltPayActivationStep.Claim
}
return when {
response.passed != true -> throw SaltPayActivationError.CardNotPassed(response.error)
response.disabledByAdmin == true -> throw SaltPayActivationError.CardDisabled(response.error)
// go to claim screen
response.active == true -> SaltPayActivationStep.Claim
response.active == true -> getStepBaseOnAmountToClaim(amountToClaim)
// pinSet is false, go toPin screen
response.pinSet == false -> SaltPayActivationStep.NeedPin
@ -316,10 +321,7 @@ private fun determineStep(
KYCStatus.NOT_STARTED, KYCStatus.STARTED -> SaltPayActivationStep.KycIntro
KYCStatus.WAITING_FOR_APPROVAL -> SaltPayActivationStep.KycWaiting
KYCStatus.CORRECTION_REQUESTED, KYCStatus.REJECTED -> SaltPayActivationStep.KycReject
KYCStatus.APPROVED -> when (amountToClaim) {
null -> SaltPayActivationStep.Success
else -> SaltPayActivationStep.Claim
}
KYCStatus.APPROVED -> getStepBaseOnAmountToClaim(amountToClaim)
else -> SaltPayActivationStep.KycIntro
}
SaltPayActivationStep.KycReject -> when (response.kycStatus) {
@ -327,20 +329,14 @@ private fun determineStep(
KYCStatus.WAITING_FOR_APPROVAL -> SaltPayActivationStep.KycWaiting
KYCStatus.CORRECTION_REQUESTED -> SaltPayActivationStep.KycStart
KYCStatus.REJECTED -> SaltPayActivationStep.KycStart
KYCStatus.APPROVED -> when (amountToClaim) {
null -> SaltPayActivationStep.Success
else -> SaltPayActivationStep.Claim
}
KYCStatus.APPROVED -> getStepBaseOnAmountToClaim(amountToClaim)
else -> SaltPayActivationStep.KycIntro
}
else -> when (response.kycStatus) {
KYCStatus.NOT_STARTED, KYCStatus.STARTED -> SaltPayActivationStep.KycIntro
KYCStatus.WAITING_FOR_APPROVAL -> SaltPayActivationStep.KycWaiting
KYCStatus.CORRECTION_REQUESTED, KYCStatus.REJECTED -> SaltPayActivationStep.KycReject
KYCStatus.APPROVED -> when (amountToClaim) {
null -> SaltPayActivationStep.Finished
else -> SaltPayActivationStep.Claim
}
KYCStatus.APPROVED -> getStepBaseOnAmountToClaim(amountToClaim)
else -> SaltPayActivationStep.KycIntro
}
}

View file

@ -38,16 +38,6 @@ class WalletBackupAnimator(
override fun updateBackupState(backupState: BackupState) {
}
override fun setupCreateWalletState() {
currentStep = STEP_CREATE_WALLET
cardsWidget.toFolded(false)
ORIGIN.alpha(1f)
FIRST_BACKUP.alpha(1f)
SECOND_BACKUP.alpha(1f)
}
override fun showBackupIntro(state: BackupState) {
currentStep = STEP_BACKUP_INTRO
@ -58,6 +48,16 @@ class WalletBackupAnimator(
cardsWidget.toWelcome()
}
override fun setupCreateWalletState() {
currentStep = STEP_CREATE_WALLET
cardsWidget.toFolded(false)
ORIGIN.alpha(1f)
FIRST_BACKUP.alpha(1f)
SECOND_BACKUP.alpha(1f)
}
override fun showScanOriginCard() {
currentStep = STEP_SCAN_ORIGIN_CARD
@ -75,7 +75,7 @@ class WalletBackupAnimator(
SECOND_BACKUP.animateAlpha(0.2f, 400)
}
STEP_BACKUP_INTRO -> {
cardsWidget.toFolded(duration = 200) { cardsWidget.toFan() }
cardsWidget.toFolded(duration = 300) { cardsWidget.toFan() }
FIRST_BACKUP.animateAlpha(0.6f, 400, 250)
SECOND_BACKUP.animateAlpha(0.2f, 400, 250)
}
@ -112,11 +112,14 @@ class WalletBackupAnimator(
)
}
override fun showWriteBackupCard(state: BackupState, backupCard: Int) {
private var firstBackupCardAnimated = false
private var secondBackupCardAnimated = false
override fun showWriteBackupCard(state: BackupState, backupCard: Int) {
when (viewState) {
State.TwoCards -> {
if (currentStep == STEP_WRITE_BACKUP_CARD) return
if (firstBackupCardAnimated) return
firstBackupCardAnimated = true
val delay = if (currentStep == UNDEFINED) 700L else 0
postUiDelayBg(delay) {
@ -129,6 +132,8 @@ class WalletBackupAnimator(
State.TreeCards -> {
when (backupCard) {
1 -> {
if (firstBackupCardAnimated) return
firstBackupCardAnimated = true
FIRST_BACKUP.alpha(1f)
cardsWidget.leapfrogWidget.leap {
SECOND_BACKUP.alpha(0.4f)
@ -136,6 +141,8 @@ class WalletBackupAnimator(
}
}
2 -> {
if (secondBackupCardAnimated) return
secondBackupCardAnimated = true
SECOND_BACKUP.alpha(1f)
cardsWidget.leapfrogWidget.leap {
ORIGIN.alpha(0.4f)