remindwall / RWPureSwift / Sources / EditSettingsNew / BusSettings / AlertWindowEditor.swift
Back to remindwall — Current RemindWall
import AppTypes
import SwiftUI
/// The one window editor every alert surface shares (TR1.4 review decision):
/// start/end time pickers plus weekday pills. Pure view - the owning feature
/// supplies the window and receives the edits.
public struct AlertWindowEditorView: View {
let window: AlertWindow
let onSetStart: (_ hour: Int, _ minute: Int) -> Void
let onSetEnd: (_ hour: Int, _ minute: Int) -> Void
let onToggleWeekday: (DaysOfWeek) -> Void
public init(
window: AlertWindow,
onSetStart: @escaping (_ hour: Int, _ minute: Int) -> Void,
onSetEnd: @escaping (_ hour: Int, _ minute: Int) -> Void,
onToggleWeekday: @escaping (DaysOfWeek) -> Void
) {
self.window = window
self.onSetStart = onSetStart
self.onSetEnd = onSetEnd
self.onToggleWeekday = onToggleWeekday
}
public var body: some View {
VStack(alignment: .leading, spacing: 8) {
DatePicker(
"Start",
selection: Binding(
get: { time(hour: window.startHour, minute: window.startMinute) },
set: { newDate in
let comps = Calendar.current.dateComponents([.hour, .minute], from: newDate)
onSetStart(comps.hour ?? 0, comps.minute ?? 0)
}
),
displayedComponents: .hourAndMinute
)
DatePicker(
"End",
selection: Binding(
get: { time(hour: window.endHour, minute: window.endMinute) },
set: { newDate in
let comps = Calendar.current.dateComponents([.hour, .minute], from: newDate)
onSetEnd(comps.hour ?? 0, comps.minute ?? 0)
}
),
displayedComponents: .hourAndMinute
)
HStack {
ForEach(DaysOfWeek.allCases, id: \.rawValue) { day in
Button {
onToggleWeekday(day)
} label: {
Text(initial(day))
.font(.callout)
.frame(width: 32, height: 32)
.background(window.weekdays.contains(day) ? Color.accentColor : Color.gray.opacity(0.2))
.foregroundStyle(window.weekdays.contains(day) ? Color.white : Color.primary)
.clipShape(Circle())
}
.buttonStyle(.plain)
.accessibilityLabel(String(describing: day))
.accessibilityValue(window.weekdays.contains(day) ? "active" : "inactive")
}
}
}
}
private func time(hour: Int, minute: Int) -> Date {
var comps = DateComponents()
comps.hour = hour
comps.minute = minute
return Calendar.current.date(from: comps) ?? Date()
}
private func initial(_ day: DaysOfWeek) -> String {
switch day {
case .Sunday: return "S"
case .Monday: return "M"
case .Tuesday: return "T"
case .Wednesday: return "W"
case .Thursday: return "T"
case .Friday: return "F"
case .Saturday: return "S"
}
}
}