Advertisement
Guest User

Untitled

a guest
Feb 19th, 2020
248
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. let SplitIt;
  2. SplitIt = {
  3.     styles: {
  4.         modal:
  5.             'z-index: 9999;' +
  6.             'display: none;' +
  7.             'position: fixed;' +
  8.             'left: 0;top: 0;' +
  9.             'width: 100%;' +
  10.             'height: 100%;' +
  11.             'background-color: rgba(0, 0, 0, 0.5);' +
  12.             'opacity: 1;' +
  13.             'visibility: visible;' +
  14.             'transform: scale(1.0);' +
  15.             'transition: visibility 0s linear 0s, opacity 0.25s 0s, transform 0.25s;',
  16.         modalContent:
  17.             'position: absolute;' +
  18.             'top: 50%;left: 50%;' +
  19.             'transform: translate(-50%, -50%);' +
  20.             'background-color: white;' +
  21.             'padding: 1rem 1.5rem;' +
  22.             'width: 600;' +
  23.             'height: 90vh;' +
  24.             'overflow: scroll;',
  25.         closeButton:
  26.             'float: right;' +
  27.             'width: 1.5rem;' +
  28.             'line-height: 1.5rem;' +
  29.             'text-align: center;' +
  30.             'cursor: pointer;' +
  31.             'border-radius: 0.25rem;' +
  32.             'background-color: lightgray;',
  33.         learnMoreText:
  34.             'font-size:14px;' +
  35.             'margin: 5px 0;' +
  36.             'text-align: right;',
  37.         learnMore:
  38.             'font-style: italic; ' +
  39.             'cursor: pointer'
  40.     },
  41.     init: function () {
  42.         var me = this;
  43.         this.apiKey = '{{ApiKey}}';
  44.         this.appBaseUrl = '{{AppUrl}}';
  45.         this.checkoutMinimumAmount = {{CheckoutMinimumAmount}};
  46.         this.checkoutMaximumAmount = {{CheckoutMaximumAmount}};
  47.         this.logoUrl = this.appBaseUrl + '/images/logo-01.png';
  48.         this.logoText = '{{CheckoutLabel}}';
  49.         this.configNumberOfInstallments = {{ExampleInstallments}};
  50.         this.ccImageBaseUrl = 'https://cdn8.bigcommerce.com/r-c9989feeb90073b5e11876b39360a7e376124460/bower/ng-payments/dist/img';
  51.         this.creditCards = {
  52.             'visa': {
  53.                 'url': this.appBaseUrl + '/images/visa.svg',
  54.                 'isAllowed': {{1}}
  55.     },
  56.         'masterCard': {
  57.             'url': this.appBaseUrl + '/images/mastercard.svg',
  58.                 'isAllowed': {{2}}
  59.         },
  60.         'amex': {
  61.             'url': this.appBaseUrl + '/images/amex.svg',
  62.                 'isAllowed': {{3}}
  63.         },
  64.         'discover': {
  65.             'url': this.appBaseUrl + '/images/discover.svg',
  66.                 'isAllowed': {{4}}
  67.         },
  68.         'diners': {
  69.             'url': this.appBaseUrl + '/images/diners.svg',
  70.                 'isAllowed': 0
  71.         },
  72.         'paypal': {
  73.             'url': this.appBaseUrl + '/images/paypal.svg',
  74.                 'isAllowed': 0
  75.         },
  76.         'paypalCredit': {
  77.             'url': this.appBaseUrl + '/images/paypalcredit.svg',
  78.                 'isAllowed': 0
  79.         }
  80.     };
  81.         this.cartItems = [];
  82.         this.placeOrderButtonSelector = '#checkout-payment-continue';
  83.         this.paymentHeaderSelector = '.paymentProviderHeader-name';
  84.         this.isLoading = false;
  85.         this.loaderClass = 'js-splitit-loader';
  86.         this.loaderSelector = '.' + this.loaderClass;
  87.         this.ccContainer = '.form-checklist.optimizedCheckout-form-checklist';
  88.         this.itemSelectedSelector = '.form-checklist-item--selected';
  89.         this.checkoutButtonSelector = '.optimizedCheckout-buttonPrimary';
  90.         this.cartPriceSelector = '.cart-priceItem--total';
  91.         this.learnMoreImageClass = 'splitit-learn-more-img';
  92.         this.learnMoreImageUrl = this.appBaseUrl + '/images/English-PNG.png';
  93.         this.installmentPlanClass = 'splitit-installment-plan';
  94.         this.installmentPlanSelector = '.' + this.installmentPlanClass;
  95.         this.learnMoreTextClass = 'splitit-learn-more-text';
  96.         this.learnMoreClass = 'splitit-learn-more';
  97.         this.learnMoreSelector = '.' + this.learnMoreClass;
  98.         this.modalClass = 'splitit-modal';
  99.         this.modalSelector = '.' + this.modalClass;
  100.         this.modalContentClass = 'splitit-modal-content';
  101.         this.closeButtonClass = 'splitit-close-button';
  102.         this.closeButtonSelector = '.' + this.closeButtonClass;
  103.         this.totalString = '';
  104.         this.bindEvents();
  105.         this.observe();
  106.         this.appendLogos();
  107.     },
  108.     bindEvents: function () {
  109.         var me = this;
  110.  
  111.         $(document).on('click', this.checkoutButtonSelector, function (e) {
  112.  
  113.             if ($(e.target).attr('id') == 'checkout-payment-continue') {
  114.                 return;
  115.             }
  116.             clearInterval(me.logoInterval);
  117.             me.appendLogos();
  118.         });
  119.  
  120.         $(document).on('click', this.placeOrderButtonSelector, function (e) {
  121.             var ccContainerObj = $(me.ccContainer);
  122.             var selectedMethodObj = ccContainerObj.find(me.itemSelectedSelector);
  123.             var methodName = selectedMethodObj
  124.                 .find(me.paymentHeaderSelector)
  125.                 .text()
  126.                 .trim()
  127.                 .toLowerCase();
  128.  
  129.             if (methodName == 'splitit') {
  130.                 e.preventDefault();
  131.  
  132.                 if (!me.isLoading) {
  133.                     me.appendLoader(selectedMethodObj);
  134.                     me.splititMethodClickEventHandler();
  135.                 }
  136.             }
  137.         });
  138.  
  139.         $(document).on('click', this.learnMoreSelector, function () {
  140.             me.learnMoreClickEventHandler();
  141.         });
  142.  
  143.         $(document).on('click', this.closeButtonSelector, function () {
  144.             me.closeButtonClickEventHandler();
  145.         });
  146.     },
  147.     observe: function() {
  148.         this.observeTotal();
  149.     },
  150.     observeTotal: function () {
  151.         var me = this;
  152.  
  153.         setInterval(function() {
  154.             var totalEl = document.querySelector(me.cartPriceSelector + ' [data-test="cart-price-value"]');
  155.  
  156.             if (!totalEl) {
  157.                 return;
  158.             }
  159.  
  160.             if (me.totalString !== totalEl.textContent) {
  161.                 me.totalString = totalEl.textContent;
  162.                 me.handleData();
  163.             }
  164.         }, 1000);
  165.     },
  166.     handleData: function() {
  167.         var me = this;
  168.         this.fetchCheckoutData().then(function () {
  169.  
  170.             if (me.validate() == false) {
  171.                 setInterval(function () {
  172.                     var label = me.getSplititMethodLabel();
  173.                     if (label) {
  174.                         label.hide();
  175.                     }
  176.                 }, 1000);
  177.             } else {
  178.                 me.appendInstallmentsExamplePlan();
  179.                 me.appendModal();
  180.             }
  181.         });
  182.     },
  183.     splititMethodClickEventHandler: function () {
  184.         const me = this;
  185.         this.fetchCheckoutData()
  186.             .then(function () {
  187.                 me.getCheckoutUrl()
  188.                     .then(function (apiResponse) {
  189.                         if (apiResponse.error) {
  190.                             //handle error
  191.                             console.log(apiResponse.Error);
  192.                             return;
  193.                         }
  194.  
  195.                         me.appendIframe();
  196.                         loadSplititPaymentForm(apiResponse.Response.CheckoutUrl);
  197.                         me.removeLoader();
  198.                     });
  199.             });
  200.     },
  201.     learnMoreClickEventHandler: function () {
  202.         this.showModal();
  203.     },
  204.     closeButtonClickEventHandler: function () {
  205.         this.hideModal();
  206.     },
  207.     showModal: function () {
  208.         document.querySelector(this.modalSelector).style.display = "block";
  209.     },
  210.     hideModal: function () {
  211.         document.querySelector(this.modalSelector).style.display = "none";
  212.     },
  213.     appendModal: function () {
  214.         var body, modal, content, img, close;
  215.         var modalEl = document.querySelector(this.modalSelector);
  216.  
  217.         if (modalEl) {
  218.             return;
  219.         }
  220.  
  221.         body = document.querySelector("body");
  222.         modal = document.createElement('div');
  223.         content = document.createElement('div');
  224.         img = document.createElement('img');
  225.         close = document.createElement('button');
  226.  
  227.         modal.className = this.modalClass;
  228.         modal.style.cssText = this.styles.modal;
  229.  
  230.         content.className = this.modalContentClass;
  231.         content.style.cssText = this.styles.modalContent;
  232.  
  233.         img.className = this.learnMoreImageClass;
  234.         img.src = this.learnMoreImageUrl;
  235.  
  236.         close.className = this.closeButtonClass;
  237.         close.style.cssText = this.styles.closeButton;
  238.         close.textContent = 'X';
  239.  
  240.         content.appendChild(img);
  241.         content.appendChild(close);
  242.         modal.appendChild(content);
  243.         body.appendChild(modal);
  244.     },
  245.     validate: function () {
  246.  
  247.         if (this.cartAmount < this.checkoutMinimumAmount) {
  248.             return false;
  249.         }
  250.  
  251.         if (this.cartAmount > this.checkoutMaximumAmount) {
  252.             return false;
  253.         }
  254.  
  255.         return true;
  256.     },
  257.     getCheckoutUrl: function () {
  258.         const me = this;
  259.         return new Promise(function (resolve, reject) {
  260.             $.ajax({
  261.                 url: me.appBaseUrl + '/api/checkout/initiate/' + me.apiKey,
  262.                 type: 'POST',
  263.                 data: me.getSplitItData(),
  264.                 contentType: 'application/json; charset=utf-8',
  265.                 dataType: 'json',
  266.                 async: false,
  267.                 success: function (data) {
  268.                     resolve(data);
  269.                 },
  270.                 error: function (request, error) {
  271.                     reject('error: ' + JSON.stringify(request));
  272.                 }
  273.             });
  274.         });
  275.     },
  276.     fetchCheckoutData: function () {
  277.         const me = this;
  278.  
  279.         return new Promise(function (resolve, reject) {
  280.             fetch('/api/storefront/cart', {
  281.                 credentials: 'include'
  282.             }).then(function (response) {
  283.                 return response.json();
  284.             }).then(function (cartJson) {
  285.                 me.cartId = cartJson[0].id;
  286.                 me.currencyCode = cartJson[0].currency.code;
  287.                 me.convertItems(cartJson[0].lineItems.physicalItems);
  288.                 me.convertItems(cartJson[0].lineItems.digitalItems);
  289.                 return cartJson[0].id;
  290.             }).catch(function (error) {
  291.                 reject(error);
  292.             }).then(function (cartId) {
  293.                 fetch('/api/storefront/checkouts/' + cartId, {
  294.                     credentials: 'include'
  295.                 }).then(function (response) {
  296.                     return response.json();
  297.                 }).then(function (checkoutJson) {
  298.                     me.cartAmount = checkoutJson.grandTotal;
  299.                     me.checkoutId = checkoutJson.id;
  300.                     me.customerFirstName = checkoutJson.billingAddress.firstName;
  301.                     me.customerLastName = checkoutJson.billingAddress.lastName;
  302.                     me.customerEmail = checkoutJson.billingAddress.email;
  303.                     me.customerPhone = checkoutJson.billingAddress.phone;
  304.                     me.customerAddressLine1 = checkoutJson.billingAddress.address1;
  305.                     me.customerAddressLine2 = checkoutJson.billingAddress.address2;
  306.                     me.customerCity = checkoutJson.billingAddress.city;
  307.                     me.customerCountry = checkoutJson.billingAddress.country;
  308.                     me.customerState = checkoutJson.billingAddress.stateOrProvince;
  309.                     me.customerZip = checkoutJson.billingAddress.postalCode;
  310.                     resolve(checkoutJson);
  311.                 }).catch(function (error) {
  312.                     reject(error);
  313.                 })
  314.             });
  315.         });
  316.     },
  317.     convertItems: function (items) {
  318.         for (let key in items) {
  319.             if (items.hasOwnProperty(key)) {
  320.                 let item = {
  321.                     "Name": items[key].name,
  322.                     "SKU": items[key].sku,
  323.                     "Price": { "Value": items[key].salePrice, "CurrencyCode": this.currencyCode },
  324.                     "Quantity": items[key].quantity
  325.                 };
  326.                 this.cartItems.push(item);
  327.             }
  328.         }
  329.     },
  330.     getSplitItData: function () {
  331.         const data = {
  332.             "CartId": this.cartId,
  333.             "PlanData": {
  334.                 "Amount": { "Value": this.cartAmount, "CurrencyCode": this.currencyCode },
  335.                 "PurchaseMethod": "ECommerce",
  336.                 "AutoCapture": true
  337.             },
  338.             "BillingAddress": {
  339.                 "AddressLine": this.customerAddressLine1,
  340.                 "AddressLine2": this.customerAddressLine2,
  341.                 "City": this.customerCity,
  342.                 "State": this.customerState,
  343.                 "Country": this.customerCountry,
  344.                 "Zip": this.customerZip
  345.             },
  346.             "ConsumerData": {
  347.                 "FullName": this.customerFirstName + ' ' + this.customerLastName,
  348.                 "Email": this.customerEmail,
  349.                 "PhoneNumber": this.customerPhone
  350.             },
  351.             "CartData": {
  352.                 "Items": this.cartItems,
  353.                 "AmountDetails": {}
  354.             },
  355.             "RedirectUrls": {
  356.                 "Succeeded": this.appBaseUrl + "/api/checkout/confirm-order?ApiKey=" + this.apiKey,
  357.                 "Failed": this.appBaseUrl + "/api/checkout/payment-failed?ApiKey=" + this.apiKey,
  358.                 "Canceled": this.appBaseUrl + "/api/checkout/payment-canceled?ApiKey=" + this.apiKey
  359.             },
  360.             "EventsEndpoints": {
  361.                 "CreateSucceeded": this.appBaseUrl + "/api/events/create-succeeded"
  362.             }
  363.         };
  364.  
  365.         return JSON.stringify(data);
  366.     },
  367.     appendIframe: function () {
  368.         $('<div id="splitit-payment-form" class="iframe-container"></div>').appendTo('body');
  369.     },
  370.     appendLoader: function (methodObj) {
  371.         let loader = $('<span class="' + this.loaderClass + '"></span>').css({
  372.             'border': '2px solid transparen',
  373.             'border-radius': '50%',
  374.             'border-top': '2px solid #4496f6',
  375.             'border-bottom': '2px solid #4496f6',
  376.             'width': '24px',
  377.             'height': '24px',
  378.             '-webkit-animation': 'spin 2s linear infinite',
  379.             'animation': 'spin 2s linear infinite',
  380.             'display': 'block',
  381.             'font-size': '0px',
  382.             'position': 'absolute',
  383.             'top': '29px',
  384.             'left': '151px'
  385.         });
  386.  
  387.         this.isLoading = true;
  388.         methodObj.after(loader);
  389.     },
  390.     removeLoader: function () {
  391.         $(this.loaderSelector).remove();
  392.         this.isLoading = false;
  393.     },
  394.     appendLogos: function () {
  395.         var me = this;
  396.  
  397.         this.logoInterval = setInterval(function () {
  398.  
  399.             var ccContainerObj = $(me.ccContainer);
  400.  
  401.             if (ccContainerObj.length) {
  402.                 var i = 0;
  403.                 var methodsObj = ccContainerObj.find(me.paymentHeaderSelector);
  404.  
  405.                 methodsObj.each(function () {
  406.                     if ($(this).text().trim().toLowerCase() == 'splitit') {
  407.                         $(this).hide();
  408.                         me.appendSplititLogo($(this));
  409.                         me.appendCreditCardLogos($(this));
  410.                         me.appendSplititText($(this));
  411.                         clearInterval(me.logoInterval);
  412.                         i++;
  413.                     }
  414.                 });
  415.             }
  416.  
  417.         }, 1000);
  418.  
  419.     },
  420.     appendSplititLogo: function (targetObj) {
  421.         targetObj.before('<img src="' + this.logoUrl + '" style="width:80px;">');
  422.     },
  423.     appendSplititText: function (targetObj) {
  424.         targetObj.after('<span style="margin-left:10px;">' + this.logoText + '</span>');
  425.     },
  426.     appendCreditCardLogos: function (targetObj) {
  427.         var ccContainerObj = $('<div class="paymentProviderHeader-cc creditCardTypes" style="margin-bottom: 10px;"></div>');
  428.         for (var key in this.creditCards) {
  429.             var card = this.creditCards[key];
  430.  
  431.             if (card.isAllowed == 1) {
  432.                 ccContainerObj.append('<img src="' + card.url + '" style="max-width: 40px;margin-left: 5px;">');
  433.             }
  434.         }
  435.  
  436.         targetObj.after(ccContainerObj);
  437.     },
  438.     getSplititMethodLabel: function () {
  439.         var label;
  440.         var methodsObj = $(this.ccContainer).find(this.paymentHeaderSelector);
  441.  
  442.  
  443.         methodsObj.each(function () {
  444.             if ($(this).text().trim().toLowerCase() == 'splitit') {
  445.  
  446.                 label = $(this)
  447.                     .parent()
  448.                     .parent()
  449.                     .parent();
  450.             }
  451.         });
  452.  
  453.         return label;
  454.     },
  455.     appendInstallmentsExamplePlan: function () {
  456.         var text = this.createText();
  457.  
  458.         var installmentPlanEl = document.querySelector(this.installmentPlanSelector);
  459.  
  460.         if (installmentPlanEl) {
  461.             installmentPlanEl.parentNode.removeChild(installmentPlanEl);
  462.         }
  463.  
  464.         $(this.cartPriceSelector).after(text);
  465.     },
  466.     createText: function() {
  467.  
  468.         var installmentValue = (this.cartAmount / this.configNumberOfInstallments).toFixed(2);
  469.         var text = '<div class="' + this.installmentPlanClass + '"><p class="splitit-installment-example" style="font-size:14px;margin: 5px 0;text-align:right">' +
  470.             'Or $' + installmentValue + ' x ' + this.configNumberOfInstallments + '</p>';
  471.  
  472.         text += '<p class="' + this.learnMoreTextClass + '" ' +
  473.             'style="' + this.styles.learnMoreText + '">' +
  474.             'Interest - Free Payments ' +
  475.             '<a class="' + this.learnMoreClass + '" ' +
  476.             'style="' + this.styles.learnMore + '">' +
  477.             'Learn more' +
  478.             '</a>' +
  479.             '</p>' +
  480.             '</div>';
  481.  
  482.         return text;
  483.     }
  484. };
  485.  
  486. $(document).ready(function () {
  487.     SplitIt.init();
  488. });
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement