Date formating, adding days to date - ios

Here is my first question;
import Foundation
let date1 = Date()
let date2 = Date().addingTimeInterval(3600)
if date1 == date2
{
print("equals")
}
else if date1 > date2
{
print("date1 is bigger")
}
else if date1 < date2
{
print("date2 is bigger")
}
It gives below output if i write print("date1") or print("date2")
2018-09-10 08:56:49 +0000
I would like to write the same example but date1 and date2 must include these 2 properties:
format: "dd.MM.yyyy"
locale: "tr_TR"
Beside this, here is my second question:
let date2 = Date().addingTimeInterval(3600)
As you know, this 3600 value adding an hour. How can I add one day? 24*3600? Is there any shortest way?

Try
extension Date {
func addDays(_ days: Int) -> Date {
Calendar.autoupdatingCurrent.date(byAdding: .day, value: days, to: self)!
}
}

Like #Larme said, you might want to look into Calendar.
var dateComponents = DateComponents()
dateComponents.day = 1
guard let date = Calendar.current.date(byAdding: dateComponents, to: Date()) else { // Adding date components to current day.
fatalError("date not found")
}
let dateFormatter = DateFormatter()
dateFormatter.dateStyle = .short // dd.MM.yyyy
dateFormatter.locale = Locale(identifier: "tr_TR") // Your preferred locale
let dateWithLocale = dateFormatter.string(from: date)
print(date)
Your comparison can be done using the Date objects. Only when you need to print it or use it as a String, you would need to do formatting.

Try this one
let today = Date() // OR your date here
let tomorrow = Calendar.current.date(byAdding: .day, value: 1, to: today)
let yesterday = Calendar.current.date(byAdding: .day, value: -1, to: today)

Related

How do i know if a specific date is a month, or a week to an parent date?

Lets say i have a program that reminds users of their appointments , from the current date until the date of the appointment, i want to find out if a particular date is a week to the appointment or a month to the appointment .
var startDate = startDate
let calendar = Calendar.current
let fmt = DateFormatter()
fmt.dateFormat = "yyyy-MM-dd"
while startDate <= endDate {
var newDate = calendar.date(byAdding: .day, value: 1, to: startDate)!
if newDate is a month to endDate {
//schedule reminder
}
if newDate is a week to endDate{
//schedule reminder
}
how can i check if the current date is a week/month to the appointment ?
You don't need to use any date comparison, you can simply generate the notification dates using Calendar.date(byAdding:value:to:) and just passing the correct components. To set the date 1 week/month before endDate, pass -1 to value.
let oneWeekBeforeAppointment = Calendar.current.date(byAdding: .weekOfYear, value: -1, to: endDate)!
let oneMonthBeforeAppointment = Calendar.current.date(byAdding: .month, value: -1, to: endDate)!
Try this to calculate the duration in days
func DateFormat() -> DateFormatter {
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "dd/MM/yyyy"
dateFormatter.timeZone = TimeZone(abbreviation: "GMT")
return dateFormatter
}
var appointementDate: Date?
var today = Date()
appointementDate = DateFormat().date(from: "22/02/2020")
today = DateFormat().date(from: DateFormat().string(from: today))!
let timeInterval = Int(exactly: (today.timeIntervalSince(appointementDate!))) ?? 0
print("\(timeInterval/86400) days left")

Get next 3rd month name from the current month in swift

How can I get The 3rd month names from Current month to Nov. Ex:-if the current month is Nov then I want the month names from Feb. Current month should be the running month.
Question: How to get 3rd month name from the current month?
Can someone please explain to me how to get month name. Any help would be greatly appreciated.
Thanks in advance.
You need to use the Calendar class, e.g.
var now = Date()
var calendar = Calendar.current
if let then = calendar.date(byAdding: .month, value: 3, to: now) {
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "LLLL"
let monthName = dateFormatter.string(from: then)
print ("\(monthName)")
}
Just keep in mind how calenar arithmetics is handled: if you add "3 months" to let's say Nov 30th, 2019, then you'll get Feb-29th, 2020, although someone might expect March-01, 2020.
//set start & end date in correct format
let startDate = "September"
let strEndDate = "December"
//create date formatter
let formatter = DateFormatter()
formatter.dateFormat = "MMMM"
//convert string into date object
guard let startDate = formatter.date(from: startDate) else {
print("invalid start date")
return
}
//convert string into date object
guard let endDate = formatter.date(from: strEndDate) else {
print("invalid end date time")
return
}
//calculate the month from end date and that should not exceed the start date
for month in 1...6 {
if let dt = Calendar.current.date(byAdding: .month, value: -month, to: endDate) {
if dt.compare(startDate) == .orderedAscending {
break
}
print(formatter.string(from: dt!))
}
}

issues in comparing Day from Date in swift 4

Comparison is required to check date is past date day.
I have tried with this
let calendar = NSCalendar.current
//Get just MM/dd/yyyy from current date
let components = calendar.dateComponents([], from: Date())
//Convert to NSDate
let pastDates = self.calendar.selectedDates.filter { $0 < calendar.date(from: components as DateComponents)! }
Update the below line to give you a date object,
let components = calendar.dateComponents([.month, .day, .year], from: Date())
Currently you are not providing any date component in the array so you will not get a date object.
I didn't understood what is your question properly, but hope this helps you:
let beforeDateStr = "04/12/2018"
let todayDate = Date()
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "MM/dd/yyyy"
let beforeDateFormatted = dateFormatter.date(from: beforeDateStr)
if Calendar.current.compare(todayDate, to: beforeDateFormatted!, toGranularity: .day) == .orderedDescending {
print("before date day is lesser than current date")
} else {
print("before date day is equal or greater than todays date")
}
To find the date is smaller or bigger:
You can use this simple Code:
let differenceBetweenTwoDate = Calendar.current.dateComponents([.day], from: previousDate, to: Date())
if differenceBetweenTwoDate.day! > 0{
print("date is bigger")
}else{
print("date is smaller")
}
Hope it Helps!
This is how you can add hours or days in current date and time -
calendar.date(byAdding: .hour, value: 1, to: currentDate)
calendar.date(byAdding: .day, value: 7, to: currentDate)
And this is how you can compare 2 dates and calculate hours, mins and also days
let calendar = Calendar.current
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ss"
dateFormatter.timeZone = TimeZone(abbreviation: "UTC")
let anyDataTime = dateFormatter.date(from: anotherDateTime)
let components = calendar.dateComponents([.minute], from: Date(), to: anyDataTime!)
let hour = (Double(components.minute!) / 60.0).rounded()

How to fetch all dates between from Date to Date in Swift 3 [duplicate]

I’m creating a date using NSDateComponents().
let startDate = NSDateComponents()
startDate.year = 2015
startDate.month = 9
startDate.day = 1
let calendar = NSCalendar.currentCalendar()
let startDateNSDate = calendar.dateFromComponents(startDate)!
... now I want to print all dates since the startDate until today, NSDate(). I’ve already tried playing with NSCalendarUnit, but it only outputs the whole difference, not the single dates between.
let unit: NSCalendarUnit = [.Year, .Month, .Day, .Hour, .Minute, .Second]
let diff = NSCalendar.currentCalendar().components(unit, fromDate: startDateNSDate, toDate: NSDate(), options: [])
How can I print all dates between two Dateobjects?
Edit 2019
In the meantime the naming of the classes had changed – NSDate is now just Date. NSDateComponents is now called DateComponents. NSCalendar.currentCalendar() is now just Calendar.current.
Just add one day unit to the date until it reaches
the current date (Swift 2 code):
var date = startDateNSDate // first date
let endDate = NSDate() // last date
// Formatter for printing the date, adjust it according to your needs:
let fmt = NSDateFormatter()
fmt.dateFormat = "dd/MM/yyyy"
// While date <= endDate ...
while date.compare(endDate) != .OrderedDescending {
print(fmt.stringFromDate(date))
// Advance by one day:
date = calendar.dateByAddingUnit(.Day, value: 1, toDate: date, options: [])!
}
Update for Swift 3:
var date = startDate // first date
let endDate = Date() // last date
// Formatter for printing the date, adjust it according to your needs:
let fmt = DateFormatter()
fmt.dateFormat = "dd/MM/yyyy"
while date <= endDate {
print(fmt.string(from: date))
date = Calendar.current.date(byAdding: .day, value: 1, to: date)!
}
Using extension:
extension Date {
static func dates(from fromDate: Date, to toDate: Date) -> [Date] {
var dates: [Date] = []
var date = fromDate
while date <= toDate {
dates.append(date)
guard let newDate = Calendar.current.date(byAdding: .day, value: 1, to: date) else { break }
date = newDate
}
return dates
}
}
Usage:
let datesBetweenArray = Date.dates(from: Date(), to: Date())
Same thing but prettier:
extension Date {
func allDates(till endDate: Date) -> [Date] {
var date = self
var array: [Date] = []
while date <= endDate {
array.append(date)
date = Calendar.current.date(byAdding: .day, value: 1, to: date)!
}
return array
}
}
How to get all dates for next 20 days:
if let date = Calendar.current.date(byAdding: .day, value: 20, to: Date()) {
print(Date().allDates(till: date))
}
Your desired code becomes like
let startDate = NSDateComponents()
startDate.year = 2015
startDate.month = 9
startDate.day = 1
let calendar = NSCalendar.currentCalendar()
let startDateNSDate = calendar.dateFromComponents(startDate)!
var offsetComponents:NSDateComponents = NSDateComponents();
offsetComponents.day = 1
var nd:NSDate = startDateNSDate;
println(nd)
while nd.timeIntervalSince1970 < NSDate().timeIntervalSince1970 {
nd = calendar.dateByAddingComponents(offsetComponents, toDate: nd, options: nil)!;
println(nd)
}
Here is Solution of Print all dates between two Dates (Swift 4 Code)
var mydates : [String] = []
var dateFrom = Date() // First date
var dateTo = Date() // Last date
// Formatter for printing the date, adjust it according to your needs:
let fmt = DateFormatter()
fmt.dateFormat = "yyy-MM-dd"
dateFrom = fmt.date(from: strstartDate)! // "2018-03-01"
dateTo = fmt.date(from: strendDate)! // "2018-03-05"
while dateFrom <= dateTo {
mydates.append(fmt.string(from: dateFrom))
dateFrom = Calendar.current.date(byAdding: .day, value: 1, to: dateFrom)!
}
print(mydates) // Your Result
Output is:
["2018-03-01", "2018-03-02", "2018-03-03", "2018-03-04", "2018-03-05"]
I am using this approach (Swift 3):
import Foundation
class Dates {
static func printDatesBetweenInterval(_ startDate: Date, _ endDate: Date) {
var startDate = startDate
let calendar = Calendar.current
let fmt = DateFormatter()
fmt.dateFormat = "yyyy-MM-dd"
while startDate <= endDate {
print(fmt.string(from: startDate))
startDate = calendar.date(byAdding: .day, value: 1, to: startDate)!
}
}
static func dateFromString(_ dateString: String) -> Date {
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd"
return dateFormatter.date(from: dateString)!
}
}
and I am calling this like:
Dates.printDatesBetweenInterval(Dates.dateFromString("2017-01-02"), Dates.dateFromString("2017-01-9"))
The output is:
2017-01-02
2017-01-03
2017-01-04
2017-01-05
2017-01-06
2017-01-07
2017-01-08
2017-01-09
You can use the compactMap operator.
I like to put these functions in an extension so they are reusable.
It's hard to make a range of dates, so I made a range of ints and loop through that.
extension Calendar {
func getDates(_ startDate: Date, _ endDate: Date) -> [Date] {
// make sure parameters are valid
guard startDate < endDate else { print("invalid parameters"); return [] }
// how many days between dates?
let dayDiff = Int(self.dateComponents([.day], from: startDate, to: endDate).day ?? 0)
let rangeOfDaysFromStart: Range<Int> = 0..<dayDiff + 1
let dates = rangeOfDaysFromStart.compactMap{ self.date(byAdding: .day, value: $0, to: startDate) }
return dates
}
}
Your usage could be:
let startDate = Date(dateString: "1/2/2017", format: "M/d/yyyy")
let endDate = Date(dateString: "1/9/2017", format: "M/d/yyyy")
let dates = Calendar.current.getDates(startDate, endDate)
let f = DateFormatter(withFormat: "yyyy-MM-dd", locale: "us_en")
print(dates.compactMap{f.string(from: $0)}.joined(separator: ", "))
output:
"2017-01-02, 2017-01-03, 2017-01-04, 2017-01-05, 2017-01-06, 2017-01-07, 2017-01-08, 2017-01-09"

Set NSDate 0 seconds in swift

I'm trying to get NSDate from UIDatePicker, but it constantly returns me a date time with trailing 20 seconds. How can I manually set NSDate's second to zero in swift?
extension Date {
var zeroSeconds: Date? {
let calendar = Calendar.current
let dateComponents = calendar.dateComponents([.year, .month, .day, .hour, .minute], from: self)
return calendar.date(from: dateComponents)
}
}
Usage:
let date1 = Date().zeroSeconds
let date2 = Date()
print(date2.zeroSeconds)
From this answer in Swift:
var date = NSDate();
let timeInterval = floor(date .timeIntervalSinceReferenceDate() / 60.0) * 60.0
date = NSDate(timeIntervalSinceReferenceDate: timeInterval)
This is how to do it in Swift 3.
In this example I remove the seconds in the date components:
let date = picker.date
let calendar = Calendar.current
let components = calendar.dateComponents([.year, .month, .day, .hour, .minute], from: date)
let fullMinuteDate = calendar.date(from: components)!
Working on a playground:
Truncating a date to a full minute can be done with
let date = NSDate()
let cal = NSCalendar.currentCalendar()
var fullMinute : NSDate?
cal.rangeOfUnit(.CalendarUnitMinute, startDate: &fullMinute, interval: nil, forDate: date)
println(fullMinute!)
Update for Swift 4 and later:
let date = Date()
let cal = Calendar.current
if let fullMinute = cal.dateInterval(of: .minute, for: date)?.start {
print(fullMinute)
}
This method can easily be adapted to truncate to a full hour, day, month, ...
Just reformat the date:
func stripSecondsFromDate(date: NSDate) -> NSDate {
let dateFormatter = NSDateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd HH:mm"
let str = dateFormatter.stringFromDate(date)
let newDate = dateFormatter.dateFromString(str)!
return newDate
}
import Foundation
let now = Date()
let calendar = Calendar.current
let date = calendar.date(bySettingHour: 0,
minute: 0,
second: 0,
of: now,
direction: .backward)
There is another way, with two more parameters: matchingpolicy and repeatedTimePolicy.
let date = calendar.date(bySettingHour: 0,
minute: 0,
second: 0,
of: now,
matchingPolicy: .strict,
repeatedTimePolicy: .first,
direction: .backward)
To check the result:
let formatter = ISO8601DateFormatter()
formatter.timeZone = TimeZone.current // defaults to GMT
let string = formatter.string(from: date!)
print(string) // 2019-03-27T00:00:00+01:00
I know this doesn't address NSDate directly, but it might be worth anyways - I had this exact same problem with Date and also because I think this might be a more clean approach.
extension Calendar {
/// Removes seconds `Calendar.Component` from a `Date`. If `removingFractional` is `true`, it also
/// removes all fractional seconds from this particular `Date`.
///
/// `removingFractional` defaults to `true`.
func removingSeconds(fromDate date: Date, removingFractional removesFractional: Bool = true) -> Date? {
let seconds = component(.second, from: date)
let noSecondsDate = self.date(byAdding: .second, value: -seconds, to: date)
if removesFractional, let noSecondsDate = noSecondsDate {
let nanoseconds = component(.nanosecond, from: noSecondsDate)
return self.date(byAdding: .nanosecond, value: -nanoseconds, to: noSecondsDate)
}
return noSecondsDate
}
}
Now, to solve your problem, we created the function removingSeconds(fromDate: removingFractional). It's really simple - as you can see in the docs of the function. It removes the .second component and, if removingFractional is true, it also removes any fractional seconds that this Date may have - or the .nanosecond component.

Resources