diff --git a/ExampleApp/Views/ProductDetailViewController.swift b/ExampleApp/Views/ProductDetailViewController.swift index 0c2e9d27..6714ed95 100644 --- a/ExampleApp/Views/ProductDetailViewController.swift +++ b/ExampleApp/Views/ProductDetailViewController.swift @@ -124,6 +124,21 @@ extension ProductDetailViewController: ChoosePaymentMethodDelegate { func choosePaymentMethodDidCancel() { omiseSDK.dismiss() } + + func choosePaymentMethodDidComplete(with whiteLabelInstallmentSource: Source, token: Token) { + print("White-label installment payment Token is created with id '\(token.id)', Source id: '\(whiteLabelInstallmentSource.id)'") + omiseSDK.dismiss { + let alertController = UIAlertController( + title: "Token & Source Created", + message: "A token with id of \(token.id) and source with id of \(whiteLabelInstallmentSource.id) was successfully created. Please send this id to server to create a charge.", + preferredStyle: .alert + ) + let okAction = UIAlertAction(title: "OK", style: .cancel, handler: nil) + alertController.addAction(okAction) + self.present(alertController, animated: true, completion: nil) + } + + } } // MARK: - Custom Credit Card Form View Controller Delegate diff --git a/OmiseSDK/Resources/en.lproj/Localizable.strings b/OmiseSDK/Resources/en.lproj/Localizable.strings index 17ca2666..c7ac4e4d 100644 --- a/OmiseSDK/Resources/en.lproj/Localizable.strings +++ b/OmiseSDK/Resources/en.lproj/Localizable.strings @@ -20,6 +20,7 @@ "SourceType.installment_scb" = "Siam Commercial Bank"; "SourceType.installment_ttb" = "TMBThanachart Bank"; "SourceType.installment_uob" = "United Overseas Bank"; +"SourceType.installment_wlb_ktc" = "KTC"; "SourceType.internet_banking_bay" = "Bank of Ayudhya"; "SourceType.internet_banking_bbl" = "Bangkok Bank"; "SourceType.paynow" = "PayNow"; diff --git a/OmiseSDK/Resources/ja.lproj/Localizable.strings b/OmiseSDK/Resources/ja.lproj/Localizable.strings index d9980345..ec0913eb 100644 --- a/OmiseSDK/Resources/ja.lproj/Localizable.strings +++ b/OmiseSDK/Resources/ja.lproj/Localizable.strings @@ -20,6 +20,7 @@ "SourceType.installment_scb" = "サイアム・コマーシャル銀行"; "SourceType.installment_ttb" = "TMBタナチャート銀行"; "SourceType.installment_uob" = "ユナイテッド・オーバーシーズ銀行"; +"SourceType.installment_wlb_ktc" = "クルンタイカード"; "SourceType.internet_banking_bay" = "アユタヤ銀行"; "SourceType.internet_banking_bbl" = "バンコク銀行"; "SourceType.paynow" = "PayNow"; diff --git a/OmiseSDK/Resources/th.lproj/Localizable.strings b/OmiseSDK/Resources/th.lproj/Localizable.strings index dd24bd49..54efcc61 100644 --- a/OmiseSDK/Resources/th.lproj/Localizable.strings +++ b/OmiseSDK/Resources/th.lproj/Localizable.strings @@ -20,6 +20,7 @@ "SourceType.installment_scb" = "ธนาคารไทยพาณิชย์"; "SourceType.installment_ttb" = "ธนาคารทีเอ็มบีธนชาต"; "SourceType.installment_uob" = "ธนาคารยูโอบี"; +"SourceType.installment_wlb_ktc" = "เคทีซี"; "SourceType.internet_banking_bay" = "ธนาคารกรุงศรีอยุธยา"; "SourceType.internet_banking_bbl" = "ธนาคารกรุงเทพ"; "SourceType.paynow" = "เพย์นาว"; diff --git a/OmiseSDK/Sources/ChoosePaymentMethodDelegate.swift b/OmiseSDK/Sources/ChoosePaymentMethodDelegate.swift new file mode 100644 index 00000000..624a755d --- /dev/null +++ b/OmiseSDK/Sources/ChoosePaymentMethodDelegate.swift @@ -0,0 +1,10 @@ +import Foundation + +/// Omise Payment delegate protocol is required to process payment results +public protocol ChoosePaymentMethodDelegate: AnyObject { + func choosePaymentMethodDidComplete(with source: Source) + func choosePaymentMethodDidComplete(with token: Token) + func choosePaymentMethodDidComplete(with whiteLabelInstallmentSource: Source, token: Token) + func choosePaymentMethodDidComplete(with error: Error) + func choosePaymentMethodDidCancel() +} diff --git a/OmiseSDK/Sources/OmiseAPI/JSON Models/Source/Source.Payment.Installment.swift b/OmiseSDK/Sources/OmiseAPI/JSON Models/Source/Source.Payment.Installment.swift index 91ba0a5c..9d6035da 100644 --- a/OmiseSDK/Sources/OmiseAPI/JSON Models/Source/Source.Payment.Installment.swift +++ b/OmiseSDK/Sources/OmiseAPI/JSON Models/Source/Source.Payment.Installment.swift @@ -50,7 +50,7 @@ extension Source.Payment.Installment { return [ 4, 6, 8, 9, 10 ] case .installmentMBB: return [ 6, 12, 18, 24 ] - case .installmentKTC: + case .installmentKTC, .installmentWhiteLabelKTC: return [ 3, 4, 5, 6, 7, 8, 9, 10 ] case .installmentKBank: return [ 3, 4, 6, 10 ] diff --git a/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType+Installments.swift b/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType+Installments.swift index 74e3e886..2e64b15e 100644 --- a/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType+Installments.swift +++ b/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType+Installments.swift @@ -12,10 +12,20 @@ extension SourceType { .installmentSCB, .installmentTTB, .installmentUOB + ] + whiteLabelInstallments + } + + public static var whiteLabelInstallments: [SourceType] { + [ + .installmentWhiteLabelKTC ] } var isInstallment: Bool { Self.installments.contains(self) } + + var isWhiteLabelInstallment: Bool { + Self.whiteLabelInstallments.contains(self) + } } diff --git a/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType.swift b/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType.swift index 4985486f..a710d063 100644 --- a/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType.swift +++ b/OmiseSDK/Sources/OmiseAPI/SourceType/SourceType.swift @@ -50,6 +50,8 @@ public enum SourceType: String, Codable, CaseIterable { case installmentTTB = "installment_ttb" /// United Overseas Bank (UOB) https://docs.opn.ooo/installment-payments case installmentUOB = "installment_uob" + /// Krungthai Card (KTC) https://docs.opn.ooo/installment-white-label-payments + case installmentWhiteLabelKTC = "installment_wlb_ktc" /// Bank of Ayudhya (Krungsri) https://docs.opn.ooo/internet-banking case internetBankingBAY = "internet_banking_bay" /// Bangkok Bank https://docs.opn.ooo/internet-banking diff --git a/OmiseSDK/Sources/OmiseSDK.swift b/OmiseSDK/Sources/OmiseSDK.swift index 63d80edd..c070f75e 100644 --- a/OmiseSDK/Sources/OmiseSDK.swift +++ b/OmiseSDK/Sources/OmiseSDK.swift @@ -1,26 +1,6 @@ import Foundation import UIKit -/// Omise Payment delegate protocol is required to process payment results -public protocol ChoosePaymentMethodDelegate: AnyObject { - func choosePaymentMethodDidComplete(with source: Source) - func choosePaymentMethodDidComplete(with token: Token) - func choosePaymentMethodDidComplete(with error: Error) - func choosePaymentMethodDidCancel() -} - -/// Payment Results -public enum PaymentResult { - /// Payment completed with Card payment and contains Token object - case token(Token) - /// Payment completed with Source payment and contains Source object - case source(Source) - /// Payment completed with Error - case error(Error) - /// Payment was cancelled by user - case cancel -} - public class OmiseSDK { /// Static container that allows to assign a shared instance of OmiseSDK to be used as a Singleton object public static var shared = OmiseSDK(publicKey: "pkey_") diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator+Helpers.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator+Helpers.swift index 7b667a60..8a1c8dfe 100644 --- a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator+Helpers.swift +++ b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator+Helpers.swift @@ -64,6 +64,36 @@ extension ChoosePaymentCoordinator { completion() } } + + func processWhiteLabelInstallmentPayment(_ payment: Source.Payment, card: CreateTokenPayload.Card, completion: @escaping () -> Void) { + + guard let delegate = choosePaymentMethodDelegate else { return } + let sourcePayload = CreateSourcePayload( + amount: amount, + currency: currency, + details: payment + ) + + let tokenPayload = CreateTokenPayload(card: card) + + client.createSource(payload: sourcePayload) { [weak self, weak delegate, tokenPayload] result in + guard let self = self else { return } + switch result { + case .failure(let error): + self.processError(error) + case .success(let source): + self.client.createToken(payload: tokenPayload) { [weak self, weak delegate] result in + switch result { + case .success(let token): + delegate?.choosePaymentMethodDidComplete(with: source, token: token) + case .failure(let error): + self?.processError(error) + } + completion() + } + } + } + } } extension ChoosePaymentCoordinator { diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator.swift index 72ccc8e8..0959bf50 100644 --- a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator.swift +++ b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ChoosePaymentCoordinator.swift @@ -69,8 +69,8 @@ class ChoosePaymentCoordinator: NSObject, ViewAttachable { } /// Creates Credit Carc Payment screen and attach current flow object inside created controller to be deallocated together - func createCreditCardPaymentController() -> CreditCardPaymentController { - let viewModel = CreditCardPaymentViewModel(currentCountry: currentCountry, delegate: self) + func createCreditCardPaymentController(paymentType: CreditCardPaymentOption = .card) -> CreditCardPaymentController { + let viewModel = CreditCardPaymentViewModel(currentCountry: currentCountry, paymentType: paymentType, delegate: self) let viewController = CreditCardPaymentController(nibName: nil, bundle: .omiseSDK) viewController.viewModel = viewModel viewController.title = PaymentMethod.creditCard.localizedTitle @@ -105,10 +105,16 @@ class ChoosePaymentCoordinator: NSObject, ViewAttachable { /// Creates Installement screen and attach current flow object inside created controller to be deallocated together func createInstallmentController() -> SelectPaymentController { - let sourceTypes = client.latestLoadedCapability?.availableSourceTypes(SourceType.installments) + var sourceTypes = client.latestLoadedCapability?.availableSourceTypes(SourceType.installments) ?? [] + + // Remove .installmentKTC if .installmentWhiteLabelKTC is present + if sourceTypes.contains(.installmentWhiteLabelKTC) { + sourceTypes.removeAll { $0 == .installmentKTC } + } + let viewModel = SelectSourceTypePaymentViewModel( title: PaymentMethod.installment.localizedTitle, - sourceTypes: sourceTypes ?? [], + sourceTypes: sourceTypes, delegate: self ) @@ -191,10 +197,19 @@ extension ChoosePaymentCoordinator: FPXPaymentFormControllerDelegate { } extension ChoosePaymentCoordinator: CreditCardPaymentDelegate { - func didSelectCardPayment(_ card: CreateTokenPayload.Card, completion: @escaping () -> Void) { - processPayment(card, completion: completion) + func didSelectCardPayment( + paymentType: CreditCardPaymentOption, + card: CreateTokenPayload.Card, + completion: @escaping () -> Void + ) { + switch paymentType { + case .card: + processPayment(card, completion: completion) + case .whiteLabelInstallment(let payment): + processWhiteLabelInstallmentPayment(payment, card: card, completion: completion) + } } - + func didCancelCardPayment() { didCancelPayment() } @@ -249,6 +264,12 @@ extension ChoosePaymentCoordinator: SelectSourceTypeDelegate { extension ChoosePaymentCoordinator: SelectSourcePaymentDelegate { func didSelectSourcePayment(_ payment: Source.Payment, completion: @escaping () -> Void) { - processPayment(payment, completion: completion) + if payment.sourceType.isWhiteLabelInstallment { + navigate(to: createCreditCardPaymentController( + paymentType: .whiteLabelInstallment(payment: payment) + )) + } else { + processPayment(payment, completion: completion) + } } } diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectDuitNowOBWBankViewModel.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectDuitNowOBWBankViewModel.swift similarity index 100% rename from OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectDuitNowOBWBankViewModel.swift rename to OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectDuitNowOBWBankViewModel.swift diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectFPXBankViewModel.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectFPXBankViewModel.swift similarity index 100% rename from OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectFPXBankViewModel.swift rename to OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectFPXBankViewModel.swift diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectInstallmentTermsViewModel.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectInstallmentTermsViewModel.swift similarity index 100% rename from OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectInstallmentTermsViewModel.swift rename to OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectInstallmentTermsViewModel.swift diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectPaymentMethodViewModel.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectPaymentMethodViewModel.swift similarity index 100% rename from OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectPaymentMethodViewModel.swift rename to OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectPaymentMethodViewModel.swift diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectSourceTypePaymentViewModel.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectSourceTypePaymentViewModel.swift similarity index 100% rename from OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/SelectSourceTypePaymentViewModel.swift rename to OmiseSDK/Sources/Views/Screens/Choose Payment Methods/Select Payment From Lists/ViewModels/SelectSourceTypePaymentViewModel.swift diff --git a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ViewPresentable/SourceType+ViewPresentable.swift b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ViewPresentable/SourceType+ViewPresentable.swift index b209b36e..5cc92f51 100644 --- a/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ViewPresentable/SourceType+ViewPresentable.swift +++ b/OmiseSDK/Sources/Views/Screens/Choose Payment Methods/ViewPresentable/SourceType+ViewPresentable.swift @@ -64,6 +64,8 @@ extension SourceType: ViewPresentable { return "TMBThanachart Bank" case .installmentUOB: return "United Overseas Bank" + case .installmentWhiteLabelKTC: + return "Krungthai Card (KTC)" case .internetBankingBAY: return "Bank of Ayudhya" case .internetBankingBBL: @@ -151,7 +153,7 @@ extension SourceType: ViewPresentable { return "First Choice" case .installmentKBank: return "KBANK" - case .installmentKTC: + case .installmentKTC, .installmentWhiteLabelKTC: return "KTC" case .installmentMBB: return "FPX/maybank" diff --git a/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentDelegate.swift b/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentDelegate.swift index f05ef430..36f3f54e 100644 --- a/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentDelegate.swift +++ b/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentDelegate.swift @@ -1,6 +1,6 @@ import Foundation protocol CreditCardPaymentDelegate: AnyObject { - func didSelectCardPayment(_ card: CreateTokenPayload.Card, completion: @escaping () -> Void) + func didSelectCardPayment(paymentType: CreditCardPaymentOption, card: CreateTokenPayload.Card, completion: @escaping () -> Void) func didCancelCardPayment() } diff --git a/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentViewModel.swift b/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentViewModel.swift index e1613ca0..78ab2a36 100644 --- a/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentViewModel.swift +++ b/OmiseSDK/Sources/Views/Screens/Credit Card Payment/CreditCardPaymentViewModel.swift @@ -1,9 +1,17 @@ import Foundation import os.log +enum CreditCardPaymentOption { + case card + case whiteLabelInstallment(payment: Source.Payment) +} + class CreditCardPaymentViewModel: CreditCardPaymentViewModelProtocol, CountryListViewModelProtocol { + + let paymentType: CreditCardPaymentOption + var addressFields: [AddressField] = [.address, .city, .state, .postalCode] - + var fieldForShippingAddressHeader: AddressField? var isAddressFieldsVisible: Bool { @@ -18,9 +26,10 @@ class CreditCardPaymentViewModel: CreditCardPaymentViewModelProtocol, CountryLis private weak var delegate: CreditCardPaymentDelegate? - init(currentCountry: Country?, delegate: CreditCardPaymentDelegate?) { + init(currentCountry: Country?, paymentType: CreditCardPaymentOption, delegate: CreditCardPaymentDelegate?) { self.delegate = delegate self.selectedCountry = currentCountry + self.paymentType = paymentType } // MARK: CountryListViewModelProtocol @@ -62,6 +71,6 @@ class CreditCardPaymentViewModel: CreditCardPaymentViewModelProtocol, CountryLis postalCode: viewContext[.postalCode] ) - delegate?.didSelectCardPayment(card, completion: completion) + delegate?.didSelectCardPayment(paymentType: paymentType, card: card, completion: completion) } } diff --git a/dev.xcodeproj/project.pbxproj b/dev.xcodeproj/project.pbxproj index 97b51833..b873a4e1 100644 --- a/dev.xcodeproj/project.pbxproj +++ b/dev.xcodeproj/project.pbxproj @@ -87,6 +87,7 @@ 756C8F262A40698600D53059 /* TextFieldView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 756C8F252A40698600D53059 /* TextFieldView.swift */; }; 757B0A742AD71E3100DEAE8F /* OmiseUnitTestKit in Frameworks */ = {isa = PBXBuildFile; productRef = 757B0A732AD71E3100DEAE8F /* OmiseUnitTestKit */; }; 757B0A752AD71E3100DEAE8F /* OmiseUnitTestKit in Embed Frameworks */ = {isa = PBXBuildFile; productRef = 757B0A732AD71E3100DEAE8F /* OmiseUnitTestKit */; settings = {ATTRIBUTES = (CodeSignOnCopy, ); }; }; + 757E14352BD61DFE005F08AD /* ChoosePaymentMethodDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 757E14342BD61DFE005F08AD /* ChoosePaymentMethodDelegate.swift */; }; 7588011E2BAAB37C00F02934 /* AppDeeplink.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7588011D2BAAB37C00F02934 /* AppDeeplink.swift */; }; 758801202BAAC70200F02934 /* URL+Helpers.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7588011F2BAAC70200F02934 /* URL+Helpers.swift */; }; 759856242A286C880087B605 /* UIScrollView+Helpers.swift in Sources */ = {isa = PBXBuildFile; fileRef = 759856232A286C880087B605 /* UIScrollView+Helpers.swift */; }; @@ -335,6 +336,7 @@ 756C8F252A40698600D53059 /* TextFieldView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TextFieldView.swift; sourceTree = ""; }; 757B0A712AD71D7B00DEAE8F /* OmiseSwiftUIKit */ = {isa = PBXFileReference; lastKnownFileType = text; name = OmiseSwiftUIKit; path = Helpers/OmiseSwiftUIKit; sourceTree = SOURCE_ROOT; }; 757B0A722AD71DCD00DEAE8F /* OmiseUnitTestKit */ = {isa = PBXFileReference; lastKnownFileType = text; name = OmiseUnitTestKit; path = Helpers/OmiseUnitTestKit; sourceTree = SOURCE_ROOT; }; + 757E14342BD61DFE005F08AD /* ChoosePaymentMethodDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ChoosePaymentMethodDelegate.swift; sourceTree = ""; }; 7588011D2BAAB37C00F02934 /* AppDeeplink.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDeeplink.swift; sourceTree = ""; }; 7588011F2BAAC70200F02934 /* URL+Helpers.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "URL+Helpers.swift"; sourceTree = ""; }; 759856232A286C880087B605 /* UIScrollView+Helpers.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = "UIScrollView+Helpers.swift"; sourceTree = ""; }; @@ -693,6 +695,18 @@ path = "UI Extensions"; sourceTree = ""; }; + 757E14332BD61DBB005F08AD /* ViewModels */ = { + isa = PBXGroup; + children = ( + 75D13DC02B8400610073A831 /* SelectPaymentMethodViewModel.swift */, + 75D13DC82B8529790073A831 /* SelectSourceTypePaymentViewModel.swift */, + 75D13DCC2B8536B10073A831 /* SelectInstallmentTermsViewModel.swift */, + 7501266F2B8A490000ED5E14 /* SelectFPXBankViewModel.swift */, + 750126732B8A580500ED5E14 /* SelectDuitNowOBWBankViewModel.swift */, + ); + path = ViewModels; + sourceTree = ""; + }; 75CFC4EF2B753AB900422A8F /* JSON Models */ = { isa = PBXGroup; children = ( @@ -857,13 +871,9 @@ 75D13DF62B866C650073A831 /* Select Payment From Lists */ = { isa = PBXGroup; children = ( + 757E14332BD61DBB005F08AD /* ViewModels */, 75D13DDC2B8658660073A831 /* SelectPaymentPresentableProtocol.swift */, 75D13DBA2B83FB470073A831 /* SelectPaymentController.swift */, - 75D13DC02B8400610073A831 /* SelectPaymentMethodViewModel.swift */, - 75D13DC82B8529790073A831 /* SelectSourceTypePaymentViewModel.swift */, - 75D13DCC2B8536B10073A831 /* SelectInstallmentTermsViewModel.swift */, - 7501266F2B8A490000ED5E14 /* SelectFPXBankViewModel.swift */, - 750126732B8A580500ED5E14 /* SelectDuitNowOBWBankViewModel.swift */, ); path = "Select Payment From Lists"; sourceTree = ""; @@ -972,6 +982,7 @@ 75E0EBBF2B7D13D200E3198A /* OmiseAPI */, 75D13DEE2B866BCA0073A831 /* Views */, 75CFC4D12B73AFD500422A8F /* OmiseSDK.swift */, + 757E14342BD61DFE005F08AD /* ChoosePaymentMethodDelegate.swift */, 755CD9222BA2000600E8FCDA /* ClientProtocol.swift */, ); path = Sources; @@ -1441,6 +1452,7 @@ 75CFC4DD2B73F75C00422A8F /* OmiseAPI.swift in Sources */, 75348D4E29C3FCC70008C8A3 /* Bundle+OmiseSDK.swift in Sources */, 755CD9232BA2000600E8FCDA /* ClientProtocol.swift in Sources */, + 757E14352BD61DFE005F08AD /* ChoosePaymentMethodDelegate.swift in Sources */, 75E0EB9D2B7BD00F00E3198A /* CardBrand.swift in Sources */, 75E0EB9A2B7BD00F00E3198A /* Currency.swift in Sources */, 75405A9C2A266F50008C21F6 /* AtomePaymentFormViewModel.swift in Sources */,