taler-ios

iOS apps for GNU Taler (wallet)
Log | Files | Refs | README | LICENSE

commit 4246c7d026046524c17de63bc6ac9066413b6ee5
parent 99687f35c1bea0745ae978ecf22dd56afd3d2be1
Author: Marc Stibane <marc@taler.net>
Date:   Sun, 14 Jun 2026 21:57:51 +0200

Eliminate PaymentDone

Diffstat:
DTalerWallet1/Views/Sheets/Payment/PaymentDone.swift | 74--------------------------------------------------------------------------
MTalerWallet1/Views/Sheets/Payment/PaymentView.swift | 28+++++++++-------------------
MTalerWallet1/Views/Transactions/TransactionSummaryList.swift | 51+++++++++++++++++++++++++++++++++++++++++++++------
3 files changed, 54 insertions(+), 99 deletions(-)

diff --git a/TalerWallet1/Views/Sheets/Payment/PaymentDone.swift b/TalerWallet1/Views/Sheets/Payment/PaymentDone.swift @@ -1,74 +0,0 @@ -/* - * This file is part of GNU Taler, ©2022-26 Taler Systems S.A. - * See LICENSE.md - */ -/** - * @author Marc Stibane - */ -import SwiftUI -import SymLog - -struct PaymentDone: View { - private let symLog = SymLogV(0) - let stack: CallStack - let url: URL -// let scope: ScopeInfo? - let transactionId: String - let choiceIndex: Int - - @EnvironmentObject private var controller: Controller - @EnvironmentObject private var model: WalletModel - - @State private var paymentDone: Bool = false - @State private var paymentPending: Bool = false - @State private var talerTX: TalerTransaction = TalerTransaction(dummyCurrency: DEMOCURRENCY) - - @MainActor - private func viewDidLoad() async { - if let confirmPayResult = try? await model.confirmPay(transactionId, - choiceIndex: choiceIndex) { -// symLog.log(confirmPayResult as Any) - if confirmPayResult.type == "done" { - controller.removeURL(url) - paymentDone = true - } else { - controller.removeURL(url) // TODO: pending might fail - in which case we might want to try again - paymentPending = true - } - } - } - - var body: some View { -#if PRINT_CHANGES - let _ = Self._printChanges() - let _ = symLog.vlog() // just to get the # to compare it with .onAppear & onDisappear -#endif - ZStack { - if paymentDone || paymentPending { -// let navTitle = paymentDone ? String(localized: "Paid", comment: "Title, short") -// : String(localized: "Pending", comment: "Title, short") - TransactionSummaryList(stack: stack.push(), -// scope: scope, - transactionId: transactionId, - talerTX: $talerTX, - navTitle: nil, // navTitle, // use navTitle2 - hasDone: true, - showDone: .bordered, - url: nil, - withActions: false) - } else { - let message = String(localized: "Paying...", comment: "loading") - LoadingView(stack: stack.push(), scopeInfo: nil, message: message) - .task { await viewDidLoad() } - } - }.onAppear() { - symLog.log("onAppear") - DebugViewC.shared.setSheetID(SHEET_PAY_CONFIRM) - } - } -} - -// MARK: - -//#Preview { -// PaymentDone(stack: CallStack("Preview")) -//} diff --git a/TalerWallet1/Views/Sheets/Payment/PaymentView.swift b/TalerWallet1/Views/Sheets/Payment/PaymentView.swift @@ -167,7 +167,7 @@ struct PaymentView2: View, Sendable { bottomAbbrev: String(localized: "Effective:", comment: "mini"), bottomAmount: effective, large: false, - pending: false, + pending: !paid, incoming: false, baseURL: baseURL, txStateLcl: nil, @@ -209,12 +209,10 @@ struct PaySafeArea: View, Sendable { let symLog: SymLogV? let stack: CallStack let terms: MerchantContractTerms - // the scanned URL - let url: URL - let effective: Amount - let transactionId: String - let choiceIndex: Int @Binding var currencyInfo: CurrencyInfo + let amountString: String + let amountA11y: String + @Binding var payNow: Bool func timeToPay(_ terms: MerchantContractTerms) -> Int { if let milliseconds = try? terms.payDeadline.milliseconds() { @@ -271,19 +269,11 @@ struct PaySafeArea: View, Sendable { Text("Payment is made in \(currency)") .talerFont(.callout) .padding(.top, 4) - let destination = PaymentDone(stack: stack.push(), - url: url, -// scope: firstScope, // TODO: let user choose which currency - transactionId: transactionId, - choiceIndex: choiceIndex) - NavigationLink(destination: destination) { - let formatted = effective.formatted(currencyInfo, isNegative: false) - Text("Pay \(formatted.0) now") - .accessibilityLabel(Text("Pay \(formatted.1) now", comment: "a11y")) - } - .buttonStyle(TalerButtonStyle(type: .prominent)) - .padding(.horizontal) - .padding(.bottom, 4) + Button("Pay \(amountString) now") { payNow = true } + .accessibilityLabel(Text("Pay \(amountA11y) now", comment: "a11y")) + .buttonStyle(TalerButtonStyle(type: .prominent)) + .padding(.horizontal) + .padding(.bottom, 4) } if #available(iOS 26.0, *) { view diff --git a/TalerWallet1/Views/Transactions/TransactionSummaryList.swift b/TalerWallet1/Views/Transactions/TransactionSummaryList.swift @@ -58,6 +58,7 @@ struct TransactionSummaryList: View { @State private var selectedChoice: Int = 0 @State private var effective: Amount? = nil @State private var scope: ScopeInfo? = nil + @State private var payNow: Bool = false @Namespace var topID func loadTransaction() async { @@ -79,6 +80,24 @@ struct TransactionSummaryList: View { } } + private func payTransaction() async { + if let confirmPayResult = try? await model.confirmPay(transactionId, + choiceIndex: selectedChoice) { +// symLog.log(confirmPayResult as Any) + if confirmPayResult.type == "done" { + if let url { + controller.removeURL(url) + } +// paymentDone = true + } else { + if let url { + controller.removeURL(url) // TODO: pending might fail - in which case we might want to try again + } +// paymentPending = true + } + } + } + @MainActor @discardableResult func checkDismiss(_ notification: Notification, _ logStr: String = EMPTYSTRING) -> Bool { @@ -242,6 +261,7 @@ struct TransactionSummaryList: View { } TypeDetail(stack: stack.push(), transaction: $talerTX, + payNow: $payNow, selectedChoice: $selectedChoice, scope: $scope, effective: $effective, @@ -261,15 +281,22 @@ struct TransactionSummaryList: View { if isPaying, case .payment(let paymentTransaction) = talerTX { let details = paymentTransaction.details if let effective, let url, let terms = details.contractTerms { - // Pay button, will advance to PaymentDone + let formatted = effective.formatted(currencyInfo) PaySafeArea(symLog: symLog, stack: stack.push(), terms: terms, - url: url, // for controller.removeURL - effective: effective, - transactionId: transactionId, - choiceIndex: selectedChoice, - currencyInfo: $currencyInfo) + currencyInfo: $currencyInfo, + amountString: formatted.0, + amountA11y: formatted.1, + payNow: $payNow) + .onChange(of: payNow) { payNow2 in + if payNow2 { + payNow = false + Task { + await payTransaction() + } + } + } } else { Button("Cancel") { dismissTop(stack.push()) } .buttonStyle(TalerButtonStyle(type: .bordered)) @@ -421,6 +448,7 @@ struct TransactionSummaryList: View { struct TypeDetail: View { let stack: CallStack @Binding var transaction: TalerTransaction + @Binding var payNow: Bool @Binding var selectedChoice: Int @Binding var scope: ScopeInfo? @Binding var effective: Amount? @@ -461,7 +489,9 @@ struct TransactionSummaryList: View { let paymentTransaction: PaymentTransaction @Binding var scope: ScopeInfo? @Binding var effective: Amount? + @Binding var payNow: Bool @Binding var selectedChoice: Int + @EnvironmentObject private var model: WalletModel @State var choicesForPayment: GetChoicesForPaymentResult? = nil @State var isLoadingChoices: Bool = false @@ -512,8 +542,11 @@ struct TransactionSummaryList: View { MerchantHeader(terms: details.contractTerms) if let choices = choiceTriple() { + let hasAutomatic = choicesForPayment?.automaticExecution ?? false + let automaticIndex = hasAutomatic ? choicesForPayment?.automaticExecutableIndex : nil ChoicesView(stack: stack.push(), choiceTriple: choices, + automaticIndex: automaticIndex, selectedChoice: $selectedChoice) .onChange(of: selectedChoice) { newValue in let newChoice = choices[newValue] @@ -524,6 +557,11 @@ struct TransactionSummaryList: View { let firstChoice = choices[selectedChoice] effective = firstChoice.0.amountEffective scope = firstChoice.0.scopeInfo + if let automaticIndex { + // Pay Automatically + selectedChoice = automaticIndex + payNow = true + } } let choice = choices[selectedChoice] @@ -630,6 +668,7 @@ struct TransactionSummaryList: View { paymentTransaction: paymentTransaction, scope: $scope, effective: $effective, + payNow: $payNow, selectedChoice: $selectedChoice) case .refund(let refundTransaction): Group {