I have sunrise time and sunset time from EDSunriseSet, now I need to compare this with current time to get night mode:
NSCalendar *todayCal = [NSCalendar currentCalendar];
NSDateComponents *todayComp = [todayCal components: NSCalendarUnitHour | NSCalendarUnitMinute | NSCalendarUnitSecond fromDate:[NSDate date]];
BOOL nightMode;
if (todayComp.date > sunriseSet.localSunrise.date & todayComp.date < sunriseSet.localSunset.date) {
nightMode = NO;
} else {
nightMode = YES;
}
if (nightMode) {
NSLog(#"the current is night zzzzzzzzzzz PM");
} else {
NSLog(#"the current is day ........... AM");
}
But it's not working!!
sunrise: 5:18:4 - sunset: 18:41:50
current time: 19:54:13
check this code its work well
NSCalendar *todayCal = [NSCalendar currentCalendar];
NSDateFormatter *dateFormater = [[NSDateFormatter alloc]init];
[dateFormater setDateFormat:#"yyyy-MM-dd HH:mm:ss"];
NSDate *startDate = [dateFormater dateFromString:#"2017-04-16 05:18:04"];
NSDate *EndDate = [dateFormater dateFromString:#"2017-04-16 18:41:50"];
NSDate *CurrentDate = [dateFormater dateFromString:#"2017-04-16 15:54:13"];
BOOL nightMode;
if (CurrentDate > startDate & CurrentDate < EndDate) {
nightMode = NO;
} else {
nightMode = YES;
}
if (nightMode) {
NSLog(#"the current is night zzzzzzzzzzz PM");
} else {
NSLog(#"the current is day ........... AM");
}
Related
How to check the date cross the Sunday and reset the data?
I need to do reset on every Sunday, if I missed that on Sunday then the reset need to happen if user open the app the following increment date(i.e mon,tue, till saturday).
For Every Sunday or crossed the Sunday one time the reset need to happened, if user forgot to open the application on Rest date.
Following the my code which i try to implemented.
Which was not working as per my requirement, Your feedback is highly appreciated.
-(void) weekDaySundayToRefresh
{
NSDate *now = [NSDate date];
NSCalendar *calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
NSDateComponents *components = [calendar components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitWeekOfMonth | NSCalendarUnitWeekday fromDate:now];
NSUInteger weekdayToday = [components weekday];
NSInteger daysToMonday = (8 - weekdayToday) % 7;
nextSunday= [now dateByAddingTimeInterval:60*60*24*daysToSunday];
NSLog(#"nextMonday : %#", nextSunday);
}
-(void) compareDate
{
NSDate *today = [NSDate date]; // it will give you current date
// NSDate *newDate = [MH_USERDEFAULTS objectForKey:#"USER_BACKGROUND_DATE"]; // your date
NSComparisonResult result;
//has three possible values: NSOrderedSame,NSOrderedDescending, NSOrderedAscending
result = [today compare:refreshGoalsDate]; // comparing two dates
if(result==NSOrderedAscending)
{
NSLog(#"today is less");
}
else if(result==NSOrderedDescending)
{
NSLog(#"newDate is less");
NSDate *fromDate;
NSDate *toDate;
NSCalendar *calendar = [NSCalendar currentCalendar];
[calendar rangeOfUnit:NSCalendarUnitDay startDate:&fromDate
interval:NULL forDate:refreshGoalsDate];
[calendar rangeOfUnit:NSCalendarUnitDay startDate:&toDate
interval:NULL forDate:today];
NSDateComponents *difference = [calendar components:NSCalendarUnitDay
fromDate:fromDate toDate:toDate options:0];
noOfDaysCount = [difference day];
NSLog(#"date difference:%ld",(long)[difference day]);
}
else
NSLog(#"Both dates are same");
}
-(void) checkRefreshGoals:(int)sectionIndex rowIndex:(int)rowIndex
{
NSDateFormatter * formatter = [NSDateFormatter new];
[formatter setDateFormat:#"yyyy-MM-dd"];
NSString * currentDateString = [formatter stringFromDate:[NSDate date]];
NSString * initialNotificationDate = [formatter stringFromDate:refreshDate];
NSDate *currentDate = [formatter dateFromString:currentDateString];
NSDate *refreshDate = [formatter dateFromString:initialNotificationDate];
if ([refreshDate compare:currentDate] == NSOrderedDescending)
{
NSLog(#"date1 is later than date2");
isGoalsRefreshed = NO;
}
else if ([refreshDate compare:currentDate] == NSOrderedAscending)
{
NSLog(#"date1 is earlier than date2");
if (sameDay == YES)
{
isGoalsRefreshed = YES;
[self refreshDataOnSunday:sectionIndex rowIndex:rowIndex];
}
else if (noOfDaysCount > 7)
{
isGoalsRefreshed = YES;
[self refreshDataOnSunday:sectionIndex rowIndex:rowIndex];
}
else
{
isGoalsRefreshed = NO;
}
}
else
{
NSLog(#"dates are the same");
isRefreshed = NO;
}
}
-(void) refreshDataOnSunday:(int)sectionIndex rowIndex:(int)rowIndex
{
if (noOfDaysCount > 7)
{
if (isGoalsRefreshed == YES)
{
// Do rest your data
}
}
else if (sameDay == YES)
{
if (isGoalsRefreshed == YES)
{
// Do reset your data
}
}
else
{
isGoalsRefreshed = NO;
}
}
First you need to save todays date and DayNumber when user opens your app at first time and then you need to compare next app open date so you can estimate either Sunday is gone or not.
/*first check in userDefault for stored Date and Day
Store values in local and check with current date */
NSMutableDictionary *dictStoredData = [USERDEFAULT valueForKey:#"dateTimeDate"];
if (!dictStoredData) {
// user comes first time so store it here
dictStoredData =[[NSMutableDictionary alloc] init];
NSDate *today =[NSDate date];
NSCalendar *gregorian =[[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
NSDateComponents *comps =[gregorian components:NSCalendarUnitWeekday fromDate:[NSDate date]];
NSInteger weekday = [comps weekday];
int nextSundayVal = 7 - (int)weekday;
NSDateFormatter *format = [[NSDateFormatter alloc] init];
[format setDateFormat:#"yyyy-MM-dd"];
NSString *startDate = [format stringFromDate: today];
[dictStoredData setObject:startDate forKey:#"startDate"];
[dictStoredData setObject:[NSString stringWithFormat:#"%d",nextSundayVal] forKey:#"nextSundayVal"];
[USERDEFAULT setObject:dictStoredData forKey:#"dateTimeDate"];
}
else{
NSString *strEndDate = #"2017-01-08";
NSString *strStartDate = [dictStoredData valueForKey:#"startDate"];
int nextSundayVal = (int)[dictStoredData valueForKey:#"nextSundayVal"];
NSDateFormatter *format = [[NSDateFormatter alloc] init];
[format setDateFormat:#"yyyy-MM-dd"];
NSDate *startDate = [format dateFromString:strStartDate];
NSDate *endDate = [format dateFromString:strEndDate];
NSCalendar *gregorianCalendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
NSDateComponents *components = [gregorianCalendar components:NSCalendarUnitDay
fromDate:startDate
toDate:endDate
options:0];
int newDayCount = (int)[components day];
if (newDayCount > nextSundayVal) {
NSLog(#"sunday is gone so reload data!!");
//save this date as a new date and check with this when user come again
}
else {
NSLog(#"sunday is not come yet!!");
}
}
here strEndDate is next date when user opens your application so you can get it from [NSDate date] with same dateformater.
I have run this code in my machine and its printing sunday is gone so reload data so hope this will help you.
As like you we had flow, every friday and more than seven days, its need to update the server.
We did it with following code:
You need to update last updated date.
Check this out:
if ([isFirday isEqualToString:#"Friday"]) {//This is my value from server side (they will give as friay), i think you dont need this condition.
BOOL isSameDay;
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:#"MMM dd yyyy,HH:mm"];
NSDate *date = [dateFormatter dateFromString:mennuRefreshTime];//Is an last updated date.
[dateFormatter setDateFormat:#"yyyy-MM-dd HH:mm:ss"];
NSString *temp = [dateFormatter stringFromDate:date];
NSDate *lastDate = [dateFormatter dateFromString:temp];
NSString *currentDaystr = [dateFormatter stringFromDate:[NSDate date]];
// Write the date back out using the same format
NSDate *currentDate = [dateFormatter dateFromString:currentDaystr];
if ([lastDate compare:currentDate] == NSOrderedDescending) {
NSLog(#"date1 is later than date2");
isSameDay = NO;
} else if ([lastDate compare:currentDate] == NSOrderedAscending) {
NSLog(#"date1 is earlier than date2");
[dateFormatter setDateFormat:#"EEEE"];
NSString *dayName = [dateFormatter stringFromDate:currentDate];
NSString *lastupdateName = [dateFormatter stringFromDate:lastDate];
if ([dayName isEqualToString:lastupdateName]) {
isSameDay = YES;
}else{
isSameDay = NO;
}
} else {
NSLog(#"dates are the same");
isSameDay = YES;
}
if (isSameDay == YES) {
return;
}
NSCalendar *calender =[[NSCalendar alloc]initWithCalendarIdentifier:NSCalendarIdentifierGregorian];
NSDateComponents *components = [calender components:NSCalendarUnitDay fromDate:lastDate toDate:currentDate options:0];
int day = (int)[components day];
if (day >= 7) {
[self getTopList];
}else{
[dateFormatter setDateFormat:#"EEEE"];
NSString *dayName = [dateFormatter stringFromDate:currentDate];
if ([dayName isEqualToString:isFirday]) {
[self getTopList];
}else{
return;
}
}
}
I am working on chat apps and I want to send date/time in particular format like Today, yesterday with date. How can I display according to this format?
- (NSString *)relativeDateStringForDate:(NSDate *)date
{
NSCalendarUnit units = NSCalendarUnitDay | NSCalendarUnitWeekOfYear |
NSCalendarUnitMonth | NSCalendarUnitYear;
NSDateComponents *components = [[NSCalendar currentCalendar] components:units
fromDate:date
toDate:[NSDate date]
options:0];
if (components.year > 0) {
return [NSString stringWithFormat:#"%ld years ago", (long)components.year];
} else if (components.month > 0) {
return [NSString stringWithFormat:#"%ld months ago", (long)components.month];
} else if (components.weekOfYear > 0) {
return [NSString stringWithFormat:#"%ld weeks ago", (long)components.weekOfYear];
} else if (components.day > 0) {
if (components.day > 1) {
return [NSString stringWithFormat:#"%ld days ago", (long)components.day];
} else {
return #"Yesterday";
}
} else
{
return #"Today";
}
}
I am using above function to get date but I want date time in combined string. So how to pass date/time combine to the above method? Is it possible to send a date time string to this method?
For getting the date in format [08-jan-17 11:20:51], you can use the below code
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
// Convert to new Date Format
[dateFormatter setDateFormat:#"dd-MMM-yy HH:mm:ss"];
NSDate *date = [NSDate date];
NSString *newDate = [dateFormatter stringFromDate:date]
NSLog(#"[%#]",newDate); // this will give you the date in format [08-jan-17 11:20:51]
For getting the time in format [10:01:20], you can use the below code
// Convert to new Time Format
[dateFormatter setDateFormat:#"HH:mm:ss"];
NSDate *date = [NSDate date];
NSString *newTime = [dateFormatter stringFromDate:date];
NSLog(#"%#",newTime); // this will give you the time in format 10:01:20
So you can use your code like this -
- (NSString *)relativeDateStringForDate:(NSDate *)date
{
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
// Convert to new Date Format
[dateFormatter setDateFormat:#"dd-MMM-yy HH:mm:ss"];
NSString *newDate = [dateFormatter stringFromDate:date];
NSLog(#"[%#]",newDate);
// Convert to new Time Format
[dateFormatter setDateFormat:#"HH:mm:ss"];
NSString *newTime = [dateFormatter stringFromDate:date];
NSLog(#"%#",newTime);
NSCalendarUnit units = NSCalendarUnitDay | NSCalendarUnitWeekOfYear |
NSCalendarUnitMonth | NSCalendarUnitYear;
NSDateComponents *components = [[NSCalendar currentCalendar] components:units
fromDate:date
toDate:[NSDate date]
options:0];
if (components.year > 0) {
return [NSString stringWithFormat:#"[%ld years ago], [%#]", (long)components.year, newDate];
} else if (components.month > 0) {
return [NSString stringWithFormat:#"[%ld months ago], [%#]", (long)components.month, newDate];
} else if (components.weekOfYear > 0) {
return [NSString stringWithFormat:#"[%ld weeks ago], [%#]", (long)components.weekOfYear, newDate];
} else if (components.day > 0) {
if (components.day > 1) {
return [NSString stringWithFormat:#"[%ld days ago], [%#]", (long)components.day, newDate];
} else {
return [NSString stringWithFormat:#"[Yesterday %#]",newTime];
}
} else
{
return [NSString stringWithFormat:#"[Today %#]", newTime];
}
}
A couple of observations:
You want NSCalendarUnitWeekOfMonth, not NSCalendarUnitWeekOfYear.
In order to distinguish between "today" and "yesterday", you can't just get the date components between two NSDate objects. You should get the date components (but not time components) of the two dates first, and then get the difference between those two sets of date components.
As it is, if it's 9am and you're looking at a message from 11pm last night, it will calculate that day < 1, and thus it will say "Today 11pm" (which is wrong) rather than "Yesterday 11pm".
If you're going to include that "x months ago" string, I'd suggest getting out of the business of building it yourself. Apple has a class that does that for you (NSDateComponentsFormatter) and it's localized.
So, pulling that all together, you get something like:
- (NSString *)relativeDateStringForDate:(NSDate *)date {
// get the number of days differences
NSCalendarUnit units = NSCalendarUnitDay | NSCalendarUnitWeekOfMonth | NSCalendarUnitMonth | NSCalendarUnitYear;
NSCalendar *calendar = [NSCalendar currentCalendar];
NSDateComponents *dateComponents = [calendar components:units fromDate:date];
NSDateComponents *nowComponents2 = [calendar components:units fromDate:[NSDate date]];
NSDateComponents *components = [calendar components:units fromDateComponents:dateComponents toDateComponents:nowComponents2 options:0];
if (components.year > 0 || components.month > 0 || components.weekOfMonth > 0 || components.day > 1) {
NSDateComponentsFormatter *formatter = [[NSDateComponentsFormatter alloc] init];
formatter.allowedUnits = units;
formatter.maximumUnitCount = 2; // set this to whatever you want, but 1 or 2 is often best
formatter.unitsStyle = NSDateComponentsFormatterUnitsStyleFull;
return [NSString stringWithFormat:#"%# %#", [formatter stringFromDateComponents:components], NSLocalizedString(#"ago", #"x days _ago_")];
} else {
// build time string
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
formatter.timeStyle = NSDateFormatterShortStyle;
NSString *timeString = [formatter stringFromDate:date];
if (components.day == 1) {
return [NSString stringWithFormat:#"%# %#", NSLocalizedString(#"Yesterday", #"day before today"), timeString];
} else {
return [NSString stringWithFormat:#"%# %#", NSLocalizedString(#"Today", #"well, er, today"), timeString];
}
}
}
Now, notice that I excluded the time if the date was before yesterday. The time doesn't make sense if the date string is measured in any units greater than days (e.g. the time is meaningless in this string: "3 months ago, 11:20am"). If you want to include the time, you have to include the date (which then renders these relative "ago" strings useless). So you might just get rid of this "ago" portion:
- (NSString *)relativeDateStringForDate:(NSDate *)date {
// get the number of days differences
NSCalendarUnit units = NSCalendarUnitDay | NSCalendarUnitWeekOfMonth | NSCalendarUnitMonth | NSCalendarUnitYear;
NSCalendar *calendar = [NSCalendar currentCalendar];
NSDateComponents *dateComponents = [calendar components:units fromDate:date];
NSDateComponents *nowComponents2 = [calendar components:units fromDate:[NSDate date]];
NSDateComponents *components = [calendar components: NSCalendarUnitDay fromDateComponents:dateComponents toDateComponents:nowComponents2 options:0];
if (components.day > 1) {
// build date/time string
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
formatter.timeStyle = NSDateFormatterShortStyle;
formatter.dateStyle = NSDateFormatterShortStyle;
return [formatter stringFromDate:date];
} else {
// build time string
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
formatter.timeStyle = NSDateFormatterShortStyle;
NSString *timeString = [formatter stringFromDate:date];
if (components.day == 1) {
return [NSString stringWithFormat:#"%#, %#", NSLocalizedString(#"Yesterday", #"day before today"), timeString];
} else {
return [NSString stringWithFormat:#"%#, %#", NSLocalizedString(#"Today", #"well, er, today"), timeString];
}
}
}
That solves the weird "3 months ago, 11:20am" problem, but then again, it's no longer a relative date/time string.
Another option is to abandon absolute time altogether, and just show a relative string:
- (NSString *)relativeDateStringForDate:(NSDate *)date {
NSCalendarUnit units = NSCalendarUnitSecond | NSCalendarUnitMinute | NSCalendarUnitHour | NSCalendarUnitDay | NSCalendarUnitWeekOfMonth | NSCalendarUnitMonth | NSCalendarUnitYear;
NSDateComponentsFormatter *formatter = [[NSDateComponentsFormatter alloc] init];
formatter.allowedUnits = units;
formatter.maximumUnitCount = 2;
formatter.unitsStyle = NSDateComponentsFormatterUnitsStyleFull;
return [NSString stringWithFormat:#"%# %#", [formatter stringFromDate:date toDate:[NSDate date]], NSLocalizedString(#"ago", #"x days _ago_")];
}
The details of the above samples is less important than the basic concepts, namely:
Be careful using date components when determining "today" vs "yesterday";
Use date formatters when trying to create the time strings or date/time strings; and
Use date components formatters when trying to build a string that represents the amount of time (or days) that has elapsed.
How to check if NSDate falls in current week of the year? I tried below but last week's date is also falling inside "Date is in this week" condition.
- (NSInteger)thisW:(NSDate *)date
{
NSCalendar *gregorian = [[NSCalendar alloc]
initWithCalendarIdentifier:NSGregorianCalendar];
NSDateComponents *todaysComponents =
[gregorian components:NSWeekCalendarUnit fromDate:[NSDate date]];
NSUInteger todaysWeek = [todaysComponents weekday];
NSDateComponents *otherComponents =
[gregorian components:NSWeekCalendarUnit fromDate:date];
NSUInteger datesWeek = [otherComponents weekday];
NSLog(#"Date %#",date);
if(todaysWeek==datesWeek){
//NSLog(#"Date is in this week");
return 1;
}else if(todaysWeek+1==datesWeek){
//NSLog(#"Date is in next week");
return 2;
} else {
return 0;
}
}
What about this short extension in Swift 4?
extension Calendar {
func isDayInCurrentWeek(date: Date) -> Bool? {
let currentComponents = Calendar.current.dateComponents([.weekOfYear], from: Date())
let dateComponents = Calendar.current.dateComponents([.weekOfYear], from: date)
guard let currentWeekOfYear = currentComponents.weekOfYear, let dateWeekOfYear = dateComponents.weekOfYear else { return nil }
return currentWeekOfYear == dateWeekOfYear
}
}
A solution using the method rangeOfUnit:startDate:interval:forDate of NSCalendar to calculate the start date and the interval of the current week
- (BOOL)isInCurrentWeek:(NSDate *)date
{
NSDate *startDate = nil;
NSTimeInterval interval = 0.0;
NSCalendar *calendar = [NSCalendar currentCalendar];
// calendar.firstWeekday = 1; set the index of the first weekday if necessary
[calendar rangeOfUnit:NSWeekOfYearCalendarUnit startDate: &startDate interval: &interval forDate: [NSDate date]];
NSDate *endDate = [calendar dateByAddingUnit:NSSecondCalendarUnit value: (NSInteger)interval toDate: startDate options:NSCalendarMatchNextTime];
return [date compare:startDate] == NSOrderedDescending && [date compare:endDate] == NSOrderedAscending;
}
or in Swift
func isDateInCurrentWeek(_ date : Date) -> Bool
{
var startDate = Date()
var interval : TimeInterval = 0.0
let calendar = Calendar.current
// calendar.firstWeekday = 1 set the index of the first weekday if necessary
calendar.dateInterval(of: .weekOfYear, start: &startDate, interval: &interval, for: Date())
let endDate = calendar.date(byAdding:.second, value: Int(interval), to: startDate)!
return date >= startDate && date < endDate
}
I had to replace NSWeekCalendarUnit with NSCalendarUnitWeekOfYear
- (NSInteger)thisW:(NSDate *)date
{
NSCalendar *gregorian = [[NSCalendar alloc]
initWithCalendarIdentifier:NSGregorianCalendar];
NSDateComponents *todaysComponents = [gregorian components:NSCalendarUnitWeekOfYear fromDate:[NSDate date]];
NSUInteger todaysWeek = [todaysComponents weekOfYear];
NSDateComponents *otherComponents = [gregorian components:NSCalendarUnitWeekOfYear fromDate:date];
NSUInteger datesWeek = [otherComponents weekOfYear];
//NSLog(#"Date %#",date);
if(todaysWeek==datesWeek){
//NSLog(#"Date is in this week");
return 1;
}else if(todaysWeek+1==datesWeek){
//NSLog(#"Date is in next week");
return 2;
} else {
return 0;
}
}
Swift 5.3.x, modified Vadian's answer. Other answers didn't work for me. For instance, test the method with the date from last year (2020), they return true.
Here's a Swift extension of NSDate because I have to use this function in an Objective-C class.
import Foundation
extension NSDate {
#objc func isInCurrentWeek() -> Bool {
var startDate = Date()
var interval : TimeInterval = 0.0
let calendar = Calendar.current
// calendar.firstWeekday = 1 set the index of the first weekday if necessary
calendar.dateInterval(of: .weekOfYear, start: &startDate, interval: &interval, for: Date())
let endDate = calendar.date(byAdding:.second, value: Int(interval), to: startDate)!
return (self as Date) >= startDate && (self as Date) < endDate
}
}
And sample test/use case:
let df = DateFormatter()
df.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZ"
let d = "2021-01-23T13:56:49+0000"
let d2 = df.date(from: d)
print((d2! as NSDate).isInCurrentWeek()) // prints true, current date is Jan 21, 2021
Use this function to get number of week:
- (NSInteger)numberOfWeek:(NSDate *)date
{
NSCalendar *calender = [NSCalendar currentCalendar];
NSDateComponents *components = [calender components:NSCalendarUnitWeekOfYear fromDate:date];
return [components weekOfYear];
}
Using this code, you can compare week like this. I am just use next week date using dateWithTimeIntervalSinceNow: only for comparison.
if ([self numberOfWeek:[NSDate date]] == [self numberOfWeek:[NSDate dateWithTimeIntervalSinceNow: (60.0f*60.0f*24.0f*7.0f)]])
{
NSLog(#"Same Week");
}
else
{
NSLog(#"Different Week");
}
First get the firstday and lastday of the week of current date.
NSCalendar *myCalendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
NSDateComponents *currentComps = [myCalendar components:( NSYearCalendarUnit | NSMonthCalendarUnit | NSWeekOfYearCalendarUnit | NSWeekdayCalendarUnit | NSHourCalendarUnit | NSMinuteCalendarUnit) fromDate:[NSDate date]];
[currentComps setWeekday:1]; // 1: sunday
NSDate *firstDayOfTheWeek = [myCalendar dateFromComponents:currentComps];
[currentComps setWeekday:7]; // 7: saturday
NSDate *lastDayOfTheWeek = [myCalendar dateFromComponents:currentComps];
Now use a method given bellow putting your interested date
BOOL isInCurrentWeek = [self date:your given date isBetweenDate:firstDayOfTheWeek andDate:lastDayOfTheWeek];
NSLog(#"%d",isInCurrentWeek);
The expecting method
- (BOOL)date:(NSDate*)date isBetweenDate:(NSDate*)beginDate andDate:(NSDate*)endDate
{
if ([date compare:beginDate] == NSOrderedAscending)
return NO;
if ([date compare:endDate] == NSOrderedDescending)
return NO;
return YES;
}
I am trying to create a catch on an iOS app to keep people from accessing things outside of a small window.
Basically, I need the action to only fire if it is between 12-1:30PM on Sundays in London (BST Time Zone). How would I check the current time, convert it to that time zone, and then see if it matches up?
I have tried the following, but it always shows it is between that range:
- (NSDate *)dateByNeutralizingDateComponentsOfDate:(NSDate *)originalDate {
NSCalendar *gregorian = [[[NSCalendar alloc]
initWithCalendarIdentifier:NSGregorianCalendar] autorelease];
// Get the components for this date
NSDateComponents *components = [gregorian components: (NSYearCalendarUnit | NSMonthCalendarUnit | NSDayCalendarUnit | NSHourCalendarUnit | NSMinuteCalendarUnit | NSSecondCalendarUnit) fromDate: originalDate];
// Set the year, month and day to some values (the values are arbitrary)
[components setYear:2000];
[components setMonth:1];
[components setDay:1];
return [gregorian dateFromComponents:components];
}
- (BOOL)isTimeOfDate:(NSDate *)targetDate betweenStartDate:(NSDate *)startDate andEndDate:(NSDate *)endDate {
if (!targetDate || !startDate || !endDate) {
return NO;
}
// Make sure all the dates have the same date component.
NSDate *newStartDate = [self dateByNeutralizingDateComponentsOfDate:startDate];
NSDate *newEndDate = [self dateByNeutralizingDateComponentsOfDate:endDate];
NSDate *newTargetDate = [self dateByNeutralizingDateComponentsOfDate:targetDate];
// Compare the target with the start and end dates
NSComparisonResult compareTargetToStart = [newTargetDate compare:newStartDate];
NSComparisonResult compareTargetToEnd = [newTargetDate compare:newEndDate];
return (compareTargetToStart == NSOrderedDescending && compareTargetToEnd == NSOrderedAscending);
}
-(void)checkDate {
NSDateFormatter *dateFormatter = [[[NSDateFormatter alloc] init] autorelease];
[dateFormatter setDateFormat:#"EEEE HH:mm"];
NSTimeZone *timeZone = [NSTimeZone timeZoneWithAbbreviation:#"BST"];
[dateFormatter setTimeZone:timeZone];
NSDate *openingDate = [dateFormatter dateFromString:#"Sunday 12:00"];
NSDate *closingDate = [dateFormatter dateFromString:#"Sunday 1:30"];
NSDate *targetDate = [NSDate date];
if ([self isTimeOfDate:targetDate betweenStartDate:openingDate andEndDate:closingDate]) {
NSLog(#"TARGET IS INSIDE!");
}else {
NSLog(#"TARGET IS NOT INSIDE!");
}
}
I assume you want to use the current time as observed in England, rather than BST specifically, as BST is British Summer Time. My understanding is that, during the winter, they use UTC (formerly known as GMT). Thus we should specify the time zone in a way that will select the proper offset from UTC based on the time of year.
static BOOL dateIsAcceptable(NSDate *date) {
NSCalendar *calendar = [NSCalendar calendarWithIdentifier:NSCalendarIdentifierGregorian];
calendar.timeZone = [NSTimeZone timeZoneWithName:#"Europe/London"];
NSDateComponents *components = [calendar
components:NSCalendarUnitWeekday | NSCalendarUnitHour | NSCalendarUnitMinute
fromDate:date];
if (components.weekday != 1) {
return NO;
}
double hour = components.hour + components.minute / 60.0;
return hour >= 12 && hour < 13.5;
}
I'm creating a simple timer but am failing to get the resulting date that I'm after.
My problem is that I'm getting -34481.274523 from my NSTimeInterval (nslog at the end) whereas I'm wanting the number of seconds since the current date (currentDate). stopDate is always a date before currentDate.
The code snippet below is called from an nstimer every second. Rather than simply increment an int I'm using a date as it's easier to perform other date related calculations on and format for display.
Here is my code:
NSDate *currentDate = [NSDate date];
NSTimeInterval timeInterval = [currentDate timeIntervalSinceDate:stopDate];
NSDate *timerDate = [NSDate dateWithTimeIntervalSince1970:timeInterval];
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:#"mm:ss"];
NSString *timeString=[dateFormatter stringFromDate:timerDate];
NSLog(#"nstimeinterval: %f", timeInterval);
NSCalendar *calendar = [NSCalendar currentCalendar];
NSDateComponents *components = [calendar components: ( NSHourCalendarUnit | NSYearCalendarUnit) fromDate:timerDate];
NSLog(#"year: %li", (long)components.year);
if (components.year == 2000) {
timeString = #"00:00";
return;
}
NSLog(#"timer: %#", timeString);
timerTicksForCounter = timeString;
NSLog(#"hour: %li", (long)components.hour);
//Used to update uilabel
[self updateTimerLabel];
if (components.year < 2000) {
return;
}
if (components.hour == 0) {
..... I'm doing a bunch of stuff here