// // Solsnu_Widget.swift // Solsnu.Widget // // Created by Ivar Løvlie on 15/12/2025. // import WidgetKit import SwiftUI struct Provider: TimelineProvider { func placeholder(in context: Context) -> SolvervEntry { SolvervEntry(def: SolvervDef(date: Date())) } func getSnapshot(in context: Context, completion: @escaping (SolvervEntry) -> ()) { let entry = SolvervEntry(def: SolvervDef(date: Date())) completion(entry) } func getTimeline(in context: Context, completion: @escaping (Timeline) -> ()) { var entries: [SolvervEntry] = [] let currentDate = Date() for hourOffset in 0 ..< 5 { let entryDate = Calendar.current.date(byAdding: .hour, value: hourOffset, to: currentDate)! let entry = SolvervEntry(def: SolvervDef(date: currentDate)) entries.append(entry) } let timeline = Timeline(entries: entries, policy: .atEnd) completion(timeline) } } struct SolvervEntry: TimelineEntry { let date: Date let emoji: String let def: SolvervDef init(def: SolvervDef, date: Date? = nil) { self.date = date ?? def.date self.emoji = def.emoji() self.def = def; } } struct Solsnu_WidgetEntryView : View { var entry: Provider.Entry var body: some View { VStack { Text("Time:") Text(entry.date, style: .time) Text("Emoji:") Text(entry.emoji) } } } struct Solsnu_Widget: Widget { let kind: String = "Solsnu_Widget" var body: some WidgetConfiguration { StaticConfiguration(kind: kind, provider: Provider()) { entry in if #available(iOS 17.0, *) { Solsnu_WidgetEntryView(entry: entry) .containerBackground(.fill.tertiary, for: .widget) } else { Solsnu_WidgetEntryView(entry: entry) .padding() .background() } } .configurationDisplayName("My Widget") .description("This is an example widget.") } } #Preview(as: .systemSmall) { Solsnu_Widget() } timeline: { SolvervEntry(def: SolvervDef(utcString: "2025-09-22 18:20:00")) SolvervEntry(def: SolvervDef(utcString: "2025-12-21 15:03:00")) SolvervEntry(def: SolvervDef(utcString: "2026-03-20 14:46:00")) SolvervEntry(def: SolvervDef(utcString: "2026-06-21 08:25:00")) SolvervEntry(def: SolvervDef(utcString: "2026-09-23 00:06:00")) SolvervEntry(def: SolvervDef(utcString: "2026-12-21 20:50:00")) SolvervEntry(def: SolvervDef(utcString: "2027-03-20 20:25:00")) SolvervEntry(def: SolvervDef(utcString: "2027-06-21 14:11:00")) SolvervEntry(def: SolvervDef(utcString: "2027-09-23 06:02:00")) SolvervEntry(def: SolvervDef(utcString: "2027-12-22 02:43:00")) SolvervEntry(def: SolvervDef(utcString: "2028-03-20 02:17:00")) SolvervEntry(def: SolvervDef(utcString: "2028-06-20 20:02:00")) SolvervEntry(def: SolvervDef(utcString: "2028-09-22 11:45:00")) SolvervEntry(def: SolvervDef(utcString: "2028-12-21 08:20:00")) SolvervEntry(def: SolvervDef(utcString: "2029-03-20 08:01:00")) SolvervEntry(def: SolvervDef(utcString: "2029-06-21 01:48:00")) SolvervEntry(def: SolvervDef(utcString: "2029-09-22 17:37:00")) SolvervEntry(def: SolvervDef(utcString: "2029-12-21 14:14:00")) SolvervEntry(def: SolvervDef(utcString: "2030-03-20 13:51:00")) SolvervEntry(def: SolvervDef(utcString: "2030-06-21 07:31:00")) SolvervEntry(def: SolvervDef(utcString: "2030-09-22 23:27:00")) SolvervEntry(def: SolvervDef(utcString: "2030-12-21 20:09:00")) } struct SolvervDef { let date: Date; init(date:Date) { self.date = date; } init(utcString:String) { let formatter = DateFormatter() formatter.dateFormat = "yyyy-MM-dd HH:mm:ss" formatter.timeZone = TimeZone(abbreviation: "UTC") // Should probably guard this, but not now let date = formatter.date(from: utcString)! self.date = date } func emoji() -> String { let components = Calendar.current.dateComponents([.year,.month,.day,.hour,.minute], from: date) let hour = components.hour! let minute = components.minute! if hour == 2 && minute == 43 { return "😀" } else { return "" } } }