'Compare Times to get active time from data
In the example above, I have a data model that contains various times for an Itinerary that will be displayed. I would like to highlight the current time with a filled circle:
struct SampleModel: Identifiable {
let id = UUID()
let title: String
let description: String
let time: Date
let icon: String
}
let timeInterval = 1652619600
class Sample: ObservableObject {
@Published var sample2 = [SampleModel(title: "Coffee", description: "Get coffee", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)), icon: "house"),
SampleModel(title: "Coffee", description: "Get coffee", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 30), icon: "house"),
SampleModel(title: "Dinner", description: "Outback Steakhouse", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 60), icon: "person"),
SampleModel(title: "Check Weather", description: "Use app to check weather", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 120), icon: "cloud.sun.fill"),
SampleModel(title: "Go To Work", description: "Leave for work", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 180), icon: "car.fill"),
SampleModel(title: "YouTube", description: "Watch youtube video", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 240), icon: "video.fill"),
SampleModel(title: "Cut Grass", description: "Work in yard", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 300), icon: "speedometer"),
SampleModel(title: "Ride Bike", description: "Go to the trace", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 360), icon: "bicycle"),
SampleModel(title: "Take Pictures", description: "Photograph the moon", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 420), icon: "camera.fill"),
SampleModel(title: "Boat Ride", description: "Go boating", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 480), icon: "ferry.fill"),
SampleModel(title: "Colorado trip", description: "Fly to Erie", time: Date(timeIntervalSince1970: TimeInterval(timeInterval)).adding(minutes: 540), icon: "airplane")]
func isCurrent(date1: Date) -> Bool {
var currentItem: Bool = false
for cTime in sample2 {
if date1 <= cTime.time && date1 <= Date() {
} else {
currentItem = false
}
}
return currentItem
}
}
The data above is just a sample mock data so I can get the UI and the functioning working properly. In my content view I have. foreach loop on the sample data, and I want to highlight the current item with a filled circle. In the isCurrent() function, I can get all items that already have occurred before, but I want to return the most recent.
ForEach(sampleVM.sample2, id: \.id) { index in
Divider()
ItemRowView(isCurrent: sampleVM.isCurrent(date1: index.time), isLastRow: lastRow(item: index.id), time: Date(), sample: index)
}
ItemRowView() is what I am using to display the data.
Solution 1:[1]
As the array is sorted you simply need to find the first item/index whose date is greater than the current date
- If the index is not found (current date is later than the date of the last item) the item is the last item
- If the index is 0 (current date is sooner than the date of the first item) the item is
nil - Otherwise the item is the item at index - 1
let currentItem : SampleModel?
if let nextIndex = sample2.firstIndex(where: {$0.time > Date()}) {
currentItem = nextIndex > 0 ? sample2[nextIndex - 1] : nil
} else {
currentItem = sample2.last!
}
Or if the result is the index
let currentIndex: Int?
if let nextIndex = sample2.firstIndex(where: {$0.time > Date()}) {
currentIndex = nextIndex > 0 ? nextIndex - 1 : nil
} else {
currentIndex = sample2.endIndex - 1
}
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 |
