summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorSteffen Ernst <steffen.ernst@mullvad.net>2025-01-20 11:42:40 +0100
committerSteffen Ernst <steffen.ernst@mullvad.net>2025-01-20 15:54:12 +0100
commit91cb3e5038e635b9a33e7f1db275a2311956b03d (patch)
tree90cfc7875ae8b537e079a5835422427883be7f32
parent9916d4009ef75f0d4c98b6869e3e0c8e34c2945e (diff)
downloadmullvadvpn-91cb3e5038e635b9a33e7f1db275a2311956b03d.tar.xz
mullvadvpn-91cb3e5038e635b9a33e7f1db275a2311956b03d.zip
Simplify code to create purchase action sheet
-rw-r--r--ios/MullvadVPN.xcodeproj/project.pbxproj4
-rw-r--r--ios/MullvadVPN/Coordinators/AccountCoordinator.swift34
-rw-r--r--ios/MullvadVPN/Coordinators/OutOfTimeCoordinator.swift30
-rw-r--r--ios/MullvadVPN/Coordinators/WelcomeCoordinator.swift43
-rw-r--r--ios/MullvadVPN/Extensions/UIAlertController+InAppPurchase.swift48
-rw-r--r--ios/MullvadVPN/View controllers/CreationAccount/Welcome/WelcomeViewController.swift4
6 files changed, 67 insertions, 96 deletions
diff --git a/ios/MullvadVPN.xcodeproj/project.pbxproj b/ios/MullvadVPN.xcodeproj/project.pbxproj
index 32abb7f779..5025450b41 100644
--- a/ios/MullvadVPN.xcodeproj/project.pbxproj
+++ b/ios/MullvadVPN.xcodeproj/project.pbxproj
@@ -1054,6 +1054,7 @@
F0F56B092C0E058A009D676B /* ObserverList.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58CC40EE24A601900019D96E /* ObserverList.swift */; };
F0FADDEA2BE90AAA000D0B02 /* LaunchArguments.swift in Sources */ = {isa = PBXBuildFile; fileRef = F0F1EF8C2BE8FF0A00CED01D /* LaunchArguments.swift */; };
F0FADDEC2BE90AB0000D0B02 /* LaunchArguments.swift in Sources */ = {isa = PBXBuildFile; fileRef = F0F1EF8C2BE8FF0A00CED01D /* LaunchArguments.swift */; };
+ F95C1C252D3E5E8E00EBE769 /* UIAlertController+InAppPurchase.swift in Sources */ = {isa = PBXBuildFile; fileRef = F95C1C242D3E5E7A00EBE769 /* UIAlertController+InAppPurchase.swift */; };
F998EFF82D359C4600D88D01 /* SKProduct+Formatting.swift in Sources */ = {isa = PBXBuildFile; fileRef = 58FD5BEF24238EB300112C88 /* SKProduct+Formatting.swift */; };
F998EFFA2D3656BA00D88D01 /* SKProduct+Sorting.swift in Sources */ = {isa = PBXBuildFile; fileRef = F998EFF92D3656B100D88D01 /* SKProduct+Sorting.swift */; };
/* End PBXBuildFile section */
@@ -2311,6 +2312,7 @@
F0F316182BF3572B0078DBCF /* RelaySelectorResult.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RelaySelectorResult.swift; sourceTree = "<group>"; };
F0F3161A2BF358590078DBCF /* NoRelaysSatisfyingConstraintsError.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = NoRelaysSatisfyingConstraintsError.swift; sourceTree = "<group>"; };
F0FBD98E2C4A60CC00EE5323 /* KeyExchangingResultStub.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = KeyExchangingResultStub.swift; sourceTree = "<group>"; };
+ F95C1C242D3E5E7A00EBE769 /* UIAlertController+InAppPurchase.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "UIAlertController+InAppPurchase.swift"; sourceTree = "<group>"; };
F998EFF92D3656B100D88D01 /* SKProduct+Sorting.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "SKProduct+Sorting.swift"; sourceTree = "<group>"; };
/* End PBXFileReference section */
@@ -3157,6 +3159,7 @@
E158B35F285381C60002F069 /* String+AccountFormatting.swift */,
7A09C98029D99215000C2CAC /* String+FuzzyMatch.swift */,
5807E2BF2432038B00F5FF30 /* String+Helpers.swift */,
+ F95C1C242D3E5E7A00EBE769 /* UIAlertController+InAppPurchase.swift */,
58CEB2F82AFD136E00E6E088 /* UIBackgroundConfiguration+Extensions.swift */,
5891BF5025E66B1E006D6FB0 /* UIBarButtonItem+KeyboardNavigation.swift */,
587CBFE222807F530028DED3 /* UIColor+Helpers.swift */,
@@ -6179,6 +6182,7 @@
A9E034642ABB302000E59A5A /* UIEdgeInsets+Extensions.swift in Sources */,
58CEB2E92AFBBA4A00E6E088 /* AddAccessMethodCoordinator.swift in Sources */,
58DFF7D02B02560400F864E0 /* NSAttributedString+Extensions.swift in Sources */,
+ F95C1C252D3E5E8E00EBE769 /* UIAlertController+InAppPurchase.swift in Sources */,
58E0A98827C8F46300FE6BDD /* Tunnel.swift in Sources */,
7A12D0762B062D5C00E9602D /* URLSessionProtocol.swift in Sources */,
58ACF64F26567A7100ACE4B7 /* CustomSwitchContainer.swift in Sources */,
diff --git a/ios/MullvadVPN/Coordinators/AccountCoordinator.swift b/ios/MullvadVPN/Coordinators/AccountCoordinator.swift
index 7b238e53b4..e8f87401ec 100644
--- a/ios/MullvadVPN/Coordinators/AccountCoordinator.swift
+++ b/ios/MullvadVPN/Coordinators/AccountCoordinator.swift
@@ -70,7 +70,7 @@ final class AccountCoordinator: Coordinator, Presentable, Presenting, @unchecked
showRestorePurchasesInfo()
case let .showPurchaseOptions(details):
showPurchaseOptions(
- availableProducts: details.products,
+ products: details.products,
accountNumber: details.accountNumber,
didRequestPurchase: details.didRequestPurchase
)
@@ -80,39 +80,11 @@ final class AccountCoordinator: Coordinator, Presentable, Presenting, @unchecked
}
func showPurchaseOptions(
- availableProducts: [SKProduct],
+ products: [SKProduct],
accountNumber: String,
didRequestPurchase: @escaping (_ product: SKProduct) -> Void
) {
- let localizedString = NSLocalizedString(
- "ADD_TIME",
- tableName: "Welcome",
- value: "Add Time",
- comment: ""
- )
- let alert = UIAlertController(title: localizedString, message: nil, preferredStyle: .actionSheet)
- availableProducts.sortedByPrice().forEach { product in
- guard let localizedTitle = product.customLocalizedTitle else {
- return
- }
- let action = UIAlertAction(title: localizedTitle, style: .default, handler: { _ in
- alert.dismiss(animated: true, completion: {
- didRequestPurchase(product)
- })
- })
- action
- .accessibilityIdentifier =
- "\(AccessibilityIdentifier.purchaseButton.asString)_\(product.productIdentifier)"
- alert.addAction(action)
- }
- let cancelAction = UIAlertAction(title: NSLocalizedString(
- "PRODUCT_LIST_CANCEL_BUTTON",
- tableName: "Welcome",
- value: "Cancel",
- comment: ""
- ), style: .cancel)
- cancelAction.accessibilityIdentifier = AccessibilityIdentifier.cancelPurchaseListButton.asString
- alert.addAction(cancelAction)
+ let alert = UIAlertController.showInAppPurchaseAlert(products: products, didRequestPurchase: didRequestPurchase)
presentationContext.present(alert, animated: true)
}
diff --git a/ios/MullvadVPN/Coordinators/OutOfTimeCoordinator.swift b/ios/MullvadVPN/Coordinators/OutOfTimeCoordinator.swift
index ccf8e442c0..003d88d2cc 100644
--- a/ios/MullvadVPN/Coordinators/OutOfTimeCoordinator.swift
+++ b/ios/MullvadVPN/Coordinators/OutOfTimeCoordinator.swift
@@ -89,35 +89,7 @@ class OutOfTimeCoordinator: Coordinator, Presenting, @preconcurrency OutOfTimeVi
products: [SKProduct],
didRequestPurchase: @escaping (SKProduct) -> Void
) {
- let localizedString = NSLocalizedString(
- "ADD_TIME_BUTTON",
- tableName: "Welcome",
- value: "Add Time",
- comment: ""
- )
- let alert = UIAlertController(title: localizedString, message: nil, preferredStyle: .actionSheet)
- products.sortedByPrice().forEach { product in
- guard let localizedTitle = product.customLocalizedTitle else {
- return
- }
- let action = UIAlertAction(title: localizedTitle, style: .default, handler: { _ in
- alert.dismiss(animated: true, completion: {
- didRequestPurchase(product)
- })
- })
- action
- .accessibilityIdentifier =
- "\(AccessibilityIdentifier.purchaseButton.asString)_\(product.productIdentifier)"
- alert.addAction(action)
- }
- let cancelAction = UIAlertAction(title: NSLocalizedString(
- "PRODUCT_LIST_CANCEL_BUTTON",
- tableName: "Welcome",
- value: "Cancel",
- comment: ""
- ), style: .cancel)
- cancelAction.accessibilityIdentifier = AccessibilityIdentifier.cancelPurchaseListButton.asString
- alert.addAction(cancelAction)
+ let alert = UIAlertController.showInAppPurchaseAlert(products: products, didRequestPurchase: didRequestPurchase)
presentationContext.present(alert, animated: true)
}
diff --git a/ios/MullvadVPN/Coordinators/WelcomeCoordinator.swift b/ios/MullvadVPN/Coordinators/WelcomeCoordinator.swift
index 0c1fc7c9df..b7af509df5 100644
--- a/ios/MullvadVPN/Coordinators/WelcomeCoordinator.swift
+++ b/ios/MullvadVPN/Coordinators/WelcomeCoordinator.swift
@@ -152,42 +152,17 @@ extension WelcomeCoordinator: @preconcurrency WelcomeViewControllerDelegate {
func didRequestToViewPurchaseOptions(
controller: WelcomeViewController,
- availableProducts: [SKProduct],
+ products: [SKProduct],
accountNumber: String
) {
- let localizedString = NSLocalizedString(
- "ADD_TIME_BUTTON",
- tableName: "Welcome",
- value: "Add Time",
- comment: ""
- )
- let alert = UIAlertController(title: localizedString, message: nil, preferredStyle: .actionSheet)
- availableProducts.sortedByPrice().forEach { product in
- guard let localizedTitle = product.customLocalizedTitle else {
- return
- }
- let action = UIAlertAction(title: localizedTitle, style: .default, handler: { _ in
- alert.dismiss(animated: true, completion: {
- self.didRequestToPurchaseCredit(
- controller: controller,
- accountNumber: accountNumber,
- product: product
- )
- })
- })
- action
- .accessibilityIdentifier =
- "\(AccessibilityIdentifier.purchaseButton.asString)_\(product.productIdentifier)"
- alert.addAction(action)
- }
- let cancelAction = UIAlertAction(title: NSLocalizedString(
- "PRODUCT_LIST_CANCEL_BUTTON",
- tableName: "Welcome",
- value: "Cancel",
- comment: ""
- ), style: .cancel)
- cancelAction.accessibilityIdentifier = AccessibilityIdentifier.cancelPurchaseListButton.asString
- alert.addAction(cancelAction)
+ let alert = UIAlertController.showInAppPurchaseAlert(products: products, didRequestPurchase: { product in
+ self.didRequestToPurchaseCredit(
+ controller: controller,
+ accountNumber: accountNumber,
+ product: product
+ )
+ })
+
presentationContext.present(alert, animated: true)
}
diff --git a/ios/MullvadVPN/Extensions/UIAlertController+InAppPurchase.swift b/ios/MullvadVPN/Extensions/UIAlertController+InAppPurchase.swift
new file mode 100644
index 0000000000..b94b457b5a
--- /dev/null
+++ b/ios/MullvadVPN/Extensions/UIAlertController+InAppPurchase.swift
@@ -0,0 +1,48 @@
+//
+// UIAlertController+InAppPurchase.swift
+// MullvadVPN
+//
+// Created by Steffen Ernst on 2025-01-20.
+// Copyright © 2025 Mullvad VPN AB. All rights reserved.
+//
+
+import StoreKit
+import UIKit
+
+extension UIAlertController {
+ public static func showInAppPurchaseAlert(
+ products: [SKProduct],
+ didRequestPurchase: @escaping (SKProduct) -> Void
+ ) -> UIAlertController {
+ let localizedString = NSLocalizedString(
+ "ADD_TIME_BUTTON",
+ tableName: "Welcome",
+ value: "Add Time",
+ comment: ""
+ )
+ let alert = UIAlertController(title: localizedString, message: nil, preferredStyle: .actionSheet)
+ products.sortedByPrice().forEach { product in
+ guard let localizedTitle = product.customLocalizedTitle else {
+ return
+ }
+ let action = UIAlertAction(title: localizedTitle, style: .default, handler: { _ in
+ alert.dismiss(animated: true, completion: {
+ didRequestPurchase(product)
+ })
+ })
+ action
+ .accessibilityIdentifier =
+ "\(AccessibilityIdentifier.purchaseButton.asString)_\(product.productIdentifier)"
+ alert.addAction(action)
+ }
+ let cancelAction = UIAlertAction(title: NSLocalizedString(
+ "PRODUCT_LIST_CANCEL_BUTTON",
+ tableName: "Welcome",
+ value: "Cancel",
+ comment: ""
+ ), style: .cancel)
+ cancelAction.accessibilityIdentifier = AccessibilityIdentifier.cancelPurchaseListButton.asString
+ alert.addAction(cancelAction)
+ return alert
+ }
+}
diff --git a/ios/MullvadVPN/View controllers/CreationAccount/Welcome/WelcomeViewController.swift b/ios/MullvadVPN/View controllers/CreationAccount/Welcome/WelcomeViewController.swift
index 5b19fb073e..70911810e0 100644
--- a/ios/MullvadVPN/View controllers/CreationAccount/Welcome/WelcomeViewController.swift
+++ b/ios/MullvadVPN/View controllers/CreationAccount/Welcome/WelcomeViewController.swift
@@ -14,7 +14,7 @@ protocol WelcomeViewControllerDelegate: AnyObject {
func didRequestToShowInfo(controller: WelcomeViewController)
func didRequestToViewPurchaseOptions(
controller: WelcomeViewController,
- availableProducts: [SKProduct],
+ products: [SKProduct],
accountNumber: String
)
func didRequestToShowFailToFetchProducts(controller: WelcomeViewController)
@@ -100,7 +100,7 @@ extension WelcomeViewController: @preconcurrency WelcomeContentViewDelegate {
if !products.isEmpty {
delegate?.didRequestToViewPurchaseOptions(
controller: self,
- availableProducts: products,
+ products: products,
accountNumber: interactor.accountNumber
)
} else {