Skip to content

Instantly share code, notes, and snippets.

@ericlewis
Created February 22, 2022 18:14
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ericlewis/5ce57c1ceb5a99383c208b27be1c4f81 to your computer and use it in GitHub Desktop.
Save ericlewis/5ce57c1ceb5a99383c208b27be1c4f81 to your computer and use it in GitHub Desktop.
import SwiftUI
import swiftui_betterpicker
struct ListPickerView: View {
enum DayOfWeek: String, CaseIterable {
case monday, tuesday, wednesday, thursday, friday, saturday, sunday
var title: String { rawValue.localizedCapitalized }
}
@State
private var selection = DayOfWeek.tuesday
var body: some View {
List {
let title: LocalizedStringKey = "List Picker"
_Picker(title, selection: $selection) {
ForEach(DayOfWeek.allCases, id: \.self) {
Text($0.title).tag($0)
}
}
.pickerStyle(.list(title: title))
}
.navigationTitle(selection.title)
}
}
extension _PickerStyle where Self == ListPickerStyle {
static func list(title: LocalizedStringKey) -> ListPickerStyle { .init(title: title) }
}
struct ListPickerStyle: _PickerStyle {
let title: LocalizedStringKey
func makeBody(configuration: Configuration) -> some View {
Style(configuration: configuration, title: title)
}
struct Style: View {
let configuration: Configuration
let title: LocalizedStringKey
var body: some View {
NavigationLink {
ListView(configuration: configuration, title: title)
} label: {
HStack {
configuration.label()
Spacer()
configuration.content { view, tag in
.init(makeBadge(view, tag))
}
}
}
}
@ViewBuilder
func makeBadge(_ option: Configuration.Option, _ tag: _Tag) -> some View {
switch tag {
case let .tagged(tag):
if tag == configuration.selection {
option
.font(.callout)
.foregroundStyle(.secondary)
} else {
EmptyView()
}
default:
EmptyView()
}
}
}
struct ListView: View {
@Environment(\.dismiss)
private var dismiss
let configuration: Configuration
let title: LocalizedStringKey
var body: some View {
List {
configuration.content { view, tag in
.init(makeOption(view, tag))
}
}
.navigationTitle(title)
}
@ViewBuilder
func makeOption(
_ option: Configuration.Option,
_ tag: _Tag
) -> some View {
switch tag {
case let .tagged(tag):
Button {
configuration.selection = tag
Task {
try? await Task.sleep(nanoseconds: 100_000_000)
DispatchQueue.main.async {
dismiss()
}
}
} label: {
HStack {
option
.foregroundColor(.primary)
Spacer()
if tag == configuration.selection {
Image(systemName: "checkmark")
}
}
}
case .untagged:
option
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment