Implement gateway ordering.
This commit is contained in:
parent
5285dd1665
commit
c17d6c2334
4 changed files with 131 additions and 54 deletions
|
@ -0,0 +1,47 @@
|
|||
/*
|
||||
* Copyright 2023 Signal Messenger, LLC
|
||||
* SPDX-License-Identifier: AGPL-3.0-only
|
||||
*/
|
||||
|
||||
package org.thoughtcrime.securesms.components.settings.app.subscription.donate.gateway
|
||||
|
||||
import com.google.i18n.phonenumbers.PhoneNumberUtil
|
||||
import org.signal.core.util.orNull
|
||||
import org.thoughtcrime.securesms.recipients.Recipient
|
||||
|
||||
sealed interface GatewayOrderStrategy {
|
||||
|
||||
val orderedGateways: Set<GatewayResponse.Gateway>
|
||||
|
||||
private object Default : GatewayOrderStrategy {
|
||||
override val orderedGateways: Set<GatewayResponse.Gateway> = setOf(
|
||||
GatewayResponse.Gateway.CREDIT_CARD,
|
||||
GatewayResponse.Gateway.PAYPAL,
|
||||
GatewayResponse.Gateway.GOOGLE_PAY,
|
||||
GatewayResponse.Gateway.SEPA_DEBIT
|
||||
)
|
||||
}
|
||||
|
||||
private object NorthAmerica : GatewayOrderStrategy {
|
||||
|
||||
override val orderedGateways: Set<GatewayResponse.Gateway> = setOf(
|
||||
GatewayResponse.Gateway.GOOGLE_PAY,
|
||||
GatewayResponse.Gateway.PAYPAL,
|
||||
GatewayResponse.Gateway.CREDIT_CARD,
|
||||
GatewayResponse.Gateway.SEPA_DEBIT
|
||||
)
|
||||
}
|
||||
|
||||
companion object {
|
||||
fun getStrategy(): GatewayOrderStrategy {
|
||||
val self = Recipient.self()
|
||||
val e164 = self.e164.orNull() ?: return Default
|
||||
|
||||
return if (PhoneNumberUtil.getInstance().parse(e164, "").countryCode == 1) {
|
||||
NorthAmerica
|
||||
} else {
|
||||
Default
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -72,66 +72,94 @@ class GatewaySelectorBottomSheet : DSLSettingsBottomSheetFragment() {
|
|||
return@configure
|
||||
}
|
||||
|
||||
if (state.isGooglePayAvailable) {
|
||||
customPref(
|
||||
GooglePayButton.Model(
|
||||
isEnabled = true,
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.GOOGLE_PAY, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
}
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
if (state.isPayPalAvailable) {
|
||||
space(8.dp)
|
||||
|
||||
customPref(
|
||||
PayPalButton.Model(
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.PAYPAL, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
},
|
||||
isEnabled = true
|
||||
)
|
||||
)
|
||||
}
|
||||
|
||||
if (state.isCreditCardAvailable) {
|
||||
space(8.dp)
|
||||
|
||||
primaryButton(
|
||||
text = DSLSettingsText.from(R.string.GatewaySelectorBottomSheet__credit_or_debit_card),
|
||||
icon = DSLSettingsIcon.from(R.drawable.credit_card, R.color.signal_colorOnPrimary),
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.CREDIT_CARD, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
if (state.isSEPADebitAvailable) {
|
||||
space(8.dp)
|
||||
|
||||
tonalButton(
|
||||
text = DSLSettingsText.from(R.string.GatewaySelectorBottomSheet__bank_transfer),
|
||||
icon = DSLSettingsIcon.from(R.drawable.bank_transfer),
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.SEPA_DEBIT, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
}
|
||||
)
|
||||
state.gatewayOrderStrategy.orderedGateways.forEachIndexed { index, gateway ->
|
||||
val isFirst = index == 0
|
||||
when (gateway) {
|
||||
GatewayResponse.Gateway.GOOGLE_PAY -> renderGooglePayButton(state, isFirst)
|
||||
GatewayResponse.Gateway.PAYPAL -> renderPayPalButton(state, isFirst)
|
||||
GatewayResponse.Gateway.CREDIT_CARD -> renderCreditCardButton(state, isFirst)
|
||||
GatewayResponse.Gateway.SEPA_DEBIT -> renderSEPADebitButton(state, isFirst)
|
||||
}
|
||||
}
|
||||
|
||||
space(16.dp)
|
||||
}
|
||||
}
|
||||
|
||||
private fun DSLConfiguration.renderGooglePayButton(state: GatewaySelectorState, isFirstButton: Boolean) {
|
||||
if (state.isGooglePayAvailable) {
|
||||
if (!isFirstButton) {
|
||||
space(8.dp)
|
||||
}
|
||||
|
||||
customPref(
|
||||
GooglePayButton.Model(
|
||||
isEnabled = true,
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.GOOGLE_PAY, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
}
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
private fun DSLConfiguration.renderPayPalButton(state: GatewaySelectorState, isFirstButton: Boolean) {
|
||||
if (state.isPayPalAvailable) {
|
||||
if (!isFirstButton) {
|
||||
space(8.dp)
|
||||
}
|
||||
|
||||
customPref(
|
||||
PayPalButton.Model(
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.PAYPAL, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
},
|
||||
isEnabled = true
|
||||
)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
private fun DSLConfiguration.renderCreditCardButton(state: GatewaySelectorState, isFirstButton: Boolean) {
|
||||
if (state.isCreditCardAvailable) {
|
||||
if (!isFirstButton) {
|
||||
space(8.dp)
|
||||
}
|
||||
|
||||
primaryButton(
|
||||
text = DSLSettingsText.from(R.string.GatewaySelectorBottomSheet__credit_or_debit_card),
|
||||
icon = DSLSettingsIcon.from(R.drawable.credit_card, R.color.signal_colorOnCustom),
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.CREDIT_CARD, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
private fun DSLConfiguration.renderSEPADebitButton(state: GatewaySelectorState, isFirstButton: Boolean) {
|
||||
if (state.isSEPADebitAvailable) {
|
||||
if (!isFirstButton) {
|
||||
space(8.dp)
|
||||
}
|
||||
|
||||
tonalButton(
|
||||
text = DSLSettingsText.from(R.string.GatewaySelectorBottomSheet__bank_transfer),
|
||||
icon = DSLSettingsIcon.from(R.drawable.bank_transfer),
|
||||
onClick = {
|
||||
findNavController().popBackStack()
|
||||
val response = GatewayResponse(GatewayResponse.Gateway.SEPA_DEBIT, args.request)
|
||||
setFragmentResult(REQUEST_KEY, bundleOf(REQUEST_KEY to response))
|
||||
}
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
companion object {
|
||||
const val REQUEST_KEY = "payment_checkout_mode"
|
||||
|
||||
|
|
|
@ -3,6 +3,7 @@ package org.thoughtcrime.securesms.components.settings.app.subscription.donate.g
|
|||
import org.thoughtcrime.securesms.badges.models.Badge
|
||||
|
||||
data class GatewaySelectorState(
|
||||
val gatewayOrderStrategy: GatewayOrderStrategy,
|
||||
val loading: Boolean = true,
|
||||
val badge: Badge,
|
||||
val isGooglePayAvailable: Boolean = false,
|
||||
|
|
|
@ -21,6 +21,7 @@ class GatewaySelectorViewModel(
|
|||
|
||||
private val store = RxStore(
|
||||
GatewaySelectorState(
|
||||
gatewayOrderStrategy = GatewayOrderStrategy.getStrategy(),
|
||||
badge = args.request.badge,
|
||||
isGooglePayAvailable = InAppDonations.isPaymentSourceAvailable(PaymentSourceType.Stripe.GooglePay, args.request.donateToSignalType),
|
||||
isCreditCardAvailable = InAppDonations.isPaymentSourceAvailable(PaymentSourceType.Stripe.CreditCard, args.request.donateToSignalType),
|
||||
|
|
Loading…
Add table
Reference in a new issue