Android API

Import

import AffiniPaySDK

Card Entry (required)

The CardEntryFragment is a view that allows the user to input credit/debit card information manually or using the AffiniPay card reader. A token that is returned from the AffiniPay Payment Gateway to the calling activity or fragment can then be used to make a charge.

Input

The calling object will pass a ChargeParams object with the following parameters:

ParameterTypeDescription
publicKeystringThe public key for your account obtained from OAuth login used to create a one-time token.
amountstringThe requested charge amount given in US cents, unformatted. The AffiniPay Payment Gateway expects the charge in the same format. For example, USD $2.46 would be returned as “246”. This amount will be displayed (formatted) in the CardInputFragment.
accountNamestringThe name of the account to receive payment, which will be shown on the Card Entry screen.
trustAccountbooleanWhether the requested account is a trust account.
requireCvvbooleanWhether CVV is required for a manual charge.
requireSwipeCvvbooleanWhether CVV is required for a charge using the card reader. An alert will be shown to get CVV from the end user.
disableCardReaderbooleanWhether all card reader actions and events (such as scan and detect) are disabled.

Output

The calling activity or fragment will receive a ChargeResult object with the following members:

ParameterTypeDescription
oneTimeTokenstringA temporary token given by the AffiniPay Payment Gateway that can be used to create a charge.
amountstringThe requested charge amount given in US cents, unformatted. The AffiniPay Payment Gateway expects the charge in the same format. For example, USD $2.46 would be returned as “246”.
pointOfSalePointOfSaleAdditional parameters that describe the payment and verification method.
paymentDataSourcestringThe reason for payment failing to use EMV (Chip Scanning) and falling back to Magstripe (Swipe) instead.

Interface

This interface should be implemented by the activity or fragment that is launching the CardInputFragment.

interface CardEntryCallbacks {
    fun onReturnCardData(typeOfCharge: CardResult)
    fun onReset()
    fun onDismiss()
    fun onComplete()
}

Example: Implement CardEntryCallack interface

override fun onReturnCardData(typeOfCharge: CardResult) {
    Log.d("ContainerActivity", "onReturnCardData")
    val intent = Intent()
    intent.putExtra(Constants.ARG_RETURN_CARD_DATA, true)
    when (typeOfCharge.typeOfCharge) {
      ChargeType.MANUAL.toString() -> {
        intent.putExtra(Constants.TYPE_OF_CHARGE, "manual")
      }
      ChargeType.INSERT.toString() -> {
        intent.putExtra(Constants.TYPE_OF_CHARGE, "insert")
      }
      ChargeType.TAP.toString() -> {
        intent.putExtra(Constants.TYPE_OF_CHARGE, "tap")
      }
      ChargeType.SWIPE.toString() -> {
        intent.putExtra(Constants.TYPE_OF_CHARGE, "swipe")
      }
      else -> {
        intent.putExtra(Constants.TYPE_OF_CHARGE, "no card")
      }
    }
    setResult(Constants.CARD_ENTRY_RETURN_CARD_DATA_RESPONSE,intent)
    finish()
  }
  override fun onReset() {
    TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}
  override fun onDismiss() {
    TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
  }
override fun onBackButtonPress() {
    backButtonPress()
  }
override fun onComplete() {
    TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}

Interface

This interface should be implemented by the activity or fragment that is launching the CardInputFragment.

interface ChargeRequester {
  fun onEMVChargeDataReceived(emvChargeResult: ChargeResult)
  fun onSwipeChargeDataReceived(swipeChargeResult: ChargeResult)
  fun onManualChargeDataReceived(manualChargeResult: ChargeResult)
}

Example: Obtain CardEntryFragment from ViewProvider

if (supportFragmentManager.findFragmentById(R.id.fragment_container) !is CardEntryFragment) {
      if (supportFragmentManager.backStackEntryCount == 0) {
        val intent = intent
        if (intent.hasExtra(Constants.ARG_PUBLIC_KEY)) {
          publicKey = intent.extras?.get(Constants.ARG_PUBLIC_KEY) as String
        }
        if (intent.hasExtra(Constants.ARG_THEME)) {
          theme = intent.extras?.get(Constants.ARG_THEME) as String
          if(theme == "lightGrey") {
            ivBack.setImageResource(R.drawable.ic_action_back_blue)
          }
        }
        if (intent.hasExtra(Constants.ARG_ACCOUNT_NAME)) {
          accountName = intent.extras?.get(Constants.ARG_ACCOUNT_NAME) as String
        }
        if (intent.hasExtra(Constants.ARG_AMOUNT)) {
          amount = intent.extras?.get(Constants.ARG_AMOUNT) as String
        }
        if (intent.hasExtra(Constants.ARG_DISABLE_CARD_READER)) {
          disableCardReader = intent.extras?.get(Constants.ARG_DISABLE_CARD_READER) as Boolean
        }
        if (intent.hasExtra(Constants.ARG_TRUST_ACCOUNT)) {
          trustAccount = intent.extras?.get(Constants.ARG_TRUST_ACCOUNT) as Boolean
        }
        if (intent.hasExtra(Constants.ARG_REOPEN)) {
          reopen = intent.extras?.get(Constants.ARG_REOPEN) as Boolean
        }
        if (intent.hasExtra(Constants.ARG_REQUIRE_CVV)) {
          requireCvv = intent.extras?.get(Constants.ARG_REQUIRE_CVV) as Boolean
        }
        if (intent.hasExtra(Constants.ARG_REQUIRE_SWIPE_CVV)) {
          requireSwipeCvv = intent.extras?.get(Constants.ARG_REQUIRE_SWIPE_CVV) as Boolean
        }
        if (intent.hasExtra(Constants.ARG_DEMO_MODE)) {
          demoMode = intent.extras?.get(Constants.ARG_DEMO_MODE) as Boolean
          if (demoMode as Boolean) {
            tvDemoMode.visibility = View.VISIBLE
            val view = window.decorView
            view.systemUiVisibility = 0
            this.window.statusBarColor = ContextCompat.getColor(this, R.color.colorDemoModeBanner)
          } else {
            tvDemoMode.visibility = View.GONE
          }
        }
        fragment = ViewProvider.getCardEntryView(this, TokenizationInitParams(publicKey as String, amount as String, accountName as String,
                disableCardReader as Boolean, trustAccount as Boolean, requireCvv as Boolean, requireSwipeCvv as Boolean, reopen as Boolean))
        goToScreen(fragment as CardEntryFragment)
}

Example: Implement the ChargeRequester interface

@Override
    public void onEMVChargeDataReceived(@NotNull ChargeResult chargeResult) {
        Log.d(TAG, "onEMVChargeDataReceived " + chargeResult.getOneTimeToken());
        sendPaymentToken(chargeResult);
    }

@Override
    public void onManualChargeDataReceived(@NotNull ChargeResult chargeResult) {
        Log.d(TAG, "onManualChargeDataReceived " + chargeResult.getOneTimeToken());
        sendPaymentToken(chargeResult);
    }

@Override
    public void onSwipeChargeDataReceived(@NotNull ChargeResult chargeResult) {
        Log.d(TAG, "onSwipeChargeDataReceived " + chargeResult.getOneTimeToken());
        sendPaymentToken(chargeResult);
    }

fun handleChargeCompletedReceipt(charge: Charge) {
  val chargeId = charge.chargeDetails?.id
  val dialog = AlertDialog.Builder(this)
  dialog.setTitle("Charge Receipt")
      .setMessage(charge.toString())
      .setPositiveButton("Sign", { _: DialogInterface, _: Int ->
        val signIntent = Intent(this, SignatureActivity::class.java)
        signIntent.putExtra(SignatureActivity.ARG_PUBLIC_KEY, publicKey)
        signIntent.putExtra(SignatureActivity.ARG_ACCOUNT_ID, accountId)
        signIntent.putExtra(SignatureActivity.ARG_CHARGE_ID, chargeId)
        signIntent.putExtra(SignatureFragment.ARG_AMOUNT, amount)
        startActivity(signIntent)
      }).show()
}

Navigation bar for card entry screen should be developed by partners.

Screen highlights

  1. The amount to be charged.
  2. The account name, with a trust icon image if it is a trust account.
  3. The Card Number, Exp. Date, and CVV fields are for manual card entry.
  4. The button to scan and connect a bluetooth reader.
  5. The button to order a card reader from the website.
  6. The Back action in the navigation bar.
  7. The Cancel action in the navigation bar.
  8. For manual entry, the user taps this to go to the next step. The button is disabled if there are any input validation errors.