SHARE
TWEET

Untitled

a guest Jun 16th, 2019 115 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. //
  2. //  BestOffersViewController.swift
  3. //  finance
  4. //
  5. //  Created by David Yanez on 4/2/18.
  6. //  Copyright © 2018 creditsesame. All rights reserved.
  7. //
  8.  
  9. import UIKit
  10. import SnapKit
  11.  
  12. enum OffersTab: String {
  13.     case creditCards = "CCs"
  14.     case personalLoans = "PLs"
  15. }
  16.  
  17. class BestOffersViewController: OffersViewController, UITableViewDelegate, UITableViewDataSource {
  18.  
  19.     let ccHeaderIdentifier = "BestCardsHeaderView"
  20.     let notFoundIdentifier = "notFoundCellIdentifier"
  21.     let pLHeaderIdentifier = "BestPersonalLoanHeaderView"
  22.     let footerIdentifier = "MoreCardsFooter"
  23.     let newMoreCardsButton = "NewMoreCardsButton"
  24.     let dismissViewTag = 989898
  25.    
  26.     var bestCards: [CreditCard]?
  27.     var creditCardSections: [[CreditCard]] = []
  28.     var personalLoan: PersonalLoan?
  29.     var offersHeaderView: UIView!
  30.     var currentTab: OffersTab = .creditCards
  31.     var previousPLCallWasEmptyNoErrors = false
  32.     var inputError: Bool {
  33.         return incomeInputError || amountInputError
  34.     }
  35.     var incomeInputError = false
  36.     var amountInputError = false
  37.    
  38.     var loanAmount: Int {
  39.         get {
  40.             return AppContext.shared.pLAmountNeeded
  41.         }
  42.         set {
  43.             AppContext.shared.pLAmountNeeded = newValue
  44.         }
  45.     }
  46.    
  47.     var loanAmountTextField: UITextField?
  48.     var annualIncomeTextField: UITextField?
  49.     var timer: CSTimer?
  50.    
  51.     override var screeName: String {
  52.         get {
  53.             return currentTab == .creditCards ? AnalyticsScreenName.ccOffers : AnalyticsScreenName.plOffers
  54.         }
  55.     }
  56.    
  57.     let filters: [FilterData] = [FilterData(title: " Best Cards", imageName: "star_bestCards"), FilterData(title: " Cash Back", imageName: "cash_cashBack"), FilterData(title: " No Annual Fee", imageName: "calendar_noAnnualFee"), FilterData(title: " 0% Intro Purchase APR", imageName: "shopping_oapr"), FilterData(title: " Rewards", imageName: "palmTrees_rewards"), FilterData(title: " Balance Transfer", imageName: "pig_balanceTransfer")
  58.     ]
  59.    
  60.     var lastFilterSelected: Int {
  61.         get {
  62.             return UserDefaults.standard.integer(forKey: "lastFilterSelected")
  63.         }
  64.         set {
  65.             UserDefaults.standard.set(newValue, forKey: "lastFilterSelected")
  66.             UserDefaults.standard.synchronize()
  67.         }
  68.     }
  69.    
  70.     override func viewDidLoad() {
  71.         super.viewDidLoad()
  72.         edgesForExtendedLayout = []
  73.         tableView.register(UINib(nibName: ccHeaderIdentifier, bundle: nil), forHeaderFooterViewReuseIdentifier: ccHeaderIdentifier)
  74.         tableView.register(UINib(nibName: pLHeaderIdentifier, bundle: nil), forHeaderFooterViewReuseIdentifier: pLHeaderIdentifier)
  75.         tableView.register(UINib(nibName: footerIdentifier, bundle: nil), forHeaderFooterViewReuseIdentifier: footerIdentifier)
  76.         tableView.register(UINib(nibName: newMoreCardsButton, bundle: nil), forHeaderFooterViewReuseIdentifier: newMoreCardsButton)
  77.         tableView.register(UITableViewCell.self, forCellReuseIdentifier: notFoundIdentifier)
  78.        
  79.         tableView.estimatedRowHeight = 300
  80.         tableView.rowHeight = UITableView.automaticDimension
  81.         tableView.estimatedSectionHeaderHeight = 300
  82.         tableView.sectionHeaderHeight = UITableView.automaticDimension
  83.         tableView.estimatedSectionFooterHeight = 36
  84.         tableView.separatorStyle = .singleLine
  85.         tableView.separatorColor = .white
  86.         tableView.backgroundColor = UIColor.creditSesameLightGrayBackgroundColor
  87.         configureStatusBar(color: UIColor.white)
  88.        
  89.         if TestingManager.shared.newCCFilteringVariation == Variations.control {
  90.             loadData(index: 0)
  91.             configureFooter()
  92.         } else {
  93.             loadData(index: lastFilterSelected)
  94.         }
  95.        
  96.         configureHeader()
  97.    
  98.     }
  99.    
  100.     override func scrollToTop() {
  101.         tableView?.setContentOffset(.zero, animated: true)
  102.     }
  103.    
  104.     func configureHeader() {
  105.         offersHeaderView = UIView.loadNib("OffersHeaderView")
  106.         offersHeaderView.backgroundColor = UIColor.white
  107.         let titleLabel = offersHeaderView.labelWithTag(20)
  108.         let descriptionLabel = offersHeaderView.labelWithTag(21)
  109.         let ccButton = offersHeaderView.buttonWithTag(31)
  110.         let pLButton = offersHeaderView.buttonWithTag(41)
  111.         titleLabel?.font = UIFont.latoHeavy(20)
  112.         titleLabel?.textColor = UIColor.creditSesameGrayTextColor
  113.         titleLabel?.text = NSLocalizedString("Your Borrowing Power", comment: "Your Borrowing Power")
  114.        
  115.         let textDescription = NSLocalizedString("CreditCardBorrowingPowerDescription", comment: "card borrowing description")
  116.         let boldText = NSLocalizedString("credit profile", comment: "credit profile text")
  117.         let attributedDescription = NSMutableAttributedString(string: textDescription, attributes: [NSAttributedString.Key.font : UIFont.lato(16), NSAttributedString.Key.foregroundColor : UIColor.creditSesameDarkTextColor])
  118.         attributedDescription.addAttributes([NSAttributedString.Key.font : UIFont.latoBold(16)], range: (textDescription as NSString).range(of: boldText))
  119.         descriptionLabel?.attributedText = attributedDescription
  120.         descriptionLabel?.numberOfLines = 0
  121.         descriptionLabel?.lineBreakMode = .byWordWrapping
  122.        
  123.         let height = offersHeaderView.systemLayoutSizeFitting(UIView.layoutFittingCompressedSize).height
  124.         let headerView = UITableViewHeaderFooterView(frame: CGRect(x: 0, y: 0, width: 0, height: height))
  125.         headerView.backgroundColor = UIColor.clear
  126.        
  127.         if TestingManager.shared.newCCFilteringVariation == Variations.control {
  128.             let topView = UIView()
  129.             let segmentControl = DGScrollableSegmentControl()
  130.             let stackView = offersHeaderView.viewWithTag(40) as! UIStackView
  131.  
  132.             topView.heightAnchor.constraint(equalToConstant: 16).isActive = true
  133.             segmentControl.heightAnchor.constraint(equalToConstant: 32).isActive = true
  134.             topView.backgroundColor = UIColor.creditSesameLightGrayBackgroundColor
  135.             topView.addTopSeparator()
  136.             segmentControl.delegate = self
  137.             segmentControl.datasource = self
  138.  
  139.             stackView.addArrangedSubview(topView)
  140.             stackView.addArrangedSubview(segmentControl)
  141.         }
  142.        
  143.         headerView.addSubview(offersHeaderView)
  144.         offersHeaderView.clipsToBounds = true
  145.         offersHeaderView.snp.makeConstraints { (make) in
  146.             make.edges.equalToSuperview()
  147.         }
  148.        
  149.         let selectedttributtes = [NSAttributedString.Key.font : UIFont.lato(16),
  150.                                   NSAttributedString.Key.foregroundColor : UIColor.creditSesameCyan,
  151.                                   NSAttributedString.Key.kern : 0.5] as [NSAttributedString.Key : Any]
  152.        
  153.         let unselectedAttributtes = [NSAttributedString.Key.font : UIFont.lato(16),
  154.                                      NSAttributedString.Key.foregroundColor : UIColor.init(rgb: 0x757575),
  155.                                      NSAttributedString.Key.kern : 0.5] as [NSAttributedString.Key : Any]
  156.        
  157.         let creditTitle = NSAttributedString(string: NSLocalizedString("Credit Cards", comment: "credit cards button"), attributes: selectedttributtes)
  158.         let creditTitleUnSelected = NSAttributedString(string: creditTitle.string, attributes: unselectedAttributtes)
  159.         ccButton?.setAttributedTitle(creditTitle, for: .selected)
  160.         ccButton?.setAttributedTitle(creditTitleUnSelected, for: .normal)
  161.         ccButton?.isSelected = true
  162.         ccButton?.addTarget(self, action: #selector(switchToCards), for: .touchUpInside)
  163.        
  164.         let debtTitle = NSAttributedString(string: NSLocalizedString("Personal Loans", comment: "personal loans button"), attributes: selectedttributtes)
  165.         let debtTitleUnSelected = NSAttributedString(string: debtTitle.string, attributes: unselectedAttributtes)
  166.         pLButton?.setAttributedTitle(debtTitleUnSelected, for: .normal)
  167.         pLButton?.setAttributedTitle(debtTitle, for: .selected)
  168.         pLButton?.backgroundColor = UIColor.clear
  169.         pLButton?.isSelected = false
  170.         pLButton?.addTarget(self, action: #selector(switchToPLs), for: .touchUpInside)
  171.        
  172.         let button = offersHeaderView.buttonWithTag(10)
  173.         button?.setThemeAdvertiserDisclosure()
  174.         button?.backgroundColor = UIColor.clear
  175.         button?.addTarget(self, action: #selector(showAdvertisersDisclosureTooltip), for: .touchUpInside)
  176.        
  177.         tableView.tableHeaderView = headerView
  178.     }
  179.    
  180.     func disclosureFooterView() -> DisclosureFooterView {
  181.         let disclosureFooterView = DisclosureFooterView()
  182.         disclosureFooterView.providerTermsPressed = { [weak self] in
  183.             self?.showProviderTermsDisclosureTooltip()
  184.         }
  185.         disclosureFooterView.editorialDisclosurePressed = { [weak self] in
  186.             self?.showEditorialDisclosureTooltip()
  187.            
  188.         }
  189.        
  190.         return disclosureFooterView
  191.     }
  192.    
  193.     func configureFooter() {
  194.        
  195.         if currentTab == .personalLoans {
  196.             tableView.tableFooterView = nil
  197.             return
  198.         }
  199.        
  200.         let offersFooterView = UIView.loadNib("OffersFooterView")
  201.         offersFooterView.backgroundColor = UIColor.creditSesameLightGrayBackgroundColor
  202.         let balanceButton = offersFooterView.buttonWithTag(11)!
  203.         balanceButton.addTarget(self, action: #selector(browseCategories(button:)), for: .touchUpInside)
  204.         balanceButton.accessibilityLabel = NSLocalizedString("Balance Transfer", comment: "BT Cards Header")
  205.         let zeroPercentButton = offersFooterView.buttonWithTag(12)!
  206.         zeroPercentButton.addTarget(self, action: #selector(browseCategories(button:)), for: .touchUpInside)
  207.         zeroPercentButton.accessibilityLabel = NSLocalizedString("ZeroPurchaseAPR", comment: "0% Intro Purchase APR Header")
  208.         let rewardsButton = offersFooterView.buttonWithTag(13)!
  209.         rewardsButton.addTarget(self, action: #selector(browseCategories(button:)), for: .touchUpInside)
  210.         rewardsButton.accessibilityLabel = NSLocalizedString("Rewards", comment: "Rewards Cards Header")
  211.        
  212.         let titleLabel = offersFooterView.labelWithTag(10)
  213.         titleLabel?.font = UIFont.latoBold(20)
  214.         titleLabel?.textColor = UIColor.creditSesameDarkTextColor
  215.         titleLabel?.text = NSLocalizedString("Credit Card Categories", comment: "Footer categories")
  216.         let height = offersFooterView.systemLayoutSizeFitting(UIView.layoutFittingCompressedSize).height
  217.         let footerView = UITableViewHeaderFooterView(frame: CGRect(x: 0, y: 0, width: 0, height: height))
  218.         footerView.backgroundColor = UIColor.clear
  219.         footerView.addSubview(offersFooterView)
  220.         offersFooterView.clipsToBounds = true
  221.         offersFooterView.snp.makeConstraints { (make) in
  222.             make.edges.equalToSuperview()
  223.         }
  224.        
  225.         let disclosureContainerView = offersFooterView.viewWithTag(14)
  226.         let disclosureView = disclosureFooterView()
  227.         disclosureContainerView?.addSubview(disclosureView)
  228.         disclosureView.snp.makeConstraints { make in
  229.             make.edges.equalToSuperview()
  230.         }
  231.        
  232.         tableView.tableFooterView = footerView
  233.     }
  234.    
  235.     func loadPersonalLoanIfNeeded(isInputChange: Bool = false) {
  236.        
  237.         let currentIncome = CreditSesameRestClient.shared.user?.annualIncome
  238.         let currentAmount = AppContext.shared.pLAmountNeeded
  239.         // update income and amount if they did change
  240.         var needsNewPLFromServer = false
  241.         if let income = annualIncomeTextField?.text?.removeMoneyFormat() {
  242.             if let userIncome = currentIncome, income.doubleValue != userIncome.doubleValue {
  243.                 let newIncome = isInputChange ? income : userIncome
  244.                 annualIncomeTextField?.text = String.moneyFormattedString(number: newIncome)
  245.                 incomeInputError = false
  246.                 needsNewPLFromServer = true
  247.             }
  248.         }
  249.         if let amount = loanAmountTextField?.text?.removeMoneyFormat() {
  250.             if amount.intValue != currentAmount {
  251.                 let newAmount = isInputChange ? amount : NSNumber(value: currentAmount)
  252.                 loanAmountTextField?.text = String.moneyFormattedString(number: newAmount)
  253.                 amountInputError = false
  254.                 needsNewPLFromServer = true
  255.             }
  256.         }
  257.        
  258.         if (personalLoan != nil || (personalLoan == nil && previousPLCallWasEmptyNoErrors && !inputError)) && !needsNewPLFromServer {
  259.             self.tableView.reloadData()
  260.             self.configureFooter()
  261.             return
  262.         }
  263.        
  264.         let annualIncome = annualIncomeTextField?.text?.removeMoneyFormat().intValue ?? CreditSesameRestClient.shared.user?.annualIncome?.intValue ?? 0
  265.         let amount = loanAmountTextField?.text?.removeMoneyFormat().intValue ?? loanAmount
  266.        
  267.         showProgressView()
  268.        
  269.         CreditSesameRestClient.shared.getAllPersonalLoans(loanAmount: amount, annualIncome: annualIncome, page: 1, itemsPerPage: 10) { (personalLoans, error) in
  270.             self.hideProgressView()
  271.            
  272.             if let _ = error {
  273.                 self.personalLoan = nil
  274.                 self.previousPLCallWasEmptyNoErrors = false
  275.             }
  276.             else if let personalLoans = personalLoans, personalLoans.count > 0 {
  277.                 self.personalLoan = personalLoans.first
  278.                 self.previousPLCallWasEmptyNoErrors = false
  279.             }
  280.             else {
  281.                 self.personalLoan = nil
  282.                 self.previousPLCallWasEmptyNoErrors = true
  283.             }
  284.             self.tableView.reloadData()
  285.             self.configureFooter()
  286.         }
  287.     }
  288.    
  289.     override func keyboardWillShow(_ notification: Notification) {
  290.         super.keyboardWillShow(notification)
  291.        
  292.         if view.viewWithTag(dismissViewTag) == nil {
  293.             let dismissView = UIView()
  294.             let dismissTapGesture = UITapGestureRecognizer(target: self, action: #selector(didTapView(_:)))
  295.             dismissView.tag = dismissViewTag
  296.             dismissView.backgroundColor = UIColor.clear
  297.             dismissView.addGestureRecognizer(dismissTapGesture)
  298.             view.addSubview(dismissView)
  299.             dismissView.snp.makeConstraints { make in
  300.                 make.edges.equalToSuperview()
  301.             }
  302.         }
  303.     }
  304.    
  305.     override func keyboardWillHide(_ notification: Notification) {
  306.         super.keyboardWillHide(notification)
  307.        
  308.         if let v = view.viewWithTag(dismissViewTag) {
  309.             v.removeFromSuperview()
  310.         }
  311.     }
  312.    
  313.     @objc func switchToCards() {
  314.        
  315.         if currentTab == .creditCards {
  316.             return
  317.         }
  318.        
  319.         let ccButton = offersHeaderView.buttonWithTag(31)
  320.         let ccBorderView = offersHeaderView.viewWithTag(32)
  321.         let pLButton = offersHeaderView.buttonWithTag(41)
  322.         let pLBorderView = offersHeaderView.viewWithTag(42)
  323.        
  324.         ccButton?.isSelected = true
  325.         ccBorderView?.isHidden = false
  326.         pLButton?.isSelected = false
  327.         pLBorderView?.isHidden = true
  328.        
  329.         currentTab = .creditCards
  330.         tableView.reloadData()
  331.         configureFooter()
  332.         trackViewPage()
  333.     }
  334.    
  335.     @objc func switchToPLs() {
  336.        
  337.         if currentTab == .personalLoans {
  338.             return
  339.         }
  340.        
  341.         let ccButton = offersHeaderView.buttonWithTag(31)
  342.         let ccBorderView = offersHeaderView.viewWithTag(32)
  343.         let pLButton = offersHeaderView.buttonWithTag(41)
  344.         let pLBorderView = offersHeaderView.viewWithTag(42)
  345.        
  346.         ccButton?.isSelected = false
  347.         ccBorderView?.isHidden = true
  348.         pLButton?.isSelected = true
  349.         pLBorderView?.isHidden = false
  350.        
  351.         currentTab = .personalLoans
  352.         loadPersonalLoanIfNeeded()
  353.         trackViewPage()
  354.     }
  355.    
  356.     @objc func browseCategories(button: UIButton) {
  357.        
  358.         switch button.tag {
  359.         case 11:
  360.            
  361.             let cards = CreditSesameRestClient.shared.balanceTransferCards ?? []
  362.             self.openCreditCards(screen: .bestCardsBT, creditCards: cards)
  363.             trackClickNavigation(navigationLocation: AnalyticsNavLocation.bestCardsBT)
  364.         case 12:
  365.            
  366.             let cards = CreditSesameRestClient.shared.zeroPercentCards ?? []
  367.             self.openCreditCards(screen: .bestCardsZeroPercent, creditCards: cards)
  368.             trackClickNavigation(navigationLocation: AnalyticsNavLocation.bestCardsZeroPercent)
  369.         case 13:
  370.            
  371.             let cards = CreditSesameRestClient.shared.rewardsCards ?? []
  372.             self.openCreditCards(screen: .bestCardsRewards, creditCards: cards)
  373.             trackClickNavigation(navigationLocation: AnalyticsNavLocation.bestCardsRewards)
  374.         default:
  375.             break
  376.         }
  377.     }
  378.    
  379.     @objc func viewMoreCards(button: UIButton) {
  380.         openCreditCardsMarketplace()
  381.     }
  382.    
  383.     @objc func editAmount() {
  384.         loanAmountTextField?.becomeFirstResponder()
  385.     }
  386.    
  387.     @objc func editIncome() {
  388.         annualIncomeTextField?.becomeFirstResponder()
  389.     }
  390.    
  391.     override func viewWillAppear(_ animated: Bool) {
  392.         super.viewWillAppear(animated)
  393.         navigationController?.setNavigationBarHidden(true, animated: true)
  394.         creditSesameNavigationController?.setNavigationBarHidden(true, animated: true)
  395.     }
  396.    
  397.     override func viewDidAppear(_ animated: Bool) {
  398.         super.viewDidAppear(animated)
  399.        
  400.        
  401.        
  402.         if currentTab == .personalLoans {
  403.             self.loadPersonalLoanIfNeeded()
  404.         }
  405.     }
  406.    
  407.     func loadData(index: Int) {
  408.         switch index {
  409.         case 0:
  410.             creditCardSections = [CreditSesameRestClient.shared.bestCards ?? []]
  411.             self.tableView.reloadData()
  412.             self.configureFooter()
  413.         case 1:
  414.             creditCardSections = [CreditSesameRestClient.shared.cashBackCards ?? []]
  415.             self.tableView.reloadData()
  416.             self.configureFooter()
  417.         case 2:
  418.             creditCardSections = [CreditSesameRestClient.shared.noAnnualFeeCards ?? []]
  419.             self.tableView.reloadData()
  420.             self.configureFooter()
  421.         case 3:
  422.             creditCardSections = [CreditSesameRestClient.shared.zeroPercentCards ?? []]
  423.             self.tableView.reloadData()
  424.             self.configureFooter()
  425.         case 4:
  426.             creditCardSections = [CreditSesameRestClient.shared.rewardsCards ?? []]
  427.             self.tableView.reloadData()
  428.             self.configureFooter()
  429.         case 5:
  430.             creditCardSections = [CreditSesameRestClient.shared.balanceTransferCards ?? []]
  431.             self.tableView.reloadData()
  432.             self.configureFooter()
  433.         default:
  434.             creditCardSections = [CreditSesameRestClient.shared.bestCards ?? []]
  435.             self.tableView.reloadData()
  436.             self.configureFooter()
  437.         }
  438.     }
  439.  
  440.    
  441.     func numberOfSections(in tableView: UITableView) -> Int {
  442.         return 1
  443.     }
  444.    
  445.     func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
  446.         switch currentTab {
  447.         case .creditCards:
  448.             let cards = creditCardSections[section]
  449.             return min(3, cards.count)
  450.         case .personalLoans:
  451.             return 1
  452.         }
  453.     }
  454.    
  455.     func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
  456.         switch currentTab {
  457.         case .creditCards:
  458.             let view = tableView.dequeueReusableHeaderFooterView(withIdentifier: ccHeaderIdentifier)
  459.             let backgroundView = view?.viewWithTag(10)
  460.             let label = view?.labelWithTag(11)
  461.            
  462.             backgroundView?.backgroundColor = UIColor.creditSesameLightGrayBackgroundColor
  463.            
  464.             label?.font = UIFont.latoBlack(20)
  465.             label?.textColor = UIColor.creditSesameDarkTextColor
  466.            
  467.             let attributedText = NSMutableAttributedString(string: NSLocalizedString("Best Cards", comment: "Best Cards Cards Header"), attributes:
  468.                 [NSAttributedString.Key.foregroundColor : UIColor.init(rgb: 0x929292),
  469.                  NSAttributedString.Key.font : UIFont.lato(20)])
  470.             attributedText.addAttributes([NSAttributedString.Key.foregroundColor : UIColor.creditSesameGrayTextColor,
  471.                                           NSAttributedString.Key.font : UIFont.latoHeavy(20)], range: (attributedText.string as NSString).range(of: "Best Cards"))
  472.             label?.attributedText = attributedText
  473.             view?.addTopSeparator()
  474.             if TestingManager.shared.newCCFilteringVariation == Variations.control {
  475.                 return nil
  476.             } else {
  477.                 return view
  478.             }
  479.            
  480.         case .personalLoans:
  481.             let view = tableView.dequeueReusableHeaderFooterView(withIdentifier: pLHeaderIdentifier)
  482.             let amountLabel = view?.labelWithTag(21)
  483.             let amountView = view?.viewWithTag(200)
  484.             let amountTextField = view?.textFieldWithTag(22) as? TextField
  485.             let amountTooltip = view?.buttonWithTag(23)
  486.             let incomeLabel = view?.labelWithTag(31)
  487.             let incomeView = view?.viewWithTag(300)
  488.             let incomeTextField = view?.textFieldWithTag(32) as? TextField
  489.             let incomeTooltip = view?.buttonWithTag(33)
  490.            
  491.             let amountNumber = loanAmountTextField?.text?.removeMoneyFormat() ?? NSNumber(value: loanAmount)
  492.             let annualIncome = annualIncomeTextField?.text?.removeMoneyFormat() ?? CreditSesameRestClient.shared.user?.annualIncome ?? NSNumber(value: 0)
  493.            
  494.             amountLabel?.font = UIFont.lato(16)
  495.             amountLabel?.textColor = UIColor.creditSesameGrayTextColor
  496.             amountLabel?.text = NSLocalizedString("Loan Amount", comment: "loan amount label")
  497.             amountTextField?.text = String.moneyFormattedString(number: amountNumber)
  498.             amountTextField?.font = UIFont.latoMedium(16)
  499.             amountTextField?.textColor = UIColor.black
  500.             amountTextField?.keyboardType = .numberPad
  501.             amountTextField?.delegate = self
  502.             amountTextField?.maxCharacters = 6
  503.             amountView?.layer.borderColor = UIColor.creditSesameGrayBackgroundColor.cgColor
  504.             amountView?.layer.borderWidth = 1
  505.             loanAmountTextField = amountTextField
  506.             amountTooltip?.addTarget(self, action: #selector(showPLAmountTooltip), for: .touchUpInside)
  507.            
  508.             amountView?.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(editAmount)))
  509.            
  510.             incomeLabel?.font = UIFont.lato(16)
  511.             incomeLabel?.textColor = UIColor.creditSesameGrayTextColor
  512.             incomeLabel?.text = NSLocalizedString("Annual Income", comment: "income label")
  513.             incomeTextField?.text = String.moneyFormattedString(number: annualIncome)
  514.             incomeTextField?.font = UIFont.latoMedium(16)
  515.             incomeTextField?.textColor = UIColor.black
  516.             incomeTextField?.keyboardType = .numberPad
  517.             incomeTextField?.delegate = self
  518.             incomeTextField?.maxCharacters = 7
  519.             incomeView?.layer.borderColor = UIColor.creditSesameGrayBackgroundColor.cgColor
  520.             incomeView?.layer.borderWidth = 1
  521.             annualIncomeTextField = incomeTextField
  522.             incomeTooltip?.addTarget(self, action: #selector(showPLIncomeTooltip), for: .touchUpInside)
  523.            
  524.             incomeView?.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(editIncome)))
  525.            
  526.             return view
  527.         }
  528.        
  529.     }
  530.    
  531.     func tableView(_ tableView: UITableView, heightForFooterInSection section: Int) -> CGFloat {
  532.         return currentTab == .creditCards ? (TestingManager.shared.newCCFilteringVariation == Variations.variation ? 72 : 36) : 60
  533.     }
  534.    
  535.     func tableView(_ tableView: UITableView, viewForFooterInSection section: Int) -> UIView? {
  536.         let view = tableView.dequeueReusableHeaderFooterView(withIdentifier: footerIdentifier)
  537.         let actionView = view?.viewWithTag(100)
  538.         let button = view?.buttonWithTag(10)
  539.         let line = view?.viewWithTag(11)
  540.         line?.backgroundColor = UIColor.creditSesameLightGrayBackgroundColor
  541.         button?.setTitleColor(UIColor.creditSesameCyan, for: .normal)
  542.         button?.titleLabel?.font = UIFont.lato(14)
  543.         view?.backgroundColor = UIColor.white
  544.         actionView?.addTopSeparator()
  545.         actionView?.addBottomSeparator()
  546.        
  547.         switch currentTab {
  548.         case .creditCards:
  549.            
  550.             if TestingManager.shared.newCCFilteringVariation == Variations.variation {
  551.                 return newMoreFooterView
  552.             }
  553.             button?.setTitle(NSLocalizedString("See All Credit Cards", comment: "More Cards button"), for: .normal)
  554.             button?.superview?.tag = section
  555.             button?.removeTarget(self, action: #selector(openPersonalLoansMarketplace), for: .touchUpInside)
  556.             button?.addTarget(self, action: #selector(viewMoreCards), for: .touchUpInside)
  557.            
  558.         case .personalLoans:
  559.             guard let _ = personalLoan else {
  560.                 return nil
  561.             }
  562.             button?.setTitle(NSLocalizedString("See More Personal Loans", comment: "More Cards button"), for: .normal)
  563.             button?.removeTarget(self, action: #selector(viewMoreCards), for: .touchUpInside)
  564.             button?.addTarget(self, action: #selector(openPersonalLoansMarketplace), for: .touchUpInside)
  565.            
  566.         }
  567.        
  568.         return view
  569.  
  570.     }
  571.    
  572.     var newMoreFooterView: UIView? {
  573.         let view = tableView.dequeueReusableHeaderFooterView(withIdentifier: newMoreCardsButton)
  574.         let button = view?.buttonWithTag(10)
  575.         button?.setTitleColor(UIColor.white, for: .normal)
  576.         button?.titleLabel?.font = UIFont.latoSemiBold(13)
  577.         button?.backgroundColor = UIColor.creditSesameCyan
  578.         button?.setTitle(NSLocalizedString("Search All Credit Cards", comment: "More Cards"), for: .normal)
  579.         view?.addTopSeparator()
  580.         button?.addTarget(self, action: #selector(viewMoreCards), for: .touchUpInside)
  581.         return view
  582.     }
  583.    
  584.     func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
  585.         switch currentTab {
  586.         case .creditCards:
  587.             let creditCards = creditCardSections[indexPath.section]
  588.             let creditCard = creditCards[indexPath.row]
  589.             var creditCardCell: ClickApplyCell? = nil
  590.             var pagePosition: String
  591.            
  592.             pagePosition = AnalyticsPagePosition.bestCards
  593.             creditCardCell = cellForCreditCard(creditCard: creditCard, offerType: .estimatedCreditLimit)
  594.             creditCardCell?.contentView.tag = indexPath.row
  595.            
  596.             let offerPosition = numberOfOffersTill(section: indexPath.section, tableView: tableView) + indexPath.row + 1
  597.             creditCardCell?.cellPosition = "\(offerPosition)"
  598.             creditCardCell?.pagePosition = pagePosition
  599.             creditCardCell?.offer = creditCard
  600.             creditCardCell?.selectionStyle = .none
  601.             creditCardCell?.addTopSeparator()
  602.            
  603.             trackViewOfferCreditCard(creditCard: creditCard, pagePosition: pagePosition, pageLocation: nil, offerPosition:  creditCardCell?.cellPosition!)
  604.             return creditCardCell!
  605.            
  606.         case .personalLoans:
  607.             if let loan = personalLoan {
  608.                 let personalLoanCell = cellForPersonalLoan(pL: loan, offerType: loan.offerType)
  609.                 let offerPosition = numberOfOffersTill(section: indexPath.section, tableView: tableView) + indexPath.row + 1
  610.                 personalLoanCell.cellPosition = "\(offerPosition)"
  611.                 personalLoanCell.pagePosition = nil
  612.                 personalLoanCell.pageLocation = nil
  613.                 personalLoanCell.offer = loan
  614.                 personalLoanCell.selectionStyle = .none
  615.                
  616.                 trackViewOfferPersonalLoan(personalLoan: personalLoan!, pagePosition: nil, pageLocation: nil, offerPosition: "1")
  617.                 return personalLoanCell
  618.             }
  619.             else if let cell = tableView.dequeueReusableCell(withIdentifier: notFoundIdentifier) {
  620.                
  621.                 for v in cell.contentView.subviews {
  622.                     v.removeFromSuperview()
  623.                 }
  624.                
  625.                 let view = UIView.loadNib("OffersNotFoundView")
  626.                 let titleLabel = view.labelWithTag(10)
  627.                 let contentLabel = view.labelWithTag(11)
  628.                 let actionView = view.viewWithTag(20)
  629.                 let actionButton = view.buttonWithTag(21)
  630.                 let accessibilityView = view.viewWithTag(30)!
  631.                
  632.                 titleLabel?.font = UIFont.latoHeavy(18)
  633.                 titleLabel?.textColor = UIColor.init(rgb: 0x606060)
  634.                 titleLabel?.text = ClientConfigurationManager.shared.configurationFile?.disclaimers?.loansNotFoundTitle ?? NSLocalizedString("Loans Offer Not Found title", comment: "Not found title")
  635.                 contentLabel?.font = UIFont.lato(14)
  636.                 contentLabel?.textColor = UIColor.init(rgb: 0x606060)
  637.                 contentLabel?.textAlignment = .left
  638.                 contentLabel?.text = ClientConfigurationManager.shared.configurationFile?.disclaimers?.loansNotFoundContent ?? NSLocalizedString("Loans Offer Not Found content", comment: "Not found content")
  639.                 contentLabel?.numberOfLines = 0
  640.                 contentLabel?.lineBreakMode = .byWordWrapping
  641.                
  642.                 actionView?.isHidden = false
  643.                 let buttonTitle = currentTab == .creditCards ? NSLocalizedString("Search All Credit Cards", comment: "Market place button") : NSLocalizedString("Search All Personal Loans", comment: "Market place button")
  644.                 actionButton?.setThemeInfoButton(title: buttonTitle)
  645.                 let selector = currentTab == .creditCards ? #selector(openCreditCardsMarketplace) : #selector(openPersonalLoansMarketplace)
  646.                 actionButton?.addTarget(self, action: selector, for: .touchUpInside)
  647.                
  648.                 cell.contentView.addSubview(view)
  649.                 view.snp.makeConstraints({ make in
  650.                     make.edges.equalToSuperview()
  651.                 })
  652.                
  653.                 cell.selectionStyle = .none
  654.                 cell.backgroundColor = UIColor.creditSesameLightGrayBackgroundColor
  655.                
  656.                 accessibilityView.isAccessibilityElement = true
  657.                 accessibilityView.accessibilityLabel = "\(titleLabel?.text ?? ""): \(contentLabel?.text ?? "")"
  658.                
  659.                 return cell
  660.             }
  661.         }
  662.        
  663.         return UITableViewCell()
  664.     }
  665.    
  666.     func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
  667.         tableView.deselectRow(at: indexPath, animated: true)
  668.     }
  669.    
  670. }
  671.  
  672. extension BestOffersViewController: UITextFieldDelegate {
  673.    
  674.     func textFieldShouldBeginEditing(_ textField: UITextField) -> Bool {
  675.         textField.text = "\(textField.text?.removeMoneyFormat().intValue ?? 0)"
  676.        
  677.         if textField == self.loanAmountTextField {
  678.             trackClick(clickType: AnalyticsClickType.enterLoanAmount, pagePosition: nil)
  679.         }
  680.        
  681.         // update annual income
  682.         if textField == self.annualIncomeTextField {
  683.             trackClick(clickType: AnalyticsClickType.updateIncome, pagePosition: nil)
  684.         }
  685.        
  686.         return true
  687.     }
  688.    
  689.     func textField(_ textField: UITextField, shouldChangeCharactersIn range: NSRange, replacementString string: String) -> Bool {
  690.        
  691.         let currentString = textField.text! as NSString
  692.         let newString = currentString.replacingCharacters(in: range, with: string) as NSString
  693.        
  694.         if let textField = textField as? TextField, let maxLength = textField.maxCharacters, newString.length > maxLength {
  695.                 return false
  696.         }
  697.        
  698.         if let timer = timer {
  699.             timer.startTimer()
  700.         }
  701.         else {
  702.             timer = CSTimer()
  703.             timer?.action = {
  704.                
  705.                 if (self.annualIncomeTextField?.text?.count ?? 0) == 0 || (self.loanAmountTextField?.text?.count ?? 0) == 0 {
  706.                     return
  707.                 }
  708.                
  709.                 self.loadPersonalLoanIfNeeded(isInputChange: true)
  710.                 DispatchQueue.main.async {
  711.                     self.hideKeyboard()
  712.                 }
  713.             }
  714.             timer?.startTimer()
  715.         }
  716.         return true
  717.     }
  718.    
  719.     func textFieldDidEndEditing(_ textField: UITextField) {
  720.         let money = textField.text?.removeMoneyFormat().doubleValue ?? 0
  721.        
  722.         // update amount needed
  723.         if textField == self.loanAmountTextField {
  724.             guard money >= 0 && money <= 100000 else {
  725.                 let message = ClientConfigurationManager.shared.configurationFile?.errorValidation?.errorLoanAmount ?? NSLocalizedString("AmountNeededTooltip", comment: "amount loan error")
  726.                 showAppClientError(message)
  727.                 textField.text = String.moneyFormattedString(number: NSNumber(value: money))
  728.                 amountInputError = true
  729.                 return
  730.             }
  731.             amountInputError = false
  732.             loanAmount = Int(money)
  733.         }
  734.        
  735.         // update annual income
  736.         if textField == self.annualIncomeTextField {
  737.             guard money > 0 else {
  738.                 let message = ClientConfigurationManager.shared.configurationFile?.errorValidation?.errorAnnualIncome ?? NSLocalizedString("CalculateDTIIncomeError", comment: "invalid income error")
  739.                 showAppClientError(message)
  740.                 textField.text = String.moneyFormattedString(number: NSNumber(value: money))
  741.                 incomeInputError = true
  742.                 return
  743.             }
  744.            
  745.             incomeInputError = false
  746.             let user = CreditSesameRestClient.shared.user?.copy() as? User ?? User()
  747.             if  user.annualIncome?.doubleValue != money {
  748.                 user.annualIncome = NSNumber(value: money)
  749.                 CreditSesameRestClient.shared.updateUser(user: user, password: AppContext.shared.password)
  750.             }
  751.         }
  752.        
  753.         textField.text = String.moneyFormattedString(number: NSNumber(value: money))
  754.     }
  755. }
  756.  
  757. extension BestOffersViewController: DGScrollableSegmentControlDataSource,DGScrollableSegmentControlDelegate {
  758.    
  759.    
  760.     func numbersOfItem() -> Int {
  761.         return filters.count
  762.     }
  763.    
  764.     func itemfor(_ index: Int) -> DGItem {
  765.        
  766.         let item = DGItem()
  767.         item.setTitle(filters[index].title, for: .normal)
  768.         item.isSelected = index == lastFilterSelected
  769.         item.setImage(UIImage(named: filters[index].imageName), for: .normal)
  770.         item.titleLabel?.font = UIFont.latoSemiBold(12)
  771.  
  772.         if item.isSelected {
  773.             item.setTitleColor(UIColor.white, for: .normal)
  774.             item.backgroundColor = UIColor.creditSesameCyan
  775.         } else {
  776.             item.setTitleColor(UIColor.creditSesameCyan, for: .normal)
  777.             item.backgroundColor = UIColor.white
  778.         }
  779.        
  780.         return item
  781.        
  782.     }
  783.    
  784.     func didSelect(_ item: DGItem, atIndex index: Int) {
  785.         lastFilterSelected = index
  786.         loadData(index: lastFilterSelected)
  787.         switch index {
  788.         case 0:
  789.             trackClick(clickType: AnalyticsClickType.filter, pagePosition: AnalyticsPagePosition.bestCards)
  790.         case 1:
  791.             trackClick(clickType: AnalyticsClickType.filter, pagePosition: AnalyticsPagePosition.cashBack)
  792.         case 2:
  793.             trackClick(clickType: AnalyticsClickType.filter, pagePosition: AnalyticsPagePosition.noAnnualFee)
  794.         case 3:
  795.             trackClick(clickType: AnalyticsClickType.filter, pagePosition: AnalyticsPagePosition.introPurchaseAPR)
  796.         case 4:
  797.             trackClick(clickType: AnalyticsClickType.filter, pagePosition: AnalyticsPagePosition.rewards)
  798.         case 5:
  799.             trackClick(clickType: AnalyticsClickType.filter, pagePosition: AnalyticsPagePosition.balanceTransfer)
  800.         default:
  801.             print("")
  802.         }
  803.     }
  804.    
  805. }
  806.  
  807. struct FilterData {
  808.  
  809.     var title = ""
  810.     var imageName = ""
  811.    
  812.     init(title: String, imageName: String) {
  813.         self.title = title
  814.         self.imageName = imageName
  815.     }
  816.    
  817. }
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
Not a member of Pastebin yet?
Sign Up, it unlocks many cool features!
 
Top