Reputation: 3
I want to find the best way to structure a custom component with multiple slots for content.
This is the best tutorial I've found: https://www.hackingwithswift.com/plus/custom-swiftui-components/creating-a-flipview-to-provide-a-card-flip-effect
The code works, but I don't understand the syntax. Why does the first slot "left header actions" not need to be written?
import SwiftUI
struct ContentView: View {
var body: some View {
VStack {
OnboardingHeader(
title: "Title",
paragraph: "Paragraph"
) {
// why doesn't this require me to say "leftHeaderActions?"
Text("Hi")
} rightHeaderActions: {
Text("Right")
}
}
}
}
struct OnboardingHeader<LeftHeaderActions: View, RightHeaderActions: View>: View {
var leftHeaderActions: () -> LeftHeaderActions
var rightHeaderActions: () -> RightHeaderActions
var title: String = ""
var paragraph: String = ""
init(title: String = "", paragraph: String = "", @ViewBuilder leftHeaderActions: @escaping () -> LeftHeaderActions, @ViewBuilder rightHeaderActions: @escaping () -> RightHeaderActions) {
self.title = title
self.paragraph = paragraph
self.leftHeaderActions = leftHeaderActions
self.rightHeaderActions = rightHeaderActions
}
var body: some View {
VStack {
HStack {
leftHeaderActions()
Spacer()
rightHeaderActions()
}
.padding(.bottom, 16)
Text(title)
.frame(maxWidth: .infinity, alignment: .leading)
.padding(.bottom, 4)//
Text(paragraph)
.frame(maxWidth: .infinity, alignment: .leading)
.lineSpacing(1.8)
}
.padding(.top, 16)
.padding(.bottom, 24)
}
}
Upvotes: 0
Views: 960
Reputation: 1088
It is a syntactic sugar of Swift compiler that you can omit name of first closure. What you shown is equivalent of:
OnboardingHeader(title: "Do you own a WalletOne hardware wallet?", paragraph: "Paragraph", leftHeaderActions: {
Text("Hi")
}, rightHeaderActions: {
Text("Right")
})
Here, you have to provide the name, because you didn’t close the OnboardingHeader
parenthesis (with )
)
Much simpler example is Button - you can write the action closure inside the parenthesis:
Button("Text", action: { print("hi") })
Or outside it (without explicit “action”):
Button("Text") {
print("hi")
}
Upvotes: 1