2

I am creating a Widget that has a textfield that counts down from a date like so:

Text(endDate, style: .relative)

This works fine, however as its relative, once it hits zero, it will continue to count back up again as the endDate becomes in the past.

Is there a way to terminate the text when it hits zero? Or do I have to rebuild this feature with a timer?

All I need to do is count down from a start date to and end date then invalidate the text field or show a message.

pawello2222
  • 46,897
  • 22
  • 145
  • 209
jwarris91
  • 902
  • 9
  • 24

2 Answers2

4

Here is how you can create a countdown and when the time is over display some other text.

  1. Create an Entry where endDate is optional - if it's nil it means that the countdown is over:
struct SimpleEntry: TimelineEntry {
    let date: Date
    var endDate: Date?
}
  1. In your Provider create two Entries - one for the countdown time and one for when the countdown is over:
struct SimpleProvider: TimelineProvider {
    ...

    func getTimeline(in context: Context, completion: @escaping (Timeline<SimpleEntry>) -> Void) {
        let currentDate = Date()
        let endDate = Calendar.current.date(byAdding: .second, value: 15, to: currentDate)!

        let entries = [
            SimpleEntry(date: currentDate, endDate: endDate),
            SimpleEntry(date: endDate),
        ]

        let timeline = Timeline(entries: entries, policy: .never)
        completion(timeline)
    }
}
  1. Use it in your view:
struct WidgetEntryView: View {
    var entry: Provider.Entry

    var body: some View {
        if let endDate = entry.endDate {
            Text(endDate, style: .relative)
        } else {
            Text("Timer finished")
        }
    }
}
pawello2222
  • 46,897
  • 22
  • 145
  • 209
  • thanks didnt know i could use entity like this, works great! – jwarris91 Oct 30 '20 at 12:03
  • Sorry to bump, I have the same approach, however, widget is not refreshed on the specified date, but at a random offset that goes from 20s to 90s after the specified date. Any ideas why could that happen? – Dliix May 02 '23 at 16:36
  • @Dliix the reason is probably because Apple doesn't guarantee it will update in the time you specified. They adapt update schedule for your widget constantly depending on how often the user is using the app, how often the app asks to get updated etc – ramzesenok Jun 23 '23 at 07:31
  • Yes, but I am trying on my personal phone with developer mode enabled for WidgetKit, so these restrictions do not apply yet – Dliix Jun 30 '23 at 12:52
0

I think you have to schedule a widget update at time zero and have conditions to hide it when less than zero.

Joseph Lord
  • 6,446
  • 1
  • 28
  • 32