DepositAmountV.swift (4194B)
1 /* 2 * This file is part of GNU Taler, ©2022-25 Taler Systems S.A. 3 * See LICENSE.md 4 */ 5 /** 6 * @author Marc Stibane 7 */ 8 import SwiftUI 9 import taler_swift 10 import SymLog 11 12 // Called from DepositSelectV 13 struct DepositAmountV: View { 14 private let symLog = SymLogV(0) 15 let stack: CallStack 16 // when Action is tapped while in currency TransactionList… 17 let selectedBalance: Balance? // …then use THIS balance, otherwise show picker 18 @Binding var amountLastUsed: Amount 19 let paytoUri: String? 20 let label: String? 21 22 @EnvironmentObject private var controller: Controller 23 @EnvironmentObject private var model: WalletModel 24 25 @State private var balanceIndex = 0 26 @State private var balance: Balance? = nil // nil only when balances == [] 27 @State private var amountToTransfer = Amount.zero(currency: EMPTYSTRING) // Update currency when used 28 @State private var amountAvailable = Amount.zero(currency: EMPTYSTRING) // GetMaxPeerPushAmount 29 30 @MainActor 31 private func viewDidLoad() async { 32 let balances = controller.balances 33 if let selectedBalance { 34 if selectedBalance.available.isZero { 35 // find another balance 36 balance = Balance.firstNonZero(balances) 37 } else { 38 balance = selectedBalance 39 } 40 } else { 41 balance = Balance.firstNonZero(balances) 42 } 43 if let balance { 44 balanceIndex = balances.firstIndex(of: balance) ?? 0 45 } else { 46 balanceIndex = 0 47 balance = (balances.count > 0) ? balances[0] : nil 48 } 49 } 50 51 @MainActor 52 private func newBalance() async { 53 // runs whenever the user changes the exchange via ScopePicker, or on new currencyInfo 54 symLog.log("❗️ task \(balanceIndex)") 55 if let balance { 56 let scope = balance.scopeInfo 57 amountToTransfer.setCurrency(scope.currency) 58 do { 59 amountAvailable = try await model.getMaxDepositAmount(scope) 60 } catch { 61 // TODO: Error 62 amountAvailable = balance.available 63 } 64 } 65 } 66 67 var body: some View { 68 #if PRINT_CHANGES 69 let _ = Self._printChanges() 70 #endif 71 let count = controller.balances.count 72 let _ = symLog.log("count = \(count)") 73 // let navTitle = String(localized: "NavTitle_Deposit", // _Currency", 74 // defaultValue: "Deposit") // \(currencySymbol)" 75 let scrollView = ScrollView { 76 if let label { 77 Text("to \(label)") 78 .talerFont(.picker) 79 .frame(maxWidth: .infinity, alignment: .leading) 80 .padding(.horizontal) 81 } 82 if count > 0 { 83 ScopePicker(value: $balanceIndex, 84 onlyNonZero: true) // can only send what exists 85 { index in 86 balanceIndex = index 87 balance = controller.balances[index] 88 } 89 .padding(.horizontal) 90 .padding(.bottom, 4) 91 } 92 DepositAmountView(stack: stack.push(), 93 balance: $balance, 94 balanceIndex: $balanceIndex, 95 amountLastUsed: $amountLastUsed, 96 amountToTransfer: $amountToTransfer, 97 amountAvailable: amountAvailable, 98 paytoUri: paytoUri) 99 } // ScrollView 100 // .navigationTitle(navTitle) 101 .frame(maxWidth: .infinity, alignment: .leading) 102 .background(WalletColors().backgroundColor.edgesIgnoringSafeArea(.all)) 103 .task { 104 setVoice(to: nil) 105 await viewDidLoad() 106 } 107 .task(id: balanceIndex + (1000 * controller.currencyTicker)) { await newBalance() } 108 109 if #available(iOS 16.4, *) { 110 scrollView.toolbar(.hidden, for: .tabBar) 111 .scrollBounceBehavior(.basedOnSize) 112 } else { 113 scrollView 114 } 115 } 116 }