How to get next n days date from the given date - ios

I am able to next 15 days date from current date, but when i tried to give custom date instead of current date, it not working.
let date = sharedAppDelegate.dueDate
let givenDate = Utility.convertStringToDate(format: "yyyy-MM-dd",
dateString: date)
let futureDate = (givenDate as NSCalendar).date(byAdding: dateComponents, to: Date()) ?? Date()
Third line gives error like Date? is not convertible to NSCalendar.
Expected result:- futureDate should be next 15 date from givenDate

A Date is not a Calendar
You can use the Calendar to do calculations or comparisons on Date objects, in your case you want to use the Calendar to add x number of days to your starting date
Try
let startDate = Date()
let tomorrow = Calendar.current.date(byAdding: .day, value: 1, to: startDate)
print(tomorrow)
OUTPUT:
Optional(2019-06-01 07:14:48 +0000)

You can extend Date class like this.
extension Date {
func dateByAddingDays(dateNum:Int) -> Date {
return Calendar.gregorian.date(byAdding: .day, value: dateNum, to: self)!
}
}
Now create date object
let today = Date()
let dayAfterTomorrow = today.dateByAddingDays(dateNum:2)
debugPrint(dayAfterTomorrow)

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")

How do I perform +1 or -1 on a date which I select from previous screen?

I want to add / or subtract a day from a selected date. The user selects for example 09-10-2019, when user press a button, the date should be 10-10-2019.
I am not trying to add or reduce a day from Current date.
On the previous screen , I have a variable -> Which is user selected and is not static
selecteddate = "09.10.2019"
I declared it as a global variable so it can be used in several screens, so in this screen , I get this 'selected date'.
I have 3 UIButtons. yesterdaybutton, selecteddatebutton and tomorrowbutton
When user presses yesterday button then 1 day should be reduced from
'selecteddate' variable
When user presses tomorrow button then 1 day should be added to
'selecteddate' variable.
I followed what the answer said. But unfortunately my selecteddate was a string and I needed to sent string to api in its format.
So , I did the following.
let dateFormattera = DateFormatter()
dateFormattera.dateFormat = "dd.MM.yyyy"
let date = dateFormattera.date(from: datetoday)
let newdate = Calendar.current.date(byAdding: .day, value: +1, to: date!)
let dateFormatterb = DateFormatter()
dateFormatterb.dateFormat = "dd.MM.yyyy"
let tomorrowdate = dateFormatterb.string(from: newdate!)
let dateFormatterx = DateFormatter()
let day = dateFormatterx.date(from: datetoday)
let newday = Calendar.current.date(byAdding: .day, value: +1, to: date!)
let dateFormattery = DateFormatter()
dateFormattery.dateFormat = "EEE"
let tomorrowday = dateFormattery.string(from: newdate!)
There might be junk code in this, but this made everything work as it should. This gets the DATE and DAY. I had to use this because converting string to date added +1 day to the date (due to UTC timing 18:00) despite doing -1 or +1
I suggest that you use:
Calendar.current.date(byAdding: .day, value: 1, to: selecteddate)
This will add one day to selecteddate
Then, if you have 2 buttons, as you have explained, you could set a tag to each button:
yesterdaybutton.tag = -1
tomorrowbutton.tag = 1
We will use each button's tag to add or reduce days from selecteddate
So, both buttons will use this:
#IBAction func buttonAction(_ sender: UIButton) {
let newDate = Calendar.current.date(byAdding: .day, value: sender.tag, to: selecteddate)
}
You can create a method like below that calculates the date.
func calculateDate(fromDate date: Date, withUnit value: Int) -> Date? {
return Calendar.current.date(byAdding: .day, value: value, to: date)
}
How to use it?
When yesterday button is selected then you need call method like below...
if let date = calculateDate(fromDate: selecteddate, withUnit: -1) {
print(date)
} else {
print("date is nil. may be due to different formats of dates")
}
When tomorrow button is selected then you need call method like below...
if let date = calculateDate(fromDate: selecteddate, withUnit: 1) {
print(date)
} else {
print("date is nil. may be due to different formats of dates")
}
Note: Please use date format if required. The date format should be same for all dates.
You still need to convert your string to a concrete object which in your case is Date. To it you can add or subtract components as you wish. In your case those are days alone. Check the following:
func addDays(_ days: Int, toDate dateString: String?) throws -> String {
guard let dateString = dateString else { throw NSError(domain: "Add days", code: 400, userInfo: ["dev_message": "String is null"]) }
let formatter = DateFormatter()
formatter.dateFormat = "dd'.'MM'.'yyyy"
// formatter.dateFormat = "MM'.'dd'.'yyyy" // Not sure which
guard let date = formatter.date(from: dateString) else { throw NSError(domain: "Add days", code: 400, userInfo: ["dev_message": "Incorrect date format. Expecting \(formatter.dateFormat!)"]) }
guard let newDate = formatter.calendar.date(byAdding: {
var components: DateComponents = DateComponents()
components.day = days
return components
}(), to: date) else { throw NSError(domain: "Add days", code: 400, userInfo: ["dev_message": "Could not add days for some reason"]) }
return formatter.string(from: newDate)
}
A usage I tried was:
print(try! addDays(1, toDate: "09.10.2019")) // Prints 10.10.2019
print(try! addDays(30, toDate: "09.10.2019")) // Prints 08.11.2019
print(try! addDays(-1, toDate: "09.10.2019")) // Prints 08.10.2019
So in your case you need addDays(1, toDate: "09.10.2019")to get to next day and addDays(-1, toDate: "09.10.2019") for previous day.

How to set maximum date in UIDatePicker?

I am trying to create UIDatePicker in my project which maximum date should be that of yesterday instead of current date. Is there a way to set selected date as yesterday instead of selecting current date?
Use maximumDate property of your date picker.
let yesterdayDate = Calendar.current.date(byAdding: .day, value: -1, to: Date())
yourPicker.maximumDate = yesterdayDate
you can use below code to achieve this
let calender = Calendar.current
let date = Date()
let finalDate = calender.date(byAdding: Calendar.Component.day, value: -1, to: date)
if let FinalDate = finalDate{
yourPicker.maximumDate = FinalDate
}

How to subtract date components?

As today is Friday, which is 6 according to NSCalendar. I can get this by using the following
Calendar.current.component(.weekday, from: Date())
How do I get weekday component of Saturday last week, which should be 7?
If I do Calendar.current.component(.weekday, from: Date()) - 6 . I am getting 0 which is not valid component.
Try this, you have to get the date first then subtract again from it:
var dayComp = DateComponents(day: -6)
let date = Calendar.current.date(byAdding: dayComp, to: Date())
Calendar.current.component(.weekday, from: date!)
For that first you need to get that date using calendar.date(byAdding:value:to:) and then get day number from it.
extension Date {
func getDateFor(days:Int) -> Date? {
return Calendar.current.date(byAdding: .day, value: days, to: Date())
}
}
Now simply use thus function and get your days.
if let date = Date().getDateFor(days: -6) {
print(Calendar.current.component(.weekday, from: date))
}
you can use calendar and date components and put everything in a Date extension, something like:
(Swift 4.1)
extension Date {
func removing(minutes: Int) -> Date? {
let result = Calendar.current.date(byAdding: .minute, value: -(minutes), to: self)
return result
}
}

How to calculate the number of days in the current month/year

Is there any methods available for NSDate/NSCalendar to calculate the number of days in the current month and current year ?
The only thing I saw is to get the number of days from a given date or between two dates.
Is this the only way ?
Here is a method which works for both months and years:
let calendar = NSCalendar.currentCalendar()
let date = NSDate()
// Calculate start and end of the current year (or month with `.Month`):
var startOfInterval : NSDate?
var lengthOfInterval = NSTimeInterval()
calendar.rangeOfUnit(.Year, startDate: &startOfInterval, interval: &lengthOfInterval, forDate: date)
let endOfInterval = startOfInterval!.dateByAddingTimeInterval(lengthOfInterval)
// Compute difference in days:
let days = calendar.components(.Day, fromDate: startOfInterval!, toDate: endOfInterval, options: [])
print(days)
(You may want to add some error checking instead of forcibly unwrapping
optionals.)
Update for Swift 3:
let calendar = Calendar.current
let date = Date()
// Calculate start and end of the current year (or month with `.month`):
let interval = calendar.dateInterval(of: .year, for: date)!
// Compute difference in days:
let days = calendar.dateComponents([.day], from: interval.start, to: interval.end).day!
print(days)
let date = NSDate()
let cal = NSCalendar(calendarIdentifier:NSCalendarIdentifierGregorian)!
let days = cal.rangeOfUnit(.Day, inUnit: .Month, forDate: date)
print("\(days) in the month of \(date)")

Resources