Created
August 15, 2017 21:49
-
-
Save SlaunchaMan/c466ca7909c4688fd8b28421d72b78ab to your computer and use it in GitHub Desktop.
Sample code for my Advanced Dates and Times in Swift talk at 360iDev 2017.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
//: Advanced Dates and Times in Swift | |
import Foundation | |
#if os(macOS) | |
import PlaygroundSupport | |
import UserNotifications | |
#endif | |
// Date Intervals | |
let calendar = Calendar.autoupdatingCurrent | |
let timeZone = TimeZone(identifier: "America/Denver")! | |
let talkStart = DateComponents( | |
timeZone: timeZone, | |
year: 2017, month: 8, day: 14, | |
hour: 15, minute: 45, second: 00) | |
let talkEnd = DateComponents( | |
timeZone: timeZone, | |
year: 2017, month: 8, day: 14, | |
hour: 16, minute: 30, second: 00) | |
let startDate = calendar.date(from: talkStart)! | |
let endDate = calendar.date(from: talkEnd)! | |
let talkInterval = DateInterval( | |
start: startDate, | |
end: endDate) | |
// 2700 | |
talkInterval.duration | |
// "2017-08-14 21:45:00 +0000 to 2017-08-14 22:30:00 +0000" | |
talkInterval.description | |
// true | |
talkInterval.contains(Date()) | |
// Date Interval Formatting | |
let formatter = DateIntervalFormatter() | |
formatter.string(from: talkInterval) | |
// "8/14/17, 3:45 - 4:30 PM" | |
var prefix = "" | |
if calendar.isDateInToday(startDate) && calendar.isDateInToday(endDate) { | |
formatter.dateStyle = .none | |
prefix = "Today " | |
} | |
else if calendar.isDateInYesterday(startDate) && calendar.isDateInYesterday(endDate) { | |
formatter.dateStyle = .none | |
prefix = "Yesterday " | |
} | |
else if calendar.isDateInTomorrow(startDate) && calendar.isDateInTomorrow(endDate) { | |
formatter.dateStyle = .none | |
prefix = "Tomorrow " | |
} | |
else { | |
formatter.dateStyle = .short | |
} | |
prefix + formatter.string(from: talkInterval)! | |
// "Today 3:45 – 4:30 PM" | |
// Converting Between Units | |
// How many days are there in this month? | |
calendar.range(of: Calendar.Component.day, in: Calendar.Component.month, for: Date())! | |
// Range(1..<31) | |
// How many days are there in this year? | |
calendar.range(of: .day, in: .year, for: Date()) | |
// Range(1..<32) | |
calendar.maximumRange(of: .second) | |
// Range(0..<60) | |
calendar.minimumRange(of: .day) | |
// Range(1..<29) | |
// How many seconds are there in this year? | |
calendar.range(of: .second, in: .year, for: Date()) | |
// Range(0..<60) | |
let monthRange = calendar.range(of: .month, in: .year, for: Date())! | |
for month in monthRange.lowerBound ..< monthRange.upperBound { | |
let date = calendar.date(bySetting: .month, value: month, of: Date())! | |
let dayRange = calendar.range(of: .day, in: .month, for: date)! | |
for day in dayRange.lowerBound ..< dayRange.upperBound { | |
let date = calendar.date(bySetting: .day, value: day, of: date)! | |
let hourRange = calendar.range(of: .hour, in: .day, for: date)! | |
for hour in hourRange.lowerBound ..< hourRange.upperBound { | |
// This is getting out of hand! | |
} | |
} | |
} | |
// Measure time interval | |
let year = 2017 | |
let beginningOfAnyYearComponents = DateComponents( | |
month: 1, | |
day: 1, | |
hour: 0, | |
minute: 0, | |
second: 0, | |
nanosecond: 0) | |
var beginningOfThisYearComponents = beginningOfAnyYearComponents | |
beginningOfThisYearComponents.year = year | |
let beginningOfThisYear = calendar.date(from: beginningOfThisYearComponents)! | |
let beginningOfNextYear = calendar | |
.nextDate(after: beginningOfThisYear, | |
matching: beginningOfAnyYearComponents, | |
matchingPolicy: .strict)! | |
let seconds = beginningOfNextYear.timeIntervalSince(beginningOfThisYear) | |
// Measure date interval | |
let interval = DateInterval(start: beginningOfThisYear, | |
end: beginningOfNextYear) | |
interval.duration | |
// Measure components | |
calendar.dateComponents([.second], | |
from: beginningOfThisYear, | |
to: beginningOfNextYear).second | |
calendar.dateComponents([.minute], | |
from: beginningOfThisYear, | |
to: beginningOfNextYear) | |
// Notifications | |
#if os(macOS) | |
let trigger = | |
UNCalendarNotificationTrigger(dateMatching:beginningOfAnyYearComponents, | |
repeats: true) | |
trigger.nextTriggerDate() | |
// "Jan 1, 2018 at 12:00 AM" | |
calendar.nextDate(after: Date(), | |
matching: beginningOfAnyYearComponents, | |
matchingPolicy: .nextTime) | |
// "Jan 1, 2018 at 12:00 AM" | |
let content = UNMutableNotificationContent() | |
content.title = "Happy new year!" | |
let request = UNNotificationRequest(identifier: "com.slaunchaman.happynewyear", | |
content: content, | |
trigger: trigger) | |
PlaygroundPage.current.needsIndefiniteExecution = true | |
UNUserNotificationCenter.current().add(request) { (error) in | |
if let error = error { | |
print("Error: \(error.localizedDescription)") | |
} | |
else { | |
print("Success!") | |
} | |
PlaygroundPage.current.finishExecution() | |
} | |
#endif |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment