xxxxxxxxxx
import SwiftUI
@main
struct How_MuchApp: App {
var body: some Scene {
WindowGroup {
ContentView()
.tint(.purple)
}
}
}
xxxxxxxxxx
import SwiftUI
struct ContentView: View {
@State private var tipPct = 0
@State private var numPeople = 1
@State private var total = "0"
@State private var calculate = false
var canAddDecimal: Bool {
// let periods = total.filter({$0 == "."})
// if periods.count == 0 {
// return true
// } else {
// return false
// }
// return total.filter({$0 == "."}).count == 0
total.filter({$0 == "."}).count == 0
}
var canAddDigit: Bool {
guard let decIndex = total.firstIndex(of: ".") else { return true }
let index = total.distance(from: total.startIndex, to: decIndex)
return (total.count - index - 1) < 2
}
var body: some View {
NavigationStack {
VStack {
Text(total)
.font(.system(size: 70))
.frame(width: 260, alignment: .trailing)
.padding(.vertical,1)
.lineLimit(1)
.minimumScaleFactor(0.5)
HStack {
ForEach(7...9, id: \.self) { number in
numberButton(number: "\(number)")
}
}
HStack {
ForEach(4...6, id: \.self) { number in
numberButton(number: "\(number)")
}
}
HStack {
ForEach(1...3, id: \.self) { number in
numberButton(number: "\(number)")
}
}
HStack {
numberButton(number: "0")
numberButton(number: ".")
Button {
if total.count == 1 {
total = "0"
} else {
total.removeLast()
}
} label: {
Image(systemName: "delete.backward.fill")
.font(.largeTitle)
.bold()
.frame(width: 80, height: 80)
.background(.gray)
.foregroundColor(.white)
.clipShape(Circle())
}
}
HStack {
Text("Tip")
Picker(selection: $tipPct, label: Text("Tip")) {
ForEach(0...100,id: \.self) { tip in
Text("\(tip)%")
}
}
.buttonStyle(.bordered)
}
HStack {
Text("Number of people")
Picker(selection: $numPeople, label: Text("Number of People")) {
ForEach(1...20,id: \.self) { numPeople in
Text("\(numPeople)").tag(numPeople)
}
}
.buttonStyle(.bordered)
}
HStack {
Button("Calculate") {
calculate = true
}
.sheet(isPresented: $calculate) {
TotalsView(total: Double(total) ?? 0, tipPct: tipPct, numPeople: numPeople)
.presentationDetents([.medium])
}
Button("Clear") {
total = "0"
}
}
.disabled(Double(total) == 0)
.buttonStyle(.borderedProminent)
Spacer()
}
.navigationTitle("Portion Calculator")
}
}
func numberButton(number: String) -> some View {
Button {
addDigit(number)
} label: {
Text(number)
.font(.largeTitle)
.bold()
.frame(width: 80, height: 80)
.background(.purple)
.foregroundColor(.white)
.clipShape(Circle())
}
}
func addDigit(_ number: String) {
if canAddDigit {
if number == "." {
if canAddDecimal {
total += number
}
} else {
total = total == "0" ? number : total + number
}
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
.tint(.purple)
}
}
xxxxxxxxxx
//
// Created for How Much
// by Stewart Lynch on 2023-02-07
// Using Swift 5.0
// Running on macOS 13.2
//
// Folllow me on Mastodon: @StewartLynch@iosdev.space
// Or, Twitter, if it still exits: https://twitter.com/StewartLynch
// Subscribe on YouTube: https://youTube.com/@StewartLynch
// Buy me a ko-fi: https://ko-fi.com/StewartLynch
import SwiftUI
struct TotalsView: View {
let total: Double
let tipPct: Int
let numPeople: Int
var tipAmount: Double {
total * Double(tipPct) / 100
}
var totalAmount: Double {
total + tipAmount
}
var portion: Double {
totalAmount / Double(numPeople)
}
let identifier = Locale.current.currency?.identifier ?? ""
var body: some View {
NavigationStack {
VStack {
Grid(horizontalSpacing: 20) {
GridRow {
Text("Original Bill")
.gridColumnAlignment(.leading)
Text("\(total, format: .currency(code: identifier))")
.gridColumnAlignment(.trailing)
}
GridRow {
Text("Tip")
Text("\(tipAmount, format: .currency(code: identifier))")
}
GridRow {
Text("Total")
Text("\(totalAmount, format: .currency(code: identifier))")
}
GridRow {
Text("Portion")
Text("\(portion, format: .currency(code: identifier))")
}
}
.font(.title)
Image("myportion")
.resizable()
.scaledToFit()
.frame(width: 150)
Spacer()
}
.navigationTitle("Amount Owing")
.navigationBarTitleDisplayMode(.inline)
}
}
}
struct TotalsView_Previews: PreviewProvider {
static var previews: some View {
TotalsView(total: 135.20, tipPct: 18, numPeople: 3)
}
}