10 July 2024
Use ZStack for wrapping views without side effects.
var body: some View {
{
ZStack ()
SomeView()
AnotherView}
}
VStack / HStack plus Spacer for quick alignment.
var body: some View {
{
VStack ("Hello")
Text()
Spacer}
}
var body: some View {
{
HStack ()
Spacer("World")
Text}
}
Use GeometryReader for getting the size of the parent view.
var body: some View {
{ geometry in
GeometryReader ("Width: \(geometry.size.width)")
Text}
}
Use @State for mutable state.
@State private var count = 0
var body: some View {
(action: {
Button+= 1
count }) {
("Count: \(count)")
Text}
}
Use @Binding for passing state down the view hierarchy.
struct ContentView: View {
@State private var count = 0
var body: some View {
(count: $count)
ChildView}
}
struct ChildView: View {
@Binding var count: Int
var body: some View {
(action: {
Button+= 1
count }) {
("Count: \(count)")
Text}
}
}
Use @ObservedObject for observing changes in an object.
class UserData: ObservableObject {
@Published var name = "Alice"
}
struct ContentView: View {
@ObservedObject var userData = UserData()
var body: some View {
("Hello, \(userData.name)!")
Text}
}
struct ChildView: View {
@ObservedObject var userData: UserData
var body: some View {
(action: {
Button.name = "Bob"
userData}) {
("Change name")
Text}
}
}
()
ContentView.sheet(isPresented: $showingSheet) {
(userData: userData)
ChildView}
Use @AppStorage for persisting user settings.
@AppStorage("name") var name = "Alice"
var body: some View {
("Hello, \(name)!")
Text}
(action: {
Button= "Bob"
name }) {
("Change name")
Text}
@AppStorage can be duplicated in multiple views as long as the key is the same.
@AppStorage("name") var name = "Alice"
var body: some View {
("Hello, \(name)!")
Text}
struct ChildView: View {
@AppStorage("name") var name = "Alice"
var body: some View {
("Hello, \(name)!")
Text}
}