Updated on 2026-08-14
This commit is contained in:
parent
c02e5b93f6
commit
6dcce60fb4
80 changed files with 1946 additions and 1738 deletions
|
|
@ -13,6 +13,8 @@ import com.tangem.tap.common.DialogManager
|
|||
import com.tangem.tap.common.IntentHandler
|
||||
import com.tangem.tap.common.SnackbarHandler
|
||||
import com.tangem.tap.common.redux.NotificationsHandler
|
||||
import com.tangem.tap.common.redux.global.AndroidResources
|
||||
import com.tangem.tap.common.redux.global.GlobalAction
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.domain.TangemSdkManager
|
||||
|
|
@ -66,9 +68,19 @@ class MainActivity : AppCompatActivity(), SnackbarHandler {
|
|||
tangemSdk = TangemSdk.init(this, TangemSdkManager.config)
|
||||
tangemSdkManager = TangemSdkManager(tangemSdk, this)
|
||||
|
||||
store.dispatch(GlobalAction.SetResources(getAndroidResources()))
|
||||
store.dispatch(WalletConnectAction.RestoreSessions)
|
||||
}
|
||||
|
||||
private fun getAndroidResources(): AndroidResources {
|
||||
return AndroidResources(
|
||||
AndroidResources.RString(
|
||||
R.string.copy_toast_msg,
|
||||
R.string.details_notification_erase_wallet_not_possible
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
private fun systemActions() {
|
||||
// makes the status bar text dark
|
||||
window.decorView.systemUiVisibility = View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR
|
||||
|
|
|
|||
|
|
@ -7,8 +7,8 @@ import com.tangem.tap.common.redux.global.GlobalState
|
|||
import com.tangem.tap.features.details.redux.walletconnect.WalletConnectDialog
|
||||
import com.tangem.tap.features.details.ui.walletconnect.dialogs.*
|
||||
import com.tangem.tap.features.onboarding.AddressInfoBottomSheetDialog
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.twins.ui.dialog.CreateWalletInterruptDialog
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.onboarding.products.twins.ui.dialog.CreateWalletInterruptDialog
|
||||
import com.tangem.tap.features.wallet.ui.dialogs.ScanFailsDialog
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
|
|
@ -45,7 +45,7 @@ class DialogManager : StoreSubscriber<GlobalState> {
|
|||
dialog = when (state.dialog) {
|
||||
is AppDialog.ScanFailsDialog -> ScanFailsDialog.create(context)
|
||||
is AppDialog.AddressInfoDialog -> AddressInfoBottomSheetDialog(state.dialog, context)
|
||||
is TwinCardsAction.Wallet.InterruptDialog -> CreateWalletInterruptDialog.create(state.dialog, context)
|
||||
is TwinCardsAction.Wallet.ShowInterruptDialog -> CreateWalletInterruptDialog.create(state.dialog, context)
|
||||
is WalletConnectDialog.UnsupportedCard ->
|
||||
SimpleAlertDialog.create(
|
||||
titleRes = R.string.wallet_connect,
|
||||
|
|
|
|||
|
|
@ -16,12 +16,10 @@ import com.tangem.tap.features.disclaimer.ui.DisclaimerFragment
|
|||
import com.tangem.tap.features.home.HomeFragment
|
||||
import com.tangem.tap.features.onboarding.products.note.OnboardingNoteFragment
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.OnboardingOtherCardsFragment
|
||||
import com.tangem.tap.features.onboarding.products.twins.OnboardingTwinsFragment
|
||||
import com.tangem.tap.features.onboarding.products.twins.ui.TwinsCardsFragment
|
||||
import com.tangem.tap.features.onboarding.products.wallet.OnboardingWalletFragment
|
||||
import com.tangem.tap.features.send.ui.SendFragment
|
||||
import com.tangem.tap.features.tokens.ui.AddTokensFragment
|
||||
import com.tangem.tap.features.twins.ui.CreateTwinWalletFragment
|
||||
import com.tangem.tap.features.twins.ui.TwinWalletWarningFragment
|
||||
import com.tangem.tap.features.wallet.ui.WalletDetailsFragment
|
||||
import com.tangem.tap.features.wallet.ui.WalletFragment
|
||||
import com.tangem.wallet.R
|
||||
|
|
@ -39,7 +37,7 @@ fun FragmentActivity.openFragment(
|
|||
transaction.setReorderingAllowed(true)
|
||||
shareElements.forEach { shareElement ->
|
||||
shareElement.wView.get()?.let { view ->
|
||||
transaction.addSharedElement(view, shareElement.name)
|
||||
transaction.addSharedElement(view, shareElement.elementName)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -70,10 +68,11 @@ fun FragmentActivity.addOnBackPressedDispatcher(
|
|||
|
||||
private fun fragmentFactory(screen: AppScreen): Fragment {
|
||||
return when (screen) {
|
||||
// AppScreen.Home -> TestLeapfrogFragment()
|
||||
AppScreen.Home -> HomeFragment()
|
||||
AppScreen.OnboardingNote -> OnboardingNoteFragment()
|
||||
AppScreen.OnboardingWallet -> OnboardingWalletFragment()
|
||||
AppScreen.OnboardingTwins -> OnboardingTwinsFragment()
|
||||
AppScreen.OnboardingTwins -> TwinsCardsFragment()
|
||||
AppScreen.OnboardingOther -> OnboardingOtherCardsFragment()
|
||||
AppScreen.Wallet -> WalletFragment()
|
||||
AppScreen.Send -> SendFragment()
|
||||
|
|
@ -81,8 +80,6 @@ private fun fragmentFactory(screen: AppScreen): Fragment {
|
|||
AppScreen.DetailsConfirm -> DetailsConfirmFragment()
|
||||
AppScreen.DetailsSecurity -> DetailsSecurityFragment()
|
||||
AppScreen.Disclaimer -> DisclaimerFragment()
|
||||
AppScreen.CreateTwinWalletWarning -> TwinWalletWarningFragment()
|
||||
AppScreen.CreateTwinWallet -> CreateTwinWalletFragment()
|
||||
AppScreen.AddTokens -> AddTokensFragment()
|
||||
AppScreen.WalletDetails -> WalletDetailsFragment()
|
||||
AppScreen.WalletConnectSessions -> WalletConnectSessionsFragment()
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@ import android.view.animation.AccelerateDecelerateInterpolator
|
|||
import android.widget.FrameLayout
|
||||
import androidx.core.animation.doOnEnd
|
||||
import androidx.core.view.children
|
||||
import com.tangem.common.extensions.VoidCallback
|
||||
import com.tangem.tangem_sdk_new.extensions.dpToPx
|
||||
|
||||
/**
|
||||
|
|
@ -15,9 +16,9 @@ class LeapfrogWidget(
|
|||
private val parentContainer: FrameLayout,
|
||||
private val calculator: PropertyCalculator = PropertyCalculator(),
|
||||
) {
|
||||
private val foldAnimationDuration = 500L
|
||||
private val leapAnimationDuration = 800L
|
||||
private val leapBackAnimationDuration = 800L
|
||||
private val foldAnimationDuration = 300L
|
||||
private val leapAnimationDuration = 500L
|
||||
private val leapBackAnimationDuration = 500L
|
||||
|
||||
private val leapViews = mutableListOf<LeapView>()
|
||||
|
||||
|
|
@ -25,9 +26,6 @@ class LeapfrogWidget(
|
|||
private var leapProgress: Int = 100
|
||||
private var leapBackProgress: Int = 100
|
||||
|
||||
var isFolded: Boolean = true
|
||||
private set
|
||||
|
||||
init {
|
||||
calculator.setTranslationConverter { parentContainer.dpToPx(it) }
|
||||
if (viewIsFullFledged()) {
|
||||
|
|
@ -43,12 +41,11 @@ class LeapfrogWidget(
|
|||
* Apply initial properties to the views
|
||||
*/
|
||||
fun initViews() {
|
||||
isFolded = true
|
||||
leapViews.forEach { it.initView() }
|
||||
}
|
||||
|
||||
fun fold(onEnd: () -> Unit = {}) {
|
||||
val animator = foldAnimator()
|
||||
fun fold(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
val animator = foldAnimator(animate)
|
||||
if (animator == null) {
|
||||
onEnd()
|
||||
} else {
|
||||
|
|
@ -57,8 +54,8 @@ class LeapfrogWidget(
|
|||
}
|
||||
}
|
||||
|
||||
fun unfold(onEnd: () -> Unit = {}) {
|
||||
val animator = unfoldAnimator()
|
||||
fun unfold(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
val animator = unfoldAnimator(animate)
|
||||
if (animator == null) {
|
||||
onEnd()
|
||||
} else {
|
||||
|
|
@ -67,33 +64,31 @@ class LeapfrogWidget(
|
|||
}
|
||||
}
|
||||
|
||||
fun foldAnimator(): Animator? {
|
||||
if (!canFoldUnfold() || isFolded) return null
|
||||
fun foldAnimator(animate: Boolean = true): Animator? {
|
||||
if (!canFoldUnfold()) return null
|
||||
|
||||
return createFoldUnfoldAnimator(true, foldAnimationDuration)
|
||||
return createFoldUnfoldAnimator(true, animate, foldAnimationDuration)
|
||||
}
|
||||
|
||||
fun unfoldAnimator(): Animator? {
|
||||
if (!canFoldUnfold() || !isFolded) return null
|
||||
fun unfoldAnimator(animate: Boolean = true): Animator? {
|
||||
if (!canFoldUnfold()) return null
|
||||
|
||||
return createFoldUnfoldAnimator(false, foldAnimationDuration)
|
||||
return createFoldUnfoldAnimator(false, animate, foldAnimationDuration)
|
||||
}
|
||||
|
||||
private fun createFoldUnfoldAnimator(isFoldAnimation: Boolean, duration: Long): Animator {
|
||||
private fun createFoldUnfoldAnimator(isFoldAnimation: Boolean, animate: Boolean, duration: Long): Animator {
|
||||
val animatorsList = mutableListOf<Animator>()
|
||||
val animateDuration = if (animate) duration else 0
|
||||
leapViews.forEach {
|
||||
if (isFoldAnimation) {
|
||||
it.fold()
|
||||
animatorsList.add(it.view.foldAnimation(duration, it.state.properties))
|
||||
animatorsList.add(it.view.foldAnimation(animateDuration, it.state.properties))
|
||||
} else {
|
||||
it.unfold()
|
||||
animatorsList.add(it.view.unfoldAnimation(duration, it.state.properties))
|
||||
animatorsList.add(it.view.unfoldAnimation(animateDuration, it.state.properties))
|
||||
}
|
||||
}
|
||||
animatorsList.add(createProgressListener(duration) {
|
||||
foldUnfoldProgress = it
|
||||
if (it == 100) isFolded = isFoldAnimation
|
||||
})
|
||||
animatorsList.add(createProgressListener(animateDuration) { foldUnfoldProgress = it })
|
||||
|
||||
val animator = AnimatorSet()
|
||||
animator.interpolator = AccelerateDecelerateInterpolator()
|
||||
|
|
@ -101,13 +96,13 @@ class LeapfrogWidget(
|
|||
return animator
|
||||
}
|
||||
|
||||
fun leap(onEnd: () -> Unit = {}) {
|
||||
fun leap(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
if (!canLeap()) {
|
||||
onEnd()
|
||||
return
|
||||
}
|
||||
|
||||
val duration = leapAnimationDuration
|
||||
val duration = if (animate) leapAnimationDuration else 0
|
||||
val animatorsList = mutableListOf<Animator>()
|
||||
leapViews.forEach {
|
||||
when (it.leap()) {
|
||||
|
|
@ -128,13 +123,13 @@ class LeapfrogWidget(
|
|||
animator.start()
|
||||
}
|
||||
|
||||
fun leapBack(onEnd: () -> Unit = {}) {
|
||||
fun leapBack(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
if (!canLeapBack()) {
|
||||
onEnd()
|
||||
return
|
||||
}
|
||||
|
||||
val duration = leapBackAnimationDuration
|
||||
val duration = if (animate) leapBackAnimationDuration else 0
|
||||
val animatorsList = mutableListOf<Animator>()
|
||||
leapViews.forEach {
|
||||
when (it.leapBack()) {
|
||||
|
|
@ -160,12 +155,11 @@ class LeapfrogWidget(
|
|||
|
||||
fun getViewByPosition(position: Int): LeapView = leapViews.first { it.state.currentPosition == position }
|
||||
|
||||
fun getState(): LeapfrogWidgetState = LeapfrogWidgetState(isFolded, leapViews.map { it.state })
|
||||
fun getState(): LeapfrogWidgetState = LeapfrogWidgetState(leapViews.map { it.state })
|
||||
|
||||
fun applyState(state: LeapfrogWidgetState) {
|
||||
isFolded = state.isFolded
|
||||
state.leapViewStates.forEach { state ->
|
||||
leapViews.firstOrNull { it.index == state.index }?.applyState(state)
|
||||
state.leapViewStates.forEach { viewState ->
|
||||
leapViews.firstOrNull { it.index == viewState.index }?.applyState(viewState)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -183,7 +177,6 @@ class LeapfrogWidget(
|
|||
private fun canLeap(): Boolean {
|
||||
return when {
|
||||
!viewIsFullFledged() -> false
|
||||
isFolded -> false
|
||||
leapBackInProgress() -> false
|
||||
leapProgress < 70 -> false
|
||||
else -> true
|
||||
|
|
@ -193,7 +186,6 @@ class LeapfrogWidget(
|
|||
private fun canLeapBack(): Boolean {
|
||||
return when {
|
||||
!viewIsFullFledged() -> false
|
||||
isFolded -> false
|
||||
leapInProgress() -> false
|
||||
leapBackProgress < 70 -> false
|
||||
else -> true
|
||||
|
|
@ -206,14 +198,13 @@ class LeapfrogWidget(
|
|||
}
|
||||
|
||||
data class LeapfrogWidgetState(
|
||||
val isFolded: Boolean,
|
||||
val leapViewStates: List<LeapViewState>
|
||||
)
|
||||
|
||||
class PropertyCalculator(
|
||||
val elevationFactor: Float = 1f,
|
||||
val decreaseScaleFactor: Float = 0.1f,
|
||||
val yTranslationFactor: Float = 20f,
|
||||
val decreaseScaleFactor: Float = 0.15f,
|
||||
val yTranslationFactor: Float = 35f,
|
||||
val decreaseOverLiftingFactor: Float = 0.85f,
|
||||
) {
|
||||
// 0 view it is view on the top of stack, but it is last in parent.children
|
||||
|
|
|
|||
|
|
@ -8,10 +8,10 @@ import com.tangem.tap.features.disclaimer.redux.DisclaimerReducer
|
|||
import com.tangem.tap.features.home.redux.HomeReducer
|
||||
import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteReducer
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.redux.OnboardingOtherCardsReducer
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsReducer
|
||||
import com.tangem.tap.features.onboarding.products.wallet.redux.OnboardingWalletReducer
|
||||
import com.tangem.tap.features.send.redux.reducers.SendScreenReducer
|
||||
import com.tangem.tap.features.tokens.redux.TokensReducer
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsReducer
|
||||
import com.tangem.tap.features.wallet.redux.reducers.WalletReducer
|
||||
import org.rekotlin.Action
|
||||
|
||||
|
|
@ -20,19 +20,19 @@ fun appReducer(action: Action, state: AppState?): AppState {
|
|||
if (action is AppAction.RestoreState) return action.state
|
||||
|
||||
return AppState(
|
||||
navigationState = NavigationReducer.reduce(action, state),
|
||||
globalState = globalReducer(action, state),
|
||||
homeState = HomeReducer.reduce(action, state),
|
||||
onboardingNoteState = OnboardingNoteReducer.reduce(action, state),
|
||||
onboardingWalletState = OnboardingWalletReducer.reduce(action, state),
|
||||
onboardingOtherCardsState = OnboardingOtherCardsReducer.reduce(action, state),
|
||||
walletState = WalletReducer.reduce(action, state),
|
||||
twinCardsState = TwinCardsReducer.reduce(action, state),
|
||||
sendState = SendScreenReducer.reduce(action, state.sendState),
|
||||
detailsState = DetailsReducer.reduce(action, state),
|
||||
disclaimerState = DisclaimerReducer.reduce(action, state),
|
||||
tokensState = TokensReducer.reduce(action, state),
|
||||
walletConnectState = WalletConnectReducer.reduce(action, state.walletConnectState)
|
||||
navigationState = NavigationReducer.reduce(action, state),
|
||||
globalState = globalReducer(action, state),
|
||||
homeState = HomeReducer.reduce(action, state),
|
||||
onboardingNoteState = OnboardingNoteReducer.reduce(action, state),
|
||||
onboardingWalletState = OnboardingWalletReducer.reduce(action, state),
|
||||
onboardingOtherCardsState = OnboardingOtherCardsReducer.reduce(action, state),
|
||||
walletState = WalletReducer.reduce(action, state),
|
||||
twinCardsState = TwinCardsReducer.reduce(action, state),
|
||||
sendState = SendScreenReducer.reduce(action, state.sendState),
|
||||
detailsState = DetailsReducer.reduce(action, state),
|
||||
disclaimerState = DisclaimerReducer.reduce(action, state),
|
||||
tokensState = TokensReducer.reduce(action, state),
|
||||
walletConnectState = WalletConnectReducer.reduce(action, state.walletConnectState)
|
||||
)
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -16,14 +16,14 @@ import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteMidd
|
|||
import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteState
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.redux.OnboardingOtherCardsMiddleware
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.redux.OnboardingOtherCardsState
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsMiddleware
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.onboarding.products.wallet.redux.OnboardingWalletMiddleware
|
||||
import com.tangem.tap.features.onboarding.products.wallet.redux.OnboardingWalletState
|
||||
import com.tangem.tap.features.send.redux.middlewares.SendMiddleware
|
||||
import com.tangem.tap.features.send.redux.states.SendState
|
||||
import com.tangem.tap.features.tokens.redux.TokensMiddleware
|
||||
import com.tangem.tap.features.tokens.redux.TokensState
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsMiddleware
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.wallet.redux.WalletState
|
||||
import com.tangem.tap.features.wallet.redux.middlewares.WalletMiddleware
|
||||
import org.rekotlin.Middleware
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
package com.tangem.tap.common.redux
|
||||
|
||||
import com.tangem.common.extensions.VoidCallback
|
||||
import com.tangem.tap.features.wallet.redux.AddressData
|
||||
|
||||
/**
|
||||
|
|
@ -11,7 +12,7 @@ sealed class AppDialog : StateDialog {
|
|||
object ScanFailsDialog : AppDialog()
|
||||
data class AddressInfoDialog(
|
||||
val addressData: AddressData,
|
||||
val onCopyAddress: () -> Unit,
|
||||
val onExploreAddress: () -> Unit
|
||||
val onCopyAddress: VoidCallback,
|
||||
val onExploreAddress: VoidCallback
|
||||
) : AppDialog()
|
||||
}
|
||||
|
|
@ -0,0 +1,35 @@
|
|||
package com.tangem.tap.common.redux.navigation
|
||||
|
||||
import android.view.View
|
||||
import androidx.transition.TransitionSet
|
||||
import java.lang.ref.WeakReference
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
data class FragmentShareTransition(
|
||||
val shareElements: List<ShareElement>,
|
||||
val enterTransitionSet: TransitionSet,
|
||||
val exitTransitionSet: TransitionSet
|
||||
)
|
||||
|
||||
/**
|
||||
* For ease of use, the name is used as transitionName\name into the FragmentTransaction.addSharedElement
|
||||
*/
|
||||
class ShareElement(view: View, name: String? = null) {
|
||||
|
||||
val wView: WeakReference<View>
|
||||
val elementName: String
|
||||
|
||||
init {
|
||||
name?.let { view.transitionName = it }
|
||||
elementName = view.transitionName
|
||||
?: throw UnsupportedOperationException("ShareElement require the name")
|
||||
wView = WeakReference(view)
|
||||
}
|
||||
|
||||
companion object {
|
||||
val imvFrontCard = "imv_front_card"
|
||||
val imvBackCard = "imv_back_card"
|
||||
}
|
||||
}
|
||||
|
|
@ -1,8 +1,6 @@
|
|||
package com.tangem.tap.common.redux.navigation
|
||||
|
||||
import android.view.View
|
||||
import androidx.fragment.app.FragmentActivity
|
||||
import androidx.transition.TransitionSet
|
||||
import org.rekotlin.Action
|
||||
import java.lang.ref.WeakReference
|
||||
|
||||
|
|
@ -19,12 +17,4 @@ sealed class NavigationAction : Action {
|
|||
|
||||
data class ActivityCreated(val activity: WeakReference<FragmentActivity>) : NavigationAction()
|
||||
object ActivityDestroyed : NavigationAction()
|
||||
}
|
||||
|
||||
data class FragmentShareTransition(
|
||||
val shareElements: List<ShareElement>,
|
||||
val enterTransitionSet: TransitionSet,
|
||||
val exitTransitionSet: TransitionSet
|
||||
)
|
||||
|
||||
data class ShareElement(val wView: WeakReference<View>, val name: String)
|
||||
}
|
||||
|
|
@ -5,8 +5,8 @@ import org.rekotlin.StateType
|
|||
import java.lang.ref.WeakReference
|
||||
|
||||
data class NavigationState(
|
||||
val backStack: List<AppScreen> = listOf(AppScreen.Home),
|
||||
val activity: WeakReference<FragmentActivity>? = null
|
||||
val backStack: List<AppScreen> = listOf(AppScreen.Home),
|
||||
val activity: WeakReference<FragmentActivity>? = null
|
||||
) : StateType
|
||||
|
||||
enum class AppScreen {
|
||||
|
|
@ -16,7 +16,6 @@ enum class AppScreen {
|
|||
Wallet, WalletDetails,
|
||||
Send,
|
||||
Details, DetailsConfirm, DetailsSecurity,
|
||||
CreateTwinWalletWarning, CreateTwinWallet,
|
||||
AddTokens,
|
||||
WalletConnectSessions,
|
||||
QrScan
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ data class Config(
|
|||
val blockchainSdkConfig: BlockchainSdkConfig = BlockchainSdkConfig(),
|
||||
val isSendingToPayIdEnabled: Boolean = true,
|
||||
val isTopUpEnabled: Boolean = false,
|
||||
@Deprecated("Not relevant since version 3.23")
|
||||
val isCreatingTwinCardsAllowed: Boolean = false
|
||||
)
|
||||
|
||||
|
|
@ -50,10 +51,10 @@ class ConfigManager(
|
|||
fun resetToDefault(name: String) {
|
||||
when (name) {
|
||||
isSendingToPayIdEnabled -> config =
|
||||
config.copy(isSendingToPayIdEnabled = defaultConfig.isSendingToPayIdEnabled)
|
||||
config.copy(isSendingToPayIdEnabled = defaultConfig.isSendingToPayIdEnabled)
|
||||
isTopUpEnabled -> config = config.copy(isTopUpEnabled = defaultConfig.isTopUpEnabled)
|
||||
isCreatingTwinCardsAllowed -> config =
|
||||
config.copy(isCreatingTwinCardsAllowed = defaultConfig.isCreatingTwinCardsAllowed)
|
||||
config.copy(isCreatingTwinCardsAllowed = defaultConfig.isCreatingTwinCardsAllowed)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,124 +0,0 @@
|
|||
package com.tangem.tap.domain.tasks
|
||||
|
||||
import com.tangem.*
|
||||
import com.tangem.common.CompletionResult
|
||||
import com.tangem.common.card.Card
|
||||
import com.tangem.common.card.FirmwareVersion
|
||||
import com.tangem.common.core.CardSession
|
||||
import com.tangem.common.core.CardSessionRunnable
|
||||
import com.tangem.common.core.TangemError
|
||||
import com.tangem.common.extensions.toHexString
|
||||
import com.tangem.operations.ScanTask
|
||||
import com.tangem.operations.issuerAndUserData.ReadIssuerDataCommand
|
||||
import com.tangem.tap.domain.ProductType
|
||||
import com.tangem.tap.domain.TapSdkError
|
||||
import com.tangem.tap.domain.TapWorkarounds.isExcluded
|
||||
import com.tangem.tap.domain.TapWorkarounds.isTangemNote
|
||||
import com.tangem.tap.domain.extensions.getSingleWallet
|
||||
import com.tangem.tap.domain.tasks.product.ScanResponse
|
||||
import com.tangem.tap.domain.twins.TwinsHelper
|
||||
|
||||
@Deprecated("Use ScanProductTask instead")
|
||||
class ScanNoteTask(val card: Card? = null) : CardSessionRunnable<ScanResponse> {
|
||||
|
||||
override fun run(
|
||||
session: CardSession,
|
||||
callback: (result: CompletionResult<ScanResponse>) -> Unit,
|
||||
) {
|
||||
ScanTask().run(session) { result ->
|
||||
when (result) {
|
||||
is CompletionResult.Failure -> callback(CompletionResult.Failure(result.error))
|
||||
|
||||
is CompletionResult.Success -> {
|
||||
val card = this.card ?: result.data
|
||||
|
||||
val error = getErrorIfExcludedCard(card)
|
||||
if (error != null) {
|
||||
callback(CompletionResult.Failure(error))
|
||||
return@run
|
||||
}
|
||||
|
||||
if (TwinsHelper.getTwinCardNumber(card.cardId) != null) {
|
||||
dealWithTwinCard(card, session, callback)
|
||||
} else if (!isTangemNote(card) && card.firmwareVersion >= FirmwareVersion.MultiWalletAvailable) {
|
||||
createMissingWalletsIfNeeded(card, session, callback)
|
||||
} else {
|
||||
callback(CompletionResult.Success(
|
||||
ScanResponse(card, ProductType.Other, session.environment.walletData)))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun createMissingWalletsIfNeeded(
|
||||
card: Card, session: CardSession,
|
||||
callback: (result: CompletionResult<ScanResponse>) -> Unit,
|
||||
) {
|
||||
val walletData = session.environment.walletData
|
||||
if (card.wallets.isEmpty()) {
|
||||
callback(CompletionResult.Success(ScanResponse(card, ProductType.Other, walletData)))
|
||||
return
|
||||
}
|
||||
|
||||
val curvesPresent = card.wallets.map { it.curve }
|
||||
// val curvesToCreate = EllipticCurve.values().subtract(curvesPresent)
|
||||
val curvesToCreate = card.supportedCurves.subtract(curvesPresent)
|
||||
|
||||
if (curvesToCreate.isEmpty()) {
|
||||
callback(CompletionResult.Success(ScanResponse(card, ProductType.Other, walletData)))
|
||||
return
|
||||
}
|
||||
|
||||
CreateWalletsTask(curvesToCreate.toList()).run(session) { result ->
|
||||
when (result) {
|
||||
is CompletionResult.Success ->
|
||||
callback(CompletionResult.Success(ScanResponse(result.data, ProductType.Other, walletData)))
|
||||
is CompletionResult.Failure -> callback(CompletionResult.Failure(result.error))
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private fun dealWithTwinCard(
|
||||
card: Card, session: CardSession,
|
||||
callback: (result: CompletionResult<ScanResponse>) -> Unit,
|
||||
) {
|
||||
ReadIssuerDataCommand().run(session) { readDataResult ->
|
||||
when (readDataResult) {
|
||||
is CompletionResult.Success -> {
|
||||
val publicKey = card.getSingleWallet()?.publicKey
|
||||
if (publicKey == null) {
|
||||
callback(CompletionResult.Success(ScanResponse(card, ProductType.Other, null)))
|
||||
return@run
|
||||
}
|
||||
val verified = TwinsHelper.verifyTwinPublicKey(
|
||||
readDataResult.data.issuerData, publicKey
|
||||
)
|
||||
if (verified) {
|
||||
val twinPublicKey = readDataResult.data.issuerData.sliceArray(0 until 65)
|
||||
callback(CompletionResult.Success(
|
||||
ScanResponse(
|
||||
card = card,
|
||||
ProductType.Other,
|
||||
walletData = session.environment.walletData,
|
||||
secondTwinPublicKey = twinPublicKey.toHexString())
|
||||
))
|
||||
return@run
|
||||
} else {
|
||||
callback(CompletionResult.Success(ScanResponse(card, ProductType.Other, null)))
|
||||
}
|
||||
}
|
||||
is CompletionResult.Failure ->
|
||||
callback(CompletionResult.Success(ScanResponse(card, ProductType.Other, null)))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun getErrorIfExcludedCard(card: Card): TangemError? {
|
||||
if (card.isExcluded()) return TapSdkError.CardForDifferentApp
|
||||
// Disable new multi-currency HD wallet cards on the old version of the app
|
||||
// if (card.isMultiCurrencyWallet()) return UpdateAppToUseThisCard()
|
||||
return null
|
||||
}
|
||||
}
|
||||
|
|
@ -4,44 +4,45 @@ import com.squareup.moshi.JsonAdapter
|
|||
import com.squareup.moshi.Types
|
||||
import com.tangem.Message
|
||||
import com.tangem.blockchain.extensions.Result
|
||||
import com.tangem.blockchain.extensions.SimpleResult
|
||||
import com.tangem.common.CompletionResult
|
||||
import com.tangem.common.KeyPair
|
||||
import com.tangem.common.card.Card
|
||||
import com.tangem.common.core.TangemSdkError
|
||||
import com.tangem.common.extensions.hexToBytes
|
||||
import com.tangem.common.extensions.toHexString
|
||||
import com.tangem.operations.wallet.CreateWalletResponse
|
||||
import com.tangem.tap.common.analytics.FirebaseAnalyticsHandler
|
||||
import com.tangem.tap.domain.tasks.product.ScanResponse
|
||||
import com.tangem.tap.network.createMoshi
|
||||
import com.tangem.tap.tangemSdkManager
|
||||
|
||||
class TwinCardsManager(private val scanResponse: ScanResponse, assetReader: AssetReader) {
|
||||
class TwinCardsManager(private val card: Card, assetReader: AssetReader) {
|
||||
|
||||
private val currentCardId: String = scanResponse.card.cardId
|
||||
private val currentCardId: String = card.cardId
|
||||
|
||||
private var currentCardPublicKey: String? = null
|
||||
private var secondCardPublicKey: String? = null
|
||||
|
||||
private val issuerKeyPair: KeyPair = getIssuerKeys(assetReader, scanResponse.card.issuer.publicKey.toHexString())
|
||||
private val issuerKeyPair: KeyPair = getIssuerKeys(assetReader, card.issuer.publicKey.toHexString())
|
||||
|
||||
suspend fun createFirstWallet(message: Message): SimpleResult {
|
||||
suspend fun createFirstWallet(message: Message): CompletionResult<CreateWalletResponse> {
|
||||
val response = tangemSdkManager.runTaskAsync(
|
||||
CreateFirstTwinWalletTask(), currentCardId, message
|
||||
)
|
||||
when (response) {
|
||||
is CompletionResult.Success -> {
|
||||
currentCardPublicKey = response.data.wallet.publicKey.toHexString()
|
||||
return SimpleResult.Success
|
||||
return response
|
||||
}
|
||||
is CompletionResult.Failure -> {
|
||||
(response.error as? TangemSdkError)?.let { error ->
|
||||
FirebaseAnalyticsHandler.logCardSdkError(
|
||||
error,
|
||||
FirebaseAnalyticsHandler.ActionToLog.CreateWallet,
|
||||
card = scanResponse.card
|
||||
card = card
|
||||
)
|
||||
}
|
||||
return SimpleResult.failure(response.error)
|
||||
return response
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -52,7 +53,7 @@ class TwinCardsManager(private val scanResponse: ScanResponse, assetReader: Asse
|
|||
initialMessage: Message,
|
||||
preparingMessage: Message,
|
||||
creatingWalletMessage: Message,
|
||||
): SimpleResult {
|
||||
): CompletionResult<CreateWalletResponse> {
|
||||
val task = CreateSecondTwinWalletTask(
|
||||
firstPublicKey = currentCardPublicKey!!,
|
||||
firstCardId = currentCardId,
|
||||
|
|
@ -64,20 +65,18 @@ class TwinCardsManager(private val scanResponse: ScanResponse, assetReader: Asse
|
|||
when (response) {
|
||||
is CompletionResult.Success -> {
|
||||
secondCardPublicKey = response.data.wallet.publicKey.toHexString()
|
||||
return SimpleResult.Success
|
||||
}
|
||||
is CompletionResult.Failure -> {
|
||||
(response.error as? TangemSdkError)?.let { error ->
|
||||
FirebaseAnalyticsHandler.logCardSdkError(
|
||||
error,
|
||||
FirebaseAnalyticsHandler.ActionToLog.CreateWallet,
|
||||
card = scanResponse.card
|
||||
card = card
|
||||
)
|
||||
}
|
||||
return SimpleResult.failure(response.error)
|
||||
}
|
||||
}
|
||||
|
||||
return response
|
||||
}
|
||||
|
||||
suspend fun complete(message: Message): Result<ScanResponse> {
|
||||
|
|
@ -92,7 +91,7 @@ class TwinCardsManager(private val scanResponse: ScanResponse, assetReader: Asse
|
|||
FirebaseAnalyticsHandler.logCardSdkError(
|
||||
error,
|
||||
FirebaseAnalyticsHandler.ActionToLog.WriteIssuerData,
|
||||
card = scanResponse.card
|
||||
card = card
|
||||
)
|
||||
}
|
||||
Result.failure(response.error)
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@ import android.animation.ObjectAnimator
|
|||
import android.animation.PropertyValuesHolder
|
||||
import android.view.View
|
||||
import androidx.core.animation.doOnEnd
|
||||
import com.tangem.common.extensions.VoidCallback
|
||||
import com.tangem.tap.common.leapfrogWidget.LeapView
|
||||
import com.tangem.tap.common.leapfrogWidget.LeapViewState
|
||||
import com.tangem.tap.common.leapfrogWidget.LeapfrogWidget
|
||||
|
|
@ -17,47 +18,60 @@ class TwinsCardWidget(
|
|||
val getTopOfAnchorViewForActivateState: () -> Float
|
||||
) {
|
||||
|
||||
var state: TwinCardsWidgetState? = null
|
||||
private set
|
||||
|
||||
private val animationDuration = 300L
|
||||
|
||||
init {
|
||||
if (leapfrogWidget.getViewsCount() != 2) throw UnsupportedOperationException()
|
||||
}
|
||||
|
||||
fun toWelcome(animate: Boolean = true, onEnd: () -> Unit = {}) {
|
||||
val animator = createAnimator(animate, onEnd)
|
||||
fun toWelcome(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
if (state == TwinCardsWidgetState.Welcome) return
|
||||
|
||||
state = TwinCardsWidgetState.Welcome
|
||||
val animator = createAnimator(animate)
|
||||
animator.playTogether(
|
||||
createAnimator(TwinCardNumber.First, createWelcomeProperties(TwinCardNumber.First)),
|
||||
createAnimator(TwinCardNumber.Second, createWelcomeProperties(TwinCardNumber.Second))
|
||||
)
|
||||
leapfrogWidget.fold { animator.start() }
|
||||
animator.doOnEnd { onEnd() }
|
||||
leapfrogWidget.fold(animate) { animator.start() }
|
||||
}
|
||||
|
||||
fun toLeapfrog(animate: Boolean = true, onEnd: () -> Unit = {}) {
|
||||
val animator = createAnimator(animate, onEnd)
|
||||
fun toLeapfrog(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
if (state == TwinCardsWidgetState.Leapfrog) return
|
||||
|
||||
state = TwinCardsWidgetState.Leapfrog
|
||||
val animator = createAnimator(animate)
|
||||
animator.playTogether(
|
||||
createAnimator(TwinCardNumber.First, createLeapfrogProperties(TwinCardNumber.First)),
|
||||
createAnimator(TwinCardNumber.Second, createLeapfrogProperties(TwinCardNumber.Second))
|
||||
)
|
||||
leapfrogWidget.fold {
|
||||
animator.doOnEnd {
|
||||
leapfrogWidget.initViews()
|
||||
leapfrogWidget.unfold()
|
||||
}
|
||||
animator.start()
|
||||
animator.doOnEnd {
|
||||
leapfrogWidget.initViews()
|
||||
leapfrogWidget.unfold(animate, onEnd)
|
||||
}
|
||||
animator.start()
|
||||
}
|
||||
|
||||
fun toActivate(animate: Boolean = true, onEnd: () -> Unit = {}) {
|
||||
val animator = createAnimator(animate, onEnd)
|
||||
fun toActivate(animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
if (state == TwinCardsWidgetState.Activate) return
|
||||
|
||||
state = TwinCardsWidgetState.Activate
|
||||
val animator = createAnimator(animate)
|
||||
animator.playTogether(
|
||||
createAnimator(TwinCardNumber.First, createActivateProperties(TwinCardNumber.First)),
|
||||
createAnimator(TwinCardNumber.Second, createActivateProperties(TwinCardNumber.Second))
|
||||
)
|
||||
animator.doOnEnd { onEnd() }
|
||||
animator.start()
|
||||
}
|
||||
|
||||
private fun createAnimator(animate: Boolean, onEnd: () -> Unit): AnimatorSet {
|
||||
private fun createAnimator(animate: Boolean): AnimatorSet {
|
||||
return AnimatorSet().apply {
|
||||
duration = if (animate) 400 else 0
|
||||
doOnEnd { onEnd() }
|
||||
duration = if (animate) animationDuration else 0
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -72,20 +86,20 @@ class TwinsCardWidget(
|
|||
return when (cardNumber) {
|
||||
TwinCardNumber.First -> {
|
||||
TwinsCardProperties(
|
||||
xTranslation = -180f,
|
||||
yTranslation = -350f,
|
||||
xTranslation = -120f,
|
||||
yTranslation = -220f,
|
||||
rotation = -3f,
|
||||
elevation = 1f,
|
||||
scale = 1.1f,
|
||||
scale = 1f,
|
||||
)
|
||||
}
|
||||
TwinCardNumber.Second -> {
|
||||
TwinsCardProperties(
|
||||
xTranslation = 180f,
|
||||
yTranslation = 10f,
|
||||
xTranslation = 170f,
|
||||
yTranslation = 170f,
|
||||
rotation = -3f,
|
||||
elevation = 0f,
|
||||
scale = 1.1f,
|
||||
scale = 1f,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
@ -108,7 +122,7 @@ class TwinsCardWidget(
|
|||
xTranslation = twinProperties.xTranslation,
|
||||
yTranslation = twinProperties.yTranslation - topOfAnchorView,
|
||||
rotation = 0f,
|
||||
scale = twinProperties.scale - 0.4f,
|
||||
scale = twinProperties.scale - 0.5f,
|
||||
)
|
||||
}
|
||||
|
||||
|
|
@ -120,6 +134,10 @@ class TwinsCardWidget(
|
|||
}
|
||||
}
|
||||
|
||||
enum class TwinCardsWidgetState {
|
||||
Welcome, Leapfrog, Activate
|
||||
}
|
||||
|
||||
private data class TwinsCardProperties(
|
||||
val xTranslation: Float = 0f,
|
||||
val yTranslation: Float = 0f,
|
||||
|
|
|
|||
|
|
@ -1,26 +1,26 @@
|
|||
package com.tangem.tap.features.send
|
||||
package com.tangem.tap.features
|
||||
|
||||
import android.annotation.SuppressLint
|
||||
import android.os.Bundle
|
||||
import android.view.LayoutInflater
|
||||
import android.view.View
|
||||
import android.view.ViewGroup
|
||||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.appcompat.widget.Toolbar
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.transition.TransitionInflater
|
||||
import com.google.android.material.snackbar.Snackbar
|
||||
import com.tangem.common.extensions.VoidCallback
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_wallet.*
|
||||
import org.rekotlin.StoreSubscriber
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
abstract class BaseStoreFragment(layoutId: Int) : Fragment(layoutId) {
|
||||
|
||||
abstract fun subscribeToStore()
|
||||
abstract class BaseFragment(layoutId: Int) : Fragment(layoutId), FragmentOnBackPressedHandler {
|
||||
|
||||
protected lateinit var mainView: View
|
||||
protected val storeSubscribersList = mutableListOf<StoreSubscriber<*>>()
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
|
|
@ -40,26 +40,32 @@ abstract class BaseStoreFragment(layoutId: Int) : Fragment(layoutId) {
|
|||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
toolbar?.setNavigationOnClickListener { activity?.onBackPressed() }
|
||||
addBackPressHandler(this)
|
||||
}
|
||||
|
||||
override fun onStart() {
|
||||
super.onStart()
|
||||
subscribeToStore()
|
||||
override fun handleOnBackPressed() {
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
}
|
||||
|
||||
|
||||
override fun onStop() {
|
||||
storeSubscribersList.forEach { store.unsubscribe(it) }
|
||||
storeSubscribersList.clear()
|
||||
super.onStop()
|
||||
}
|
||||
|
||||
fun showRetrySnackbar(message: String, action: () -> Unit) {
|
||||
fun showRetrySnackbar(message: String, action: VoidCallback) {
|
||||
val snackbar = Snackbar.make(mainView, message, Snackbar.LENGTH_INDEFINITE)
|
||||
snackbar.setAction(getString(R.string.common_retry)) {
|
||||
snackbar.dismiss()
|
||||
action()
|
||||
}.show()
|
||||
}
|
||||
}
|
||||
|
||||
interface FragmentOnBackPressedHandler {
|
||||
fun handleOnBackPressed()
|
||||
}
|
||||
|
||||
@SuppressLint("FragmentBackPressedCallback")
|
||||
fun Fragment.addBackPressHandler(handler: FragmentOnBackPressedHandler) {
|
||||
activity?.onBackPressedDispatcher?.addCallback(this, object : OnBackPressedCallback(true) {
|
||||
override fun handleOnBackPressed() {
|
||||
handler.handleOnBackPressed()
|
||||
}
|
||||
})
|
||||
view?.findViewById<Toolbar>(R.id.toolbar)?.setNavigationOnClickListener { activity?.onBackPressed() }
|
||||
}
|
||||
|
|
@ -0,0 +1,24 @@
|
|||
package com.tangem.tap.features
|
||||
|
||||
import com.tangem.tap.store
|
||||
import org.rekotlin.StoreSubscriber
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
abstract class BaseStoreFragment(layoutId: Int) : BaseFragment(layoutId) {
|
||||
|
||||
abstract fun subscribeToStore()
|
||||
protected val storeSubscribersList = mutableListOf<StoreSubscriber<*>>()
|
||||
|
||||
override fun onStart() {
|
||||
super.onStart()
|
||||
subscribeToStore()
|
||||
}
|
||||
|
||||
override fun onStop() {
|
||||
storeSubscribersList.forEach { store.unsubscribe(it) }
|
||||
storeSubscribersList.clear()
|
||||
super.onStop()
|
||||
}
|
||||
}
|
||||
|
|
@ -11,8 +11,8 @@ import com.tangem.tap.common.redux.global.GlobalAction
|
|||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.features.disclaimer.redux.DisclaimerAction
|
||||
import com.tangem.tap.features.onboarding.twins.redux.CreateTwinWalletMode
|
||||
import com.tangem.tap.features.onboarding.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.CreateTwinWalletMode
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.wallet.models.hasSendableAmountsOrPendingTransactions
|
||||
import com.tangem.tap.features.wallet.redux.WalletAction
|
||||
import com.tangem.tap.network.coinmarketcap.CoinMarketCapService
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ import com.tangem.common.card.Card
|
|||
import com.tangem.tap.common.entities.Button
|
||||
import com.tangem.tap.common.entities.TapCurrency.Companion.DEFAULT_FIAT_CURRENCY
|
||||
import com.tangem.tap.common.redux.global.FiatCurrencyName
|
||||
import com.tangem.tap.features.onboarding.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.network.coinmarketcap.FiatCurrency
|
||||
import com.tangem.tap.store
|
||||
import org.rekotlin.StateType
|
||||
|
|
|
|||
|
|
@ -6,7 +6,6 @@ import android.view.View
|
|||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.transition.TransitionInflater
|
||||
import com.tangem.tap.common.extensions.hide
|
||||
import com.tangem.tap.common.extensions.show
|
||||
import com.tangem.tap.common.redux.global.GlobalAction
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
|
|
@ -16,8 +15,6 @@ import com.tangem.tap.features.details.redux.DetailsAction
|
|||
import com.tangem.tap.features.details.redux.DetailsState
|
||||
import com.tangem.tap.features.details.redux.SecurityOption
|
||||
import com.tangem.tap.features.feedback.FeedbackEmail
|
||||
import com.tangem.tap.features.twins.redux.CreateTwinWalletMode
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_details.*
|
||||
|
|
@ -91,17 +88,10 @@ class DetailsFragment : Fragment(R.layout.fragment_details), StoreSubscriber<Det
|
|||
}
|
||||
|
||||
if (state.isTangemTwins) {
|
||||
if (state.twinCardsState.isCreatingTwinCardsAllowed) {
|
||||
tv_erase_wallet.show()
|
||||
tv_erase_wallet.text = getText(R.string.details_row_title_twins_recreate)
|
||||
tv_erase_wallet.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.Create(
|
||||
state.twinCardsState.cardNumber!!,
|
||||
CreateTwinWalletMode.RecreateWallet
|
||||
))
|
||||
}
|
||||
} else {
|
||||
tv_erase_wallet.hide()
|
||||
tv_erase_wallet.show()
|
||||
tv_erase_wallet.text = getText(R.string.details_row_title_twins_recreate)
|
||||
tv_erase_wallet.setOnClickListener {
|
||||
store.dispatch(DetailsAction.ReCreateTwinsWallet(state.twinCardsState.cardNumber!!))
|
||||
}
|
||||
} else {
|
||||
tv_erase_wallet.show()
|
||||
|
|
|
|||
|
|
@ -16,15 +16,14 @@ import com.tangem.tap.features.onboarding.products.BaseOnboardingFragment
|
|||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_onboarding_main.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_bottom_action_views.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_home.*
|
||||
import java.lang.ref.WeakReference
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_bottom.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_home_top.*
|
||||
|
||||
class HomeFragment : BaseOnboardingFragment<HomeState>() {
|
||||
|
||||
private lateinit var btnScanCard: ViewStateWidget
|
||||
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_home
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_home_top
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
|
|
@ -38,7 +37,10 @@ class HomeFragment : BaseOnboardingFragment<HomeState>() {
|
|||
|
||||
toolbar.hide()
|
||||
val shareTransition = FragmentShareTransition(
|
||||
listOf(ShareElement(WeakReference(imv_front_card), imv_front_card.transitionName)),
|
||||
listOf(
|
||||
ShareElement(imv_front_card, ShareElement.imvFrontCard),
|
||||
ShareElement(imv_back_card, ShareElement.imvBackCard)
|
||||
),
|
||||
FrontCardEnterTransition(),
|
||||
FrontCardExitTransition()
|
||||
)
|
||||
|
|
@ -62,6 +64,7 @@ class HomeFragment : BaseOnboardingFragment<HomeState>() {
|
|||
oldState.homeState == newState.homeState
|
||||
}.select { it.homeState }
|
||||
}
|
||||
storeSubscribersList.add(this)
|
||||
}
|
||||
|
||||
override fun newState(state: HomeState) {
|
||||
|
|
|
|||
|
|
@ -2,6 +2,8 @@ package com.tangem.tap.features.home.redux
|
|||
|
||||
import com.tangem.tap.common.entities.IndeterminateProgressButton
|
||||
import com.tangem.tap.common.extensions.dispatchOpenUrl
|
||||
import com.tangem.tap.common.extensions.onCardScanned
|
||||
import com.tangem.tap.common.extensions.withMainContext
|
||||
import com.tangem.tap.common.post
|
||||
import com.tangem.tap.common.postUi
|
||||
import com.tangem.tap.common.redux.AppState
|
||||
|
|
@ -10,10 +12,10 @@ import com.tangem.tap.common.redux.navigation.AppScreen
|
|||
import com.tangem.tap.common.redux.navigation.FragmentShareTransition
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.domain.DELAY_SDK_DIALOG_CLOSE
|
||||
import com.tangem.tap.domain.twins.getTwinCardNumber
|
||||
import com.tangem.tap.features.onboarding.OnboardingHelper
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsStep
|
||||
import com.tangem.tap.features.send.redux.states.ButtonState
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.preferencesStorage
|
||||
import com.tangem.tap.scope
|
||||
import com.tangem.tap.store
|
||||
|
|
@ -58,21 +60,24 @@ private fun handleReadCard() {
|
|||
} else {
|
||||
changeButtonState(ButtonState.PROGRESS)
|
||||
store.dispatch(GlobalAction.ScanCard({ scanResponse ->
|
||||
if (scanResponse.isTangemTwins()) {
|
||||
scanResponse.card.getTwinCardNumber()?.let {
|
||||
val configManager = store.state.globalState.configManager
|
||||
val isCreatingTwinsAllowed = configManager?.config?.isCreatingTwinCardsAllowed ?: false
|
||||
store.dispatch(TwinCardsAction.SetTwinCard(it, null, isCreatingTwinsAllowed))
|
||||
}
|
||||
}
|
||||
store.dispatch(TwinCardsAction.IfTwinsPrepareState(scanResponse))
|
||||
|
||||
if (OnboardingHelper.isOnboardingCase(scanResponse)) {
|
||||
val navigateTo = OnboardingHelper.whereToNavigate(scanResponse)
|
||||
store.dispatch(GlobalAction.Onboarding.Start(scanResponse))
|
||||
navigateTo(navigateTo, store.state.homeState.shareTransition)
|
||||
} else {
|
||||
scope.launch { store.state.globalState.tapWalletManager.onCardScanned(scanResponse) }
|
||||
navigateTo(AppScreen.Wallet, null)
|
||||
scope.launch {
|
||||
store.onCardScanned(scanResponse)
|
||||
withMainContext {
|
||||
if (scanResponse.twinsIsTwinned() && !preferencesStorage.wasTwinsOnboardingShown()) {
|
||||
store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.WelcomeOnly))
|
||||
navigateTo(AppScreen.OnboardingTwins, store.state.homeState.shareTransition)
|
||||
} else {
|
||||
navigateTo(AppScreen.Wallet, null)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}, {
|
||||
changeButtonState(ButtonState.ENABLED)
|
||||
|
|
|
|||
|
|
@ -5,7 +5,7 @@ import android.view.View
|
|||
import com.tangem.tap.common.extensions.inflate
|
||||
import com.tangem.tap.common.extensions.show
|
||||
import com.tangem.tap.common.transitions.HomeToOnboardingTransition
|
||||
import com.tangem.tap.features.send.BaseStoreFragment
|
||||
import com.tangem.tap.features.BaseStoreFragment
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_onboarding_main.*
|
||||
import kotlinx.android.synthetic.main.view_confetti.*
|
||||
|
|
@ -16,11 +16,6 @@ import org.rekotlin.StoreSubscriber
|
|||
*/
|
||||
abstract class BaseOnboardingFragment<T> : BaseStoreFragment(R.layout.fragment_onboarding_main), StoreSubscriber<T> {
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
configureTransitions()
|
||||
}
|
||||
|
||||
override fun configureTransitions() {
|
||||
enterTransition = HomeToOnboardingTransition()
|
||||
exitTransition = HomeToOnboardingTransition()
|
||||
|
|
|
|||
|
|
@ -16,18 +16,18 @@ import com.tangem.tangem_sdk_new.extensions.fadeOut
|
|||
import com.tangem.tap.common.extensions.getDrawableCompat
|
||||
import com.tangem.tap.common.extensions.stripZeroPlainString
|
||||
import com.tangem.tap.common.postUi
|
||||
import com.tangem.tap.common.redux.navigation.ShareElement
|
||||
import com.tangem.tap.common.toggleWidget.RefreshBalanceWidget
|
||||
import com.tangem.tap.common.transitions.InternalNoteLayoutTransition
|
||||
import com.tangem.tap.features.onboarding.products.BaseOnboardingFragment
|
||||
import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteAction
|
||||
import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteResources
|
||||
import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteState
|
||||
import com.tangem.tap.features.onboarding.products.note.redux.OnboardingNoteStep
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_onboarding_main.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_bottom_action_views.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_note.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_bottom.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_top.*
|
||||
import kotlinx.android.synthetic.main.view_onboarding_progress.*
|
||||
import kotlinx.android.synthetic.main.view_onboarding_tv_balance.*
|
||||
|
||||
|
|
@ -36,23 +36,26 @@ import kotlinx.android.synthetic.main.view_onboarding_tv_balance.*
|
|||
*/
|
||||
class OnboardingNoteFragment : BaseOnboardingFragment<OnboardingNoteState>() {
|
||||
|
||||
private lateinit var btnRefreshBalanceWidget: RefreshBalanceWidget
|
||||
private var currentStep: OnboardingNoteStep = OnboardingNoteStep.None
|
||||
private var previousStep: OnboardingNoteStep = OnboardingNoteStep.None
|
||||
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_note
|
||||
private lateinit var btnRefreshBalanceWidget: RefreshBalanceWidget
|
||||
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_container_top
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
postponeEnterTransition()
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
imv_front_card.transitionName = ShareElement.imvFrontCard
|
||||
startPostponedEnterTransition()
|
||||
|
||||
toolbar.setTitle(R.string.onboarding_title)
|
||||
btnRefreshBalanceWidget = RefreshBalanceWidget(onboarding_main_container)
|
||||
|
||||
val resources = OnboardingNoteResources(
|
||||
OnboardingNoteResources.Strings(
|
||||
R.string.copy_toast_msg
|
||||
)
|
||||
)
|
||||
store.dispatch(OnboardingNoteAction.SetResources(resources))
|
||||
store.dispatch(OnboardingNoteAction.LoadCardArtwork)
|
||||
store.dispatch(OnboardingNoteAction.DetermineStepOfScreen)
|
||||
}
|
||||
|
|
@ -81,7 +84,7 @@ class OnboardingNoteFragment : BaseOnboardingFragment<OnboardingNoteState>() {
|
|||
}
|
||||
setBalance(state)
|
||||
showConfetti(state.showConfetti)
|
||||
currentStep = state.currentStep
|
||||
previousStep = state.currentStep
|
||||
}
|
||||
|
||||
private fun setBalance(state: OnboardingNoteState) {
|
||||
|
|
@ -166,7 +169,7 @@ class OnboardingNoteFragment : BaseOnboardingFragment<OnboardingNoteState>() {
|
|||
}
|
||||
|
||||
private fun updateConstraints(currentStep: OnboardingNoteStep, @LayoutRes layoutId: Int) {
|
||||
if (this.currentStep == currentStep) return
|
||||
if (this.previousStep == currentStep) return
|
||||
|
||||
val constraintSet = ConstraintSet()
|
||||
constraintSet.clone(requireContext(), layoutId)
|
||||
|
|
|
|||
|
|
@ -10,7 +10,6 @@ import org.rekotlin.Action
|
|||
*/
|
||||
sealed class OnboardingNoteAction : Action {
|
||||
// from user, ui
|
||||
data class SetResources(val resources: OnboardingNoteResources) : OnboardingNoteAction()
|
||||
object LoadCardArtwork : OnboardingNoteAction()
|
||||
object CreateWallet : OnboardingNoteAction()
|
||||
object TopUp : OnboardingNoteAction()
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ import com.tangem.tap.common.redux.navigation.NavigationAction
|
|||
import com.tangem.tap.domain.TapError
|
||||
import com.tangem.tap.domain.extensions.hasWallets
|
||||
import com.tangem.tap.domain.extensions.makePrimaryWalletManager
|
||||
import com.tangem.tap.features.wallet.redux.Currency
|
||||
import com.tangem.tap.features.wallet.redux.ProgressState
|
||||
import com.tangem.tap.scope
|
||||
import com.tangem.tap.store
|
||||
|
|
@ -107,6 +108,7 @@ private fun handleNoteAction(action: Action, dispatch: DispatchFunction) {
|
|||
|
||||
val isLoadedBefore = noteState.walletBalance.state != ProgressState.Loading
|
||||
val balanceIsLoading = noteState.walletBalance.copy(
|
||||
currency = Currency.Blockchain(walletManager.wallet.blockchain),
|
||||
state = ProgressState.Loading,
|
||||
error = null,
|
||||
criticalError = null
|
||||
|
|
@ -128,7 +130,7 @@ private fun handleNoteAction(action: Action, dispatch: DispatchFunction) {
|
|||
}
|
||||
is OnboardingNoteAction.ShowAddressInfoDialog -> {
|
||||
val addressData = noteState.walletManager?.getAddressData() ?: return
|
||||
val addressWasCopied = noteState.resources.strings.addressWasCopied
|
||||
val addressWasCopied = globalState.resources.strings.addressWasCopied
|
||||
val appDialog = AppDialog.AddressInfoDialog(
|
||||
addressData,
|
||||
onCopyAddress = { store.dispatchToastNotification(addressWasCopied) },
|
||||
|
|
@ -143,7 +145,7 @@ private fun handleNoteAction(action: Action, dispatch: DispatchFunction) {
|
|||
OnboardingNoteAction.Done -> {
|
||||
store.dispatch(GlobalAction.Onboarding.Stop)
|
||||
scope.launch {
|
||||
globalState.tapWalletManager.onCardScanned(scanResponse)
|
||||
store.onCardScanned(scanResponse)
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.Wallet))
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -23,9 +23,6 @@ private fun internalReduce(action: Action, appState: AppState): OnboardingNoteSt
|
|||
is OnboardingNoteAction.SetWalletManager -> {
|
||||
state = state.copy(walletManager = action.walletManager)
|
||||
}
|
||||
is OnboardingNoteAction.SetResources -> {
|
||||
state = state.copy(resources = action.resources)
|
||||
}
|
||||
is OnboardingNoteAction.Balance.Set -> {
|
||||
state = state.copy(walletBalance = action.balance)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,7 +10,6 @@ import org.rekotlin.StateType
|
|||
*/
|
||||
data class OnboardingNoteState(
|
||||
val walletManager: WalletManager? = null,
|
||||
val resources: OnboardingNoteResources = OnboardingNoteResources(),
|
||||
// UI
|
||||
val cardArtwork: Artwork? = null,
|
||||
val walletBalance: OnboardingWalletBalance = OnboardingWalletBalance.loading(),
|
||||
|
|
@ -25,12 +24,4 @@ data class OnboardingNoteState(
|
|||
|
||||
enum class OnboardingNoteStep {
|
||||
None, CreateWallet, TopUpWallet, Done
|
||||
}
|
||||
|
||||
data class OnboardingNoteResources(
|
||||
val strings: Strings = Strings()
|
||||
) {
|
||||
data class Strings(
|
||||
val addressWasCopied: Int = -1
|
||||
)
|
||||
}
|
||||
|
|
@ -8,16 +8,18 @@ import androidx.constraintlayout.widget.ConstraintSet
|
|||
import androidx.core.view.isVisible
|
||||
import androidx.transition.TransitionManager
|
||||
import com.tangem.tap.common.extensions.getDrawableCompat
|
||||
import com.tangem.tap.common.redux.navigation.ShareElement
|
||||
import com.tangem.tap.common.transitions.InternalNoteLayoutTransition
|
||||
import com.tangem.tap.features.onboarding.products.BaseOnboardingFragment
|
||||
import com.tangem.tap.features.onboarding.products.note.swapToBitmapDrawable
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.redux.OnboardingOtherCardsAction
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.redux.OnboardingOtherCardsState
|
||||
import com.tangem.tap.features.onboarding.products.otherCards.redux.OnboardingOtherCardsStep
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_onboarding_main.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_bottom_action_views.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_note.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_bottom.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_top.*
|
||||
import kotlinx.android.synthetic.main.view_onboarding_progress.*
|
||||
|
||||
/**
|
||||
|
|
@ -25,11 +27,19 @@ import kotlinx.android.synthetic.main.view_onboarding_progress.*
|
|||
*/
|
||||
class OnboardingOtherCardsFragment : BaseOnboardingFragment<OnboardingOtherCardsState>() {
|
||||
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_note
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_container_top
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
postponeEnterTransition()
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
imv_front_card.transitionName = ShareElement.imvFrontCard
|
||||
startPostponedEnterTransition()
|
||||
|
||||
toolbar.setTitle(R.string.onboarding_title)
|
||||
store.dispatch(OnboardingOtherCardsAction.LoadCardArtwork)
|
||||
store.dispatch(OnboardingOtherCardsAction.DetermineStepOfScreen)
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package com.tangem.tap.features.onboarding.products.otherCards.redux
|
||||
|
||||
import com.tangem.common.CompletionResult
|
||||
import com.tangem.tap.common.extensions.onCardScanned
|
||||
import com.tangem.tap.common.extensions.withMainContext
|
||||
import com.tangem.tap.common.postUi
|
||||
import com.tangem.tap.common.redux.AppState
|
||||
|
|
@ -83,7 +84,7 @@ private fun handleOtherCardsAction(action: Action, dispatch: DispatchFunction) {
|
|||
OnboardingOtherCardsAction.Done -> {
|
||||
store.dispatch(GlobalAction.Onboarding.Stop)
|
||||
scope.launch {
|
||||
globalState.tapWalletManager.onCardScanned(onboardingManager.scanResponse)
|
||||
store.onCardScanned(onboardingManager.scanResponse)
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.Wallet))
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,72 +0,0 @@
|
|||
package com.tangem.tap.features.onboarding.products.twins
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.transition.TransitionInflater
|
||||
import com.squareup.picasso.Picasso
|
||||
import com.tangem.tap.common.extensions.dispatchDebugErrorNotification
|
||||
import com.tangem.tap.common.extensions.withMainContext
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.wallet.redux.Artwork
|
||||
import com.tangem.tap.scope
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_twin_cards_welcome.*
|
||||
import kotlinx.android.synthetic.main.layout_twin_cards.*
|
||||
import kotlinx.coroutines.launch
|
||||
|
||||
class OnboardingTwinsFragment : Fragment(R.layout.fragment_twin_cards_welcome) {
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
activity?.onBackPressedDispatcher?.addCallback(this, object : OnBackPressedCallback(true) {
|
||||
override fun handleOnBackPressed() {
|
||||
store.dispatch(NavigationAction.PopBackTo(AppScreen.Home))
|
||||
}
|
||||
})
|
||||
val inflater = TransitionInflater.from(requireContext())
|
||||
enterTransition = inflater.inflateTransition(R.transition.slide_right)
|
||||
exitTransition = inflater.inflateTransition(R.transition.fade)
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
store.dispatch(TwinCardsAction.SetOnboardingShown)
|
||||
val secondTwinNumber = store.state.twinCardsState.cardNumber?.pairNumber()?.number ?: ""
|
||||
val text = getString(R.string.twins_onboarding_description_format, secondTwinNumber)
|
||||
tv_twin_cards_description_1.text = text
|
||||
|
||||
setOnClickListeners()
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_1)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
?.into(iv_twin_card_1)
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_2)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
?.into(iv_twin_card_2)
|
||||
}
|
||||
|
||||
private fun setOnClickListeners() {
|
||||
btn_continue.setOnClickListener {
|
||||
scope.launch {
|
||||
val global = store.state.globalState
|
||||
val scanResponse = global.onboardingManager?.scanResponse ?: return@launch
|
||||
global.tapWalletManager.onCardScanned(scanResponse)
|
||||
withMainContext {
|
||||
store.dispatchDebugErrorNotification("Делаем онбоардинг")
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.Wallet))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,64 @@
|
|||
package com.tangem.tap.features.onboarding.products.twins.redux
|
||||
|
||||
import com.tangem.Message
|
||||
import com.tangem.blockchain.common.WalletManager
|
||||
import com.tangem.common.extensions.VoidCallback
|
||||
import com.tangem.tap.common.redux.StateDialog
|
||||
import com.tangem.tap.domain.tasks.product.ScanResponse
|
||||
import com.tangem.tap.domain.twins.AssetReader
|
||||
import com.tangem.tap.domain.twins.TwinCardsManager
|
||||
import com.tangem.tap.features.onboarding.OnboardingWalletBalance
|
||||
import org.rekotlin.Action
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
sealed class TwinCardsAction : Action {
|
||||
data class IfTwinsPrepareState(val scanResponse: ScanResponse) : TwinCardsAction()
|
||||
|
||||
object Init : TwinCardsAction()
|
||||
data class SetMode(val mode: CreateTwinWalletMode) : TwinCardsAction()
|
||||
data class SetStepOfScreen(val step: TwinCardsStep) : TwinCardsAction()
|
||||
data class SetUserUnderstand(val isUnderstand: Boolean) : TwinCardsAction()
|
||||
|
||||
sealed class CardsManager {
|
||||
data class Set(val manager: TwinCardsManager) : TwinCardsAction()
|
||||
object Release : TwinCardsAction()
|
||||
}
|
||||
|
||||
sealed class Wallet : TwinCardsAction() {
|
||||
data class HandleOnBackPressed(
|
||||
// this is necessary for the correct animation of the return of cards to the Home screen
|
||||
val shouldResetTwinCardsWidget: (should: Boolean, popAction: VoidCallback) -> Unit
|
||||
) : TwinCardsAction()
|
||||
|
||||
data class ShowInterruptDialog(val onOk: VoidCallback) : TwinCardsAction(), StateDialog
|
||||
|
||||
data class LaunchFirstStep(val initialMessage: Message, val reader: AssetReader) : TwinCardsAction()
|
||||
data class LaunchSecondStep(
|
||||
val initialMessage: Message,
|
||||
val preparingMessage: Message,
|
||||
val creatingWalletMessage: Message,
|
||||
) : TwinCardsAction()
|
||||
|
||||
data class LaunchThirdStep(val message: Message) : TwinCardsAction()
|
||||
}
|
||||
|
||||
|
||||
// for the onboarding
|
||||
data class SetPairCardId(val cardId: String) : TwinCardsAction()
|
||||
object TopUp : TwinCardsAction()
|
||||
object ShowAddressInfoDialog : TwinCardsAction()
|
||||
data class SetWalletManager(val walletManager: WalletManager) : TwinCardsAction()
|
||||
object Done : TwinCardsAction()
|
||||
|
||||
sealed class Balance {
|
||||
object Update : TwinCardsAction()
|
||||
data class Set(val balance: OnboardingWalletBalance) : TwinCardsAction()
|
||||
}
|
||||
|
||||
sealed class Confetti {
|
||||
object Show : TwinCardsAction()
|
||||
object Hide : TwinCardsAction()
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,275 @@
|
|||
package com.tangem.tap.features.onboarding.products.twins.redux
|
||||
|
||||
import com.tangem.blockchain.extensions.Result
|
||||
import com.tangem.common.CompletionResult
|
||||
import com.tangem.common.extensions.guard
|
||||
import com.tangem.tap.common.extensions.*
|
||||
import com.tangem.tap.common.postUi
|
||||
import com.tangem.tap.common.redux.AppDialog
|
||||
import com.tangem.tap.common.redux.AppState
|
||||
import com.tangem.tap.common.redux.global.GlobalAction
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.domain.DELAY_SDK_DIALOG_CLOSE
|
||||
import com.tangem.tap.domain.TapError
|
||||
import com.tangem.tap.domain.extensions.makePrimaryWalletManager
|
||||
import com.tangem.tap.domain.tasks.product.ScanResponse
|
||||
import com.tangem.tap.domain.twins.TwinCardsManager
|
||||
import com.tangem.tap.features.wallet.redux.Currency
|
||||
import com.tangem.tap.features.wallet.redux.ProgressState
|
||||
import com.tangem.tap.preferencesStorage
|
||||
import com.tangem.tap.scope
|
||||
import com.tangem.tap.store
|
||||
import kotlinx.coroutines.delay
|
||||
import kotlinx.coroutines.launch
|
||||
import org.rekotlin.Action
|
||||
import org.rekotlin.DispatchFunction
|
||||
import org.rekotlin.Middleware
|
||||
|
||||
class TwinCardsMiddleware {
|
||||
companion object {
|
||||
val handler = twinsWalletMiddleware
|
||||
}
|
||||
}
|
||||
|
||||
private val twinsWalletMiddleware: Middleware<AppState> = { dispatch, state ->
|
||||
{ next ->
|
||||
{ action ->
|
||||
handle(action, dispatch)
|
||||
next(action)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun handle(action: Action, dispatch: DispatchFunction) {
|
||||
val action = action as? TwinCardsAction ?: return
|
||||
|
||||
val globalState = store.state.globalState
|
||||
val onboardingManager = globalState.onboardingManager
|
||||
val twinCardsState = store.state.twinCardsState
|
||||
|
||||
fun getScanResponse(): ScanResponse {
|
||||
return when (twinCardsState.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> onboardingManager?.scanResponse
|
||||
CreateTwinWalletMode.RecreateWallet -> globalState.scanResponse
|
||||
} ?: throw NullPointerException("ScanResponse can't be NULL")
|
||||
}
|
||||
|
||||
fun updateScanResponse(response: ScanResponse) {
|
||||
when (twinCardsState.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> onboardingManager?.scanResponse = response
|
||||
CreateTwinWalletMode.RecreateWallet -> store.dispatch(GlobalAction.SaveScanNoteResponse(response))
|
||||
}
|
||||
}
|
||||
|
||||
fun startCardActivation(cardId: String) {
|
||||
if (twinCardsState.mode == CreateTwinWalletMode.CreateWallet) {
|
||||
onboardingManager?.activationStarted(cardId)
|
||||
}
|
||||
}
|
||||
|
||||
fun finishCardActivation() {
|
||||
if (twinCardsState.mode == CreateTwinWalletMode.CreateWallet) {
|
||||
onboardingManager?.activationFinished(getScanResponse().card.cardId)
|
||||
twinCardsState.pairCardId?.let { onboardingManager?.activationFinished(it) }
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
when (action) {
|
||||
is TwinCardsAction.Init -> {
|
||||
if (twinCardsState.currentStep == TwinCardsStep.WelcomeOnly) return
|
||||
|
||||
when (twinCardsState.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> {
|
||||
if (preferencesStorage.wasTwinsOnboardingShown()) {
|
||||
val step = when {
|
||||
!getScanResponse().twinsIsTwinned() -> TwinCardsStep.CreateFirstWallet
|
||||
twinCardsState.walletBalance.balanceIsToppedUp() -> TwinCardsStep.Done
|
||||
else -> TwinCardsStep.TopUpWallet
|
||||
}
|
||||
store.dispatch((TwinCardsAction.SetStepOfScreen(step)))
|
||||
} else {
|
||||
store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.Welcome))
|
||||
}
|
||||
}
|
||||
CreateTwinWalletMode.RecreateWallet -> {
|
||||
store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.Warning))
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.HandleOnBackPressed -> {
|
||||
val shouldReturnCardBack = twinCardsState.mode == CreateTwinWalletMode.CreateWallet
|
||||
&& twinCardsState.currentStep != TwinCardsStep.TopUpWallet
|
||||
&& twinCardsState.currentStep != TwinCardsStep.Done
|
||||
|
||||
if (twinCardsState.showAlert) {
|
||||
val onInterruptPrompt = {
|
||||
store.dispatch(TwinCardsAction.CardsManager.Release)
|
||||
action.shouldResetTwinCardsWidget(shouldReturnCardBack) {
|
||||
store.dispatch(NavigationAction.PopBackTo(AppScreen.Home))
|
||||
}
|
||||
}
|
||||
val stateDialog = TwinCardsAction.Wallet.ShowInterruptDialog(onInterruptPrompt)
|
||||
store.dispatchDialogShow(stateDialog)
|
||||
} else {
|
||||
store.dispatch(TwinCardsAction.CardsManager.Release)
|
||||
action.shouldResetTwinCardsWidget(shouldReturnCardBack) {
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.SetStepOfScreen -> {
|
||||
when (action.step) {
|
||||
TwinCardsStep.WelcomeOnly -> {
|
||||
preferencesStorage.saveTwinsOnboardingShown()
|
||||
}
|
||||
TwinCardsStep.Welcome -> {
|
||||
preferencesStorage.saveTwinsOnboardingShown()
|
||||
}
|
||||
TwinCardsStep.Warning -> {
|
||||
}
|
||||
TwinCardsStep.CreateFirstWallet -> {
|
||||
}
|
||||
TwinCardsStep.CreateSecondWallet -> {
|
||||
}
|
||||
TwinCardsStep.CreateThirdWallet -> {
|
||||
}
|
||||
TwinCardsStep.TopUpWallet -> {
|
||||
store.dispatch(TwinCardsAction.Balance.Update)
|
||||
}
|
||||
TwinCardsStep.Done -> {
|
||||
finishCardActivation()
|
||||
postUi(500) { store.dispatch(TwinCardsAction.Confetti.Show) }
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchFirstStep -> {
|
||||
val manager = TwinCardsManager(getScanResponse().card, action.reader)
|
||||
store.dispatch(TwinCardsAction.CardsManager.Set(manager))
|
||||
|
||||
scope.launch {
|
||||
when (val result = manager.createFirstWallet(action.initialMessage)) {
|
||||
is CompletionResult.Success -> {
|
||||
startCardActivation(result.data.cardId)
|
||||
delay(DELAY_SDK_DIALOG_CLOSE)
|
||||
withMainContext {
|
||||
store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.CreateSecondWallet))
|
||||
}
|
||||
}
|
||||
is CompletionResult.Failure -> {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchSecondStep -> {
|
||||
val manager = twinCardsState.twinCardsManager ?: return
|
||||
|
||||
scope.launch {
|
||||
val result = manager.createSecondWallet(
|
||||
action.initialMessage,
|
||||
action.preparingMessage,
|
||||
action.creatingWalletMessage
|
||||
)
|
||||
when (result) {
|
||||
is CompletionResult.Success -> {
|
||||
startCardActivation(result.data.cardId)
|
||||
delay(DELAY_SDK_DIALOG_CLOSE)
|
||||
withMainContext {
|
||||
store.dispatch(TwinCardsAction.SetPairCardId(result.data.cardId))
|
||||
store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.CreateThirdWallet))
|
||||
}
|
||||
}
|
||||
is CompletionResult.Failure -> {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchThirdStep -> {
|
||||
val manager = twinCardsState.twinCardsManager ?: return
|
||||
|
||||
scope.launch {
|
||||
when (val result = manager.complete(action.message)) {
|
||||
is Result.Success -> {
|
||||
updateScanResponse(result.data)
|
||||
delay(DELAY_SDK_DIALOG_CLOSE)
|
||||
withMainContext { store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.TopUpWallet)) }
|
||||
}
|
||||
is Result.Failure -> {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
is TwinCardsAction.Balance.Update -> {
|
||||
val walletManager = if (twinCardsState.walletManager != null) {
|
||||
twinCardsState.walletManager
|
||||
} else {
|
||||
val wmFactory = globalState.tapWalletManager.walletManagerFactory
|
||||
val walletManager = wmFactory.makePrimaryWalletManager(getScanResponse()).guard {
|
||||
val message = "Loading cancelled. Cause: wallet manager didn't created"
|
||||
val customError = TapError.CustomError(message)
|
||||
store.dispatchErrorNotification(customError)
|
||||
return
|
||||
}
|
||||
dispatch(TwinCardsAction.SetWalletManager(walletManager))
|
||||
walletManager
|
||||
}
|
||||
val isLoadedBefore = twinCardsState.walletBalance.state != ProgressState.Loading
|
||||
val balanceIsLoading = twinCardsState.walletBalance.copy(
|
||||
currency = Currency.Blockchain(walletManager.wallet.blockchain),
|
||||
state = ProgressState.Loading,
|
||||
error = null,
|
||||
criticalError = null
|
||||
)
|
||||
store.dispatch(TwinCardsAction.Balance.Set(balanceIsLoading))
|
||||
|
||||
scope.launch {
|
||||
val loadedBalance = onboardingManager?.updateBalance(walletManager) ?: return@launch
|
||||
loadedBalance.criticalError?.let { store.dispatchErrorNotification(it) }
|
||||
delay(if (isLoadedBefore) 0 else 300)
|
||||
withMainContext { store.dispatch(TwinCardsAction.Balance.Set(loadedBalance)) }
|
||||
}
|
||||
|
||||
}
|
||||
is TwinCardsAction.Balance.Set -> {
|
||||
if (action.balance.balanceIsToppedUp()) {
|
||||
scope.launch {
|
||||
withMainContext { store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.Done)) }
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.ShowAddressInfoDialog -> {
|
||||
val addressData = twinCardsState.walletManager?.getAddressData() ?: return
|
||||
|
||||
val addressWasCopied = globalState.resources.strings.addressWasCopied
|
||||
val appDialog = AppDialog.AddressInfoDialog(
|
||||
addressData,
|
||||
onCopyAddress = { store.dispatchToastNotification(addressWasCopied) },
|
||||
onExploreAddress = { store.dispatchOpenUrl(addressData.exploreUrl) }
|
||||
)
|
||||
store.dispatchDialogShow(appDialog)
|
||||
}
|
||||
is TwinCardsAction.TopUp -> {
|
||||
val topUpUrl = twinCardsState.walletManager?.getToUpUrl() ?: return
|
||||
store.dispatchOpenUrl(topUpUrl)
|
||||
}
|
||||
TwinCardsAction.Done -> {
|
||||
scope.launch {
|
||||
val scanResponse = getScanResponse()
|
||||
store.onCardScanned(scanResponse)
|
||||
withMainContext {
|
||||
when (twinCardsState.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> {
|
||||
store.dispatch(GlobalAction.Onboarding.Stop)
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.Wallet))
|
||||
}
|
||||
CreateTwinWalletMode.RecreateWallet -> {
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,64 @@
|
|||
package com.tangem.tap.features.onboarding.products.twins.redux
|
||||
|
||||
import com.tangem.tap.common.redux.AppState
|
||||
import com.tangem.tap.domain.twins.getTwinCardNumber
|
||||
import org.rekotlin.Action
|
||||
|
||||
class TwinCardsReducer {
|
||||
companion object {
|
||||
fun reduce(action: Action, state: AppState): TwinCardsState = internalReduce(action, state)
|
||||
}
|
||||
}
|
||||
|
||||
private fun internalReduce(action: Action, state: AppState): TwinCardsState {
|
||||
if (action !is TwinCardsAction) return state.twinCardsState
|
||||
|
||||
var state = state.twinCardsState
|
||||
|
||||
when (action) {
|
||||
is TwinCardsAction.IfTwinsPrepareState -> {
|
||||
state = if (action.scanResponse.isTangemTwins()) {
|
||||
val cardNumber = action.scanResponse.card.getTwinCardNumber() ?: return state
|
||||
|
||||
TwinCardsState(
|
||||
cardNumber = cardNumber,
|
||||
mode = CreateTwinWalletMode.CreateWallet,
|
||||
)
|
||||
} else {
|
||||
TwinCardsState()
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.SetMode -> {
|
||||
state = state.copy(mode = action.mode)
|
||||
}
|
||||
is TwinCardsAction.SetStepOfScreen -> {
|
||||
state = state.copy(currentStep = action.step)
|
||||
}
|
||||
is TwinCardsAction.SetUserUnderstand -> {
|
||||
state = state.copy(userWasUnderstandIfWalletRecreate = action.isUnderstand)
|
||||
}
|
||||
is TwinCardsAction.CardsManager.Set -> {
|
||||
state = state.copy(twinCardsManager = action.manager)
|
||||
}
|
||||
TwinCardsAction.CardsManager.Release -> {
|
||||
state = state.copy(twinCardsManager = null)
|
||||
}
|
||||
is TwinCardsAction.SetPairCardId -> {
|
||||
state = state.copy(pairCardId = action.cardId)
|
||||
}
|
||||
is TwinCardsAction.SetWalletManager -> {
|
||||
state = state.copy(walletManager = action.walletManager)
|
||||
}
|
||||
is TwinCardsAction.Balance.Set -> {
|
||||
state = state.copy(walletBalance = action.balance)
|
||||
}
|
||||
is TwinCardsAction.Confetti.Show -> {
|
||||
state = state.copy(showConfetti = true)
|
||||
}
|
||||
is TwinCardsAction.Confetti.Hide -> {
|
||||
state = state.copy(showConfetti = false)
|
||||
}
|
||||
}
|
||||
|
||||
return state
|
||||
}
|
||||
|
|
@ -0,0 +1,61 @@
|
|||
package com.tangem.tap.features.onboarding.products.twins.redux
|
||||
|
||||
import com.tangem.blockchain.common.WalletManager
|
||||
import com.tangem.tap.domain.twins.TwinCardNumber
|
||||
import com.tangem.tap.domain.twins.TwinCardsManager
|
||||
import com.tangem.tap.features.onboarding.OnboardingWalletBalance
|
||||
import org.rekotlin.StateType
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
data class TwinCardsState(
|
||||
// if cardNumber = null -> the scanned card is not Twin
|
||||
val cardNumber: TwinCardNumber? = null,
|
||||
val mode: CreateTwinWalletMode = CreateTwinWalletMode.CreateWallet,
|
||||
val currentStep: TwinCardsStep = TwinCardsStep.Welcome,
|
||||
val userWasUnderstandIfWalletRecreate: Boolean = false,
|
||||
// available only when creating or recreating wallets
|
||||
val twinCardsManager: TwinCardsManager? = null,
|
||||
|
||||
// for the onboarding
|
||||
val pairCardId: String? = null, // available after create\recreate wallets
|
||||
val walletManager: WalletManager? = null,
|
||||
val walletBalance: OnboardingWalletBalance = OnboardingWalletBalance.loading(),
|
||||
val showConfetti: Boolean = false,
|
||||
) : StateType {
|
||||
|
||||
val steps: List<TwinCardsStep>
|
||||
get() = when (mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> listOf(
|
||||
TwinCardsStep.None,
|
||||
TwinCardsStep.CreateFirstWallet,
|
||||
TwinCardsStep.CreateSecondWallet,
|
||||
TwinCardsStep.CreateThirdWallet,
|
||||
TwinCardsStep.TopUpWallet,
|
||||
TwinCardsStep.Done
|
||||
)
|
||||
CreateTwinWalletMode.RecreateWallet -> listOf(
|
||||
TwinCardsStep.None,
|
||||
TwinCardsStep.CreateFirstWallet,
|
||||
TwinCardsStep.CreateSecondWallet,
|
||||
TwinCardsStep.CreateThirdWallet,
|
||||
TwinCardsStep.Done
|
||||
)
|
||||
}
|
||||
|
||||
val progress: Int
|
||||
get() = steps.indexOf(currentStep)
|
||||
|
||||
val showAlert: Boolean
|
||||
get() = currentStep == TwinCardsStep.CreateSecondWallet || currentStep == TwinCardsStep.CreateThirdWallet
|
||||
}
|
||||
|
||||
enum class CreateTwinWalletMode { CreateWallet, RecreateWallet }
|
||||
|
||||
enum class TwinCardsStep {
|
||||
None, WelcomeOnly, Welcome, Warning, CreateFirstWallet, CreateSecondWallet, CreateThirdWallet,
|
||||
|
||||
// for the onboarding
|
||||
TopUpWallet, Done
|
||||
}
|
||||
|
|
@ -0,0 +1,366 @@
|
|||
package com.tangem.tap.features.onboarding.products.twins.ui
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import android.view.animation.OvershootInterpolator
|
||||
import androidx.annotation.LayoutRes
|
||||
import androidx.constraintlayout.widget.ConstraintSet
|
||||
import androidx.core.view.isVisible
|
||||
import androidx.transition.TransitionInflater
|
||||
import androidx.transition.TransitionManager
|
||||
import com.squareup.picasso.Picasso
|
||||
import com.tangem.Message
|
||||
import com.tangem.blockchain.common.Blockchain
|
||||
import com.tangem.common.extensions.VoidCallback
|
||||
import com.tangem.tap.common.extensions.*
|
||||
import com.tangem.tap.common.leapfrogWidget.LeapfrogWidget
|
||||
import com.tangem.tap.common.postUi
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.common.redux.navigation.ShareElement
|
||||
import com.tangem.tap.common.toggleWidget.RefreshBalanceWidget
|
||||
import com.tangem.tap.common.transitions.InternalNoteLayoutTransition
|
||||
import com.tangem.tap.domain.twins.AssetReader
|
||||
import com.tangem.tap.domain.twins.TwinCardNumber
|
||||
import com.tangem.tap.domain.twins.TwinsCardWidget
|
||||
import com.tangem.tap.features.onboarding.products.BaseOnboardingFragment
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.CreateTwinWalletMode
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsStep
|
||||
import com.tangem.tap.features.wallet.redux.Artwork
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_onboarding_main.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_bottom.*
|
||||
import kotlinx.android.synthetic.main.layout_onboarding_container_top.*
|
||||
import kotlinx.android.synthetic.main.view_bg_twins_welcome.*
|
||||
import kotlinx.android.synthetic.main.view_onboarding_progress.*
|
||||
import kotlinx.android.synthetic.main.view_onboarding_tv_balance.*
|
||||
import org.rekotlin.Action
|
||||
|
||||
class TwinsCardsFragment : BaseOnboardingFragment<TwinCardsState>() {
|
||||
|
||||
private var previousStep = TwinCardsStep.None
|
||||
|
||||
private lateinit var twinsWidget: TwinsCardWidget
|
||||
private lateinit var btnRefreshBalanceWidget: RefreshBalanceWidget
|
||||
|
||||
private val assetReader: AssetReader by lazy {
|
||||
object : AssetReader {
|
||||
override fun readAssetAsString(name: String): String = requireContext().readAssetAsString(name)
|
||||
}
|
||||
}
|
||||
|
||||
override fun getOnboardingTopContainerId(): Int = R.layout.layout_onboarding_container_top
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
postponeEnterTransition()
|
||||
store.dispatch(TwinCardsAction.Init)
|
||||
}
|
||||
|
||||
override fun configureTransitions() {
|
||||
when (store.state.twinCardsState.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> super.configureTransitions()
|
||||
CreateTwinWalletMode.RecreateWallet -> {
|
||||
val inflater = TransitionInflater.from(requireContext())
|
||||
enterTransition = inflater.inflateTransition(R.transition.slide_right)
|
||||
exitTransition = inflater.inflateTransition(R.transition.fade)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
reconfigureLayoutForTwins()
|
||||
twinsWidget = TwinsCardWidget(LeapfrogWidget(cards_container)) { 250f }
|
||||
btnRefreshBalanceWidget = RefreshBalanceWidget(onboarding_main_container)
|
||||
|
||||
toolbar.title = getText(R.string.twins_recreate_toolbar)
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_1)
|
||||
.placeholder(R.drawable.card_placeholder_black)
|
||||
?.into(imv_twin_front_card)
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_2)
|
||||
.placeholder(R.drawable.card_placeholder_white)
|
||||
?.into(imv_twin_back_card)
|
||||
}
|
||||
|
||||
private fun reconfigureLayoutForTwins() {
|
||||
imv_front_card.hide()
|
||||
imv_card_background.hide()
|
||||
cards_container.show()
|
||||
|
||||
imv_twin_front_card.transitionName = ShareElement.imvFrontCard
|
||||
imv_twin_back_card.transitionName = ShareElement.imvBackCard
|
||||
}
|
||||
|
||||
override fun subscribeToStore() {
|
||||
store.subscribe(this) { state ->
|
||||
state.skipRepeats { oldState, newState ->
|
||||
oldState.twinCardsState == newState.twinCardsState
|
||||
}.select { it.twinCardsState }
|
||||
}
|
||||
storeSubscribersList.add(this)
|
||||
}
|
||||
|
||||
override fun newState(state: TwinCardsState) {
|
||||
if (activity == null) return
|
||||
|
||||
// toolbar.title = when (state.mode) {
|
||||
// CreateTwinWalletMode.CreateWallet -> getText(R.string.wallet_button_create_wallet)
|
||||
// CreateTwinWalletMode.RecreateWallet -> getText(R.string.twins_recreate_toolbar)
|
||||
// }
|
||||
|
||||
pb_state.max = state.steps.size - 1
|
||||
pb_state.progress = state.progress
|
||||
|
||||
when (state.currentStep) {
|
||||
TwinCardsStep.WelcomeOnly -> setupWelcomeOnlyState(state)
|
||||
TwinCardsStep.Welcome -> setupWelcomeState(state)
|
||||
TwinCardsStep.Warning -> setupWarningState(state)
|
||||
TwinCardsStep.CreateFirstWallet -> setupCreateFirstWalletState(state)
|
||||
TwinCardsStep.CreateSecondWallet -> setupCreateSecondWalletState(state)
|
||||
TwinCardsStep.CreateThirdWallet -> setupCreateThirdWalletState(state)
|
||||
TwinCardsStep.TopUpWallet -> setupTopUpWalletState(state)
|
||||
TwinCardsStep.Done -> setupDoneState(state)
|
||||
}
|
||||
|
||||
setBalance(state)
|
||||
showConfetti(state.showConfetti)
|
||||
previousStep = state.currentStep
|
||||
}
|
||||
|
||||
private fun setBalance(state: TwinCardsState) {
|
||||
if (state.walletBalance.currency.blockchain == Blockchain.Unknown) return
|
||||
|
||||
val balanceValue = state.walletBalance.value.stripZeroPlainString()
|
||||
val currency = state.walletBalance.currency.currencySymbol
|
||||
tv_balance_value.text = "$balanceValue $currency"
|
||||
}
|
||||
|
||||
private fun setupWelcomeOnlyState(state: TwinCardsState) {
|
||||
setupWelcomeState(state, NavigationAction.NavigateTo(AppScreen.Wallet))
|
||||
}
|
||||
|
||||
private fun setupWelcomeState(state: TwinCardsState) {
|
||||
setupWelcomeState(state, TwinCardsAction.SetStepOfScreen(TwinCardsStep.CreateFirstWallet))
|
||||
}
|
||||
|
||||
private fun setupWelcomeState(state: TwinCardsState, mainAction: Action) {
|
||||
twinsWidget.toWelcome(false) { startPostponedEnterTransition() }
|
||||
|
||||
pb_state.hide()
|
||||
|
||||
tv_header.setText(R.string.twins_onboarding_subtitle)
|
||||
tv_body.text = getString(R.string.twins_onboarding_description_format, state.cardNumber?.pairIndexNumber())
|
||||
|
||||
btn_main_action.setText(R.string.common_continue)
|
||||
btn_main_action.setOnClickListener { store.dispatch(mainAction) }
|
||||
}
|
||||
|
||||
private fun setupWarningState(state: TwinCardsState) {
|
||||
twinsWidget.toWelcome(false) { startPostponedEnterTransition() }
|
||||
pb_state.hide()
|
||||
chb_understand.show()
|
||||
|
||||
tv_header.setText(R.string.common_warning)
|
||||
tv_body.setText(R.string.twins_recreate_warning)
|
||||
|
||||
chb_understand.setOnCheckedChangeListener { buttonView, isChecked ->
|
||||
store.dispatch(TwinCardsAction.SetUserUnderstand(isChecked))
|
||||
}
|
||||
btn_main_action.isEnabled = state.userWasUnderstandIfWalletRecreate
|
||||
btn_main_action.setText(R.string.common_continue)
|
||||
btn_main_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.SetStepOfScreen(TwinCardsStep.CreateFirstWallet))
|
||||
}
|
||||
}
|
||||
|
||||
private fun setupCreateFirstWalletState(state: TwinCardsState) {
|
||||
bg_circle_large.hide()
|
||||
bg_circle_medium.hide()
|
||||
bg_circle_min.hide()
|
||||
chb_understand.hide()
|
||||
pb_state.show()
|
||||
|
||||
onboarding_main_container.beginDelayedTransition()
|
||||
|
||||
when (previousStep) {
|
||||
TwinCardsStep.None -> {
|
||||
twinsWidget.toLeapfrog(false) {
|
||||
when (state.cardNumber) {
|
||||
TwinCardNumber.First -> startPostponedEnterTransition()
|
||||
TwinCardNumber.Second -> {
|
||||
switchToCard(state.cardNumber, false) { startPostponedEnterTransition() }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
TwinCardsStep.Welcome, TwinCardsStep.Warning -> {
|
||||
twinsWidget.toLeapfrog(onEnd = { switchToCard(state.cardNumber) })
|
||||
}
|
||||
}
|
||||
|
||||
val twinIndexNumber = state.cardNumber?.indexNumber()
|
||||
tv_header.text = getString(R.string.twins_recreate_title_format, twinIndexNumber)
|
||||
tv_body.setText(R.string.onboarding_twins_interrupt_warning)
|
||||
|
||||
btn_main_action.text = getString(R.string.twins_recreate_button_format, twinIndexNumber)
|
||||
btn_main_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchFirstStep(
|
||||
Message(getString(R.string.twins_recreate_title_format, twinIndexNumber)),
|
||||
assetReader
|
||||
))
|
||||
}
|
||||
|
||||
btn_alternative_action.isVisible = false
|
||||
btn_alternative_action.isClickable = false
|
||||
}
|
||||
|
||||
private fun setupCreateSecondWalletState(state: TwinCardsState) {
|
||||
switchToCard(state.cardNumber?.pairNumber())
|
||||
|
||||
val twinPairIndexNumber = state.cardNumber?.pairIndexNumber()
|
||||
tv_header.text = getString(R.string.twins_recreate_title_format, twinPairIndexNumber)
|
||||
tv_body.setText(R.string.onboarding_twins_interrupt_warning)
|
||||
|
||||
btn_main_action.text = getString(R.string.twins_recreate_button_format, twinPairIndexNumber)
|
||||
btn_main_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchSecondStep(
|
||||
Message(getString(R.string.twins_recreate_title_format, twinPairIndexNumber)),
|
||||
Message(getString(R.string.twins_recreate_title_preparing)),
|
||||
Message(getString(R.string.twins_recreate_title_creating_wallet)),
|
||||
))
|
||||
}
|
||||
}
|
||||
|
||||
private fun setupCreateThirdWalletState(state: TwinCardsState) {
|
||||
switchToCard(state.cardNumber)
|
||||
|
||||
val twinIndexNumber = state.cardNumber?.indexNumber()
|
||||
tv_header.text = getString(R.string.twins_recreate_title_format, twinIndexNumber)
|
||||
tv_body.setText(R.string.onboarding_twins_interrupt_warning)
|
||||
|
||||
btn_main_action.text = getString(R.string.twins_recreate_button_format, twinIndexNumber)
|
||||
btn_main_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchThirdStep(
|
||||
Message(getString(R.string.twins_recreate_title_format, twinIndexNumber))
|
||||
))
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private fun setupTopUpWalletState(state: TwinCardsState) {
|
||||
when (previousStep) {
|
||||
TwinCardsStep.None -> {
|
||||
when (state.cardNumber) {
|
||||
TwinCardNumber.First -> {
|
||||
twinsWidget.leapfrogWidget.unfold(false) {
|
||||
twinsWidget.toActivate(false) {
|
||||
startPostponedEnterTransition()
|
||||
}
|
||||
}
|
||||
}
|
||||
TwinCardNumber.Second -> {
|
||||
switchToCard(state.cardNumber, false) {
|
||||
twinsWidget.toActivate(false)
|
||||
startPostponedEnterTransition()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
TwinCardsStep.CreateThirdWallet -> {
|
||||
twinsWidget.toActivate()
|
||||
}
|
||||
}
|
||||
|
||||
btn_main_action.setText(R.string.onboarding_top_up_button_but_crypto)
|
||||
btn_main_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.TopUp)
|
||||
}
|
||||
|
||||
btn_alternative_action.setText(R.string.onboarding_top_up_button_show_wallet_address)
|
||||
btn_alternative_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.ShowAddressInfoDialog)
|
||||
}
|
||||
|
||||
tv_header.setText(R.string.onboarding_top_up_header)
|
||||
tv_body.setText(R.string.onboarding_top_up_body)
|
||||
|
||||
btnRefreshBalanceWidget.changeState(state.walletBalance.state)
|
||||
if (btnRefreshBalanceWidget.isShowing != true) {
|
||||
postUi(300) {
|
||||
btnRefreshBalanceWidget.mainView.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Balance.Update)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
imv_card_background.setBackgroundDrawable(requireContext().getDrawableCompat(R.drawable.shape_rectangle_rounded_8))
|
||||
updateConstraints(state.currentStep, R.layout.lp_onboarding_topup_wallet_twins)
|
||||
}
|
||||
|
||||
private fun setupDoneState(state: TwinCardsState) {
|
||||
btn_main_action.setText(R.string.onboarding_done_button_continue)
|
||||
btn_main_action.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Confetti.Hide)
|
||||
store.dispatch(TwinCardsAction.Done)
|
||||
}
|
||||
|
||||
btn_alternative_action.isVisible = false
|
||||
btn_alternative_action.isClickable = false
|
||||
|
||||
tv_header.setText(R.string.onboarding_done_header)
|
||||
tv_body.setText(R.string.onboarding_done_body)
|
||||
|
||||
val layout = when (state.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> R.layout.lp_onboarding_done_activation_twins
|
||||
CreateTwinWalletMode.RecreateWallet -> R.layout.lp_onboarding_done
|
||||
}
|
||||
updateConstraints(state.currentStep, layout)
|
||||
}
|
||||
|
||||
private fun updateConstraints(currentStep: TwinCardsStep, @LayoutRes layoutId: Int) {
|
||||
if (this.previousStep == currentStep) return
|
||||
|
||||
val constraintSet = ConstraintSet()
|
||||
constraintSet.clone(requireContext(), layoutId)
|
||||
constraintSet.applyTo(onboarding_main_container)
|
||||
val transition = InternalNoteLayoutTransition()
|
||||
transition.interpolator = OvershootInterpolator()
|
||||
TransitionManager.beginDelayedTransition(onboarding_main_container, transition)
|
||||
}
|
||||
|
||||
private fun switchToCard(cardNumber: TwinCardNumber?, animate: Boolean = true, onEnd: VoidCallback = {}) {
|
||||
val position = cardNumber?.number ?: return
|
||||
|
||||
if (twinsWidget.leapfrogWidget.getViewPositionByIndex(1) != position - 1) {
|
||||
twinsWidget.leapfrogWidget.leap(animate, onEnd)
|
||||
} else {
|
||||
onEnd()
|
||||
}
|
||||
}
|
||||
|
||||
override fun handleOnBackPressed() {
|
||||
store.dispatch(TwinCardsAction.Wallet.HandleOnBackPressed { should, popAction ->
|
||||
store.dispatch(TwinCardsAction.Confetti.Hide)
|
||||
showConfetti(false)
|
||||
if (should) switchToCard(TwinCardNumber.First, true, popAction)
|
||||
else popAction()
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
private fun TwinCardNumber?.indexNumber(): String {
|
||||
return this?.number?.toString() ?: ""
|
||||
}
|
||||
|
||||
private fun TwinCardNumber?.pairIndexNumber(): String {
|
||||
return this?.pairNumber()?.number?.toString() ?: ""
|
||||
}
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
package com.tangem.tap.features.twins.ui.dialog
|
||||
package com.tangem.tap.features.onboarding.products.twins.ui.dialog
|
||||
|
||||
import android.content.Context
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import com.google.android.material.dialog.MaterialAlertDialogBuilder
|
||||
import com.tangem.tap.common.extensions.dispatchDialogHide
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
|
||||
|
|
@ -13,10 +13,10 @@ import com.tangem.wallet.R
|
|||
*/
|
||||
class CreateWalletInterruptDialog {
|
||||
companion object {
|
||||
fun create(state: TwinCardsAction.Wallet.InterruptDialog, context: Context): AlertDialog {
|
||||
fun create(state: TwinCardsAction.Wallet.ShowInterruptDialog, context: Context): AlertDialog {
|
||||
return MaterialAlertDialogBuilder(context)
|
||||
.setMessage(R.string.details_twins_recreate_alert)
|
||||
.setPositiveButton(R.string.common_ok) { _, _ -> state.interrupt() }
|
||||
.setMessage(R.string.twins_recreate_alert)
|
||||
.setPositiveButton(R.string.common_ok) { _, _ -> state.onOk() }
|
||||
.setNegativeButton(R.string.common_cancel) { _, _ -> }
|
||||
.setOnDismissListener { store.dispatchDialogHide() }
|
||||
.create()
|
||||
|
|
@ -3,8 +3,8 @@ package com.tangem.tap.features.onboarding.products.wallet
|
|||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import androidx.transition.TransitionInflater
|
||||
import com.tangem.tap.features.BaseStoreFragment
|
||||
import com.tangem.tap.features.onboarding.products.wallet.redux.OnboardingWalletState
|
||||
import com.tangem.tap.features.send.BaseStoreFragment
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import org.rekotlin.StoreSubscriber
|
||||
|
|
|
|||
|
|
@ -7,7 +7,6 @@ import android.text.method.DigitsKeyListener
|
|||
import android.view.View
|
||||
import android.view.inputmethod.EditorInfo
|
||||
import android.widget.EditText
|
||||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.core.view.postDelayed
|
||||
import androidx.core.widget.addTextChangedListener
|
||||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
|
|
@ -25,7 +24,7 @@ import com.tangem.tap.common.redux.navigation.NavigationAction
|
|||
import com.tangem.tap.common.snackBar.MaxAmountSnackbar
|
||||
import com.tangem.tap.common.text.truncateMiddleWith
|
||||
import com.tangem.tap.common.toggleWidget.*
|
||||
import com.tangem.tap.features.send.BaseStoreFragment
|
||||
import com.tangem.tap.features.BaseStoreFragment
|
||||
import com.tangem.tap.features.send.redux.*
|
||||
import com.tangem.tap.features.send.redux.AddressPayIdActionUi.*
|
||||
import com.tangem.tap.features.send.redux.AmountActionUi.*
|
||||
|
|
@ -63,23 +62,6 @@ class SendFragment : BaseStoreFragment(R.layout.fragment_send) {
|
|||
private val sendSubscriber = SendStateSubscriber(this)
|
||||
private lateinit var keyboardObserver: KeyboardObserver
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
|
||||
activity?.onBackPressedDispatcher?.addCallback(this, object : OnBackPressedCallback(true) {
|
||||
override fun handleOnBackPressed() {
|
||||
val externalTransactionData = store.state.sendState.externalTransactionData
|
||||
if (externalTransactionData == null) {
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
} else {
|
||||
store.dispatch(
|
||||
WalletAction.TradeCryptoAction.FinishSelling(externalTransactionData.transactionId)
|
||||
)
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
|
|
@ -97,7 +79,7 @@ class SendFragment : BaseStoreFragment(R.layout.fragment_send) {
|
|||
private fun initSendButtonStates() {
|
||||
btnSend.setOnClickListener {
|
||||
store.dispatch(SendActionUi.SendAmountToRecipient(
|
||||
Message(getString(R.string.initial_message_sign_header))
|
||||
Message(getString(R.string.initial_message_sign_header))
|
||||
))
|
||||
}
|
||||
sendBtn = IndeterminateProgressButtonWidget(btnSend, progress)
|
||||
|
|
@ -124,8 +106,8 @@ class SendFragment : BaseStoreFragment(R.layout.fragment_send) {
|
|||
}
|
||||
imvQrCode.setOnClickListener {
|
||||
startActivityForResult(
|
||||
Intent(requireContext(), ScanQrCodeActivity::class.java),
|
||||
ScanQrCodeActivity.SCAN_QR_REQUEST_CODE
|
||||
Intent(requireContext(), ScanQrCodeActivity::class.java),
|
||||
ScanQrCodeActivity.SCAN_QR_REQUEST_CODE
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
@ -281,6 +263,17 @@ class SendFragment : BaseStoreFragment(R.layout.fragment_send) {
|
|||
sp.edit().putString("mainCurrency", type.name).apply()
|
||||
}
|
||||
|
||||
override fun handleOnBackPressed() {
|
||||
val externalTransactionData = store.state.sendState.externalTransactionData
|
||||
if (externalTransactionData == null) {
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
} else {
|
||||
store.dispatch(
|
||||
WalletAction.TradeCryptoAction.FinishSelling(externalTransactionData.transactionId)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
override fun onDestroy() {
|
||||
keyboardObserver.unregisterListener()
|
||||
store.dispatch(ReleaseSendState)
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
package com.tangem.tap.features.send.ui.stateSubscribers
|
||||
|
||||
import com.tangem.tap.features.send.BaseStoreFragment
|
||||
import com.tangem.tap.features.BaseStoreFragment
|
||||
import org.rekotlin.StateType
|
||||
import org.rekotlin.StoreSubscriber
|
||||
import java.lang.ref.WeakReference
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import com.tangem.tap.common.redux.getMessageString
|
|||
import com.tangem.tap.common.text.DecimalDigitsInputFilter
|
||||
import com.tangem.tap.domain.MultiMessageError
|
||||
import com.tangem.tap.domain.assembleErrors
|
||||
import com.tangem.tap.features.send.BaseStoreFragment
|
||||
import com.tangem.tap.features.BaseStoreFragment
|
||||
import com.tangem.tap.features.send.redux.AddressPayIdVerifyAction.Error
|
||||
import com.tangem.tap.features.send.redux.FeeAction
|
||||
import com.tangem.tap.features.send.redux.SendAction
|
||||
|
|
@ -188,15 +188,15 @@ class SendStateSubscriber(fragment: BaseStoreFragment) : FragmentStateSubscriber
|
|||
(fg as? SendFragment)?.saveMainCurrency(state.mainCurrency.type)
|
||||
|
||||
val balanceText = fg.getString(R.string.send_balance_subtitle_format,
|
||||
state.mainCurrency.currencySymbol,
|
||||
state.viewBalanceValue)
|
||||
state.mainCurrency.currencySymbol,
|
||||
state.viewBalanceValue)
|
||||
fg.tvBalance.update(balanceText)
|
||||
|
||||
fg.tilAmountToSend.isEnabled = state.inputIsEnabled
|
||||
|
||||
val imageRes = if (state.inputIsEnabled) R.drawable.ic_arrows_up_down else 0
|
||||
fg.tvAmountCurrency.setCompoundDrawablesWithIntrinsicBounds(0, 0, imageRes, 0)
|
||||
val textColor = if (state.inputIsEnabled) R.color.blue else R.color.textGray
|
||||
val textColor = if (state.inputIsEnabled) R.color.blue else R.color.textGray
|
||||
fg.tvAmountCurrency.setTextColor(fg.getColor(textColor))
|
||||
|
||||
}
|
||||
|
|
@ -245,7 +245,7 @@ class SendStateSubscriber(fragment: BaseStoreFragment) : FragmentStateSubscriber
|
|||
totalLayout.tvTotalValue.update("${roughOrEmpty(receipt.totalFiat)} ${receipt.symbols.fiat}")
|
||||
|
||||
val willSent = getString(R.string.send_total_subtitle_format,
|
||||
receipt.willSentCrypto, receipt.symbols.crypto)
|
||||
receipt.willSentCrypto, receipt.symbols.crypto)
|
||||
totalLayout.tvWillBeSentValue.update(willSent)
|
||||
|
||||
}
|
||||
|
|
@ -277,9 +277,9 @@ class SendStateSubscriber(fragment: BaseStoreFragment) : FragmentStateSubscriber
|
|||
totalLayout.tvTotalValue.update("${roughOrEmpty(receipt.totalFiat)} ${receipt.symbols.fiat}")
|
||||
|
||||
val willSent = getString(
|
||||
R.string.send_total_subtitle_asset_format,
|
||||
receipt.symbols.token ?: "", receipt.willSentToken,
|
||||
receipt.symbols.crypto, receipt.willSentFeeCoin
|
||||
R.string.send_total_subtitle_asset_format,
|
||||
receipt.symbols.token ?: "", receipt.willSentToken,
|
||||
receipt.symbols.crypto, receipt.willSentFeeCoin
|
||||
)
|
||||
totalLayout.tvWillBeSentValue.update(willSent)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,62 +0,0 @@
|
|||
package com.tangem.tap.features.twins.redux
|
||||
|
||||
import com.tangem.Message
|
||||
import com.tangem.tap.common.redux.StateDialog
|
||||
import com.tangem.tap.domain.tasks.product.ScanResponse
|
||||
import com.tangem.tap.domain.twins.AssetReader
|
||||
import com.tangem.tap.domain.twins.TwinCardNumber
|
||||
import com.tangem.tap.domain.twins.TwinCardsManager
|
||||
import org.rekotlin.Action
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
sealed class TwinCardsAction : Action {
|
||||
|
||||
data class SetResources(val resources: TwinCardsResources) : TwinCardsAction()
|
||||
|
||||
data class SetTwinCard(
|
||||
val number: TwinCardNumber,
|
||||
val secondCardId: String?,
|
||||
val isCreatingTwinCardsAllowed: Boolean,
|
||||
) : TwinCardsAction()
|
||||
|
||||
sealed class CardsManager {
|
||||
data class Set(val manager: TwinCardsManager) : TwinCardsAction()
|
||||
object Release : TwinCardsAction()
|
||||
}
|
||||
|
||||
object ShowOnboarding : TwinCardsAction()
|
||||
object SetOnboardingShown : TwinCardsAction()
|
||||
object ProceedToCreateWallet : TwinCardsAction()
|
||||
|
||||
sealed class Wallet : TwinCardsAction() {
|
||||
object HandleOnBackPressed : TwinCardsAction()
|
||||
|
||||
data class Create(
|
||||
val number: TwinCardNumber,
|
||||
val createTwinWalletMode: CreateTwinWalletMode
|
||||
) : TwinCardsAction()
|
||||
|
||||
data class InterruptDialog(val interrupt: () -> Unit) : TwinCardsAction(), StateDialog
|
||||
|
||||
data class LaunchFirstStep(
|
||||
val initialMessage: Message,
|
||||
val reader: AssetReader
|
||||
) : TwinCardsAction() {
|
||||
object Success : TwinCardsAction()
|
||||
}
|
||||
|
||||
data class LaunchSecondStep(
|
||||
val initialMessage: Message,
|
||||
val preparingMessage: Message,
|
||||
val creatingWalletMessage: Message,
|
||||
) : TwinCardsAction() {
|
||||
object Success : TwinCardsAction()
|
||||
}
|
||||
|
||||
data class LaunchThirdStep(val message: Message) : TwinCardsAction() {
|
||||
data class Success(val scanResponse: ScanResponse) : TwinCardsAction()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1,139 +0,0 @@
|
|||
package com.tangem.tap.features.twins.redux
|
||||
|
||||
import com.tangem.blockchain.extensions.Result
|
||||
import com.tangem.blockchain.extensions.SimpleResult
|
||||
import com.tangem.tap.common.extensions.dispatchDialogShow
|
||||
import com.tangem.tap.common.extensions.dispatchNotification
|
||||
import com.tangem.tap.common.redux.AppState
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.domain.extensions.toSendableAmounts
|
||||
import com.tangem.tap.domain.twins.TwinCardsManager
|
||||
import com.tangem.tap.preferencesStorage
|
||||
import com.tangem.tap.scope
|
||||
import com.tangem.tap.store
|
||||
import kotlinx.coroutines.Dispatchers
|
||||
import kotlinx.coroutines.launch
|
||||
import kotlinx.coroutines.withContext
|
||||
import org.rekotlin.Action
|
||||
import org.rekotlin.DispatchFunction
|
||||
import org.rekotlin.Middleware
|
||||
|
||||
class TwinCardsMiddleware {
|
||||
companion object {
|
||||
val handler = twinsWalletMiddleware
|
||||
}
|
||||
}
|
||||
|
||||
private val twinsWalletMiddleware: Middleware<AppState> = { dispatch, state ->
|
||||
{ next ->
|
||||
{ action ->
|
||||
handle(action, dispatch)
|
||||
next(action)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun handle(action: Action, dispatch: DispatchFunction) {
|
||||
val action = action as? TwinCardsAction ?: return
|
||||
|
||||
val twinCardsState = store.state.twinCardsState
|
||||
|
||||
when (action) {
|
||||
is TwinCardsAction.SetTwinCard -> {
|
||||
val showOnboarding = !preferencesStorage.wasTwinsOnboardingShown()
|
||||
if (showOnboarding) store.dispatch(TwinCardsAction.ShowOnboarding)
|
||||
}
|
||||
TwinCardsAction.SetOnboardingShown -> {
|
||||
preferencesStorage.saveTwinsOnboardingShown()
|
||||
}
|
||||
is TwinCardsAction.ProceedToCreateWallet -> {
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.CreateTwinWallet))
|
||||
}
|
||||
is TwinCardsAction.Wallet.HandleOnBackPressed -> {
|
||||
if (twinCardsState.createWalletState?.showAlert == true) {
|
||||
val stateDialog = TwinCardsAction.Wallet.InterruptDialog {
|
||||
store.dispatch(TwinCardsAction.CardsManager.Release)
|
||||
store.dispatch(NavigationAction.PopBackTo(AppScreen.Home))
|
||||
}
|
||||
store.dispatchDialogShow(stateDialog)
|
||||
} else {
|
||||
store.dispatch(TwinCardsAction.CardsManager.Release)
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.Create -> {
|
||||
val wallet = store.state.walletState.walletManagers.map { it.wallet }.firstOrNull()
|
||||
if (wallet == null) {
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.CreateTwinWalletWarning))
|
||||
return
|
||||
}
|
||||
val notEmpty = wallet.recentTransactions.isNotEmpty() || wallet.amounts.toSendableAmounts().isNotEmpty()
|
||||
if (notEmpty) {
|
||||
store.dispatchNotification(twinCardsState.resources.strings.walletIsNotEmpty)
|
||||
} else {
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.CreateTwinWalletWarning))
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchFirstStep -> {
|
||||
val scanResponse = store.state.globalState.scanResponse ?: return
|
||||
|
||||
val manager = TwinCardsManager(scanResponse, action.reader)
|
||||
store.dispatch(TwinCardsAction.CardsManager.Set(manager))
|
||||
|
||||
scope.launch {
|
||||
val result = manager.createFirstWallet(action.initialMessage)
|
||||
withContext(Dispatchers.Main) {
|
||||
when (result) {
|
||||
SimpleResult.Success -> {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchFirstStep.Success)
|
||||
}
|
||||
is SimpleResult.Failure -> {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchSecondStep -> {
|
||||
val manager = twinCardsState.twinCardsManager ?: return
|
||||
|
||||
scope.launch {
|
||||
val result = manager.createSecondWallet(action.initialMessage,
|
||||
action.preparingMessage, action.creatingWalletMessage)
|
||||
withContext(Dispatchers.Main) {
|
||||
when (result) {
|
||||
SimpleResult.Success -> {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchSecondStep.Success)
|
||||
}
|
||||
is SimpleResult.Failure -> {
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchThirdStep -> {
|
||||
val manager = twinCardsState.twinCardsManager ?: return
|
||||
|
||||
scope.launch {
|
||||
val result = manager.complete(action.message)
|
||||
withContext(Dispatchers.Main) {
|
||||
when (result) {
|
||||
is Result.Success -> {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchThirdStep.Success(result.data))
|
||||
}
|
||||
is Result.Failure -> {
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
is TwinCardsAction.Wallet.LaunchThirdStep.Success -> {
|
||||
scope.launch {
|
||||
store.state.globalState.tapWalletManager.onCardScanned(action.scanResponse)
|
||||
}
|
||||
store.dispatch(NavigationAction.PopBackTo(AppScreen.Home))
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.Wallet))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1,60 +0,0 @@
|
|||
package com.tangem.tap.features.twins.redux
|
||||
|
||||
import com.tangem.tap.common.redux.AppState
|
||||
import org.rekotlin.Action
|
||||
|
||||
class TwinCardsReducer {
|
||||
companion object {
|
||||
fun reduce(action: Action, state: AppState): TwinCardsState = internalReduce(action, state)
|
||||
}
|
||||
}
|
||||
|
||||
private fun internalReduce(action: Action, state: AppState): TwinCardsState {
|
||||
if (action !is TwinCardsAction) return state.twinCardsState
|
||||
|
||||
val state = state.twinCardsState
|
||||
return when (action) {
|
||||
is TwinCardsAction.SetResources -> {
|
||||
state.copy(resources = action.resources)
|
||||
}
|
||||
is TwinCardsAction.SetTwinCard -> {
|
||||
state.copy(
|
||||
cardNumber = action.number,
|
||||
secondCardId = action.secondCardId,
|
||||
showTwinOnboarding = state.showTwinOnboarding,
|
||||
isCreatingTwinCardsAllowed = action.isCreatingTwinCardsAllowed,
|
||||
)
|
||||
}
|
||||
is TwinCardsAction.CardsManager.Set -> {
|
||||
state.copy(twinCardsManager = action.manager)
|
||||
}
|
||||
TwinCardsAction.CardsManager.Release -> {
|
||||
state.copy(twinCardsManager = null)
|
||||
}
|
||||
is TwinCardsAction.ShowOnboarding -> {
|
||||
state.copy(showTwinOnboarding = true)
|
||||
}
|
||||
is TwinCardsAction.SetOnboardingShown -> {
|
||||
state.copy(showTwinOnboarding = false)
|
||||
}
|
||||
is TwinCardsAction.Wallet.Create -> {
|
||||
val prevState = state.createWalletState
|
||||
state.copy(createWalletState = CreateTwinWalletState(
|
||||
prevState?.scanResponse,
|
||||
prevState?.number ?: action.number,
|
||||
prevState?.mode ?: action.createTwinWalletMode,
|
||||
))
|
||||
}
|
||||
TwinCardsAction.Wallet.LaunchFirstStep.Success -> {
|
||||
state.copy(createWalletState = state.createWalletState?.copy(
|
||||
step = CreateTwinWalletStep.SecondStep
|
||||
))
|
||||
}
|
||||
TwinCardsAction.Wallet.LaunchSecondStep.Success ->
|
||||
state.copy(createWalletState = state.createWalletState?.copy(
|
||||
step = CreateTwinWalletStep.ThirdStep
|
||||
))
|
||||
else -> state
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -1,43 +0,0 @@
|
|||
package com.tangem.tap.features.twins.redux
|
||||
|
||||
import com.tangem.tap.domain.tasks.product.ScanResponse
|
||||
import com.tangem.tap.domain.twins.TwinCardNumber
|
||||
import com.tangem.tap.domain.twins.TwinCardsManager
|
||||
import org.rekotlin.StateType
|
||||
|
||||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
data class TwinCardsState(
|
||||
val twinCardsManager: TwinCardsManager? = null,
|
||||
// if cardNumber is not set -> the scanned card is not Twin
|
||||
val cardNumber: TwinCardNumber? = null,
|
||||
val secondCardId: String? = null,
|
||||
val showTwinOnboarding: Boolean = false,
|
||||
val isCreatingTwinCardsAllowed: Boolean = false,
|
||||
val createWalletState: CreateTwinWalletState? = null,
|
||||
val resources: TwinCardsResources = TwinCardsResources(),
|
||||
) : StateType
|
||||
|
||||
data class CreateTwinWalletState(
|
||||
val scanResponse: ScanResponse?,
|
||||
val number: TwinCardNumber = TwinCardNumber.First,
|
||||
val mode: CreateTwinWalletMode = CreateTwinWalletMode.CreateWallet,
|
||||
val step: CreateTwinWalletStep = CreateTwinWalletStep.FirstStep,
|
||||
) {
|
||||
val showAlert: Boolean
|
||||
get() = step != CreateTwinWalletStep.FirstStep
|
||||
}
|
||||
|
||||
enum class CreateTwinWalletStep { FirstStep, SecondStep, ThirdStep }
|
||||
|
||||
enum class CreateTwinWalletMode { CreateWallet, RecreateWallet }
|
||||
|
||||
data class TwinCardsResources(
|
||||
val strings: Strings = Strings()
|
||||
) {
|
||||
//TODO: create global structure for StringRes. Set it from the MainActivity.
|
||||
data class Strings(
|
||||
val walletIsNotEmpty: Int = -1
|
||||
)
|
||||
}
|
||||
|
|
@ -1,162 +0,0 @@
|
|||
package com.tangem.tap.features.twins.ui
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.core.content.ContextCompat.getColor
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.transition.TransitionInflater
|
||||
import com.squareup.picasso.Picasso
|
||||
import com.tangem.Message
|
||||
import com.tangem.tap.common.extensions.readAssetAsString
|
||||
import com.tangem.tap.domain.twins.AssetReader
|
||||
import com.tangem.tap.domain.twins.TwinCardNumber
|
||||
import com.tangem.tap.features.twins.redux.*
|
||||
import com.tangem.tap.features.wallet.redux.Artwork
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_twin_cards_create.*
|
||||
import org.rekotlin.StoreSubscriber
|
||||
|
||||
class CreateTwinWalletFragment : Fragment(R.layout.fragment_twin_cards_create),
|
||||
StoreSubscriber<TwinCardsState> {
|
||||
|
||||
private val assetReader: AssetReader by lazy {
|
||||
object : AssetReader {
|
||||
override fun readAssetAsString(name: String): String = requireContext().readAssetAsString(name)
|
||||
}
|
||||
}
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
activity?.onBackPressedDispatcher?.addCallback(this, object : OnBackPressedCallback(true) {
|
||||
override fun handleOnBackPressed() {
|
||||
store.dispatch(TwinCardsAction.Wallet.HandleOnBackPressed)
|
||||
}
|
||||
})
|
||||
|
||||
initResources()
|
||||
val inflater = TransitionInflater.from(requireContext())
|
||||
enterTransition = inflater.inflateTransition(R.transition.slide_right)
|
||||
exitTransition = inflater.inflateTransition(R.transition.fade)
|
||||
}
|
||||
|
||||
private fun initResources() {
|
||||
val resources = TwinCardsResources(
|
||||
TwinCardsResources.Strings(
|
||||
R.string.details_notification_erase_wallet_not_possible
|
||||
)
|
||||
)
|
||||
store.dispatch(TwinCardsAction.SetResources(resources))
|
||||
}
|
||||
|
||||
override fun onStart() {
|
||||
super.onStart()
|
||||
store.subscribe(this) { state ->
|
||||
state.skipRepeats { oldState, newState ->
|
||||
oldState.twinCardsState == newState.twinCardsState
|
||||
}.select { it.twinCardsState }
|
||||
}
|
||||
}
|
||||
|
||||
override fun onStop() {
|
||||
super.onStop()
|
||||
store.unsubscribe(this)
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
|
||||
toolbar.setNavigationOnClickListener { store.dispatch(TwinCardsAction.Wallet.HandleOnBackPressed) }
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_1)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
?.into(iv_card_1)
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_2)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
?.into(iv_card_2)
|
||||
}
|
||||
|
||||
|
||||
override fun newState(state: TwinCardsState) {
|
||||
if (activity == null) return
|
||||
|
||||
toolbar.title = when (state.createWalletState?.mode) {
|
||||
CreateTwinWalletMode.CreateWallet -> getText(R.string.wallet_button_create_wallet)
|
||||
CreateTwinWalletMode.RecreateWallet, null -> getText(R.string.details_twins_recreate_toolbar)
|
||||
|
||||
}
|
||||
|
||||
val selectedColor = getColor(requireContext(), R.color.colorSecondary)
|
||||
val defaultColor = getColor(requireContext(), R.color.blue_pale)
|
||||
|
||||
val twinCardNumber = state.createWalletState?.number ?: TwinCardNumber.First
|
||||
|
||||
val cardNumber = when (state.createWalletState?.step) {
|
||||
CreateTwinWalletStep.FirstStep -> {
|
||||
val twinCardNumberString = twinCardNumber.number.toString()
|
||||
tv_step_number.text =
|
||||
getString(R.string.details_twins_recreate_step_format, "1")
|
||||
v_step_1.setBackgroundColor(selectedColor)
|
||||
v_step_2.setBackgroundColor(defaultColor)
|
||||
v_step_3.setBackgroundColor(defaultColor)
|
||||
btn_tap.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchFirstStep(
|
||||
Message(getString(
|
||||
R.string.details_twins_recreate_title_format,
|
||||
twinCardNumberString
|
||||
)),
|
||||
assetReader
|
||||
))
|
||||
}
|
||||
btn_tap.text = getString(R.string.details_twins_recreate_button_format,
|
||||
twinCardNumber.number.toString())
|
||||
twinCardNumberString
|
||||
}
|
||||
CreateTwinWalletStep.SecondStep -> {
|
||||
val twinCardNumberString = twinCardNumber.pairNumber().number.toString()
|
||||
|
||||
tv_step_number.text =
|
||||
getString(R.string.details_twins_recreate_step_format, "2")
|
||||
v_step_1.setBackgroundColor(selectedColor)
|
||||
v_step_2.setBackgroundColor(selectedColor)
|
||||
v_step_3.setBackgroundColor(defaultColor)
|
||||
btn_tap.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchSecondStep(
|
||||
Message(getString(R.string.details_twins_recreate_title_format, twinCardNumberString)),
|
||||
Message(getString(R.string.details_twins_recreate_title_preparing)),
|
||||
Message(getString(R.string.details_twins_recreate_title_creating_wallet)),
|
||||
))
|
||||
}
|
||||
btn_tap.text = getString(R.string.details_twins_recreate_button_format, "2")
|
||||
twinCardNumberString
|
||||
}
|
||||
CreateTwinWalletStep.ThirdStep -> {
|
||||
val twinCardNumberString = twinCardNumber.number.toString()
|
||||
|
||||
tv_step_number.text =
|
||||
getString(R.string.details_twins_recreate_step_format, "3")
|
||||
v_step_1.setBackgroundColor(selectedColor)
|
||||
v_step_2.setBackgroundColor(selectedColor)
|
||||
v_step_3.setBackgroundColor(selectedColor)
|
||||
btn_tap.setOnClickListener {
|
||||
store.dispatch(TwinCardsAction.Wallet.LaunchThirdStep(
|
||||
Message(getString(
|
||||
R.string.details_twins_recreate_title_format, twinCardNumberString)
|
||||
)
|
||||
))
|
||||
}
|
||||
btn_tap.text = getString(R.string.details_twins_recreate_button_format, twinCardNumberString)
|
||||
twinCardNumberString
|
||||
}
|
||||
else -> null
|
||||
}
|
||||
btn_tap.text = getString(R.string.details_twins_recreate_button_format, cardNumber)
|
||||
tv_twin_title.text = getString(R.string.details_twins_recreate_title_format, cardNumber)
|
||||
}
|
||||
}
|
||||
|
|
@ -1,57 +0,0 @@
|
|||
package com.tangem.tap.features.twins.ui
|
||||
|
||||
import android.os.Bundle
|
||||
import android.view.View
|
||||
import androidx.activity.OnBackPressedCallback
|
||||
import androidx.fragment.app.Fragment
|
||||
import androidx.transition.TransitionInflater
|
||||
import com.squareup.picasso.Picasso
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.features.twins.redux.CreateTwinWalletMode
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.wallet.redux.Artwork
|
||||
import com.tangem.tap.store
|
||||
import com.tangem.wallet.R
|
||||
import kotlinx.android.synthetic.main.fragment_twin_cards_warning.*
|
||||
import kotlinx.android.synthetic.main.layout_twin_cards_orange.*
|
||||
|
||||
class TwinWalletWarningFragment : Fragment(R.layout.fragment_twin_cards_warning) {
|
||||
|
||||
override fun onCreate(savedInstanceState: Bundle?) {
|
||||
super.onCreate(savedInstanceState)
|
||||
activity?.onBackPressedDispatcher?.addCallback(this, object : OnBackPressedCallback(true) {
|
||||
override fun handleOnBackPressed() {
|
||||
store.dispatch(NavigationAction.PopBackTo())
|
||||
}
|
||||
})
|
||||
val inflater = TransitionInflater.from(requireContext())
|
||||
enterTransition = inflater.inflateTransition(R.transition.slide_right)
|
||||
exitTransition = inflater.inflateTransition(R.transition.fade)
|
||||
}
|
||||
|
||||
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
|
||||
super.onViewCreated(view, savedInstanceState)
|
||||
val createTwinWallet = store.state.twinCardsState.createWalletState?.mode
|
||||
if (createTwinWallet == CreateTwinWalletMode.CreateWallet) {
|
||||
tv_twin_cards_description.text = getText(R.string.details_twins_recreate_subtitle)
|
||||
} else if (createTwinWallet == CreateTwinWalletMode.RecreateWallet) {
|
||||
tv_twin_cards_description.text = getText(R.string.details_twins_recreate_warning)
|
||||
}
|
||||
|
||||
btn_cancel.setOnClickListener { store.dispatch(NavigationAction.PopBackTo()) }
|
||||
btn_start.setOnClickListener { store.dispatch(TwinCardsAction.ProceedToCreateWallet) }
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_1)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
?.into(iv_twin_card_1)
|
||||
|
||||
Picasso.get()
|
||||
.load(Artwork.TWIN_CARD_2)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
?.into(iv_twin_card_2)
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
|
@ -5,12 +5,13 @@ import com.tangem.blockchain.common.TransactionData
|
|||
import com.tangem.blockchain.common.TransactionStatus
|
||||
import com.tangem.blockchain.common.Wallet
|
||||
import com.tangem.tap.common.extensions.toFormattedString
|
||||
import com.tangem.tap.domain.extensions.toSendableAmounts
|
||||
|
||||
data class PendingTransaction(
|
||||
val address: String?,
|
||||
val amount: String?,
|
||||
val currency: String,
|
||||
val type: PendingTransactionType
|
||||
val address: String?,
|
||||
val amount: String?,
|
||||
val currency: String,
|
||||
val type: PendingTransactionType
|
||||
)
|
||||
|
||||
enum class PendingTransactionType { Incoming, Outgoing, Unknown }
|
||||
|
|
@ -36,10 +37,10 @@ fun TransactionData.toPendingTransaction(walletAddress: String): PendingTransact
|
|||
}
|
||||
|
||||
return PendingTransaction(
|
||||
if (address == "unknown") null else address,
|
||||
this.amount.value?.toFormattedString(amount.decimals),
|
||||
this.amount.currencySymbol,
|
||||
type
|
||||
if (address == "unknown") null else address,
|
||||
this.amount.value?.toFormattedString(amount.decimals),
|
||||
this.amount.currencySymbol,
|
||||
type
|
||||
)
|
||||
}
|
||||
|
||||
|
|
@ -66,4 +67,8 @@ fun Wallet.getPendingTransactions(): List<PendingTransaction> {
|
|||
|
||||
fun Wallet.hasPendingTransactions(): Boolean {
|
||||
return getPendingTransactions().isNotEmpty()
|
||||
}
|
||||
|
||||
fun Wallet.hasSendableAmountsOrPendingTransactions(): Boolean {
|
||||
return hasPendingTransactions() || amounts.toSendableAmounts().isNotEmpty()
|
||||
}
|
||||
|
|
@ -12,7 +12,7 @@ import com.tangem.tap.common.toggleWidget.WidgetState
|
|||
import com.tangem.tap.domain.configurable.warningMessage.WarningMessage
|
||||
import com.tangem.tap.domain.extensions.toSendableAmounts
|
||||
import com.tangem.tap.domain.topup.TradeCryptoHelper
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.wallet.models.PendingTransaction
|
||||
import com.tangem.tap.features.wallet.models.toPendingTransactions
|
||||
import com.tangem.tap.features.wallet.models.toPendingTransactionsForToken
|
||||
|
|
|
|||
|
|
@ -19,8 +19,6 @@ import com.tangem.tap.common.redux.navigation.NavigationAction
|
|||
import com.tangem.tap.domain.extensions.toSendableAmounts
|
||||
import com.tangem.tap.features.home.redux.HomeAction
|
||||
import com.tangem.tap.features.send.redux.PrepareSendScreen
|
||||
import com.tangem.tap.features.twins.redux.CreateTwinWalletMode
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsAction
|
||||
import com.tangem.tap.features.wallet.redux.*
|
||||
import com.tangem.tap.network.NetworkStateChanged
|
||||
import kotlinx.coroutines.launch
|
||||
|
|
@ -96,31 +94,22 @@ class WalletMiddleware {
|
|||
}
|
||||
}
|
||||
is WalletAction.CreateWallet -> {
|
||||
if (walletState.isTangemTwins) {
|
||||
store.dispatch(TwinCardsAction.Wallet.Create(
|
||||
walletState.twinCardsState.cardNumber!!,
|
||||
CreateTwinWalletMode.CreateWallet
|
||||
))
|
||||
} else {
|
||||
scope.launch {
|
||||
val result = tangemSdkManager.createWallet(
|
||||
globalState.scanResponse?.card?.cardId
|
||||
)
|
||||
when (result) {
|
||||
is CompletionResult.Success -> {
|
||||
val scanNoteResponse = globalState.scanResponse?.copy(card = result.data)
|
||||
scanNoteResponse?.let {
|
||||
globalState.tapWalletManager.onCardScanned(scanNoteResponse)
|
||||
}
|
||||
}
|
||||
is CompletionResult.Failure -> {
|
||||
(result.error as? TangemSdkError)?.let { error ->
|
||||
FirebaseAnalyticsHandler.logCardSdkError(
|
||||
error,
|
||||
FirebaseAnalyticsHandler.ActionToLog.CreateWallet,
|
||||
card = store.state.detailsState.card
|
||||
)
|
||||
}
|
||||
scope.launch {
|
||||
val result = tangemSdkManager.createWallet(
|
||||
globalState.scanResponse?.card?.cardId
|
||||
)
|
||||
when (result) {
|
||||
is CompletionResult.Success -> {
|
||||
val scanNoteResponse = globalState.scanResponse?.copy(card = result.data)
|
||||
scanNoteResponse?.let { store.onCardScanned(scanNoteResponse) }
|
||||
}
|
||||
is CompletionResult.Failure -> {
|
||||
(result.error as? TangemSdkError)?.let { error ->
|
||||
FirebaseAnalyticsHandler.logCardSdkError(
|
||||
error,
|
||||
FirebaseAnalyticsHandler.ActionToLog.CreateWallet,
|
||||
card = store.state.detailsState.card
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -38,13 +38,12 @@ private fun internalReduce(action: Action, state: AppState): WalletState {
|
|||
is WalletAction.ResetState -> newState = WalletState()
|
||||
is WalletAction.SetIfTestnetCard -> newState = newState.copy(isTestnet = action.isTestnet)
|
||||
is WalletAction.EmptyWallet -> {
|
||||
val creatingWalletAllowed = state.twinCardsState.isCreatingTwinCardsAllowed
|
||||
newState = newState.copy(
|
||||
state = ProgressState.Done,
|
||||
wallets = listOf(
|
||||
WalletData(
|
||||
currencyData = BalanceWidgetData(BalanceStatus.EmptyCard),
|
||||
mainButton = WalletMainButton.CreateWalletButton(creatingWalletAllowed),
|
||||
mainButton = WalletMainButton.CreateWalletButton(true),
|
||||
)
|
||||
)
|
||||
)
|
||||
|
|
|
|||
|
|
@ -150,8 +150,8 @@ class WalletFragment : Fragment(R.layout.fragment_wallet), StoreSubscriber<Walle
|
|||
private fun setupCardImage(cardImage: Artwork?) {
|
||||
Picasso.get()
|
||||
.load(cardImage?.artworkId)
|
||||
.placeholder(R.drawable.card_placeholder)
|
||||
?.error(R.drawable.card_placeholder)
|
||||
.placeholder(R.drawable.card_placeholder_black)
|
||||
?.error(R.drawable.card_placeholder_black)
|
||||
?.into(iv_card)
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -7,10 +7,8 @@ import android.widget.Button
|
|||
import androidx.recyclerview.widget.LinearLayoutManager
|
||||
import com.tangem.tap.common.extensions.*
|
||||
import com.tangem.tap.common.redux.StateDialog
|
||||
import com.tangem.tap.common.redux.navigation.AppScreen
|
||||
import com.tangem.tap.common.redux.navigation.NavigationAction
|
||||
import com.tangem.tap.domain.twins.TwinCardNumber
|
||||
import com.tangem.tap.features.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.onboarding.products.twins.redux.TwinCardsState
|
||||
import com.tangem.tap.features.wallet.models.PendingTransaction
|
||||
import com.tangem.tap.features.wallet.redux.*
|
||||
import com.tangem.tap.features.wallet.ui.BalanceWidget
|
||||
|
|
@ -93,7 +91,7 @@ class SingleWalletView : WalletView {
|
|||
}
|
||||
|
||||
private fun setupTwinCards(
|
||||
twinCardsState: TwinCardsState?, fragment: WalletFragment
|
||||
twinCardsState: TwinCardsState?, fragment: WalletFragment
|
||||
) = with(fragment) {
|
||||
twinCardsState?.cardNumber?.let { cardNumber ->
|
||||
tv_twin_card_number.show()
|
||||
|
|
@ -107,11 +105,6 @@ class SingleWalletView : WalletView {
|
|||
if (twinCardsState?.cardNumber == null) {
|
||||
tv_twin_card_number.hide()
|
||||
}
|
||||
if (twinCardsState?.showTwinOnboarding == true) {
|
||||
store.dispatch(NavigationAction.NavigateTo(AppScreen.OnboardingTwins))
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
private fun setupButtons(
|
||||
|
|
|
|||
|
|
@ -1,22 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<item>
|
||||
<shape android:shape="rectangle">
|
||||
|
||||
<corners android:radius="12dp" />
|
||||
<size
|
||||
android:width="328dp"
|
||||
android:height="174dp" />
|
||||
<gradient
|
||||
android:endColor="#FFFFFF"
|
||||
android:startColor="#FFFFFF" />
|
||||
</shape>
|
||||
</item>
|
||||
<item
|
||||
android:drawable="@drawable/ic_tangem_pale"
|
||||
android:gravity="center">
|
||||
<size
|
||||
android:width="85dp"
|
||||
android:height="23dp" />
|
||||
</item>
|
||||
</layer-list>
|
||||
126
app/src/main/res/drawable/card_placeholder_black.xml
Normal file
126
app/src/main/res/drawable/card_placeholder_black.xml
Normal file
|
|
@ -0,0 +1,126 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:aapt="http://schemas.android.com/aapt"
|
||||
android:width="249dp"
|
||||
android:height="150dp"
|
||||
android:viewportWidth="249"
|
||||
android:viewportHeight="150">
|
||||
<path
|
||||
android:fillAlpha="0.03"
|
||||
android:pathData="M10,0L238,0A9.999,10.001 134.998,0 1,248.001 10L248.017,140A9.999,10.001 134.998,0 1,238.019 150L10.019,150A9.999,10.001 134.998,0 1,0.017 140L0.001,10A9.999,10.001 134.998,0 1,10 0z" />
|
||||
<path
|
||||
android:fillAlpha="0.5"
|
||||
android:pathData="M10,0L238,0A9.999,10.001 134.998,0 1,248.001 10L248.017,140A9.999,10.001 134.998,0 1,238.019 150L10.019,150A9.999,10.001 134.998,0 1,0.017 140L0.001,10A9.999,10.001 134.998,0 1,10 0z">
|
||||
<aapt:attr name="android:fillColor">
|
||||
<gradient
|
||||
android:centerX="7.404067"
|
||||
android:centerY="8.65384"
|
||||
android:gradientRadius="267.36932"
|
||||
android:type="radial">
|
||||
<item
|
||||
android:color="#FFFFFFFF"
|
||||
android:offset="0" />
|
||||
<item
|
||||
android:color="#19FFFFFF"
|
||||
android:offset="1" />
|
||||
</gradient>
|
||||
</aapt:attr>
|
||||
</path>
|
||||
<path
|
||||
android:fillColor="#1B1D1C"
|
||||
android:pathData="M10,0L238,0A9.999,10.001 134.998,0 1,248.001 10L248.017,140A9.999,10.001 134.998,0 1,238.019 150L10.019,150A9.999,10.001 134.998,0 1,0.017 140L0.001,10A9.999,10.001 134.998,0 1,10 0z" />
|
||||
<path
|
||||
android:fillColor="#00000000"
|
||||
android:pathData="M10,0.5L238,0.5A9.499,9.501 134.998,0 1,247.501 10L247.517,140A9.499,9.501 134.998,0 1,238.019 149.5L10.019,149.5A9.499,9.501 134.998,0 1,0.517 140L0.501,10A9.499,9.501 134.998,0 1,10 0.5z"
|
||||
android:strokeWidth="1">
|
||||
<aapt:attr name="android:strokeColor">
|
||||
<gradient
|
||||
android:endX="246.96196"
|
||||
android:endY="144.774"
|
||||
android:startX="2.844399"
|
||||
android:startY="3.38345"
|
||||
android:type="linear">
|
||||
<item
|
||||
android:color="#FF1A1A1A"
|
||||
android:offset="0" />
|
||||
<item
|
||||
android:color="#FF565656"
|
||||
android:offset="1" />
|
||||
</gradient>
|
||||
</aapt:attr>
|
||||
</path>
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M28.359,121.942L26.389,120.734L26.472,123H25.41L25.498,120.734L23.505,121.95L23.002,121.003L25.044,119.992L23.009,118.974L23.511,118.058L25.497,119.25L25.415,117H26.468L26.389,119.258L28.365,118.058L28.884,118.974L26.826,120L28.885,121.011L28.359,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M38.855,121.942L36.885,120.734L36.967,123H35.906L35.994,120.734L34.001,121.95L33.498,121.003L35.54,119.992L33.505,118.974L34.007,118.058L35.993,119.25L35.911,117H36.964L36.884,119.258L38.861,118.058L39.38,118.974L37.322,120L39.381,121.011L38.855,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M49.351,121.942L47.381,120.734L47.463,123H46.402L46.49,120.734L44.497,121.95L43.994,121.003L46.035,119.992L44.001,118.974L44.503,118.058L46.489,119.25L46.407,117H47.46L47.38,119.258L49.357,118.058L49.876,118.974L47.818,120L49.877,121.011L49.351,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M59.847,121.942L57.877,120.734L57.959,123H56.897L56.985,120.734L54.993,121.95L54.49,121.003L56.531,119.992L54.497,118.974L54.999,118.058L56.985,119.25L56.902,117H57.956L57.876,119.258L59.853,118.058L60.372,118.974L58.314,120L60.373,121.011L59.847,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M76.235,121.942L74.266,120.734L74.348,123H73.286L73.374,120.734L71.381,121.95L70.879,121.003L72.92,119.992L70.885,118.974L71.387,118.058L73.373,119.25L73.291,117H74.345L74.265,119.258L76.242,118.058L76.761,118.974L74.703,120L76.762,121.011L76.235,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M86.731,121.942L84.761,120.734L84.844,123H83.782L83.87,120.734L81.877,121.95L81.374,121.003L83.416,119.992L81.381,118.974L81.883,118.058L83.869,119.25L83.787,117H84.841L84.761,119.258L86.737,118.058L87.257,118.974L85.199,120L87.258,121.011L86.731,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M97.227,121.942L95.257,120.734L95.34,123H94.278L94.366,120.734L92.373,121.95L91.87,121.003L93.912,119.992L91.877,118.974L92.379,118.058L94.365,119.25L94.283,117H95.337L95.257,119.258L97.233,118.058L97.752,118.974L95.695,120L97.753,121.011L97.227,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M107.723,121.942L105.753,120.734L105.835,123H104.774L104.862,120.734L102.869,121.95L102.366,121.003L104.408,119.992L102.373,118.974L102.875,118.058L104.861,119.25L104.779,117H105.832L105.752,119.258L107.729,118.058L108.248,118.974L106.19,120L108.249,121.011L107.723,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M124.112,121.942L122.142,120.734L122.224,123H121.163L121.251,120.734L119.258,121.95L118.755,121.003L120.796,119.992L118.762,118.974L119.264,118.058L121.25,119.25L121.168,117H122.221L122.141,119.258L124.118,118.058L124.637,118.974L122.579,120L124.638,121.011L124.112,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M134.608,121.942L132.638,120.734L132.72,123H131.659L131.746,120.734L129.754,121.95L129.251,121.003L131.292,119.992L129.258,118.974L129.76,118.058L131.746,119.25L131.664,117H132.717L132.637,119.258L134.614,118.058L135.133,118.974L133.075,120L135.134,121.011L134.608,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M145.104,121.942L143.134,120.734L143.216,123H142.154L142.242,120.734L140.249,121.95L139.747,121.003L141.788,119.992L139.754,118.974L140.256,118.058L142.242,119.25L142.159,117H143.213L143.133,119.258L145.11,118.058L145.629,118.974L143.571,120L145.63,121.011L145.104,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M155.599,121.942L153.63,120.734L153.712,123H152.65L152.738,120.734L150.745,121.95L150.242,121.003L152.284,119.992L150.249,118.974L150.751,118.058L152.737,119.25L152.655,117H153.709L153.629,119.258L155.606,118.058L156.125,118.974L154.067,120L156.126,121.011L155.599,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M171.988,121.942L170.018,120.734L170.101,123H169.039L169.127,120.734L167.134,121.95L166.631,121.003L168.673,119.992L166.638,118.974L167.14,118.058L169.126,119.25L169.044,117H170.098L170.018,119.258L171.994,118.058L172.513,118.974L170.456,120L172.515,121.011L171.988,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M182.484,121.942L180.514,120.734L180.597,123H179.535L179.623,120.734L177.63,121.95L177.127,121.003L179.169,119.992L177.134,118.974L177.636,118.058L179.622,119.25L179.54,117H180.593L180.514,119.258L182.49,118.058L183.009,118.974L180.952,120L183.01,121.011L182.484,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M192.98,121.942L191.01,120.734L191.092,123H190.031L190.119,120.734L188.126,121.95L187.623,121.003L189.665,119.992L187.63,118.974L188.132,118.058L190.118,119.25L190.036,117H191.089L191.009,119.258L192.986,118.058L193.505,118.974L191.447,120L193.506,121.011L192.98,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#A5A5A5"
|
||||
android:pathData="M203.476,121.942L201.506,120.734L201.588,123H200.527L200.615,120.734L198.622,121.95L198.119,121.003L200.16,119.992L198.126,118.974L198.628,118.058L200.614,119.25L200.532,117H201.585L201.505,119.258L203.482,118.058L204.001,118.974L201.943,120L204.002,121.011L203.476,121.942Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M26.483,30.4L26.483,36.64L29.382,36.64C29.494,36.639 29.602,36.596 29.681,36.522C29.761,36.447 29.806,36.346 29.807,36.241L29.807,30.4L26.483,30.4Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M20,36.241C20.001,36.346 20.046,36.447 20.126,36.522C20.205,36.596 20.313,36.639 20.425,36.64L23.324,36.64L23.324,30.4L20,30.4L20,36.241Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M29.807,27.2L29.807,24.409C29.807,24.301 29.763,24.197 29.685,24.12C29.606,24.043 29.5,24 29.389,24L20.418,24C20.307,24 20.201,24.043 20.123,24.12C20.044,24.197 20,24.301 20,24.409L20,27.2L29.807,27.2Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M45.32,28.163C44.719,27.921 44.068,27.812 43.416,27.846C42.555,27.844 41.696,27.934 40.856,28.113L40.856,29.532C41.526,29.455 42.199,29.412 42.874,29.4C43.236,29.385 43.598,29.418 43.949,29.5C44.062,29.532 44.164,29.59 44.247,29.669C44.33,29.748 44.392,29.846 44.425,29.953C44.531,30.334 44.576,30.728 44.558,31.122L44.558,31.539C43.764,31.498 43.131,31.476 42.698,31.476C42.236,31.454 41.775,31.539 41.356,31.725C41.025,31.903 40.779,32.195 40.666,32.54C40.509,33.044 40.438,33.569 40.456,34.095C40.398,34.771 40.564,35.448 40.932,36.029C41.127,36.243 41.372,36.409 41.648,36.513C41.924,36.618 42.222,36.659 42.517,36.632C42.864,36.632 43.945,36.605 44.421,36.007C44.499,35.912 44.566,35.808 44.62,35.699L44.673,36.496L46.424,36.496L46.424,31.222C46.45,30.539 46.371,29.857 46.191,29.196C46.127,28.977 46.017,28.772 45.867,28.594C45.717,28.417 45.531,28.27 45.32,28.163ZM44.54,33.256C44.589,33.736 44.503,34.219 44.292,34.656C44.189,34.783 44.048,34.876 43.887,34.924C43.706,34.972 43.519,34.995 43.331,34.992C43.037,35.028 42.74,34.953 42.503,34.783C42.343,34.523 42.277,34.221 42.312,33.922C42.302,33.681 42.327,33.44 42.388,33.206C42.407,33.139 42.44,33.076 42.486,33.021C42.532,32.966 42.59,32.921 42.655,32.889C42.834,32.821 43.028,32.791 43.221,32.803L44.54,32.803L44.54,33.256Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M60.474,28.645C60.438,28.584 60.398,28.526 60.354,28.471C59.777,27.736 58.401,27.846 58.401,27.846C57.946,27.832 57.499,27.964 57.126,28.222C56.75,28.573 56.507,29.042 56.438,29.55C56.168,31.328 56.168,33.136 56.438,34.915C56.504,35.417 56.74,35.882 57.108,36.233C57.509,36.52 58,36.659 58.493,36.623C58.493,36.623 58.521,36.623 58.539,36.623C58.539,36.623 59.782,36.72 60.386,36.104C60.398,36.607 60.364,37.11 60.285,37.606C60.264,37.738 60.212,37.864 60.131,37.971C60.051,38.078 59.945,38.164 59.823,38.222C59.439,38.351 59.033,38.406 58.627,38.382L56.72,38.35L56.72,39.788C57.071,39.853 57.426,39.9 57.782,39.93C58.221,39.972 58.636,39.99 59.034,39.99C59.773,40.044 60.512,39.884 61.162,39.53C61.39,39.374 61.583,39.174 61.732,38.943C61.88,38.71 61.98,38.451 62.026,38.18C62.174,37.297 62.237,36.402 62.215,35.507L62.215,27.979L60.516,27.979L60.474,28.645ZM60.262,34.221C60.233,34.452 60.118,34.664 59.938,34.813C59.729,34.939 59.486,34.999 59.241,34.984C58.968,35.006 58.694,34.95 58.452,34.823C58.263,34.636 58.153,34.384 58.147,34.12C58.042,32.876 58.042,31.625 58.147,30.381C58.153,30.125 58.259,29.882 58.442,29.701C58.69,29.579 58.966,29.526 59.241,29.55C59.502,29.529 59.761,29.599 59.975,29.747C60.166,29.947 60.28,30.207 60.299,30.482C60.369,31.072 60.396,31.666 60.382,32.26C60.405,32.916 60.364,33.573 60.262,34.221Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M69.304,28.124C68.702,27.787 68.01,27.636 67.319,27.691C66.601,27.642 65.884,27.802 65.259,28.152C64.804,28.473 64.497,28.959 64.408,29.502C64.259,30.388 64.196,31.286 64.219,32.184C64.195,33.083 64.261,33.983 64.417,34.87C64.465,35.139 64.568,35.395 64.72,35.623C64.872,35.851 65.07,36.046 65.301,36.197C65.961,36.531 66.701,36.681 67.441,36.631C67.913,36.63 68.384,36.603 68.852,36.552C69.241,36.517 69.626,36.453 70.005,36.359L70.005,34.916C69.139,35.004 68.429,35.05 67.874,35.05C67.464,35.074 67.053,35.025 66.66,34.907C66.54,34.857 66.433,34.778 66.351,34.677C66.269,34.577 66.214,34.458 66.19,34.331C66.106,33.822 66.071,33.307 66.087,32.792L70.193,32.792L70.193,32.165C70.215,31.241 70.167,30.317 70.047,29.4C69.98,28.896 69.713,28.438 69.304,28.124ZM68.41,31.428L66.087,31.428C66.086,30.95 66.119,30.473 66.186,30C66.195,29.887 66.228,29.777 66.283,29.678C66.338,29.579 66.414,29.492 66.505,29.424C66.988,29.233 67.527,29.233 68.01,29.424C68.1,29.494 68.173,29.583 68.227,29.682C68.28,29.782 68.312,29.892 68.321,30.004C68.394,30.475 68.424,30.952 68.41,31.428Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M81.818,29.12C81.739,28.745 81.527,28.406 81.218,28.161C80.849,27.928 80.409,27.817 79.966,27.844C79.966,27.844 79.924,27.844 79.895,27.844C79.895,27.844 78.467,27.767 77.877,28.464C77.813,28.542 77.755,28.625 77.705,28.713C77.61,28.478 77.445,28.275 77.229,28.129C76.858,27.924 76.431,27.826 76.001,27.848C76.001,27.848 74.573,27.767 73.983,28.468C73.917,28.545 73.86,28.629 73.812,28.717L73.764,27.984L72.027,27.984L72.027,36.48L73.931,36.48L73.931,32.051C73.921,31.52 73.942,30.988 73.993,30.459C74.005,30.198 74.107,29.949 74.283,29.749C74.493,29.584 74.764,29.506 75.035,29.531C75.276,29.513 75.518,29.557 75.735,29.658C75.815,29.731 75.879,29.819 75.923,29.916C75.967,30.013 75.991,30.118 75.992,30.224C76.042,30.747 76.063,31.272 76.054,31.798L76.054,36.48L77.958,36.48L77.958,32.051C77.958,31.314 77.958,30.785 78.015,30.459C78.028,30.197 78.133,29.946 78.315,29.749C78.53,29.586 78.802,29.508 79.076,29.531C79.319,29.513 79.562,29.557 79.781,29.658C79.86,29.732 79.923,29.82 79.966,29.917C80.01,30.014 80.033,30.118 80.033,30.224C80.086,30.747 80.106,31.272 80.095,31.798L80.095,36.48L81.999,36.48L81.999,30.884C82.009,30.291 81.949,29.699 81.818,29.12Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M53.781,28.171C53.383,27.928 52.913,27.814 52.44,27.845C52.44,27.845 52.402,27.845 52.382,27.845C52.382,27.845 50.936,27.773 50.343,28.465C50.301,28.514 50.262,28.565 50.227,28.619L50.184,27.981L48.424,27.981L48.424,36.48L50.353,36.48L50.353,32.049C50.342,31.521 50.363,30.992 50.415,30.465C50.429,30.203 50.538,29.952 50.724,29.755C50.957,29.584 51.25,29.503 51.543,29.529C51.8,29.511 52.057,29.555 52.291,29.655C52.378,29.728 52.448,29.816 52.497,29.915C52.546,30.014 52.572,30.121 52.575,30.23C52.63,30.75 52.653,31.273 52.643,31.796L52.643,36.48L54.571,36.48L54.571,30.963C54.587,30.356 54.533,29.75 54.412,29.153C54.333,28.765 54.109,28.417 53.781,28.171Z" />
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M38.128,25.44L36.175,25.44L36.175,27.877L34.96,27.877L34.96,29.434L36.175,29.434L36.175,36.48L38.128,36.48L38.128,29.434L39.614,29.434L39.614,27.877L38.128,27.877L38.128,25.44Z" />
|
||||
</vector>
|
||||
108
app/src/main/res/drawable/card_placeholder_white.xml
Normal file
108
app/src/main/res/drawable/card_placeholder_white.xml
Normal file
|
|
@ -0,0 +1,108 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:aapt="http://schemas.android.com/aapt"
|
||||
android:width="214dp"
|
||||
android:height="130dp"
|
||||
android:viewportWidth="214"
|
||||
android:viewportHeight="130">
|
||||
<path
|
||||
android:fillColor="#E4E4E4"
|
||||
android:pathData="M1.043,8.273C1.019,4.256 4.265,1 8.294,1H205.706C209.735,1 213.019,4.256 213.043,8.273L213.709,121.725C213.733,125.742 210.487,128.998 206.459,128.998H9.046C5.018,128.998 1.733,125.742 1.709,121.725L1.043,8.273Z" />
|
||||
<path
|
||||
android:fillColor="#00000000"
|
||||
android:pathData="M1.043,8.273C1.019,4.256 4.265,1 8.294,1H205.706C209.735,1 213.019,4.256 213.043,8.273L213.709,121.725C213.733,125.742 210.487,128.998 206.459,128.998H9.046C5.018,128.998 1.733,125.742 1.709,121.725L1.043,8.273Z"
|
||||
android:strokeWidth="0.5">
|
||||
<aapt:attr name="android:strokeColor">
|
||||
<gradient
|
||||
android:endX="216.304"
|
||||
android:endY="122.149"
|
||||
android:startX="-1.98014"
|
||||
android:startY="-1.3567"
|
||||
android:type="linear">
|
||||
<item
|
||||
android:color="#FFDCDCDC"
|
||||
android:offset="0" />
|
||||
<item
|
||||
android:color="#FFDEDEDE"
|
||||
android:offset="0.9999" />
|
||||
<item
|
||||
android:color="#00000000"
|
||||
android:offset="1" />
|
||||
</gradient>
|
||||
</aapt:attr>
|
||||
</path>
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M25.274,26.4L25.274,32.64L28.079,32.64C28.188,32.639 28.292,32.596 28.369,32.522C28.446,32.447 28.49,32.346 28.491,32.241L28.491,26.4L25.274,26.4Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M19,32.241C19.001,32.346 19.045,32.447 19.122,32.522C19.199,32.596 19.303,32.639 19.412,32.64L22.217,32.64L22.217,26.4L19,26.4L19,32.241Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M28.491,23.2L28.491,20.409C28.491,20.301 28.448,20.197 28.372,20.12C28.296,20.043 28.194,20 28.086,20L19.405,20C19.297,20 19.195,20.043 19.119,20.12C19.043,20.197 19,20.301 19,20.409L19,23.2L28.491,23.2Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M43.503,24.163C42.922,23.921 42.292,23.812 41.661,23.846C40.827,23.844 39.996,23.934 39.183,24.113L39.183,25.532C39.832,25.455 40.483,25.412 41.136,25.4C41.486,25.385 41.836,25.418 42.177,25.5C42.286,25.532 42.385,25.59 42.465,25.669C42.546,25.748 42.605,25.846 42.637,25.953C42.74,26.334 42.783,26.728 42.766,27.122L42.766,27.539C41.997,27.498 41.385,27.476 40.965,27.476C40.519,27.454 40.073,27.539 39.667,27.725C39.347,27.903 39.109,28.195 38.999,28.54C38.847,29.044 38.779,29.569 38.796,30.094C38.74,30.771 38.901,31.448 39.257,32.029C39.445,32.243 39.683,32.409 39.95,32.513C40.216,32.618 40.505,32.659 40.791,32.632C41.127,32.632 42.172,32.605 42.633,32.007C42.709,31.912 42.774,31.808 42.826,31.698L42.877,32.496L44.572,32.496L44.572,27.222C44.596,26.539 44.52,25.857 44.346,25.196C44.284,24.977 44.178,24.772 44.033,24.594C43.888,24.417 43.708,24.27 43.503,24.163ZM42.748,29.256C42.796,29.736 42.713,30.219 42.508,30.656C42.409,30.782 42.272,30.876 42.117,30.924C41.942,30.972 41.76,30.995 41.578,30.992C41.294,31.028 41.006,30.953 40.777,30.783C40.623,30.523 40.558,30.221 40.592,29.922C40.582,29.681 40.607,29.44 40.666,29.206C40.684,29.139 40.716,29.075 40.761,29.021C40.805,28.966 40.861,28.921 40.924,28.889C41.098,28.821 41.285,28.791 41.472,28.803L42.748,28.803L42.748,29.256Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M58.169,24.645C58.133,24.584 58.095,24.526 58.053,24.471C57.494,23.736 56.162,23.846 56.162,23.846C55.722,23.831 55.29,23.964 54.929,24.222C54.564,24.573 54.329,25.042 54.263,25.55C54.001,27.328 54.001,29.136 54.263,30.914C54.326,31.417 54.555,31.882 54.911,32.233C55.299,32.52 55.774,32.659 56.251,32.623C56.251,32.623 56.278,32.623 56.296,32.623C56.296,32.623 57.498,32.72 58.084,32.104C58.095,32.607 58.062,33.11 57.985,33.606C57.966,33.738 57.915,33.864 57.837,33.971C57.759,34.078 57.656,34.164 57.539,34.222C57.166,34.351 56.773,34.406 56.381,34.382L54.535,34.35L54.535,35.788C54.876,35.853 55.219,35.9 55.563,35.93C55.988,35.972 56.39,35.99 56.774,35.99C57.49,36.044 58.205,35.884 58.834,35.53C59.055,35.374 59.242,35.174 59.386,34.943C59.529,34.71 59.626,34.451 59.67,34.18C59.813,33.297 59.875,32.402 59.853,31.507L59.853,23.979L58.209,23.979L58.169,24.645ZM57.963,30.221C57.936,30.452 57.824,30.664 57.65,30.813C57.447,30.94 57.212,30.999 56.975,30.983C56.711,31.006 56.446,30.95 56.211,30.823C56.028,30.636 55.923,30.385 55.916,30.12C55.815,28.876 55.815,27.625 55.916,26.381C55.923,26.125 56.025,25.882 56.202,25.701C56.442,25.579 56.709,25.526 56.975,25.55C57.227,25.529 57.479,25.599 57.686,25.747C57.87,25.947 57.981,26.207 57.999,26.482C58.066,27.072 58.093,27.666 58.079,28.26C58.101,28.916 58.062,29.573 57.963,30.221Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M66.713,24.124C66.131,23.787 65.461,23.636 64.793,23.691C64.098,23.642 63.404,23.802 62.799,24.152C62.358,24.473 62.062,24.959 61.975,25.502C61.831,26.388 61.77,27.286 61.793,28.184C61.769,29.083 61.833,29.983 61.984,30.87C62.031,31.139 62.131,31.395 62.278,31.623C62.425,31.851 62.616,32.046 62.84,32.197C63.478,32.531 64.194,32.681 64.911,32.631C65.367,32.63 65.823,32.603 66.276,32.552C66.653,32.517 67.025,32.453 67.392,32.359L67.392,30.916C66.554,31.004 65.867,31.05 65.33,31.05C64.933,31.074 64.535,31.025 64.155,30.907C64.038,30.857 63.936,30.778 63.856,30.677C63.777,30.577 63.723,30.458 63.7,30.331C63.618,29.823 63.585,29.307 63.6,28.792L67.574,28.792L67.574,28.165C67.596,27.241 67.548,26.317 67.433,25.4C67.368,24.896 67.109,24.438 66.713,24.124ZM65.849,27.428L63.6,27.428C63.6,26.95 63.632,26.473 63.696,26C63.704,25.887 63.736,25.777 63.79,25.678C63.843,25.579 63.917,25.492 64.005,25.424C64.473,25.233 64.994,25.233 65.462,25.424C65.548,25.494 65.619,25.583 65.671,25.683C65.723,25.782 65.754,25.892 65.762,26.004C65.833,26.475 65.862,26.952 65.849,27.428Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M78.824,25.12C78.747,24.744 78.542,24.406 78.243,24.161C77.886,23.928 77.46,23.817 77.032,23.844C77.032,23.844 76.991,23.844 76.963,23.844C76.963,23.844 75.581,23.767 75.01,24.464C74.948,24.542 74.892,24.625 74.844,24.712C74.752,24.478 74.592,24.275 74.383,24.129C74.024,23.923 73.61,23.826 73.195,23.848C73.195,23.848 71.813,23.767 71.242,24.468C71.178,24.545 71.122,24.629 71.076,24.717L71.03,23.984L69.349,23.984L69.349,32.48L71.191,32.48L71.191,28.051C71.182,27.52 71.201,26.988 71.251,26.459C71.263,26.198 71.362,25.949 71.532,25.749C71.736,25.584 71.997,25.506 72.26,25.531C72.493,25.513 72.727,25.557 72.937,25.658C73.015,25.731 73.076,25.819 73.119,25.916C73.162,26.013 73.185,26.118 73.186,26.223C73.234,26.747 73.254,27.272 73.245,27.798L73.245,32.48L75.088,32.48L75.088,28.051C75.088,27.314 75.088,26.785 75.143,26.459C75.156,26.197 75.258,25.946 75.434,25.749C75.642,25.586 75.906,25.508 76.171,25.531C76.405,25.513 76.641,25.557 76.852,25.658C76.929,25.732 76.99,25.82 77.032,25.917C77.074,26.014 77.096,26.118 77.096,26.223C77.147,26.747 77.167,27.272 77.156,27.798L77.156,32.48L78.999,32.48L78.999,26.884C79.009,26.291 78.951,25.699 78.824,25.12Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M51.691,24.171C51.307,23.928 50.851,23.814 50.394,23.845C50.394,23.845 50.356,23.845 50.338,23.845C50.338,23.845 48.938,23.773 48.364,24.465C48.323,24.514 48.286,24.565 48.252,24.619L48.21,23.981L46.507,23.981L46.507,32.48L48.373,32.48L48.373,28.049C48.363,27.521 48.384,26.992 48.434,26.465C48.448,26.203 48.553,25.952 48.733,25.755C48.958,25.584 49.242,25.503 49.526,25.528C49.774,25.511 50.023,25.555 50.249,25.655C50.333,25.728 50.401,25.816 50.448,25.915C50.496,26.014 50.521,26.121 50.524,26.23C50.578,26.75 50.6,27.273 50.59,27.796L50.59,32.48L52.456,32.48L52.456,26.963C52.471,26.356 52.419,25.749 52.302,25.153C52.226,24.765 52.009,24.417 51.691,24.171Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M36.543,21.44L34.653,21.44L34.653,23.877L33.477,23.877L33.477,25.434L34.653,25.434L34.653,32.48L36.543,32.48L36.543,25.434L37.981,25.434L37.981,23.877L36.543,23.877L36.543,21.44Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M23.463,105.118L21.826,104.112L21.904,106H21.024L21.087,104.112L19.441,105.125L19.02,104.335L20.707,103.493L19.016,102.645L19.428,101.882L21.08,102.875L21.001,101H21.874L21.818,102.882L23.451,101.882L23.885,102.645L22.184,103.5L23.895,104.342L23.463,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M32.161,105.118L30.524,104.112L30.602,106H29.722L29.785,104.112L28.139,105.125L27.718,104.335L29.405,103.493L27.715,102.645L28.126,101.882L29.778,102.875L29.699,101H30.573L30.517,102.882L32.149,101.882L32.583,102.645L30.883,103.5L32.593,104.342L32.161,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M40.86,105.118L39.222,104.112L39.3,106H38.42L38.483,104.112L36.837,105.125L36.416,104.335L38.104,103.493L36.413,102.645L36.825,101.882L38.476,102.875L38.398,101H39.271L39.215,102.882L40.847,101.882L41.282,102.645L39.581,103.5L41.292,104.342L40.86,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M49.558,105.118L47.92,104.112L47.998,106H47.119L47.181,104.112L45.535,105.125L45.114,104.335L46.802,103.493L45.111,102.645L45.523,101.882L47.174,102.875L47.096,101H47.969L47.913,102.882L49.546,101.882L49.98,102.645L48.279,103.5L49.99,104.342L49.558,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M63.14,105.118L61.502,104.112L61.58,106H60.701L60.763,104.112L59.117,105.125L58.696,104.335L60.384,103.493L58.693,102.645L59.105,101.882L60.756,102.875L60.678,101H61.551L61.495,102.882L63.128,101.882L63.562,102.645L61.861,103.5L63.572,104.342L63.14,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M71.838,105.118L70.2,104.112L70.279,106H69.399L69.462,104.112L67.815,105.125L67.394,104.335L69.082,103.493L67.391,102.645L67.803,101.882L69.454,102.875L69.376,101H70.249L70.193,102.882L71.826,101.882L72.26,102.645L70.559,103.5L72.27,104.342L71.838,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M80.536,105.118L78.898,104.112L78.977,106H78.097L78.16,104.112L76.514,105.125L76.093,104.335L77.78,103.493L76.089,102.645L76.501,101.882L78.152,102.875L78.074,101H78.947L78.891,102.882L80.524,101.882L80.958,102.645L79.257,103.5L80.968,104.342L80.536,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M89.234,105.118L87.597,104.112L87.675,106H86.795L86.858,104.112L85.212,105.125L84.791,104.335L86.478,103.493L84.788,102.645L85.2,101.882L86.851,102.875L86.772,101H87.646L87.59,102.882L89.222,101.882L89.657,102.645L87.956,103.5L89.666,104.342L89.234,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M102.816,105.118L101.179,104.112L101.257,106H100.377L100.44,104.112L98.794,105.125L98.373,104.335L100.06,103.493L98.369,102.645L98.781,101.882L100.433,102.875L100.354,101H101.227L101.171,102.882L102.804,101.882L103.238,102.645L101.538,103.5L103.248,104.342L102.816,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M111.515,105.118L109.877,104.112L109.955,106H109.075L109.138,104.112L107.492,105.125L107.071,104.335L108.758,103.493L107.068,102.645L107.48,101.882L109.131,102.875L109.053,101H109.926L109.87,102.882L111.502,101.882L111.937,102.645L110.236,103.5L111.947,104.342L111.515,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M120.213,105.118L118.575,104.112L118.653,106H117.774L117.836,104.112L116.19,105.125L115.769,104.335L117.457,103.493L115.766,102.645L116.178,101.882L117.829,102.875L117.751,101H118.624L118.568,102.882L120.201,101.882L120.635,102.645L118.934,103.5L120.645,104.342L120.213,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M128.911,105.118L127.273,104.112L127.352,106H126.472L126.535,104.112L124.888,105.125L124.467,104.335L126.155,103.493L124.464,102.645L124.876,101.882L126.527,102.875L126.449,101H127.322L127.266,102.882L128.899,101.882L129.333,102.645L127.632,103.5L129.343,104.342L128.911,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M142.493,105.118L140.855,104.112L140.933,106H140.054L140.116,104.112L138.47,105.125L138.049,104.335L139.737,103.493L138.046,102.645L138.458,101.882L140.109,102.875L140.031,101H140.904L140.848,102.882L142.481,101.882L142.915,102.645L141.214,103.5L142.925,104.342L142.493,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M151.191,105.118L149.553,104.112L149.632,106H148.752L148.815,104.112L147.169,105.125L146.748,104.335L148.435,103.493L146.744,102.645L147.156,101.882L148.807,102.875L148.729,101H149.602L149.546,102.882L151.179,101.882L151.613,102.645L149.912,103.5L151.623,104.342L151.191,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M159.889,105.118L158.252,104.112L158.33,106H157.45L157.513,104.112L155.867,105.125L155.446,104.335L157.133,103.493L155.443,102.645L155.854,101.882L157.506,102.875L157.427,101H158.3L158.244,102.882L159.877,101.882L160.311,102.645L158.611,103.5L160.321,104.342L159.889,105.118Z" />
|
||||
<path
|
||||
android:fillColor="#707070"
|
||||
android:pathData="M168.588,105.118L166.95,104.112L167.028,106H166.148L166.211,104.112L164.565,105.125L164.144,104.335L165.831,103.493L164.141,102.645L164.553,101.882L166.204,102.875L166.126,101H166.999L166.943,102.882L168.575,101.882L169.01,102.645L167.309,103.5L169.02,104.342L168.588,105.118Z" />
|
||||
</vector>
|
||||
|
|
@ -1,102 +0,0 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:aapt="http://schemas.android.com/aapt"
|
||||
android:width="214dp"
|
||||
android:height="130dp"
|
||||
android:viewportWidth="214"
|
||||
android:viewportHeight="130">
|
||||
<path
|
||||
android:pathData="M1.043,8.273C1.019,4.256 4.265,1 8.294,1H205.706C209.735,1 213.019,4.256 213.043,8.273L213.709,121.725C213.733,125.742 210.487,128.998 206.459,128.998H9.046C5.018,128.998 1.733,125.742 1.709,121.725L1.043,8.273Z"
|
||||
android:fillColor="#E4E4E4"/>
|
||||
<path
|
||||
android:pathData="M1.043,8.273C1.019,4.256 4.265,1 8.294,1H205.706C209.735,1 213.019,4.256 213.043,8.273L213.709,121.725C213.733,125.742 210.487,128.998 206.459,128.998H9.046C5.018,128.998 1.733,125.742 1.709,121.725L1.043,8.273Z"
|
||||
android:strokeWidth="0.5"
|
||||
android:fillColor="#00000000">
|
||||
<aapt:attr name="android:strokeColor">
|
||||
<gradient
|
||||
android:startY="-1.3567"
|
||||
android:startX="-1.98014"
|
||||
android:endY="122.149"
|
||||
android:endX="216.304"
|
||||
android:type="linear">
|
||||
<item android:offset="0" android:color="#FFDCDCDC"/>
|
||||
<item android:offset="0.9999" android:color="#FFDEDEDE"/>
|
||||
<item android:offset="1" android:color="#00000000"/>
|
||||
</gradient>
|
||||
</aapt:attr>
|
||||
</path>
|
||||
<path
|
||||
android:pathData="M25.274,26.4L25.274,32.64L28.079,32.64C28.188,32.639 28.292,32.596 28.369,32.522C28.446,32.447 28.49,32.346 28.491,32.241L28.491,26.4L25.274,26.4Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M19,32.241C19.001,32.346 19.045,32.447 19.122,32.522C19.199,32.596 19.303,32.639 19.412,32.64L22.217,32.64L22.217,26.4L19,26.4L19,32.241Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M28.491,23.2L28.491,20.409C28.491,20.301 28.448,20.197 28.372,20.12C28.296,20.043 28.194,20 28.086,20L19.405,20C19.297,20 19.195,20.043 19.119,20.12C19.043,20.197 19,20.301 19,20.409L19,23.2L28.491,23.2Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M43.503,24.163C42.922,23.921 42.292,23.812 41.661,23.846C40.827,23.844 39.996,23.934 39.183,24.113L39.183,25.532C39.832,25.455 40.483,25.412 41.136,25.4C41.486,25.385 41.836,25.418 42.177,25.5C42.286,25.532 42.385,25.59 42.465,25.669C42.546,25.748 42.605,25.846 42.637,25.953C42.74,26.334 42.783,26.728 42.766,27.122L42.766,27.539C41.997,27.498 41.385,27.476 40.965,27.476C40.519,27.454 40.073,27.539 39.667,27.725C39.347,27.903 39.109,28.195 38.999,28.54C38.847,29.044 38.779,29.569 38.796,30.094C38.74,30.771 38.901,31.448 39.257,32.029C39.445,32.243 39.683,32.409 39.95,32.513C40.216,32.618 40.505,32.659 40.791,32.632C41.127,32.632 42.172,32.605 42.633,32.007C42.709,31.912 42.774,31.808 42.826,31.698L42.877,32.496L44.572,32.496L44.572,27.222C44.596,26.539 44.52,25.857 44.346,25.196C44.284,24.977 44.178,24.772 44.033,24.594C43.888,24.417 43.708,24.27 43.503,24.163ZM42.748,29.256C42.796,29.736 42.713,30.219 42.508,30.656C42.409,30.782 42.272,30.876 42.117,30.924C41.942,30.972 41.76,30.995 41.578,30.992C41.294,31.028 41.006,30.953 40.777,30.783C40.623,30.523 40.558,30.221 40.592,29.922C40.582,29.681 40.607,29.44 40.666,29.206C40.684,29.139 40.716,29.075 40.761,29.021C40.805,28.966 40.861,28.921 40.924,28.889C41.098,28.821 41.285,28.791 41.472,28.803L42.748,28.803L42.748,29.256Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M58.169,24.645C58.133,24.584 58.095,24.526 58.053,24.471C57.494,23.736 56.162,23.846 56.162,23.846C55.722,23.831 55.29,23.964 54.929,24.222C54.564,24.573 54.329,25.042 54.263,25.55C54.001,27.328 54.001,29.136 54.263,30.914C54.326,31.417 54.555,31.882 54.911,32.233C55.299,32.52 55.774,32.659 56.251,32.623C56.251,32.623 56.278,32.623 56.296,32.623C56.296,32.623 57.498,32.72 58.084,32.104C58.095,32.607 58.062,33.11 57.985,33.606C57.966,33.738 57.915,33.864 57.837,33.971C57.759,34.078 57.656,34.164 57.539,34.222C57.166,34.351 56.773,34.406 56.381,34.382L54.535,34.35L54.535,35.788C54.876,35.853 55.219,35.9 55.563,35.93C55.988,35.972 56.39,35.99 56.774,35.99C57.49,36.044 58.205,35.884 58.834,35.53C59.055,35.374 59.242,35.174 59.386,34.943C59.529,34.71 59.626,34.451 59.67,34.18C59.813,33.297 59.875,32.402 59.853,31.507L59.853,23.979L58.209,23.979L58.169,24.645ZM57.963,30.221C57.936,30.452 57.824,30.664 57.65,30.813C57.447,30.94 57.212,30.999 56.975,30.983C56.711,31.006 56.446,30.95 56.211,30.823C56.028,30.636 55.923,30.385 55.916,30.12C55.815,28.876 55.815,27.625 55.916,26.381C55.923,26.125 56.025,25.882 56.202,25.701C56.442,25.579 56.709,25.526 56.975,25.55C57.227,25.529 57.479,25.599 57.686,25.747C57.87,25.947 57.981,26.207 57.999,26.482C58.066,27.072 58.093,27.666 58.079,28.26C58.101,28.916 58.062,29.573 57.963,30.221Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M66.713,24.124C66.131,23.787 65.461,23.636 64.793,23.691C64.098,23.642 63.404,23.802 62.799,24.152C62.358,24.473 62.062,24.959 61.975,25.502C61.831,26.388 61.77,27.286 61.793,28.184C61.769,29.083 61.833,29.983 61.984,30.87C62.031,31.139 62.131,31.395 62.278,31.623C62.425,31.851 62.616,32.046 62.84,32.197C63.478,32.531 64.194,32.681 64.911,32.631C65.367,32.63 65.823,32.603 66.276,32.552C66.653,32.517 67.025,32.453 67.392,32.359L67.392,30.916C66.554,31.004 65.867,31.05 65.33,31.05C64.933,31.074 64.535,31.025 64.155,30.907C64.038,30.857 63.936,30.778 63.856,30.677C63.777,30.577 63.723,30.458 63.7,30.331C63.618,29.823 63.585,29.307 63.6,28.792L67.574,28.792L67.574,28.165C67.596,27.241 67.548,26.317 67.433,25.4C67.368,24.896 67.109,24.438 66.713,24.124ZM65.849,27.428L63.6,27.428C63.6,26.95 63.632,26.473 63.696,26C63.704,25.887 63.736,25.777 63.79,25.678C63.843,25.579 63.917,25.492 64.005,25.424C64.473,25.233 64.994,25.233 65.462,25.424C65.548,25.494 65.619,25.583 65.671,25.683C65.723,25.782 65.754,25.892 65.762,26.004C65.833,26.475 65.862,26.952 65.849,27.428Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M78.824,25.12C78.747,24.744 78.542,24.406 78.243,24.161C77.886,23.928 77.46,23.817 77.032,23.844C77.032,23.844 76.991,23.844 76.963,23.844C76.963,23.844 75.581,23.767 75.01,24.464C74.948,24.542 74.892,24.625 74.844,24.712C74.752,24.478 74.592,24.275 74.383,24.129C74.024,23.923 73.61,23.826 73.195,23.848C73.195,23.848 71.813,23.767 71.242,24.468C71.178,24.545 71.122,24.629 71.076,24.717L71.03,23.984L69.349,23.984L69.349,32.48L71.191,32.48L71.191,28.051C71.182,27.52 71.201,26.988 71.251,26.459C71.263,26.198 71.362,25.949 71.532,25.749C71.736,25.584 71.997,25.506 72.26,25.531C72.493,25.513 72.727,25.557 72.937,25.658C73.015,25.731 73.076,25.819 73.119,25.916C73.162,26.013 73.185,26.118 73.186,26.223C73.234,26.747 73.254,27.272 73.245,27.798L73.245,32.48L75.088,32.48L75.088,28.051C75.088,27.314 75.088,26.785 75.143,26.459C75.156,26.197 75.258,25.946 75.434,25.749C75.642,25.586 75.906,25.508 76.171,25.531C76.405,25.513 76.641,25.557 76.852,25.658C76.929,25.732 76.99,25.82 77.032,25.917C77.074,26.014 77.096,26.118 77.096,26.223C77.147,26.747 77.167,27.272 77.156,27.798L77.156,32.48L78.999,32.48L78.999,26.884C79.009,26.291 78.951,25.699 78.824,25.12Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M51.691,24.171C51.307,23.928 50.851,23.814 50.394,23.845C50.394,23.845 50.356,23.845 50.338,23.845C50.338,23.845 48.938,23.773 48.364,24.465C48.323,24.514 48.286,24.565 48.252,24.619L48.21,23.981L46.507,23.981L46.507,32.48L48.373,32.48L48.373,28.049C48.363,27.521 48.384,26.992 48.434,26.465C48.448,26.203 48.553,25.952 48.733,25.755C48.958,25.584 49.242,25.503 49.526,25.528C49.774,25.511 50.023,25.555 50.249,25.655C50.333,25.728 50.401,25.816 50.448,25.915C50.496,26.014 50.521,26.121 50.524,26.23C50.578,26.75 50.6,27.273 50.59,27.796L50.59,32.48L52.456,32.48L52.456,26.963C52.471,26.356 52.419,25.749 52.302,25.153C52.226,24.765 52.009,24.417 51.691,24.171Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M36.543,21.44L34.653,21.44L34.653,23.877L33.477,23.877L33.477,25.434L34.653,25.434L34.653,32.48L36.543,32.48L36.543,25.434L37.981,25.434L37.981,23.877L36.543,23.877L36.543,21.44Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M23.463,105.118L21.826,104.112L21.904,106H21.024L21.087,104.112L19.441,105.125L19.02,104.335L20.707,103.493L19.016,102.645L19.428,101.882L21.08,102.875L21.001,101H21.874L21.818,102.882L23.451,101.882L23.885,102.645L22.184,103.5L23.895,104.342L23.463,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M32.161,105.118L30.524,104.112L30.602,106H29.722L29.785,104.112L28.139,105.125L27.718,104.335L29.405,103.493L27.715,102.645L28.126,101.882L29.778,102.875L29.699,101H30.573L30.517,102.882L32.149,101.882L32.583,102.645L30.883,103.5L32.593,104.342L32.161,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M40.86,105.118L39.222,104.112L39.3,106H38.42L38.483,104.112L36.837,105.125L36.416,104.335L38.104,103.493L36.413,102.645L36.825,101.882L38.476,102.875L38.398,101H39.271L39.215,102.882L40.847,101.882L41.282,102.645L39.581,103.5L41.292,104.342L40.86,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M49.558,105.118L47.92,104.112L47.998,106H47.119L47.181,104.112L45.535,105.125L45.114,104.335L46.802,103.493L45.111,102.645L45.523,101.882L47.174,102.875L47.096,101H47.969L47.913,102.882L49.546,101.882L49.98,102.645L48.279,103.5L49.99,104.342L49.558,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M63.14,105.118L61.502,104.112L61.58,106H60.701L60.763,104.112L59.117,105.125L58.696,104.335L60.384,103.493L58.693,102.645L59.105,101.882L60.756,102.875L60.678,101H61.551L61.495,102.882L63.128,101.882L63.562,102.645L61.861,103.5L63.572,104.342L63.14,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M71.838,105.118L70.2,104.112L70.279,106H69.399L69.462,104.112L67.815,105.125L67.394,104.335L69.082,103.493L67.391,102.645L67.803,101.882L69.454,102.875L69.376,101H70.249L70.193,102.882L71.826,101.882L72.26,102.645L70.559,103.5L72.27,104.342L71.838,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M80.536,105.118L78.898,104.112L78.977,106H78.097L78.16,104.112L76.514,105.125L76.093,104.335L77.78,103.493L76.089,102.645L76.501,101.882L78.152,102.875L78.074,101H78.947L78.891,102.882L80.524,101.882L80.958,102.645L79.257,103.5L80.968,104.342L80.536,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M89.234,105.118L87.597,104.112L87.675,106H86.795L86.858,104.112L85.212,105.125L84.791,104.335L86.478,103.493L84.788,102.645L85.2,101.882L86.851,102.875L86.772,101H87.646L87.59,102.882L89.222,101.882L89.657,102.645L87.956,103.5L89.666,104.342L89.234,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M102.816,105.118L101.179,104.112L101.257,106H100.377L100.44,104.112L98.794,105.125L98.373,104.335L100.06,103.493L98.369,102.645L98.781,101.882L100.433,102.875L100.354,101H101.227L101.171,102.882L102.804,101.882L103.238,102.645L101.538,103.5L103.248,104.342L102.816,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M111.515,105.118L109.877,104.112L109.955,106H109.075L109.138,104.112L107.492,105.125L107.071,104.335L108.758,103.493L107.068,102.645L107.48,101.882L109.131,102.875L109.053,101H109.926L109.87,102.882L111.502,101.882L111.937,102.645L110.236,103.5L111.947,104.342L111.515,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M120.213,105.118L118.575,104.112L118.653,106H117.774L117.836,104.112L116.19,105.125L115.769,104.335L117.457,103.493L115.766,102.645L116.178,101.882L117.829,102.875L117.751,101H118.624L118.568,102.882L120.201,101.882L120.635,102.645L118.934,103.5L120.645,104.342L120.213,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M128.911,105.118L127.273,104.112L127.352,106H126.472L126.535,104.112L124.888,105.125L124.467,104.335L126.155,103.493L124.464,102.645L124.876,101.882L126.527,102.875L126.449,101H127.322L127.266,102.882L128.899,101.882L129.333,102.645L127.632,103.5L129.343,104.342L128.911,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M142.493,105.118L140.855,104.112L140.933,106H140.054L140.116,104.112L138.47,105.125L138.049,104.335L139.737,103.493L138.046,102.645L138.458,101.882L140.109,102.875L140.031,101H140.904L140.848,102.882L142.481,101.882L142.915,102.645L141.214,103.5L142.925,104.342L142.493,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M151.191,105.118L149.553,104.112L149.632,106H148.752L148.815,104.112L147.169,105.125L146.748,104.335L148.435,103.493L146.744,102.645L147.156,101.882L148.807,102.875L148.729,101H149.602L149.546,102.882L151.179,101.882L151.613,102.645L149.912,103.5L151.623,104.342L151.191,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M159.889,105.118L158.252,104.112L158.33,106H157.45L157.513,104.112L155.867,105.125L155.446,104.335L157.133,103.493L155.443,102.645L155.854,101.882L157.506,102.875L157.427,101H158.3L158.244,102.882L159.877,101.882L160.311,102.645L158.611,103.5L160.321,104.342L159.889,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
<path
|
||||
android:pathData="M168.588,105.118L166.95,104.112L167.028,106H166.148L166.211,104.112L164.565,105.125L164.144,104.335L165.831,103.493L164.141,102.645L164.553,101.882L166.204,102.875L166.126,101H166.999L166.943,102.882L168.575,101.882L169.01,102.645L167.309,103.5L169.02,104.342L168.588,105.118Z"
|
||||
android:fillColor="#707070"/>
|
||||
</vector>
|
||||
|
|
@ -1,118 +0,0 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:aapt="http://schemas.android.com/aapt"
|
||||
android:width="249dp"
|
||||
android:height="150dp"
|
||||
android:viewportWidth="249"
|
||||
android:viewportHeight="150">
|
||||
<path
|
||||
android:pathData="M10,0L238,0A9.999,10.001 134.998,0 1,248.001 10L248.017,140A9.999,10.001 134.998,0 1,238.019 150L10.019,150A9.999,10.001 134.998,0 1,0.017 140L0.001,10A9.999,10.001 134.998,0 1,10 0z"
|
||||
android:fillAlpha="0.03"/>
|
||||
<path
|
||||
android:pathData="M10,0L238,0A9.999,10.001 134.998,0 1,248.001 10L248.017,140A9.999,10.001 134.998,0 1,238.019 150L10.019,150A9.999,10.001 134.998,0 1,0.017 140L0.001,10A9.999,10.001 134.998,0 1,10 0z"
|
||||
android:fillAlpha="0.5">
|
||||
<aapt:attr name="android:fillColor">
|
||||
<gradient
|
||||
android:gradientRadius="267.36932"
|
||||
android:centerX="7.404067"
|
||||
android:centerY="8.65384"
|
||||
android:type="radial">
|
||||
<item android:offset="0" android:color="#FFFFFFFF"/>
|
||||
<item android:offset="1" android:color="#19FFFFFF"/>
|
||||
</gradient>
|
||||
</aapt:attr>
|
||||
</path>
|
||||
<path
|
||||
android:pathData="M10,0L238,0A9.999,10.001 134.998,0 1,248.001 10L248.017,140A9.999,10.001 134.998,0 1,238.019 150L10.019,150A9.999,10.001 134.998,0 1,0.017 140L0.001,10A9.999,10.001 134.998,0 1,10 0z"
|
||||
android:fillColor="#1B1D1C"/>
|
||||
<path
|
||||
android:strokeWidth="1"
|
||||
android:pathData="M10,0.5L238,0.5A9.499,9.501 134.998,0 1,247.501 10L247.517,140A9.499,9.501 134.998,0 1,238.019 149.5L10.019,149.5A9.499,9.501 134.998,0 1,0.517 140L0.501,10A9.499,9.501 134.998,0 1,10 0.5z"
|
||||
android:fillColor="#00000000">
|
||||
<aapt:attr name="android:strokeColor">
|
||||
<gradient
|
||||
android:startY="3.38345"
|
||||
android:startX="2.844399"
|
||||
android:endY="144.774"
|
||||
android:endX="246.96196"
|
||||
android:type="linear">
|
||||
<item android:offset="0" android:color="#FF1A1A1A"/>
|
||||
<item android:offset="1" android:color="#FF565656"/>
|
||||
</gradient>
|
||||
</aapt:attr>
|
||||
</path>
|
||||
<path
|
||||
android:pathData="M28.359,121.942L26.389,120.734L26.472,123H25.41L25.498,120.734L23.505,121.95L23.002,121.003L25.044,119.992L23.009,118.974L23.511,118.058L25.497,119.25L25.415,117H26.468L26.389,119.258L28.365,118.058L28.884,118.974L26.826,120L28.885,121.011L28.359,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M38.855,121.942L36.885,120.734L36.967,123H35.906L35.994,120.734L34.001,121.95L33.498,121.003L35.54,119.992L33.505,118.974L34.007,118.058L35.993,119.25L35.911,117H36.964L36.884,119.258L38.861,118.058L39.38,118.974L37.322,120L39.381,121.011L38.855,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M49.351,121.942L47.381,120.734L47.463,123H46.402L46.49,120.734L44.497,121.95L43.994,121.003L46.035,119.992L44.001,118.974L44.503,118.058L46.489,119.25L46.407,117H47.46L47.38,119.258L49.357,118.058L49.876,118.974L47.818,120L49.877,121.011L49.351,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M59.847,121.942L57.877,120.734L57.959,123H56.897L56.985,120.734L54.993,121.95L54.49,121.003L56.531,119.992L54.497,118.974L54.999,118.058L56.985,119.25L56.902,117H57.956L57.876,119.258L59.853,118.058L60.372,118.974L58.314,120L60.373,121.011L59.847,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M76.235,121.942L74.266,120.734L74.348,123H73.286L73.374,120.734L71.381,121.95L70.879,121.003L72.92,119.992L70.885,118.974L71.387,118.058L73.373,119.25L73.291,117H74.345L74.265,119.258L76.242,118.058L76.761,118.974L74.703,120L76.762,121.011L76.235,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M86.731,121.942L84.761,120.734L84.844,123H83.782L83.87,120.734L81.877,121.95L81.374,121.003L83.416,119.992L81.381,118.974L81.883,118.058L83.869,119.25L83.787,117H84.841L84.761,119.258L86.737,118.058L87.257,118.974L85.199,120L87.258,121.011L86.731,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M97.227,121.942L95.257,120.734L95.34,123H94.278L94.366,120.734L92.373,121.95L91.87,121.003L93.912,119.992L91.877,118.974L92.379,118.058L94.365,119.25L94.283,117H95.337L95.257,119.258L97.233,118.058L97.752,118.974L95.695,120L97.753,121.011L97.227,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M107.723,121.942L105.753,120.734L105.835,123H104.774L104.862,120.734L102.869,121.95L102.366,121.003L104.408,119.992L102.373,118.974L102.875,118.058L104.861,119.25L104.779,117H105.832L105.752,119.258L107.729,118.058L108.248,118.974L106.19,120L108.249,121.011L107.723,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M124.112,121.942L122.142,120.734L122.224,123H121.163L121.251,120.734L119.258,121.95L118.755,121.003L120.796,119.992L118.762,118.974L119.264,118.058L121.25,119.25L121.168,117H122.221L122.141,119.258L124.118,118.058L124.637,118.974L122.579,120L124.638,121.011L124.112,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M134.608,121.942L132.638,120.734L132.72,123H131.659L131.746,120.734L129.754,121.95L129.251,121.003L131.292,119.992L129.258,118.974L129.76,118.058L131.746,119.25L131.664,117H132.717L132.637,119.258L134.614,118.058L135.133,118.974L133.075,120L135.134,121.011L134.608,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M145.104,121.942L143.134,120.734L143.216,123H142.154L142.242,120.734L140.249,121.95L139.747,121.003L141.788,119.992L139.754,118.974L140.256,118.058L142.242,119.25L142.159,117H143.213L143.133,119.258L145.11,118.058L145.629,118.974L143.571,120L145.63,121.011L145.104,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M155.599,121.942L153.63,120.734L153.712,123H152.65L152.738,120.734L150.745,121.95L150.242,121.003L152.284,119.992L150.249,118.974L150.751,118.058L152.737,119.25L152.655,117H153.709L153.629,119.258L155.606,118.058L156.125,118.974L154.067,120L156.126,121.011L155.599,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M171.988,121.942L170.018,120.734L170.101,123H169.039L169.127,120.734L167.134,121.95L166.631,121.003L168.673,119.992L166.638,118.974L167.14,118.058L169.126,119.25L169.044,117H170.098L170.018,119.258L171.994,118.058L172.513,118.974L170.456,120L172.515,121.011L171.988,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M182.484,121.942L180.514,120.734L180.597,123H179.535L179.623,120.734L177.63,121.95L177.127,121.003L179.169,119.992L177.134,118.974L177.636,118.058L179.622,119.25L179.54,117H180.593L180.514,119.258L182.49,118.058L183.009,118.974L180.952,120L183.01,121.011L182.484,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M192.98,121.942L191.01,120.734L191.092,123H190.031L190.119,120.734L188.126,121.95L187.623,121.003L189.665,119.992L187.63,118.974L188.132,118.058L190.118,119.25L190.036,117H191.089L191.009,119.258L192.986,118.058L193.505,118.974L191.447,120L193.506,121.011L192.98,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M203.476,121.942L201.506,120.734L201.588,123H200.527L200.615,120.734L198.622,121.95L198.119,121.003L200.16,119.992L198.126,118.974L198.628,118.058L200.614,119.25L200.532,117H201.585L201.505,119.258L203.482,118.058L204.001,118.974L201.943,120L204.002,121.011L203.476,121.942Z"
|
||||
android:fillColor="#A5A5A5"/>
|
||||
<path
|
||||
android:pathData="M26.483,30.4L26.483,36.64L29.382,36.64C29.494,36.639 29.602,36.596 29.681,36.522C29.761,36.447 29.806,36.346 29.807,36.241L29.807,30.4L26.483,30.4Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M20,36.241C20.001,36.346 20.046,36.447 20.126,36.522C20.205,36.596 20.313,36.639 20.425,36.64L23.324,36.64L23.324,30.4L20,30.4L20,36.241Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M29.807,27.2L29.807,24.409C29.807,24.301 29.763,24.197 29.685,24.12C29.606,24.043 29.5,24 29.389,24L20.418,24C20.307,24 20.201,24.043 20.123,24.12C20.044,24.197 20,24.301 20,24.409L20,27.2L29.807,27.2Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M45.32,28.163C44.719,27.921 44.068,27.812 43.416,27.846C42.555,27.844 41.696,27.934 40.856,28.113L40.856,29.532C41.526,29.455 42.199,29.412 42.874,29.4C43.236,29.385 43.598,29.418 43.949,29.5C44.062,29.532 44.164,29.59 44.247,29.669C44.33,29.748 44.392,29.846 44.425,29.953C44.531,30.334 44.576,30.728 44.558,31.122L44.558,31.539C43.764,31.498 43.131,31.476 42.698,31.476C42.236,31.454 41.775,31.539 41.356,31.725C41.025,31.903 40.779,32.195 40.666,32.54C40.509,33.044 40.438,33.569 40.456,34.095C40.398,34.771 40.564,35.448 40.932,36.029C41.127,36.243 41.372,36.409 41.648,36.513C41.924,36.618 42.222,36.659 42.517,36.632C42.864,36.632 43.945,36.605 44.421,36.007C44.499,35.912 44.566,35.808 44.62,35.699L44.673,36.496L46.424,36.496L46.424,31.222C46.45,30.539 46.371,29.857 46.191,29.196C46.127,28.977 46.017,28.772 45.867,28.594C45.717,28.417 45.531,28.27 45.32,28.163ZM44.54,33.256C44.589,33.736 44.503,34.219 44.292,34.656C44.189,34.783 44.048,34.876 43.887,34.924C43.706,34.972 43.519,34.995 43.331,34.992C43.037,35.028 42.74,34.953 42.503,34.783C42.343,34.523 42.277,34.221 42.312,33.922C42.302,33.681 42.327,33.44 42.388,33.206C42.407,33.139 42.44,33.076 42.486,33.021C42.532,32.966 42.59,32.921 42.655,32.889C42.834,32.821 43.028,32.791 43.221,32.803L44.54,32.803L44.54,33.256Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M60.474,28.645C60.438,28.584 60.398,28.526 60.354,28.471C59.777,27.736 58.401,27.846 58.401,27.846C57.946,27.832 57.499,27.964 57.126,28.222C56.75,28.573 56.507,29.042 56.438,29.55C56.168,31.328 56.168,33.136 56.438,34.915C56.504,35.417 56.74,35.882 57.108,36.233C57.509,36.52 58,36.659 58.493,36.623C58.493,36.623 58.521,36.623 58.539,36.623C58.539,36.623 59.782,36.72 60.386,36.104C60.398,36.607 60.364,37.11 60.285,37.606C60.264,37.738 60.212,37.864 60.131,37.971C60.051,38.078 59.945,38.164 59.823,38.222C59.439,38.351 59.033,38.406 58.627,38.382L56.72,38.35L56.72,39.788C57.071,39.853 57.426,39.9 57.782,39.93C58.221,39.972 58.636,39.99 59.034,39.99C59.773,40.044 60.512,39.884 61.162,39.53C61.39,39.374 61.583,39.174 61.732,38.943C61.88,38.71 61.98,38.451 62.026,38.18C62.174,37.297 62.237,36.402 62.215,35.507L62.215,27.979L60.516,27.979L60.474,28.645ZM60.262,34.221C60.233,34.452 60.118,34.664 59.938,34.813C59.729,34.939 59.486,34.999 59.241,34.984C58.968,35.006 58.694,34.95 58.452,34.823C58.263,34.636 58.153,34.384 58.147,34.12C58.042,32.876 58.042,31.625 58.147,30.381C58.153,30.125 58.259,29.882 58.442,29.701C58.69,29.579 58.966,29.526 59.241,29.55C59.502,29.529 59.761,29.599 59.975,29.747C60.166,29.947 60.28,30.207 60.299,30.482C60.369,31.072 60.396,31.666 60.382,32.26C60.405,32.916 60.364,33.573 60.262,34.221Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M69.304,28.124C68.702,27.787 68.01,27.636 67.319,27.691C66.601,27.642 65.884,27.802 65.259,28.152C64.804,28.473 64.497,28.959 64.408,29.502C64.259,30.388 64.196,31.286 64.219,32.184C64.195,33.083 64.261,33.983 64.417,34.87C64.465,35.139 64.568,35.395 64.72,35.623C64.872,35.851 65.07,36.046 65.301,36.197C65.961,36.531 66.701,36.681 67.441,36.631C67.913,36.63 68.384,36.603 68.852,36.552C69.241,36.517 69.626,36.453 70.005,36.359L70.005,34.916C69.139,35.004 68.429,35.05 67.874,35.05C67.464,35.074 67.053,35.025 66.66,34.907C66.54,34.857 66.433,34.778 66.351,34.677C66.269,34.577 66.214,34.458 66.19,34.331C66.106,33.822 66.071,33.307 66.087,32.792L70.193,32.792L70.193,32.165C70.215,31.241 70.167,30.317 70.047,29.4C69.98,28.896 69.713,28.438 69.304,28.124ZM68.41,31.428L66.087,31.428C66.086,30.95 66.119,30.473 66.186,30C66.195,29.887 66.228,29.777 66.283,29.678C66.338,29.579 66.414,29.492 66.505,29.424C66.988,29.233 67.527,29.233 68.01,29.424C68.1,29.494 68.173,29.583 68.227,29.682C68.28,29.782 68.312,29.892 68.321,30.004C68.394,30.475 68.424,30.952 68.41,31.428Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M81.818,29.12C81.739,28.745 81.527,28.406 81.218,28.161C80.849,27.928 80.409,27.817 79.966,27.844C79.966,27.844 79.924,27.844 79.895,27.844C79.895,27.844 78.467,27.767 77.877,28.464C77.813,28.542 77.755,28.625 77.705,28.713C77.61,28.478 77.445,28.275 77.229,28.129C76.858,27.924 76.431,27.826 76.001,27.848C76.001,27.848 74.573,27.767 73.983,28.468C73.917,28.545 73.86,28.629 73.812,28.717L73.764,27.984L72.027,27.984L72.027,36.48L73.931,36.48L73.931,32.051C73.921,31.52 73.942,30.988 73.993,30.459C74.005,30.198 74.107,29.949 74.283,29.749C74.493,29.584 74.764,29.506 75.035,29.531C75.276,29.513 75.518,29.557 75.735,29.658C75.815,29.731 75.879,29.819 75.923,29.916C75.967,30.013 75.991,30.118 75.992,30.224C76.042,30.747 76.063,31.272 76.054,31.798L76.054,36.48L77.958,36.48L77.958,32.051C77.958,31.314 77.958,30.785 78.015,30.459C78.028,30.197 78.133,29.946 78.315,29.749C78.53,29.586 78.802,29.508 79.076,29.531C79.319,29.513 79.562,29.557 79.781,29.658C79.86,29.732 79.923,29.82 79.966,29.917C80.01,30.014 80.033,30.118 80.033,30.224C80.086,30.747 80.106,31.272 80.095,31.798L80.095,36.48L81.999,36.48L81.999,30.884C82.009,30.291 81.949,29.699 81.818,29.12Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M53.781,28.171C53.383,27.928 52.913,27.814 52.44,27.845C52.44,27.845 52.402,27.845 52.382,27.845C52.382,27.845 50.936,27.773 50.343,28.465C50.301,28.514 50.262,28.565 50.227,28.619L50.184,27.981L48.424,27.981L48.424,36.48L50.353,36.48L50.353,32.049C50.342,31.521 50.363,30.992 50.415,30.465C50.429,30.203 50.538,29.952 50.724,29.755C50.957,29.584 51.25,29.503 51.543,29.529C51.8,29.511 52.057,29.555 52.291,29.655C52.378,29.728 52.448,29.816 52.497,29.915C52.546,30.014 52.572,30.121 52.575,30.23C52.63,30.75 52.653,31.273 52.643,31.796L52.643,36.48L54.571,36.48L54.571,30.963C54.587,30.356 54.533,29.75 54.412,29.153C54.333,28.765 54.109,28.417 53.781,28.171Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
<path
|
||||
android:pathData="M38.128,25.44L36.175,25.44L36.175,27.877L34.96,27.877L34.96,29.434L36.175,29.434L36.175,36.48L38.128,36.48L38.128,29.434L39.614,29.434L39.614,27.877L38.128,27.877L38.128,25.44Z"
|
||||
android:fillColor="#ffffff"/>
|
||||
</vector>
|
||||
|
|
@ -7,6 +7,7 @@
|
|||
android:clipChildren="false">
|
||||
|
||||
<androidx.appcompat.widget.LinearLayoutCompat
|
||||
android:id="@+id/linearLayoutCompat"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="16dp"
|
||||
|
|
@ -37,6 +38,7 @@
|
|||
android:layout_marginStart="64dp"
|
||||
android:layout_marginTop="10dp"
|
||||
android:layout_marginEnd="64dp"
|
||||
android:minLines="3"
|
||||
app:layout_constraintBottom_toTopOf="@+id/fl_scan_card_container"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
|
|
@ -45,6 +47,20 @@
|
|||
|
||||
</androidx.appcompat.widget.LinearLayoutCompat>
|
||||
|
||||
<androidx.appcompat.widget.AppCompatCheckBox
|
||||
android:id="@+id/chb_understand"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="@string/alert_button_i_understand"
|
||||
android:textStyle="bold"
|
||||
android:visibility="gone"
|
||||
app:buttonTint="@color/accent"
|
||||
app:layout_constraintBottom_toTopOf="@+id/fl_scan_card_container"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/linearLayoutCompat"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/fl_scan_card_container"
|
||||
android:layout_width="wrap_content"
|
||||
|
|
@ -41,7 +41,7 @@
|
|||
|
||||
<include
|
||||
android:id="@+id/onboarding_action_container"
|
||||
layout="@layout/layout_onboarding_bottom_action_views"
|
||||
layout="@layout/layout_onboarding_container_bottom"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="0dp"
|
||||
android:layout_weight="1" />
|
||||
|
|
|
|||
|
|
@ -1,160 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/coordinator_details_confirm"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:background="@color/backgroundLightGray"
|
||||
android:orientation="vertical">
|
||||
|
||||
<com.google.android.material.appbar.AppBarLayout
|
||||
android:id="@+id/app_bar"
|
||||
style="@style/Widget.MaterialComponents.Toolbar.Surface"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@color/backgroundLightGray"
|
||||
android:fitsSystemWindows="true"
|
||||
app:liftOnScroll="true">
|
||||
|
||||
<com.google.android.material.appbar.MaterialToolbar
|
||||
android:id="@+id/toolbar"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="?attr/actionBarSize"
|
||||
app:navigationIcon="@drawable/ic_baseline_arrow_back_24"
|
||||
app:title="Re-create wallet" />
|
||||
</com.google.android.material.appbar.AppBarLayout>
|
||||
|
||||
<androidx.constraintlayout.widget.ConstraintLayout
|
||||
android:id="@+id/cl_details_confirm"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_marginTop="16dp"
|
||||
android:layout_marginBottom="33dp"
|
||||
app:layout_behavior="@string/appbar_scrolling_view_behavior">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_step_number"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="8dp"
|
||||
android:gravity="start"
|
||||
android:text="@string/details_twins_recreate_step_format"
|
||||
android:textColor="@color/colorSecondary"
|
||||
android:textSize="20sp"
|
||||
android:textStyle="bold"
|
||||
app:layout_constraintEnd_toEndOf="@+id/v_step_1"
|
||||
app:layout_constraintStart_toStartOf="@id/v_step_1"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<View
|
||||
android:id="@+id/v_step_1"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="3dp"
|
||||
android:layout_marginStart="24dp"
|
||||
android:layout_marginTop="14dp"
|
||||
android:layout_marginEnd="4dp"
|
||||
android:background="@color/colorSecondary"
|
||||
app:layout_constraintEnd_toStartOf="@+id/v_step_2"
|
||||
app:layout_constraintHorizontal_bias="0.5"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/tv_step_number" />
|
||||
|
||||
<View
|
||||
android:id="@+id/v_step_2"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="3dp"
|
||||
android:layout_marginStart="4dp"
|
||||
android:layout_marginEnd="4dp"
|
||||
android:background="@color/colorSecondary"
|
||||
app:layout_constraintEnd_toStartOf="@+id/v_step_3"
|
||||
app:layout_constraintHorizontal_bias="0.5"
|
||||
app:layout_constraintStart_toEndOf="@+id/v_step_1"
|
||||
app:layout_constraintTop_toTopOf="@id/v_step_1" />
|
||||
|
||||
<View
|
||||
android:id="@+id/v_step_3"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="3dp"
|
||||
android:layout_marginStart="4dp"
|
||||
android:layout_marginEnd="24dp"
|
||||
android:background="@color/colorSecondary"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintHorizontal_bias="0.5"
|
||||
app:layout_constraintStart_toEndOf="@+id/v_step_2"
|
||||
app:layout_constraintTop_toTopOf="@id/v_step_1" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_title"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="30dp"
|
||||
android:layout_marginBottom="8dp"
|
||||
android:paddingStart="24dp"
|
||||
android:paddingEnd="24dp"
|
||||
android:text="@string/details_twins_recreate_title_format"
|
||||
android:textColor="@color/darkGray6"
|
||||
android:textSize="20sp"
|
||||
android:textStyle="bold"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/v_step_1" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_cards_description"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="24dp"
|
||||
android:paddingStart="24dp"
|
||||
android:paddingEnd="24dp"
|
||||
android:text="@string/details_twins_recreate_subtitle"
|
||||
android:textSize="14sp"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/tv_twin_title" />
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_card_1"
|
||||
android:layout_width="130dp"
|
||||
android:layout_height="70dp"
|
||||
android:layout_marginStart="47dp"
|
||||
android:layout_marginTop="16dp"
|
||||
android:src="@drawable/card_placeholder"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/tv_twin_cards_description" />
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_card_2"
|
||||
android:layout_width="130dp"
|
||||
android:layout_height="70dp"
|
||||
android:layout_marginStart="24dp"
|
||||
android:layout_marginTop="20dp"
|
||||
android:src="@drawable/card_placeholder"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="@id/iv_card_1" />
|
||||
|
||||
|
||||
<androidx.constraintlayout.widget.Guideline
|
||||
android:id="@+id/guideline"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintGuide_percent="0.37" />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/btn_tap"
|
||||
style="@style/TapBlackButton"
|
||||
android:layout_width="0dp"
|
||||
android:layout_marginStart="7dp"
|
||||
android:layout_marginTop="30dp"
|
||||
android:layout_marginEnd="16dp"
|
||||
app:icon="@drawable/ic_scan"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toEndOf="@+id/guideline"
|
||||
tools:text="@string/details_twins_recreate_button_format" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
||||
|
||||
</androidx.coordinatorlayout.widget.CoordinatorLayout>
|
||||
|
|
@ -1,103 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/coordinator_details_confirm"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:background="@color/backgroundLightGray"
|
||||
android:orientation="vertical">
|
||||
|
||||
<androidx.constraintlayout.widget.ConstraintLayout
|
||||
android:id="@+id/cl_details_confirm"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_marginBottom="33dp">
|
||||
|
||||
<View
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="0dp"
|
||||
android:alpha="0.55"
|
||||
android:background="@color/warning"
|
||||
app:layout_constraintBottom_toTopOf="@id/l_twin_cards"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<include
|
||||
android:id="@+id/l_twin_cards"
|
||||
layout="@layout/layout_twin_cards_orange"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="-40dp"
|
||||
android:layout_marginBottom="24dp"
|
||||
app:layout_constraintBottom_toTopOf="@id/tv_twin_title"
|
||||
app:layout_constraintVertical_bias="0" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_title"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="16dp"
|
||||
android:drawablePadding="4dp"
|
||||
android:paddingStart="24dp"
|
||||
android:paddingEnd="24dp"
|
||||
android:text="@string/common_warning"
|
||||
android:textColor="@color/darkGray6"
|
||||
android:textSize="20sp"
|
||||
android:textStyle="bold"
|
||||
app:drawableStartCompat="@drawable/ic_warning"
|
||||
app:drawableTint="@color/darkGray6"
|
||||
app:layout_constraintBottom_toTopOf="@id/tv_twin_cards_description"
|
||||
app:layout_constraintStart_toStartOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_cards_description"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="24dp"
|
||||
android:paddingStart="24dp"
|
||||
android:paddingEnd="24dp"
|
||||
android:text="@string/details_twins_recreate_warning"
|
||||
android:textSize="16sp"
|
||||
app:layout_constraintBottom_toTopOf="@id/btn_start"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent" />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/btn_cancel"
|
||||
style="@style/TapBlackButton"
|
||||
android:layout_width="0dp"
|
||||
android:layout_marginStart="16dp"
|
||||
android:layout_marginTop="30dp"
|
||||
android:gravity="center"
|
||||
android:text="@string/common_back"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toStartOf="@+id/guideline"
|
||||
app:layout_constraintHorizontal_bias="0.5"
|
||||
app:layout_constraintHorizontal_chainStyle="packed"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintVertical_bias="1" />
|
||||
|
||||
<androidx.constraintlayout.widget.Guideline
|
||||
android:id="@+id/guideline"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintGuide_percent="0.37" />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/btn_start"
|
||||
style="@style/TapButtonWithIcon"
|
||||
android:layout_width="0dp"
|
||||
android:layout_marginStart="7dp"
|
||||
android:layout_marginTop="30dp"
|
||||
android:layout_marginEnd="16dp"
|
||||
android:text="@string/common_start"
|
||||
app:icon="@drawable/ic_send"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toEndOf="@+id/guideline" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
||||
|
||||
</androidx.coordinatorlayout.widget.CoordinatorLayout>
|
||||
|
|
@ -1,97 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:background="@color/backgroundLightGray"
|
||||
android:orientation="vertical">
|
||||
|
||||
<androidx.constraintlayout.widget.ConstraintLayout
|
||||
android:id="@+id/cl_details_confirm"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_marginBottom="33dp">
|
||||
|
||||
<View
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="0dp"
|
||||
android:alpha="0.22"
|
||||
android:background="@color/darkGray6"
|
||||
app:layout_constraintBottom_toTopOf="@id/l_twin_cards"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<include
|
||||
android:id="@+id/l_twin_cards"
|
||||
layout="@layout/layout_twin_cards"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="-40dp"
|
||||
android:layout_marginBottom="24dp"
|
||||
android:gravity="top"
|
||||
app:layout_constraintBottom_toTopOf="@id/tv_twin_title"
|
||||
app:layout_constraintVertical_bias="0" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_title"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="24sp"
|
||||
android:layout_marginBottom="8dp"
|
||||
android:text="@string/twins_onboarding_title"
|
||||
android:textColor="@color/darkGray6"
|
||||
android:textSize="20sp"
|
||||
android:textStyle="bold"
|
||||
app:layout_constraintBottom_toTopOf="@id/tv_twin_subtitle"
|
||||
app:layout_constraintStart_toStartOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_subtitle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="24dp"
|
||||
android:layout_marginBottom="16dp"
|
||||
android:text="@string/twins_onboarding_subtitle"
|
||||
android:textColor="@color/darkGray6"
|
||||
android:textSize="17sp"
|
||||
android:textStyle="bold"
|
||||
app:layout_constraintBottom_toTopOf="@id/tv_twin_cards_description_1"
|
||||
app:layout_constraintStart_toStartOf="parent" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/tv_twin_cards_description_1"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="24dp"
|
||||
android:paddingStart="24dp"
|
||||
android:paddingEnd="24dp"
|
||||
android:text="@string/twins_onboarding_description_format"
|
||||
android:textSize="16sp"
|
||||
app:layout_constraintBottom_toTopOf="@id/btn_continue"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent" />
|
||||
|
||||
<androidx.constraintlayout.widget.Guideline
|
||||
android:id="@+id/guideline"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintGuide_percent="0.37" />
|
||||
|
||||
<com.google.android.material.button.MaterialButton
|
||||
android:id="@+id/btn_continue"
|
||||
style="@style/TapBlackButton"
|
||||
android:layout_width="0dp"
|
||||
android:layout_marginStart="7dp"
|
||||
android:layout_marginTop="30dp"
|
||||
android:layout_marginEnd="16dp"
|
||||
android:text="@string/common_continue"
|
||||
app:icon="@drawable/ic_send"
|
||||
app:layout_constraintBottom_toBottomOf="parent"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toEndOf="@+id/guideline" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
||||
|
||||
</androidx.coordinatorlayout.widget.CoordinatorLayout>
|
||||
|
|
@ -58,7 +58,7 @@
|
|||
android:elevation="3dp"
|
||||
android:maxHeight="215dp"
|
||||
android:scaleType="fitCenter"
|
||||
android:src="@drawable/card_placeholder"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<TextView
|
||||
|
|
|
|||
|
|
@ -7,9 +7,10 @@
|
|||
android:clipChildren="false">
|
||||
|
||||
<androidx.appcompat.widget.LinearLayoutCompat
|
||||
android:id="@+id/linearLayoutCompat"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginBottom="16dp"
|
||||
android:layout_marginBottom="8dp"
|
||||
android:gravity="center"
|
||||
android:orientation="vertical"
|
||||
app:layout_constraintBottom_toTopOf="@+id/fl_scan_card_container"
|
||||
|
|
@ -37,6 +38,7 @@
|
|||
android:layout_marginStart="64dp"
|
||||
android:layout_marginTop="10dp"
|
||||
android:layout_marginEnd="64dp"
|
||||
android:minLines="3"
|
||||
app:layout_constraintBottom_toTopOf="@+id/fl_scan_card_container"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
|
|
@ -45,6 +47,20 @@
|
|||
|
||||
</androidx.appcompat.widget.LinearLayoutCompat>
|
||||
|
||||
<androidx.appcompat.widget.AppCompatCheckBox
|
||||
android:id="@+id/chb_understand"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:text="@string/alert_button_i_understand"
|
||||
android:textStyle="bold"
|
||||
android:visibility="gone"
|
||||
app:buttonTint="@color/accent"
|
||||
app:layout_constraintBottom_toTopOf="@+id/fl_scan_card_container"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/linearLayoutCompat"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/fl_scan_card_container"
|
||||
android:layout_width="wrap_content"
|
||||
|
|
@ -1,11 +1,19 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/onboarding_main_container"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:clipChildren="false"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone"
|
||||
tools:visibility="visible" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
|
|
@ -38,12 +46,43 @@
|
|||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:src="@drawable/ic_home_front_card"
|
||||
android:transitionName="imv_front_card"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:clipChildren="false"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
|
|
@ -13,7 +13,7 @@
|
|||
android:elevation="0dp"
|
||||
android:rotation="-21"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/ic_home_back_card"
|
||||
android:src="@drawable/card_placeholder_white"
|
||||
android:translationY="@dimen/home_back_card_translationY"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_front_card"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_front_card"
|
||||
|
|
@ -26,8 +26,7 @@
|
|||
android:elevation="1dp"
|
||||
android:rotation="-3"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/ic_home_front_card"
|
||||
android:transitionName="imv_front_card"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:translationY="@dimen/home_front_card_translationY"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
|
|
@ -1,38 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="-40dp">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="40dp"
|
||||
android:layout_marginTop="60dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/ic_group_1258"
|
||||
app:layout_constraintBottom_toBottomOf="@id/iv_twin_card_2"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_twin_card_1"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="170dp"
|
||||
android:layout_marginTop="50dp"
|
||||
android:rotation="-19.5"
|
||||
android:src="@drawable/card_placeholder"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_twin_card_2"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="170dp"
|
||||
android:layout_marginTop="20dp"
|
||||
android:rotation="-19.5"
|
||||
android:src="@drawable/card_placeholder"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/iv_twin_card_1" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
|
@ -1,38 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_marginStart="-40dp">
|
||||
|
||||
<ImageView
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="40dp"
|
||||
android:layout_marginTop="60dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/ic_twin_cards_background_warning"
|
||||
app:layout_constraintBottom_toBottomOf="@id/iv_twin_card_2"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_twin_card_1"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="170dp"
|
||||
android:layout_marginTop="50dp"
|
||||
android:rotation="-19.5"
|
||||
android:src="@drawable/card_placeholder"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/iv_twin_card_2"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="170dp"
|
||||
android:layout_marginTop="20dp"
|
||||
android:rotation="-19.5"
|
||||
android:src="@drawable/card_placeholder"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@id/iv_twin_card_1" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
|
@ -6,6 +6,11 @@
|
|||
android:layout_height="match_parent"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
|
|
@ -38,12 +43,43 @@
|
|||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:src="@drawable/ic_home_front_card"
|
||||
android:transitionName="imv_front_card"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:clipChildren="false"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
|
|
|
|||
|
|
@ -6,6 +6,11 @@
|
|||
android:layout_height="match_parent"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
|
|
@ -38,14 +43,45 @@
|
|||
android:layout_width="140dp"
|
||||
android:layout_height="88dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder"
|
||||
android:transitionName="imv_front_card"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:translationY="-30dp"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:clipChildren="false"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
|
|
|
|||
|
|
@ -6,6 +6,11 @@
|
|||
android:layout_height="match_parent"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
|
|
@ -37,14 +42,45 @@
|
|||
android:layout_width="140dp"
|
||||
android:layout_height="88dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/ic_home_front_card"
|
||||
android:transitionName="imv_front_card"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:translationY="-30dp"
|
||||
android:visibility="visible"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:clipChildren="false"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
|
|
|
|||
116
app/src/main/res/layout/lp_onboarding_done_activation_twins.xml
Normal file
116
app/src/main/res/layout/lp_onboarding_done_activation_twins.xml
Normal file
|
|
@ -0,0 +1,116 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/onboarding_main_container"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_progress_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_card_background"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="230dp"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_square_background_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:background="@drawable/shape_rectangle_rounded_8"
|
||||
android:backgroundTint="@color/lightGray0"
|
||||
android:elevation="0dp"
|
||||
android:scaleType="fitCenter"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/pb_state" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_front_card"
|
||||
android:layout_width="140dp"
|
||||
android:layout_height="88dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:translationY="-30dp"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:clipChildren="false"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="visible"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="32dp"
|
||||
app:layout_constraintBottom_toBottomOf="@+id/imv_card_background"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_card_background"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_card_background"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<include
|
||||
android:id="@+id/btn_refresh_balance"
|
||||
layout="@layout/view_onboarding_refresh_balance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:visibility="invisible"
|
||||
app:layout_constraintBottom_toBottomOf="@+id/imv_card_background"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_card_background"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_card_background"
|
||||
app:layout_constraintTop_toBottomOf="@+id/imv_card_background" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_activation_success"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:src="@drawable/ic_activation_success"
|
||||
app:layout_constraintBottom_toBottomOf="@+id/imv_card_background"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_card_background"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_card_background"
|
||||
app:layout_constraintTop_toBottomOf="@+id/imv_card_background" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
|
@ -6,6 +6,11 @@
|
|||
android:layout_height="match_parent"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
|
|
@ -20,7 +25,7 @@
|
|||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_card_background"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="200dp"
|
||||
android:layout_height="230dp"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_square_background_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
|
|
@ -37,14 +42,45 @@
|
|||
android:layout_width="140dp"
|
||||
android:layout_height="88dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/ic_home_front_card"
|
||||
android:transitionName="imv_front_card"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:translationY="-30dp"
|
||||
android:visibility="visible"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:clipChildren="false"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
|
|
|
|||
116
app/src/main/res/layout/lp_onboarding_topup_wallet_twins.xml
Normal file
116
app/src/main/res/layout/lp_onboarding_topup_wallet_twins.xml
Normal file
|
|
@ -0,0 +1,116 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:id="@+id/onboarding_main_container"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:visibility="visible">
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_twins_welcome_bg"
|
||||
layout="@layout/view_bg_twins_welcome"
|
||||
android:visibility="gone" />
|
||||
|
||||
<include
|
||||
layout="@layout/view_onboarding_progress"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_progress_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_card_background"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="230dp"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_square_background_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:background="@drawable/shape_rectangle_rounded_8"
|
||||
android:backgroundTint="@color/lightGray0"
|
||||
android:elevation="0dp"
|
||||
android:scaleType="fitCenter"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toBottomOf="@+id/pb_state" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_front_card"
|
||||
android:layout_width="140dp"
|
||||
android:layout_height="88dp"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:translationY="-30dp"
|
||||
android:visibility="gone"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/cards_container"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="@dimen/onboarding_card_margin_top"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:clipChildren="false"
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:visibility="visible"
|
||||
app:layout_constraintEnd_toEndOf="parent"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_back_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_white" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_twin_front_card"
|
||||
android:layout_width="328dp"
|
||||
android:layout_height="174dp"
|
||||
android:layout_gravity="center"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
|
||||
<include
|
||||
android:id="@+id/onboarding_tv_balance"
|
||||
layout="@layout/view_onboarding_tv_balance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="32dp"
|
||||
app:layout_constraintBottom_toBottomOf="@+id/imv_card_background"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_card_background"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_card_background"
|
||||
app:layout_constraintTop_toTopOf="@+id/imv_card_background" />
|
||||
|
||||
<include
|
||||
android:id="@+id/btn_refresh_balance"
|
||||
layout="@layout/view_onboarding_refresh_balance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
app:layout_constraintBottom_toBottomOf="@+id/imv_card_background"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_card_background"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_card_background"
|
||||
app:layout_constraintTop_toBottomOf="@+id/imv_card_background" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/imv_activation_success"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:src="@drawable/ic_activation_success"
|
||||
android:visibility="invisible"
|
||||
app:layout_constraintBottom_toBottomOf="@+id/imv_card_background"
|
||||
app:layout_constraintEnd_toEndOf="@+id/imv_card_background"
|
||||
app:layout_constraintStart_toStartOf="@+id/imv_card_background"
|
||||
app:layout_constraintTop_toBottomOf="@+id/imv_card_background" />
|
||||
|
||||
</androidx.constraintlayout.widget.ConstraintLayout>
|
||||
|
|
@ -11,13 +11,12 @@
|
|||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:tint="@color/colorPrimary"
|
||||
android:src="@drawable/card_placeholder" />
|
||||
android:src="@drawable/card_placeholder_black"
|
||||
android:tint="@color/colorPrimary" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:tint="@color/accent"
|
||||
android:src="@drawable/card_placeholder" />
|
||||
android:src="@drawable/card_placeholder_black" />
|
||||
|
||||
</FrameLayout>
|
||||
46
app/src/main/res/layout/view_bg_twins_welcome.xml
Normal file
46
app/src/main/res/layout/view_bg_twins_welcome.xml
Normal file
|
|
@ -0,0 +1,46 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content">
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/bg_circle_large"
|
||||
android:layout_width="736dp"
|
||||
android:layout_height="609dp"
|
||||
android:alpha="0.4"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/shape_circle"
|
||||
android:tint="#DEDEE0"
|
||||
android:translationX="-272dp"
|
||||
android:translationY="-200dp"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/bg_circle_medium"
|
||||
android:layout_width="651dp"
|
||||
android:layout_height="569dp"
|
||||
android:alpha="0.4"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/shape_circle"
|
||||
android:tint="#DCDCDC"
|
||||
android:translationX="-254dp"
|
||||
android:translationY="-269dp"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
<androidx.appcompat.widget.AppCompatImageView
|
||||
android:id="@+id/bg_circle_min"
|
||||
android:layout_width="712dp"
|
||||
android:layout_height="591dp"
|
||||
android:alpha="0.4"
|
||||
android:scaleType="fitXY"
|
||||
android:src="@drawable/shape_circle"
|
||||
android:tint="#D9D9D9"
|
||||
android:translationX="-394dp"
|
||||
android:translationY="-411dp"
|
||||
app:layout_constraintStart_toStartOf="parent"
|
||||
app:layout_constraintTop_toTopOf="parent" />
|
||||
|
||||
</FrameLayout>
|
||||
|
|
@ -1,10 +1,13 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:id="@+id/pb_state"
|
||||
style="@style/Widget.AppCompat.ProgressBar.Horizontal"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="16dp"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:progressTint="@color/accent" />
|
||||
<merge>
|
||||
|
||||
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:id="@+id/pb_state"
|
||||
style="@style/Widget.AppCompat.ProgressBar.Horizontal"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginStart="32dp"
|
||||
android:layout_marginTop="16dp"
|
||||
android:layout_marginEnd="32dp"
|
||||
android:progressTint="@color/accent" />
|
||||
</merge>
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@
|
|||
android:id="@+id/tv_balance"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:elevation="0dp"
|
||||
android:fontFamily="sans-serif-medium"
|
||||
android:text="@string/onboarding_balance_title"
|
||||
android:textAllCaps="true"
|
||||
|
|
|
|||
|
|
@ -14,25 +14,22 @@
|
|||
|
||||
<string name="twins_onboarding_title" translatable="false">Tangem Twin</string>
|
||||
<string name="twins_onboarding_subtitle" translatable="false">One wallet. Two cards.</string>
|
||||
<string name="twins_onboarding_description_format" translatable="false">This one that you are holding in your hands
|
||||
and the other one with number %s.\n\nBoth cards can be used to extract funds from
|
||||
this wallet.
|
||||
</string>
|
||||
<string name="twins_onboarding_description_format" translatable="false">This one that you are holding in your handsand the other one with number #%s.</string>
|
||||
|
||||
<string name="wallet_twins_chip_format" translatable="false">Card %s of 2</string>
|
||||
|
||||
<string name="details_row_title_twins_recreate" translatable="false">Re-create twin wallet</string>
|
||||
<string name="details_twins_recreate_warning" translatable="false">This action is irreversible. You will not have access to the old wallet.\nThe wallet re-creation procedure consists of three steps. You must complete it to the end, otherwise you will have to start from the beginning.</string>
|
||||
<string name="details_twins_recreate_toolbar" translatable="false">Re-create wallet</string>
|
||||
<string name="details_twins_recreate_step_format" translatable="false">Step %s</string>
|
||||
<string name="details_twins_recreate_title_format" translatable="false">Tap the #%s twin card</string>
|
||||
<string name="details_twins_recreate_title_preparing" translatable="false">Preparing card</string>
|
||||
<string name="details_twins_recreate_title_creating_wallet" translatable="false">Creating wallet</string>
|
||||
<string name="details_twins_recreate_subtitle" translatable="false">The wallet creation procedure consists of three steps. You must complete it to the end, otherwise you will have to start from the beginning.</string>
|
||||
<string name="details_twins_recreate_button_format" translatable="false">Tap the card #%s</string>
|
||||
<string name="details_twins_recreate_alert" translatable="false">You have already started the process of recreating twin wallet. If you interrupt it, you won\'t be able to use your twin cards until you start it again and complete recreating the wallet.</string>
|
||||
<string name="details_row_title_card_tou" translatable="false">Card terms of use</string>
|
||||
|
||||
<string name="twins_recreate_toolbar" translatable="false">Tangem Twin</string>
|
||||
<string name="twins_recreate_warning" translatable="false">This action is irreversible. You will not have access to the old wallet.</string>
|
||||
<string name="twins_recreate_title_format" translatable="false">Tap the #%s twin card</string>
|
||||
<string name="twins_recreate_title_preparing" translatable="false">Preparing card</string>
|
||||
<string name="twins_recreate_title_creating_wallet" translatable="false">Creating wallet</string>
|
||||
<string name="twins_recreate_subtitle" translatable="false">The wallet creation procedure consists of three steps. You must complete it to the end, otherwise you will have to start from the beginning.</string>
|
||||
<string name="twins_recreate_button_format" translatable="false">Tap the card #%s</string>
|
||||
<string name="twins_recreate_alert" translatable="false">You have already started the process of recreating twin wallet. If you interrupt it, you won\'t be able to use your twin cards until you start it again and complete recreating the wallet.</string>
|
||||
|
||||
<string name="notification_twins_recreate_success" translatable="false">The twin address was successfully created</string>
|
||||
|
||||
//Common
|
||||
|
|
@ -188,11 +185,13 @@ this wallet.
|
|||
<string name="onboarding_top_up_button_show_wallet_address" translatable="false">Show the wallet’s address</string>
|
||||
<string name="onboarding_dialog_wallet_address" translatable="false">Scan the address to top up your wallet</string>
|
||||
|
||||
<string name="onboarding_done_header" translatable="false">Done!</string>
|
||||
<string name="onboarding_done_header" translatable="false">Success!</string>
|
||||
<string name="onboarding_done_body" translatable="false">Your crypto card is activated and ready to be used</string>
|
||||
<string name="onboarding_done_button_continue" translatable="false">Continue</string>
|
||||
<string name="onboarding_balance_title" translatable="false">Balance</string>
|
||||
|
||||
<string name="onboarding_twins_interrupt_warning" translatable="false">If the process of re-creating the wallet gets interrupted in any way, you’ll have to start over.</string>
|
||||
|
||||
<string name="onboarding_error_create_primary_wallet" translatable="false">Internal error: can\'t create wallet manager</string>
|
||||
|
||||
</resources>
|
||||
|
|
|
|||
|
|
@ -5,8 +5,7 @@
|
|||
<item name="colorPrimary">@color/colorPrimary</item>
|
||||
<item name="colorSecondary">@color/colorSecondary</item>
|
||||
<item name="android:textColor">@color/darkGray6</item>
|
||||
<item name="android:statusBarColor">@color/backgroundLightGray</item>
|
||||
<item name="android:windowTranslucentStatus">false</item>
|
||||
<item name="android:windowTranslucentStatus">true</item>
|
||||
<item name="android:windowDrawsSystemBarBackgrounds">true</item>
|
||||
<item name="android:windowActionBarOverlay">true</item>
|
||||
<item name="android:windowContentOverlay">@null</item>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue