How do you get a numerical value from a UIDatepicker? - iphone

i am developing an app that involves getting a value from a datepicker and subtracting it from the date displayed on the actual iphone. how will i do this? i have looked everywhere for an answer!
thanks Rafee

You should implement datePickerValueChanged as the selector, and implement like this.
- (void)datePickerValueChanged:(UIDatePicker*) date_Picker{
NSDateFormatter *df = [[NSDateFormatter alloc] init];
df.dateStyle = NSDateFormatterMediumStyle;
NSString *dateFromPicker = [NSString stringWithFormat:#"%#",[df stringFromDate:date_Picker.date]];
// calculating time difference now
NSDate *timeRightNow = [NSDate date];
NSTimeInterval diff = [timeRightNow timeIntervalSinceDate:date_Picker.date];
// The difference should always be in seconds. Here, 3628800 represents 6 weeks.
if (diff > 3628800){
// Do something if the entered date is six weeks from the iPhone date.
}
}

Related

Generating Date Logic for UIPickerView

I am new to ios development.
I am making a custom datepicker using UIPickerView.
I have to show dates ranging from today to next 20 days & I am done with generating those dates & assigning them to an array.Those Dates have format: Oct 16,2013.
But my problem is I want to show Weekday(in 3 characters),Month & day i.e. Wed,Oct 16 on UIpickerView. And for one current week only Days are shown i.e today,tomorrow,Fri,Sat,Sun,Mon,Tue and for Next Week it would have Wed,Oct 23 and so on.
Thanks in advance! Any help would be greatly appreciated!
Assuming that you have a NSDate object called myDate for example, You need to format the dates using a date formater:
NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
[dateFormat setDateFormat:#"EEE, LLL d"];
NSString *myString = [dateFormat stringFromDate:myDate];
You can find the formatters and what they mean here:
NSDateFormatter formatting
To get today:
NSdate *today = [NSDate date];
Tomorrow:
NSDate *tomorrow = [NSDate dateWithTimeInterval:(24*60*60) sinceDate:[NSDate date]]
After tomorrow:
NSDate *afterTomorrow = [NSDate dateWithTimeInterval:(24*60*60) sinceDate:tomorrow]

Time difference between two times in iPhone

I have two times :
10:23:51
10:31:54
Both values are stored as strings in a SQLite database.
I want to find the difference between these two times in hh:mm format.
How can I do this?
I have searched a lot. But can't find a proper solution.
Help me out.
Thanks.
Edit :
See basically I am having two arrays:
InTimeArray and OuttimeArray.
Now in the viewDidload method , I am fetching all the intime entries in the IntimeArray and Outtime entries in the outtime Arrays.
Now I am passing one by one values in tableview like in 1st row
IntimeArray[0]
OuyTimeArray[0]
second row:
IntimeArray[1]
OuyTimeArray[1]
Now I want to count the differences between 1st row's intime and outtime in HH:MM format.
I am really confused.
you can take a look at that :
-(NSDate *)dateFromString:(NSString *)string
{
NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
NSLocale *locale = [[NSLocale alloc] initWithLocaleIdentifier:#"en_US"];
[dateFormat setLocale:locale];
[dateFormat setDateFormat:#"HH:mm:ss"];
NSDate *date1 = [dateFormat dateFromString:string];
if(!date1) date1= [NSDate date];
[dateFormat release];
[locale release];
return date1;
}
this will turn the NSDate to you and when you change them both to NSDates then you can learn the difference by looking at this.
i hope this will help you..
You have to first change your both strings into date format using this method :-
- (NSDate *)dateFromString:(NSString *)string;
after that you just have to calculate number of seconds between both the dates.Thats it.
OR there is another simple way to do this. i.e.
get dates from both arrays first like this:-
NSDate *eventStartDate = [IntimeArray objectAtIndex:indexpath.row];
NSDate *eventEndDate = [OuyTimeArray objectAtIndex:indexpath.row];
Then calculate difference between both the dates like this :-
NSTimeInterval startTimeInterval = [eventStartDate timeIntervalSinceDate:currentDate];
Hope it helps Thanks :)
Try this:
NSDateFormatter *formatter = [[[NSDateFormatter alloc] init] autorelease];
[formatter setDateFormat:#"HH:mm:ss"];
NSDate *d1 = [formatter dateFromString:IntimeArray[0]];
NSDate *d2 = [formatter dateFromString:OuyTimeArray[0]];
NSTimeInterval ti = [d2 timeIntervalSinceDate:d1];
float hours = floor(ti / 3600);
float minutes = floor((ti - hours*3600) / 60);
NSString *s = [NSString stringWithFormat:#"%02.0f:%02.0f",hours,minutes];
For your given example, NSLog(#"Time passed: %#",s); will print 00:08.

iPhone - Strange problem with NSDate, NSString, and Timezones

I've searched and haven't found an exact question like mine, so here goes nothing:
I have a NSString containing a key that I pull from an XML feed. The key is a time in 24-hour format (e.g. 13:30 or 15:00.) I'd like to convert the NSString to an NSDate and have it converted to the appropriate timezone based on the device's set timezone. The key is Unicode HH:mm (24:00), so I'm curious why this does not work as it should.
I've already gotten a basic outline that should work, but alas does not. The 2nd NSLog (Got NS Date) returns null and the final log returns a strange number (1969-12--2147483629 -596:-31:-23 +0000 to be precise.) What am I doing wrong here?
Thanks in advance,
NSString *dateString = [dict objectForKey:#"24hrdate"];
NSLog(#"NSString Date: %#", dateString);
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:#"HH:mm"];
NSDate *sourceDate = [formatter dateFromString:dateString];
NSLog(#"Got NS Date: %#", sourceDate);
NSTimeZone *sourceTimeZone = [NSTimeZone timeZoneWithAbbreviation:#"GMT"];
NSTimeZone *destinationTimeZone = [NSTimeZone systemTimeZone];
NSInteger sourceGMTOffset = [sourceTimeZone secondsFromGMTForDate:sourceDate];
NSInteger destinationGMTOffset = [destinationTimeZone secondsFromGMTForDate:sourceDate];
NSTimeInterval interval = destinationGMTOffset - sourceGMTOffset;
NSDate* destinationDate = [[[NSDate alloc] initWithTimeInterval:interval sinceDate:sourceDate] autorelease];
NSLog(#"Final Date: %#", destinationDate);
First of all understand that the date component will be 01-01-1970 because it isn't provided. I am assuming that you want the time to be 04:00 GMT if the input string is #"04:00". That you can achieve by setting the time zone of the formatter.
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setTimeZone:[NSTimeZone timeZoneWithName:#"GMT"]];
[formatter setDateFormat:#"HH:mm"];
NSDate *sourceDate = [formatter dateFromString:dateString];
NSDate is used to represent a date and time. While you can represent just a date by sticking with midnight, you can't really represent just a time of day with it. You can sort of fake this on the Mac (it defaults to some reasonable day), but on iOS you'll get wildly inaccurate times instead. (At least, you do on certain versions. This may have been fixed.)
There's two approaches here:
You can build a NSDateComponents from your time of day and using dateByAddingComponents to add that to midnight on the date you want the time to appear on. This will fail to return the time you expect on a day where daylight savings begins or ends.
You can build a date/time string using the date you want (NSDate) and the time (likely, as a NSString).
- (NSDate *)timeInHours: (NSInteger)hours
minutes: (NSInteger)minutes
seconds: (NSInteger)seconds
onDate: (NSDate *)inDate;
{
id timeStr = [[NSMutableString alloc] initWithFormat: #"%02d:%02d:%02d", hours, minutes, seconds];
id dateStr = [dateWithoutTimeFormatter stringFromDate: inDate];
id dateTimeStr = [[NSString alloc] initWithFormat: #"%# %#", dateStr, timeStr];
[timeStr release];
id dateTime = [dateWithTimeFormatter dateFromString: dateTimeStr];
[dateTimeStr release];
return dateTime;
}
If you really want just the time of day, just keep it around as a string.
Just wanted to post back that I did manage to achieve what I initially set out to do without any issues. Basically, I had to convert the string to NSDate, run that NSDate through a NSDateFormatter (set to the time's original timezone--NSDateFormatter's setTimeZone was helpful), pull an NSDate out of that, and then run that through another NSDateFormatter for the device's timezone. I then converted the resulting NSDate back to NSString, and stuck it on a UILabel.
This solution seems to have worked quite well, as I've set my devices to various timezones, and the timezone change is still correct.
EDIT: this was important to included, too:
NSString *date…….
date = [date stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];

Comparing a date from the picker to current date

In my date picker i can select a date from the list.
I save it in my string pickUpDateTime
self.pickUpDateTime = [NSString stringWithString:[apiFormat stringFromDate:d]];
I'm having a problem where the user is able to pick a date in the past. Is there some way to get the current day and check that its in the future?
My string holds the date like this 2010-11-04.
The user shouldnt be able to select a day in the past or the current day.
Thanks
-Code
You can get the current date and time with:
NSDate *now = [NSDate date];
Compare the 2 dates with:
if ([d compare:now] == NSOrderedDescending) {
// d is later than now
} else {
// d is earlier than or equal to now
}
If you're using a UIDatePicker, just set
datePicker.minimumDate = [NSDate dateWithTimeIntervalSinceNow:24*3600];
e.g. to allow dates starting tomorrow. Working back from the date string "2010-11-04" to a NSDate object is possible but cumbersome. (but if you insist, have a look at NSDateFormatter)
Lots of answers above give good advice about working with NSDates in general; things are a tiny bit more complicated if you want to round to the start of the day to say e.g. 'at least tomorrow' rather than 'at least 24 hours away'.
In general terms:
get an instance of NSCalendar to represent the Gregorian calendar
use the NSCalendar to convert an NSDate into an NSDateComponents representing just the day, month and year
use the NSCalendar to convert the NSDateComponents back into an NSDate
use arithmetic as recommended elsewhere to increment the NSDate a day into the future, for example
I have to dash, but relevant methods are:
NSCalendar +currentCalendar or -initWithCalendarIdentifier:NSGregorianCalendar to be extra safe
NSCalendar -components:fromDate: (the first parameter is a flag field indicating which bits of the date you need to be filled in) and -dateFromComponents:
NSDate -timeIntervalSinceDate:
NSDateFormatter *df = [[NSDateFormatter alloc] init];
df.dateStyle = NSDateFormatterMediumStyle;
NSString *tempStr=[NSString stringWithFormat:#"%#",[df stringFromDate:datePicker.date]];
txtBirth.text=tempStr;
NSString *birthDate = tempStr;
NSDate *todayDate = [NSDate date];
int time = [todayDate timeIntervalSinceDate:[df dateFromString:birthDate]];
int numberOfDays = time/86400;
hear number of data return data difference.....

NSDateFormatter, am I doing something wrong or is this a bug?

I'm trying to print out the date in a certain format:
NSDate *today = [[NSDate alloc] init];
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setDateFormat:#"yyyyMMddHHmmss"];
NSString *dateStr = [dateFormatter stringFromDate:today];
If the iPhone is set to 24 hour time, this works fine, if on the other hand the user has set it to 24 hour time, then back to AM/PM (it works fine until you toggle this setting) then it appends the AM/PM on the end even though I didn't ask for it:
20080927030337 PM
Am I doing something wrong or is this a bug with firmware 2.1?
Edit 1: Made description clearer
Edit 2 workaround: It turns out this is a bug, to fix it I set the AM and PM characters to "":
[dateFormatter setAMSymbol:#""];
[dateFormatter setPMSymbol:#""];
The reason for this behaviour is Locale, It sets the correct Locale.
Set the local of your NSDateFormatter to en_US_POSIX will fix this.
It works for both 24-hour and 12 hour format.
On iPhone OS, the user can override the default AM/PM versus 24-hour time setting (via Settings > General > Date & Time > 24-Hour Time), which causes NSDateFormatter to rewrite the format string you set. From apple doc
Try this,
NSDate *today = [[NSDate alloc] init];
NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
[dateFormatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:#"en_US_POSIX"]];
[dateFormatter setDateFormat:#"yyyyMMddHHmmss"];
NSString *dateStr = [dateFormatter stringFromDate:today];
Here's the explanation of the iPhone SDK bug (also still there in 3.1 beta SDK)
First, a little background on the iPhone user interface. When iPhone
users change their region format between, say, “United States” and
“France”, the users’ “24-Hour Time” setting is automatically switched
to the mode that is most prevalent in that region. In France, that
would set 24-Hour Time to “ON”, and in the U.S., that would set it to
“OFF”. The users can then manually override that setting and that’s
where trouble starts.
The problem comes from NSDateFormatter somehow “getting stuck” in the
12 or 24-hour time mode that the user has manually selected. So if a
French user manually selects 12-hour mode, and the application
requested NSDateFormatter to output time with the 24-hour format
“HHmm”, it would actually receive time in a 12-hour format, e.g.
“01:00 PM”, as if the application had instead requested “hhmm aa”.
The reverse would happen if a US user manually selected 24-hour mode:
outputting time with the 12-hour format “hhmm aa” would actually get
you time in the 24-hour format instead, e.g. “17:00″.
More details and a possible workaround can be found on this blog.
Using the code you posted on both the simulator and a phone with the 2.1 firmware and 24-hour time set to off, I never had an AM/PM appended to dateStr when I do:
NSLog(#"%#", dateStr);
Are you doing anything else with dateStr that you didn't post here? How are you checking the value?
Follow up
Try turning the am/pm setting on then off. I didn't have the problem either, until I did that. I am printing it out the same way you are.
Okay, I see it when I do this also. It's gotta be a bug. I recommend you file a bug report and just check for and filter out the unwanted characters in the meantime.
Setting locale on date formatter to en_US fixes the problem for me:
NSDateFormatter * f = [[NSDateFormatter alloc] init];
[f setDateFormat:#"yyyy-MM-dd'T'HH:mm:ss'Z'"];
f.timeZone = [NSTimeZone timeZoneForSecondsFromGMT:0];
f.calendar = [[[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar] autorelease];
f.locale = [[[NSLocale alloc] initWithLocaleIdentifier:#"en_US"] autorelease];
I'm not sure if adding the calendar is also needed, but this works well.
I think this is the solution .
NSDateFormatter *df =[[NSDateFormatter alloc] init];
[df setDateFormat:#"yyyy-MM-dd HH:mm:ss"];
NSLocale *usLocale = [[NSLocale alloc] initWithLocaleIdentifier:#"en_US"];
[df setLocale: usLocale];
[usLocale release];
NSDate *documento_en_Linea =[[[NSDate alloc] init]autorelease];
documento_en_Linea=[df dateFromString:#"2010-07-16 21:40:33"];
[df release];
NSLog(#"fdocumentoenLineaUTC:%#!",documento_en_Linea);
//ouput
fdocumentoenLineaUTC:2010-07-16 09:40:33 p.m. -0500!
For those finding this question who want to use NSDateFormatter to parse 24-hour time and are hitting this bug, using NSDateComponents to parse dates and times which have a known format sidesteps this issue:
NSString *dateStr = #"2010-07-05";
NSString *timeStr = #"13:30";
NSDateComponents *components = [[NSDateComponents alloc] init];
components.year = [[dateStr substringToIndex:4] intValue];
components.month = [[dateStr substringWithRange:NSMakeRange(5, 2)] intValue];
components.day = [[dateStr substringFromIndex:8] intValue];
components.hour = [[timeStr substringToIndex:2] intValue];
components.minute = [[timeStr substringFromIndex:3] intValue];
NSCalendar *calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
NSDate *date = [calendar dateFromComponents:components];
[components release];
[calendar release];
This should also work (I am seeing some bizzare results though).
-(NSString*)lowLevTime:(NSString*)stringFormat {
char buffer[50];
const char *format = [stringFormat UTF8String];
time_t rawtime;
struct tm * timeinfo;
time(&rawtime);
timeinfo = localtime(&rawtime);
strftime(buffer, sizeof(buffer), format, timeinfo);
return [NSString stringWithCString:buffer encoding:NSASCIIStringEncoding];
}
Short answer: try [dateFormatter setDateFormat:#"yyyyMMddhhmmss"]; for 12 hour format (note the lowercase hh).
It's been a frustrating topic because so many websites indicate to use HH for hours (including the official Apple documentation), but that sets it to 24 hour format, whereas hh uses 12 hour format. See http://unicode.org/reports/tr35/tr35-6.html#Date_Format_Patterns for more details.
As a bonus, note that you can also use KK or kk for hour of the day format, which will likely be off by one.
Update:
I was recently looking at NSLocale (https://developer.apple.com/library/mac/#documentation/Cocoa/Reference/Foundation/Classes/NSLocale_Class/Reference/Reference.html) and it would seem that you can use autoupdatingCurrentLocale to apply changes made from within the app to the Locale. The upshot of this is that even if the phone is set to use a 24 hour clock (like when you switched to France), you can make a 12/24 toggle for the app that won't impact any other apps on the phone, or require you to leave the app to make the change.