<div class="container">
<div class="alertSuccess" id="response">
<p id="response-code" style="padding: 0px 10px"></p>
<p id="response-message" style="padding: 0px 10px"></p>
</div>
<!-- First page -->
<div class="form-page card-details show">
<div class="card">
<div class="flex-x flex-sb">
<div class="col col-6">
<h3>Pay with Card</h3>
</div>
<div class="logo-container">
<div class="image">
<img src="https://upload.wikimedia.org/wikipedia/commons/thumb/2/2a/Mastercard-logo.svg/618px-Mastercard-logo.svg.png" />
</div>
<div class="image">
<img src="data:image/png;base64,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" />
</div>
</div>
</div>
<div>
<div class="form-group">
<div class="input-label">Card number</div>
<div class="input" id='cardNumber-container'></div>
</div>
</div>
<div class="flex-x flex-sb">
<div class="col-6 form-group">
<div class="input-label">Expiry</div>
<div class="input" id='expirationDate-container'></div>
</div>
<div class="col-6 form-group">
<div class="input-label">CVV</div>
<div class="input" id="cvv-container"></div>
</div>
</div>
</div>
<button class='btn' id="pay-button">Pay ₦ <span id='amount'></span></button>
</div>
<!-- Second page -->
<div class="form-page pin">
<div class="card">
<span class="back-control" id="pin-back-button">
<label>Back</label>
</span>
<div class="form-control" style="margin-top: 20px">
<div class="input-label">Please provide your PIN</div>
<div id="pin-container" class="input"></div>
</div>
<div class="button-container">
<button id="continue-button" class="btn">Continue</button>
</div>
</div>
</div>
<!-- Third page -->
<div class="form-page otp">
<div class="card">
<span class="back-control" id="otp-back-button">
<label>Back</label>
</span>
<div class="form-control" style="margin-top: 20px">
<label>Please input the OTP sent to your mobile number</label>
<div id="otp-container" class="input"></div>
</div>
<div class="button-container">
<button id="validate-button" class="btn">Validate</button>
</div>
</div>
</div>
<div class="form-page cardinal">
<div class="cardinal-container"></div>
</div>
</div>
<script src="https://isw-hosted-fields.k8.isw.la/sdk.js"></script>
*{
font-family: 'Roboto', sans-serif;
box-sizing: border-box;
}
body{
margin: 0
}
.container {
margin: 0px;
height: 100vh;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
background-color: #eee;
}
.flex-x{
display: flex;
flex-direction: row;
}
.flex-sb{
justify-content: space-between;
}
.col-6{
width: 48%
}
.form-page {
display: none;
width: 35%;
}
.card{
/* background-color: rgb(56, 24, 199); */
background-color: #fff;
border-radius: 6px;
padding: 20px;
box-shadow: 0 2px 2px rgba(0,0,0,0.2);
}
.btn-container{
margin-top: 20px
}
.form-group{
margin-top: 10px;
margin-bottom: 10px;
}
.input-label{
margin-right: 10px;
margin-bottom: 10px;
width: 100%
}
.input{
width: 100%;
/* padding: 10px 0 10px 5px; */
font-size: 1.2em;
border: none;
border-bottom: solid 2px #ccc;
outline: none;
height: 45px;
display: inline-block;
}
input{
height: 50px !important
}
.btn{
width: 100%;
padding-top: 15px;
padding-bottom: 15px;
background-color: rgb(29, 9, 119);
border: none;
border-radius: 4px;
color: #fff;
margin-top: 20px;
transition: .5s;
cursor: pointer;
}
.back-control{
background-color: #ccc;
padding: 5px 10px;
border-radius: 3px;
cursor: pointer;
}
.btn:hover{
background-color: rgb(21, 6, 85);;
}
.logo-container{
height: auto;
display: flex;
justify-content: center;
align-items: center;
flex-direction: row;
margin-bottom: 20px
}
.logo-container img{
width: 50px;
height: auto;
margin-right: 10px
}
.cardinal-container {
position: absolute;
width: 100%;
height: 100%;
background: white;
left: 0;
top: 0;
z-index: 10;
}
.form-page.show {
display: block;
}
.form-page.cardinal {
min-height: 350px;
}
.showNotification{
/* height: 50px; */
}
/* .alertSuccess{
width: 300px;
overflow: hidden;
background: #5fdc91;
margin: 0 auto;
transition: all 0.4s ease-in-out;
margin-top: 15px;
font-size: 20px;
margin-bottom: 20px;
} */
.alertError{
color: '#ff0000' !important;
}
let loading = false;
var configuration = {
fields: {
cardNumber: {
selector: '#cardNumber-container',
placeholder: '0000 0000 0000 0000',
styles: {
fontSize: '16px',
padding: '0px 0px 0px 10px',
padding: '0px 0px 0px 10px',
}
},
expirationDate: {
selector: '#expirationDate-container',
placeholder: 'MM / YY',
styles: {
fontSize: '16px',
padding: '0px 0px 0px 10px',
padding: '0px 0px 0px 10px',
}
},
cvv: {
selector: '#cvv-container',
placeholder: '***',
styles: {
fontSize: '16px',
padding: '0px 0px 0px 10px',
padding: '0px 0px 0px 10px',
}
},
pin: {
selector: '#pin-container',
placeholder: '* * * *',
styles: {
fontSize: '16px',
padding: '0px 0px 0px 10px',
textAlign: 'center'
}
},
otp: {
selector: '#otp-container',
placeholder: '* * * * * *',
styles: {
fontSize: '16px',
padding: '0px 0px 0px 10px',
textAlign: 'center'
}
}
},
cardinal: {
containerSelector: '.cardinal-container',
activeClass: 'show'
},
paymentParameters: {
amount: 10000,
currencyCode: "566",
dateOfPayment: '2019-11-08T00:00:00',
payableCode: "Default_Payable_MX26070",
merchantCustomerName: "John Doe",
merchantCode: 'MX26070',
transactionReference: "isw_hosted_field_test:" + Date.now(),
}
}
let instance;
let payButton = document.getElementById('pay-button');
let continueButton = document.getElementById('continue-button');
let validateButton = document.getElementById('validate-button');
let pinBackButton = document.getElementById('pin-back-button');
let otpBackButton = document.getElementById('otp-back-button');
pinBackButton.addEventListener('click', function () {
setActivePage('card-details');
instance.clearField('pin');
});
otpBackButton.addEventListener('click', function () {
setActivePage('pin');
instance.clearField('otp');
});
function callback(createError, hostedFieldsInstance) {
if (createError != null) {
throw createError;
}
instance = hostedFieldsInstance;
instance.on('focus', function (event) {
let fieldContainer = document.querySelector(event.selector);
fieldContainer.style.borderBottomColor = '#a0c8e2';
});
instance.on('blur', function (event) {
let fieldContainer = document.querySelector(event.selector);
fieldContainer.style.borderBottomColor = '#e4e4e4';
});
instance.on('validation', function (event) {
});
instance.on('cardinal-response', handleCardinalValidateResponse);
payButton.addEventListener('click', function () {
instance.getBinConfiguration(handleBinConfigResponse);
});
continueButton.addEventListener('click', function () {
instance.makePayment(handlePayResponse);
});
validateButton.addEventListener('click', function () {
instance.validatePayment(handleValidateResponse);
});
}
isw.hostedFields.create(configuration, callback);
function handleBinConfigResponse(err, response) {
loading = true;
if (err != null && err.validationError === true) {
let fieldContainer = document.getElementById('cardNumber-container');
fieldContainer.style.borderBottomColor = '#FF0000';
return;
}
if(err != null && err.networkError === true){
showNotification(err, null);
return;
}
if (err !== null) {
showNotification(err, null)
return;
}
if (response.supportsPin) {
setActivePage('pin');
return;
}
instance.makePayment(handlePayResponse);
}
function handlePayResponse(err, response) {
loading = false;
if (err != null && err.validationError === true) {
showNotification(err, null);
return;
}
if(err != null && err.networkError === true){
showNotification(err, null);
return;
}
if (err != null) {
showNotification(err, null)
return;
}
if (response.requiresCentinelAuthorization === true) {
setActivePage('cardinal');
return;
}
if (response.responseCode === 'T0') {
setActivePage('otp');
showNotification(null, response);
return;
}
}
function handleValidateResponse(err, response) {
if (err != null && err.validationError === true) {
showNotification(err, null);
return;
}
if(err != null && err.networkError === true){
showNotification(err, null);
return;
}
if (err != null) {
showNotification(err, null);
return;
}
console.log('rrrr: ', response)
if(response){
showNotification(null, response)
return;
}
}
let alertDiv = document.getElementById('response')
let responseCodeDiv = document.getElementById('response-code')
let responseMessageDiv = document.getElementById('response-message')
function showNotification(error, response){
if(response){
let responseCode = response.responseCode
let responseMessage = response.plainTextSupportMessage
if(response.plainTextSupportMessage){
setNotificationText(`${responseCode}`, `${responseMessage}`)
} else {
setNotificationText(`${responseCode}`, null)
}
} else if(error) {
alertDiv.classList.add('alertError', true)
let errorCode = error.responseCode;
let validationError = error.validationError;
let networkError = error.networkError;
if(validationError){
setNotificationText(null, `There's Validation Error`)
}
if(networkError){
setNotificationText(null, `Network Error`)
}
if(errorCode){
setNotificationText(`${errorCode}`, null)
}
}
if (response.responseCode === '00') {
setNotificationText(response.responseCode, "Transaction Successful");
setActivePage('card-details');
return;
}
}
function handleCardinalValidateResponse(err, response) {
setActivePage('card-details');
}
function setNotificationText(responseCode, responseMessage){
responseCodeDiv.innerHTML = responseCode;
responseMessageDiv.innerHTML = responseMessage
alertDiv.classList.add('showNotification')
setTimeout(function(){
alertDiv.classList.remove('showNotification', 'alertError')
}, 7000)
}
function setActivePage(pageName) {
let pages = document.querySelectorAll('.form-page');
for (let i = 0; i < pages.length; i++) {
let page = pages[i];
page.classList.remove('show');
}
let activePage = document.querySelector('.form-page.' + pageName);
activePage.classList.add('show');
}
window.onload = function(){
//display the amount being processed on page
document.getElementById('amount').innerHTML = configuration.paymentParameters.amount / 100;
}
This Pen doesn't use any external CSS resources.
This Pen doesn't use any external JavaScript resources.