// // ExchangeRatesViewController.swift // GMERemittance // // Created by gme_2 on 24/08/2018. //Copyright © 2018 Gobal Money Express Co. Ltd. All rights reserved. // import UIKit import Hex enum PaymentMode: String { case cashDelivery = "1" case bankDeposite = "2" case homeDelivery = "12" case mobileWallet = "13" case cardPayment = "14" } class ExchangeRatesViewController: UIViewController { struct Constants { let transferFeeDetailText = StringConstants().transferFeeDetailText let currentExchangeRateText = StringConstants().currentExchangeRateText let paymentModeHeightConstant: CGFloat = 154 let title = StringConstants().title } struct StringConstants { let selectPaymentModeText = "" let youSendText = "you_send_text".localized() let recepientGetsText = "receipient_gets_text".localized() let calculate = "calculate_text".localized() let title = "todays_rate_text".localized() let currentExchangeRateText = "current_exchange_rate_text".localized() let transferFeeDetailText = "transfer_fee_included_text".localized() } struct ApiConstants { static let recieverCountryId = "pCountry" static let senderCurrency = "sCurrency" static let recieverCurrency = "pCurrency" static let senderAmount = "cAmount" static let recieverAmount = "pAmount" static let paymentMethod = "serviceType" static let calcBy = "calcBy" static let recieverCountryName = "pCountryName" static let senderCountryId = "sCountry" } // MARK: IBOutlets @IBOutlet weak var scrollView: UIScrollView! @IBOutlet weak var collectionView: UICollectionView! @IBOutlet weak var exchangeBackground1: UIView! @IBOutlet weak var exchangeBackground2: UIView! @IBOutlet weak var dropDownImageView: UIImageView! @IBOutlet weak var backgroundViewCountryLabel1: UIView! @IBOutlet weak var backgroundViewCountryLabel2: UIView! @IBOutlet weak var countryListStackView: UIStackView! @IBOutlet weak var countryCodeLabel: UILabel! @IBOutlet weak var countryFlagImage: UIImageView! @IBOutlet weak var paymentModeStackViewConstraint: NSLayoutConstraint! @IBOutlet weak var paymentModeStackView: UIStackView! @IBOutlet weak var senderTextField: GMENumberTextField! @IBOutlet weak var reciepientTextField: GMENumberTextField! @IBOutlet weak var transferFeeInfoLabel: UILabel! @IBOutlet weak var exchangeRateInfoLabel: UILabel! @IBOutlet private weak var forUnitToKoreanLabel: UILabel! @IBOutlet weak var youSendTitleLabel: UILabel! @IBOutlet weak var recepientGetsTitleLabel: UILabel! @IBOutlet weak var selectPaymentModeTitleLabel: UILabel! @IBOutlet weak var executeButton: UIButton! @IBOutlet weak var calculatedInfoView: UIView! @IBOutlet weak var serviceChargeView: UIStackView! @IBOutlet weak var exchangeRateView: UIStackView! var presenter: ExchangeRatesModuleInterface? var countryListTapGuesture: UITapGestureRecognizer? var selectedPaymentModeIndex = 0 var translated: Bool = false var nativeCountryCode: String? = "np" var calcBy = "" private var exchangeRateModels: [ExchangeRateModel]? { didSet { let countryCode = GMEDB.shared.user.string(.countryCode) if let defaultExchangeRate = exchangeRateModels?.filter({ ($0.countryCode ?? "").lowercased() == countryCode?.lowercased() }).first { selectedExchangeRateModel = defaultExchangeRate } else { selectedExchangeRateModel = exchangeRateModels?.filter({ ($0.countryCode ?? "").lowercased() == "az" }).first } } } private var selectedExchangeRateModel: ExchangeRateModel? { didSet { collectionView.reloadData() let code = selectedExchangeRateModel?.countryCode?.lowercased() ?? "az" let codeEnum = CountryEnum(rawValue: code) countryFlagImage.image = codeEnum?.flag countryCodeLabel.text = selectedExchangeRateModel?.currency guard let defaultAmount = codeEnum?.getDefaultRecipientAcount( currency: selectedExchangeRateModel?.currency ?? "" ) else { calcBy = "c" senderTextField.text = codeEnum?.defaultSenderAmount.likeCommaMoney() reciepientTextField.text = "" calculateExchangeRate() return } calcBy = "p" senderTextField.text = "" reciepientTextField.text = defaultAmount.likeCommaMoney() calculateExchangeRate() } } private var exchangeRateDetailModel: ExchangeRateDetailModel? { didSet { guard let model = exchangeRateDetailModel else { showExchangeRateInfomation(isHidden: true) return } showExchangeRateInfomation(isHidden: false) reciepientTextField.text = Utility.getCommaSeperatedStringWithDecimal( numberString: model.recipientAmount ?? "" ) senderTextField.text = Utility.getCommaSeperatedStringWithDecimal( numberString: model.senderAmount ?? "" ) let transferFee = model.transferFee ?? "" let currency = model.senderCurrency ?? "" transferFeeInfoLabel.text = "-\(transferFee) \(currency) (" + "transfer_fee_included_text".localized() + ")" let exchangeRate = model.exchangeRate ?? "" exchangeRateInfoLabel.text = "\(exchangeRate) " + "(" + "current_exchange_rate_text".localized() + ")" calculatedInfoView.isHidden = false guard let intExchangeRate = Double(exchangeRate) else { return } let calculatedForUnit = (1/intExchangeRate) let roundedForUnit = round((calculatedForUnit) * 10) / 10 let translated = "current_exchange_rate_text".localized() forUnitToKoreanLabel.text = "\(translated) : 1 \(selectedExchangeRateModel?.currency ?? "") = \(roundedForUnit) KRW" forUnitToKoreanLabel.layer.cornerRadius = 5 forUnitToKoreanLabel.layer.borderWidth = 1 forUnitToKoreanLabel.layer.borderColor = UIColor.themeSubBackground.cgColor } } // MARK: VC's Life cycle override func viewDidLoad() { super.viewDidLoad() setup() setupDelegates() setupNavigation() self.nativeCountryCode = GMEDB.shared.user.string(.countryCode) } override func viewWillAppear(_ animated: Bool) { super.viewWillAppear(animated) self.title = Constants().title presenter?.fetchExchangeRate() } override func viewWillDisappear(_ animated: Bool) { super.viewWillDisappear(animated) self.view.endEditing(true) } // IBActions @IBAction func calculateExchangeRate(_ sender: Any?) { calculateExchangeRate() } private func calculateExchangeRate() { let model = ExchangeRateRequestModel( senderAmount: (senderTextField.text ?? "").stringRemovingComma(), senderCurrency: "KRW", senderCountryID: "118", recipientAmount: (reciepientTextField.text ?? "").stringRemovingComma(), recipientCurrency: selectedExchangeRateModel?.currency ?? "", recipientCountryID: selectedExchangeRateModel?.countryId ?? "", recipientCountry: selectedExchangeRateModel?.country ?? "", serviceType: selectedExchangeRateModel? .availableServices? .elementAt(index: selectedPaymentModeIndex)?.id ?? "", calcBy: calcBy ) presenter?.exchangeCalculate(use: model) } @objc func showCountryList(_ sender: UITapGestureRecognizer) { DispatchQueue.main.async { self.reciepientTextField.resignFirstResponder() self.senderTextField.resignFirstResponder() } TablePresenterWireframe().openWith( delegate: self, model: exchangeRateModels, source: self ) } // other function private func setExchangeRateUI() { [backgroundViewCountryLabel1, backgroundViewCountryLabel2] .forEach { $0?.layer.cornerRadius = 5 } [exchangeBackground1, exchangeBackground2] .forEach { $0?.layer.borderWidth = 1 $0?.layer.borderColor = UIColor.themeSeparate.cgColor //init(hex: "#E0E0E0").cgColor $0?.layer.cornerRadius = 5 } let dropDownImage = #imageLiteral(resourceName: "dropdown_white").withRenderingMode(UIImage.RenderingMode.alwaysTemplate) let image = dropDownImage dropDownImageView.image = image dropDownImageView.tintColor = UIColor.white senderTextField.delegate = self reciepientTextField.delegate = self } private func showExchangeRateInfomation(isHidden flag: Bool) { calculatedInfoView.isHidden = flag calculatedInfoView.alpha = flag ? 0.0 : 1.0 if !flag { self.serviceChargeView.isHidden = false self.exchangeRateView.isHidden = false let animator = UIViewPropertyAnimator(duration: 0.5, curve: .easeIn) { self.serviceChargeView.alpha = 1.0 } animator.addCompletion { _ in let subAnimator = UIViewPropertyAnimator(duration: 0.5, curve: .easeIn) { self.exchangeRateView.alpha = 1.0 } subAnimator.startAnimation() } animator.startAnimation() } else { serviceChargeView.isHidden = true serviceChargeView.alpha = 0.0 exchangeRateView.isHidden = true exchangeRateView.alpha = 0.0 } } func showPaymentModeView() { UIView.animate(withDuration: 0.33) { self.paymentModeStackViewConstraint.constant = Constants().paymentModeHeightConstant self.paymentModeStackView.alpha = 1 self.view.layoutIfNeeded() } } private func setupTargets() { let tapGuesture = UITapGestureRecognizer(target: self, action: #selector(showCurrencyCountryPickerview)) countryListStackView.addGestureRecognizer(tapGuesture) reciepientTextField.addTarget( self, action: #selector(self.textChanged(sender:)), for: UIControl.Event.editingChanged ) senderTextField.addTarget( self, action: #selector(self.textChanged(sender:)), for: UIControl.Event.editingChanged ) } @objc private func textChanged(sender: UITextField) { switch sender { case senderTextField: reciepientTextField.text = "" calcBy = "c" senderTextField.text = Utility.getCommaSeperatedString(numberString: senderTextField.text!) case reciepientTextField: senderTextField.text = "" calcBy = "p" reciepientTextField.text = Utility.getCommaSeperatedString(numberString: reciepientTextField.text!) default: break } } @objc private func showCurrencyCountryPickerview() { DispatchQueue.main.async { self.reciepientTextField.resignFirstResponder() self.senderTextField.resignFirstResponder() } TablePresenterWireframe().openWith( tag: 1, delegate: self, model: exchangeRateModels, source: self ) } private func setupDelegates() { self.collectionView.delegate = self self.collectionView.dataSource = self } private func setup() { setupLanguage() setupTargets() setExchangeRateUI() showExchangeRateInfomation(isHidden: true) executeButton.layer.cornerRadius = 5 executeButton.backgroundColor = .themeRed senderTextField.textColor = .themeRed reciepientTextField.textColor = .themeRed backgroundViewCountryLabel1.backgroundColor = .themeBlue backgroundViewCountryLabel2.backgroundColor = .themeBlue forUnitToKoreanLabel.adjustsFontSizeToFitWidth = true } private func setupLanguage() { let constant = StringConstants() self.youSendTitleLabel.text = constant.youSendText self.recepientGetsTitleLabel.text = constant.recepientGetsText self.selectPaymentModeTitleLabel.text = "select_payment_mode_text".localized() self.executeButton.setTitle(constant.calculate, for: UIControl.State.normal) } private func setupNavigation() { self.setupNormalNavigation() } } extension ExchangeRatesViewController: UICollectionViewDelegate { func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) { self.selectedPaymentModeIndex = indexPath.row self.collectionView.reloadData() self.calculateExchangeRate(nil) } } extension ExchangeRatesViewController: UICollectionViewDataSource { func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int { return self.selectedExchangeRateModel?.availableServices?.count ?? 0 } func collectionView( _ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath ) -> UICollectionViewCell { let service = self.selectedExchangeRateModel?.availableServices?.elementAt(index: indexPath.row) guard let index = PaymentMode.init(rawValue: service?.id ?? "") else { return UICollectionViewCell() } switch index { case .bankDeposite: return configureBankDepositeCell(collectionView: collectionView, indexPath: indexPath) case .cashDelivery: return configureCashDeliveryCell(collectionView: collectionView, indexPath: indexPath) case .homeDelivery: return configureHomeDeliveryCell(collectionView: collectionView, indexPath: indexPath) case .mobileWallet: return configureWalletDeliveryCell(collectionView: collectionView, indexPath: indexPath) case .cardPayment: return configureCardPaymentCell(collectionView: collectionView, indexPath: indexPath) } } func configureBankDepositeCell( collectionView: UICollectionView, indexPath: IndexPath ) -> UICollectionViewCell { guard let cell = collectionView.dequeueReusableCell( withReuseIdentifier: "ExchangeRateCollectionViewCell", for: indexPath ) as? ExchangeRateCollectionViewCell else { return UICollectionViewCell() } cell.cellSelected = self.selectedPaymentModeIndex == indexPath.row cell.paymentServiceMethod = self.selectedExchangeRateModel?.availableServices?.elementAt( index: indexPath.row ) cell.image = #imageLiteral(resourceName: "ic_bank") cell.setup() return cell } func configureCardPaymentCell( collectionView: UICollectionView, indexPath: IndexPath ) -> UICollectionViewCell { guard let cell = collectionView.dequeueReusableCell( withReuseIdentifier: "ExchangeRateCollectionViewCell", for: indexPath ) as? ExchangeRateCollectionViewCell else { return UICollectionViewCell() } cell.cellSelected = self.selectedPaymentModeIndex == indexPath.row cell.paymentServiceMethod = self.selectedExchangeRateModel?.availableServices?.elementAt( index: indexPath.row ) cell.image = #imageLiteral(resourceName: "ic_card_payment") cell.setup() return cell } func configureWalletDeliveryCell( collectionView: UICollectionView, indexPath: IndexPath ) -> UICollectionViewCell { guard let cell = collectionView.dequeueReusableCell( withReuseIdentifier: "ExchangeRateCollectionViewCell", for: indexPath ) as? ExchangeRateCollectionViewCell else { return UICollectionViewCell() } cell.cellSelected = self.selectedPaymentModeIndex == indexPath.row cell.paymentServiceMethod = self.selectedExchangeRateModel?.availableServices?.elementAt( index: indexPath.row ) cell.image = #imageLiteral(resourceName: "wallet-transfer") cell.setup() return cell } func configureCashDeliveryCell( collectionView: UICollectionView, indexPath: IndexPath ) -> UICollectionViewCell { guard let cell = collectionView.dequeueReusableCell( withReuseIdentifier: "ExchangeRateCollectionViewCell", for: indexPath ) as? ExchangeRateCollectionViewCell else { return UICollectionViewCell() } cell.cellSelected = self.selectedPaymentModeIndex == indexPath.row cell.paymentServiceMethod = self.selectedExchangeRateModel?.availableServices?.elementAt( index: indexPath.row ) cell.image = #imageLiteral(resourceName: "ic_cash") cell.setup() return cell } func configureHomeDeliveryCell( collectionView: UICollectionView, indexPath: IndexPath ) -> UICollectionViewCell { guard let cell = collectionView.dequeueReusableCell( withReuseIdentifier: "ExchangeRateCollectionViewCell", for: indexPath ) as? ExchangeRateCollectionViewCell else { return UICollectionViewCell() } cell.cellSelected = self.selectedPaymentModeIndex == indexPath.row cell.paymentServiceMethod = self.selectedExchangeRateModel?.availableServices?.elementAt( index: indexPath.row ) cell.image = #imageLiteral(resourceName: "ic_homeDelivery") cell.setup() return cell } } extension ExchangeRatesViewController: FetchCountryCurrencyInformation, getExchangeRateInformation {} extension ExchangeRatesViewController: UITextFieldDelegate { func textFieldDidEndEditing(_ textField: UITextField) { self.calculateExchangeRate(nil) } } // MARK: ExchangeRatesViewInterface extension ExchangeRatesViewController: ExchangeRatesViewInterface { func setModel(with model: [ExchangeRateModel]?) { exchangeRateModels = model } func setModel(with model: ExchangeRateDetailModel?) { exchangeRateDetailModel = model } func setError(with error: Error) { if (error as NSError).code == -99 { alert( type: .error, message: error.localizedDescription, rightButtomTitle: "retry_text".localized(), okAction: { self.presenter?.fetchExchangeRate() } ) return } alert(type: .error, message: error.localizedDescription) } func showLoading() { showProgressHud() } func hideLoading() { hideProgressHud() } } // MARK: - TablePresenterDelegate extension ExchangeRatesViewController: TablePresenterDelegate { func tablePresenterView(_ viewController: TablePresenterViewController) -> TablePresenterConfiguration { return TablePresenterConfiguration( presenterTitle: "search_currency_text".localized(), closeButtonTitle: "cancel_text".localized(), notFoundTitle: "no_result_found_text".localized(), searchBarPlaceHolder: "search_currency_text".localized() ) } func tablePresenterView( _ viewController: TablePresenterViewController, didSelectModel model: TablePresenterProtocol? ) { showExchangeRateInfomation(isHidden: true) selectedPaymentModeIndex = 0 selectedExchangeRateModel = (model as? ExchangeRateModel) ?? selectedExchangeRateModel } }