3

i am little bit new at iPhone application development.So at first sorry from my side if it is a lame question.Now my question is.In my app user has dial of clock where he will select hour and minute.using that hour and minute i want to set alarm for user according to alarm system and later it will set for local notification,My local notification is working only alarm time is showing wrong.So far i have done like this

NSCalendar *calendar = [NSCalendar autoupdatingCurrentCalendar];
calendar.timeZone = [NSTimeZone defaultTimeZone];
calendar.locale = [[NSLocale alloc]initWithLocaleIdentifier:@"en_US_POSIX"];

NSDateComponents *currentTimeComponents = [calendar   components:NSCalendarUnitYear|NSCalendarUnitMonth|NSCalendarUnitDay|NSCalendarUnitHour|NSCalendarUnitMinute fromDate:[NSDate date]];
currentTimeComponents.hour = [_hourlLabel.text intValue];
currentTimeComponents.minute = [_minuteLabel.text intValue];
currentTimeComponents.second = 00;
NSDate *date = [calendar dateFromComponents:currentTimeComponents];
NSLog(@"User set date: %@",date);


UILocalNotification *localNotification = [[UILocalNotification alloc] init];
localNotification.repeatInterval = NSCalendarUnitDay;
localNotification.timeZone = [NSTimeZone defaultTimeZone];

// Schedule the notification
localNotification.fireDate = date;
localNotification.alertBody = @"It has notification from xxxx";
localNotification.alertAction = @"Show me the item";
localNotification.applicationIconBadgeNumber = [[UIApplication sharedApplication] applicationIconBadgeNumber] + 1;
localNotification.soundName = @"clockalarmfrog.mp3";

[[UIApplication sharedApplication] scheduleLocalNotification:localNotification];
NSLog(@"User setup local notifications: %@",localNotification);

NSTimeInterval secs = [localNotification.fireDate timeIntervalSinceDate:[NSDate date]];
NSLog(@"animation time duration in NSTimeInterval: %f",secs);

Now suppose user has set 5:51 PM for next alarm time and current time is 5:20 PM.Now using my code i get this.

2015-05-29 17:20:11.626 xxxx[651:12248] 17:20:11 PM
2015-05-29 17:21:05.988 xxxx[651:12248] User set date: 2015-05-28 23:51:00 +0000
2015-05-29 17:21:06.099 xxxx[651:12248] User setup local notifications:  <UIConcreteLocalNotification: 0x7fd9a8c7de60>{fire date = Friday, May 29, 2015 at 5:51:00 AM Bangladesh Standard Time, time zone = Asia/Dhaka (GMT+6) offset  21600, repeat interval = NSCalendarUnitDay, repeat count =     UILocalNotificationInfiniteRepeatCount, next fire date = Saturday, May 30, 2015 at 5:51:00 AM Bangladesh Standard Time, user info = (null)}
2015-05-29 17:21:06.099 xxxx[651:12248] animation time duration in NSTimeInterval: -41406.099645
2015-05-29 17:21:06.099 xxxx[651:12248] animation reverse time duration in NSTimeInterval: 44993.900355
2015-05-29 17:21:06.168 xxxx[651:12248] duration: 44993.900355 
Juan Catalan
  • 2,299
  • 1
  • 17
  • 23
Emon
  • 452
  • 3
  • 11
  • 21

3 Answers3

1

Change

localNotification.timeZone = [NSTimeZone defaultTimeZone];

to

localNotification.timeZone = [NSTimeZone localTimeZone];
Shruti
  • 1,849
  • 1
  • 13
  • 21
  • i also tried that. :( its not working. Actually problem on AM/PM i am setting PM/AM but it always calculation for AM. – Emon May 29 '15 at 11:35
1

You need to set current time format with AM/PM to Local Notification fireDate property in order to fire alarm at current time.

Below method is used to convert your Hours, Minutes and Period(AM/PM) to current date format..so that it fires the alarm with specified time.

//Add this method

- (NSDate *)dateModifiedWithHours:(NSString *)hours
                           minutes:(NSString *)minutes
                         andPeriod:(NSString *)period
{
    NSDate *dateModified = NSDate.date;

    NSCalendar *calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];

    NSDateComponents *components = [calendar components:NSYearCalendarUnit|NSMonthCalendarUnit|NSDayCalendarUnit|NSMinuteCalendarUnit fromDate:dateModified];

    [components setMinute:minutes.intValue];

    int hour = 0;

    if ([period.uppercaseString isEqualToString:@"AM"]) {

        if (hours.intValue == 12) {
            hour = 0;
        }
        else {
            hour = hours.intValue;
        }
    }
    else if ([period.uppercaseString isEqualToString:@"PM"]) {

        if (hours.intValue != 12) {
            hour = hours.intValue + 12;
        }
        else {
            hour = 12;
        }
    }
    [components setHour:hour];

    dateModified = [calendar dateFromComponents:components];

    return dateModified;
} 

Modify your code as below

NSCalendar *calendar = [NSCalendar autoupdatingCurrentCalendar];
calendar.timeZone = [NSTimeZone defaultTimeZone];
calendar.locale = [[NSLocale alloc]initWithLocaleIdentifier:@"en_US_POSIX"];

NSDateComponents *currentTimeComponents = [calendar   components:NSCalendarUnitYear|NSCalendarUnitMonth|NSCalendarUnitDay|NSCalendarUnitHour|NSCalendarUnitMinute fromDate:[NSDate date]];
currentTimeComponents.hour = [_hourlLabel.text intValue];
currentTimeComponents.minute = [_minuteLabel.text intValue];
currentTimeComponents.second = 00;
NSDate *date = [calendar dateFromComponents:currentTimeComponents];
NSLog(@"User set date: %@",date);


UILocalNotification *localNotification = [[UILocalNotification alloc] init];
localNotification.repeatInterval = NSCalendarUnitDay;
localNotification.timeZone = [NSTimeZone defaultTimeZone];


NSDate *firedModifiedDate = [self dateModifiedWithHours:@"5"
                                               minutes:@"51"
                                             andPeriod:@"pm"];

// Schedule the notification
localNotification.fireDate = firedModifiedDate;
localNotification.alertBody = @"It has notification from xxxx";
localNotification.alertAction = @"Show me the item";
localNotification.applicationIconBadgeNumber = [[UIApplication sharedApplication] applicationIconBadgeNumber] + 1;
localNotification.soundName = @"clockalarmfrog.mp3";

[[UIApplication sharedApplication] scheduleLocalNotification:localNotification];
NSLog(@"User setup local notifications: %@",localNotification);

NSTimeInterval secs = [localNotification.fireDate timeIntervalSinceDate:[NSDate date]];
NSLog(@"animation time duration in NSTimeInterval: %f",secs);

Then your Log looks like below

2015-05-29 17:21:06.099 xxxx[651:12248] User setup local notifications:  <UIConcreteLocalNotification: 0x7fd9a8c7de60>{fire date = Friday, May 29, 2015 at 5:51:00 PM Bangladesh Standard Time, time zone = Asia/Dhaka (GMT+6) offset  21600, repeat interval = NSCalendarUnitDay, repeat count =     UILocalNotificationInfiniteRepeatCount, next fire date = Saturday, May 30, 2015 at 5:51:00 AM Bangladesh Standard Time, user info = (null)}

Hope it helps you..to fix.

Vidhyanand
  • 5,369
  • 4
  • 26
  • 59
  • Thank you very much.Let me check. – Emon Jun 02 '15 at 05:51
  • I am facing another problem regarding your answer,If i make the minute time lower than current minute then it shows me wrong time interval.what can i do for that? – Emon Jun 03 '15 at 16:25
0

[NSDate date] always return GMT+0 date, no matter where is your timezone.

The date you are passing to UILocalNotification has GMT+0, whereas [localNotification.timezone] set to defaultTimeZone(which is GMT +6 in your case).

// the time zone to interpret fireDate in. pass nil if fireDate is an absolute GMT time (e.g. for an egg timer).
// pass a time zone to interpret fireDate as a wall time to be adjusted automatically upon time zone changes (e.g. for an alarm clock).
@property(nonatomic,copy) NSTimeZone *timeZone;

to get correct expected output, either set localNotification.timeZone = nil; or update the date accordingly to defaultTimeZone(GMT +6) and set to fireDate.

jkr
  • 630
  • 1
  • 11
  • 24