Iphone file I/O operation and file structure - iphone

I want to write a iphone SDK program to download and upload files from server. Server application is written in php.
But I m confusing following points in client application.
1) How can I download the file from server
2) How can I store it in iphone (accessing iphone file system)
3) How can I display all file in a directory to the users.
Can anybody help me ?

Create an NSURL
NSURL * theURL = [NSURL URLWithString: #"http://foo.bar/whatever.php"];
Fetch the data with NSData
NSData * theData = [NSData dataWithContentsOfURL: theURL];
Save it to a file with the same NSData object
NSString * theFolder = [NSHomeDirectory() stringByAppendingPathComponent:#"Documents"];
NSString * theFileName = [theFolder stringByAppendingPathComponent:#"MyFile.txt"]
[theData writeToFile:theFileName atomically:true];
Use NSFileManager to list the files in the folder
NSError *error = nil;
NSFileManager* fileManager = [NSFileManager defaultManager];
NSArray * filesInFolderStringArray = [fileManager contentsOfDirectoryAtPath:theFolder error:error];
This will give you an array of NSStrings with the names of the files in the folder.

Related

The operation couldn’t be completed. (Cocoa error 260.)

I'm new on IOS development and i'm working on a pdf application and i need to store a PDF file on a NSData variable, I have the PDF path but i get this message error when i try to put this pdf on the NSData variable using dataWithContentsOfFile her is my simple code :
NSError *error;
NSString *PdfPath = [NSString stringWithFormat:(#"%#"),document.fileURL ];
NSString *newPath = [PdfPath stringByReplacingOccurrencesOfString:#"file://localhost" withString:#""];
NSLog(#"OriginalPdfPath => %#", newPath);
NSData *pdfData = [NSData dataWithContentsOfFile:newPath options:NSDataReadingUncached error:&error];
NB : the pdf path is in this format : /Users/bluesettle/Library/Application%20Support/iPhone%20Simulator/6.0/Applications/BBEF320E-7E2A-49DA-9FCF-9CFB01CC0402/ContractApp.app/Pro.iOS.Table.Views.pdf
thanks for your help
Cocoa error 260 is a NSFileReadNoSuchFileError (as listed in FoundationErrors.h), meaning the file could not be found at the path you specified.
The problem is that your path still contains encoded spaces (%20), because you're basing it on the URL. You can simply do this:
NSData *pdfData = [NSData dataWithContentsOfFile:[document.fileURL path]];
Try to use NSBundle
NSString *newPath = [[NSBundle mainBundle] pathForResource:#"filename" ofType:#"pdf"]
Edit:
Than you can use bundleWithPath method, here is an example:
NSString *documentsDir= [NSString stringWithFormat:#"%#/Documents", NSHomeDirectory()];
NSString *newPath= [[NSBundle bundleWithPath:documentsDir] bundlePath];

Check if file is already saved to disk?

I am downloading files from my server, saving them to device, and displaying them to the user in my app. I want to implement a check to see if the file already exists on the device so we can skip the download and just display, but I can't figure out the best way to do that.
I create a unique fileName for each file and then convert it to an NSURL like this:
NSString *fileString = [[NSString alloc] initWithString:[documentsDirectory stringByAppendingPathComponent:fileName]];
self.fileURL = [[NSURL alloc] initFileURLWithPath:fileString];
Then I write to file and save the URL for use shortly after:
[data writeToFile:fileString atomically:YES];
self.fileURL = [[NSURL alloc] initFileURLWithPath:fileString];
How can I check if that File or URL already exists?
Thanks
NSFileManager has a method to check if a file exists at a path:
[[NSFileManager defaultManager] fileExistsAtPath: fileString]
https://developer.apple.com/library/mac/#documentation/Cocoa/Reference/Foundation/Classes/nsfilemanager_Class/Reference/Reference.html#//apple_ref/doc/uid/20000305-CHDDDDJG

Read Image file from custom directory using NSBundle

Creating a custom directory which has all the images. Designing it custom because, it will help me to get the images as an when I need at various places in the configuration.
NSFileManager *filemgr;
filemgr = [NSFileManager defaultManager];
[filemgr createDirectoryAtPath: #"/Users/home/lifemoveson/test" withIntermediateDirectories:YES attributes: nil error:NULL];
I have placed images under test folder and are of .png types.
Is there a way to retrieve the images like below.
/** UPDATED again **/
Currently this folder is under Application_Home/Resources/ImageTiles/ as per Photoscroller example.
How can we change it to /Users/home/lifemoveson/test/ImageTiles/ folder ?
- (UIImage *)tileForScale:(CGFloat)scale row:(int)row col:(int)col
{
// we use "imageWithContentsOfFile:" instead of "imageNamed:" here because we don't want UIImage to cache our tiles
NSString *tileName = [NSString stringWithFormat:#"%#_%d_%d_%d", imageName, (int)(scale * 1000), col, row];
// Currently this folder is under <Application_Home>/Resources/ImageTiles/ as per Photoscroller example.
// How can we change it to /Users/home/lifemoveson/test/ImageTiles/ folder ?
NSString *path = [[NSBundle mainBundle] pathForResource:tileName ofType:#"png"];
UIImage *image = [UIImage imageWithContentsOfFile:path];
return image;
}
Applications running on iOS are sandboxed; you can't simply create directories wherever you please. Your createDirectoryAtPath: call will fail. You should use one of the directories set aside for your application instead.
Once you obtain the path for one of those directories, getting the path for files within them is simply a case of using NSString's stringByAppendingPathComponent: method.
Makin a call to the functions such as
NSString* newDirPath = [self createDirectoryWithName:#"Test"];
if (newDirPath) {
[self saveFile:#"MasterDB.sqlite" atPath:newDirPath];
}
which are implemented as follows
-(NSString*)createDirectoryWithName:(NSString*)dirName{
NSArray* directoryArray = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask , YES);
NSString* directoryPath = [directoryArray objectAtIndex:0];
NSString* newPath = [directoryPath stringByAppendingString:[NSString stringWithFormat:#"/%#",dirName]];
NSFileManager *filemamager = [NSFileManager defaultManager];
BOOL flag = [filemamager createDirectoryAtPath:newPath withIntermediateDirectories:YES attributes: nil error:NULL];
return flag == YES ?newPath: nil;
}
-(BOOL)saveFile:(NSString*)fileName atPath:(NSString*)path{
BOOL success;
// Create a FileManager object, we will use this to check the status
// of the File and to copy it over if required
NSFileManager *fileManager = [NSFileManager defaultManager];
// Check if the File has already been created in the users filesystem
NSString *filePath = [path stringByAppendingPathComponent:fileName];
success = [fileManager fileExistsAtPath:filePath];
// If the File already exists then return without doing anything
if(success) return YES;
// If not then proceed to copy the File from the application to the users filesystem
// Get the path to the database in the application package
NSString *pathFromApp = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:fileName];
// Copy the database from the package to the users filesystem
NSError *error = nil;
BOOL flag = [fileManager copyItemAtPath:pathFromApp toPath:filePath error:&error];
return flag;
}
might help you solve your problem. Creating a directory is achieved using first function and the second will let you save files from your application bundle to any of the previously created directory. I hope you can modify it save files located at places other than Application bundle to suit to your need.

Store and Load File from URL

iPhone App
I am currently trying to understand how i can store a file from a URL to the documents directory and then read the file from the documents directory..
NSURL *url = [NSURL URLWithString:#"http://some.website.com/file"];
NSData *data = [NSData dataWithContentsOfURL:url];
NSString *applicationDocumentsDir = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject];
NSString *storePath = [applicationDocumentsDir stringByAppendingPathComponent:#"Timetable.ics"];
[data writeToFile:storePath atomically:TRUE];
I got this code from http://swatiardeshna.blogspot.com/2010/06/how-to-save-file-to-iphone-documents.html
I want to know if this is the correct way to do this and i want to know how i can load the file from the documents directory into an NSString..
Any help will be greatly appreciated.
What you have looks correct, to read that file back into a string use:
EDIT: (changed usedEncoding to encoding)
NSError *error = nil;
NSString *fileContents = [NSString stringWithContentsOfFile:storePath encoding:NSUTF8StringEncoding error:&error];
Of course you should change the string encoding type if you are using a specific encoding type, but UTF8 is likely correct.
If you're doing this on your main thread, then no it's not correct. Any sort of network connection should be done in the background so you don't lock up the interface. For that, you can create a new thread (NSThread, performSelectorInBackground:, NSOperation+NSOperationQueue) or schedule it on the run loop (NSURLConnection).

Geo-tagging a photo on the iPhone?

A link or a bit of code would be much appreciated!
I have an app that lets users take photos. Here's the code I use to create the jpeg file.
How can I add a geo-tag to the photo's EXIF data, assuming the parameter info has a lat and lon?
- (void) saveImage:(NSDictionary*) info {
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *filePath = [self applicationDocumentsDirectory]
stringByAppendingString: #"/photos/"];
[fileManager createDirectoryAtPath: filePath withIntermediateDirectories: NO attributes: nil error: nil];
filePath = [filePath stringByAppendingString: [info objectForKey: #"title"]];
filePath = [filePath stringByAppendingString: #".jpg"];
[fileManager createFileAtPath:filePath contents:nil attributes:nil];
NSFileHandle *fileHandle = [NSFileHandle fileHandleForWritingAtPath:filePath];
NSData * imgData = [[NSData alloc] initWithData:
UIImageJPEGRepresentation([info objectForKey: #"image"],.8)];
[fileHandle writeData:imgData];
[fileHandle closeFile];
[imgData release];
}
iPhone photos are automatically geotagged in the JPEG EXIF
The iPhone does not currently offer the ImageIO library that can be used for this on the Mac. Take a look at the iphone-exif project, it might provide what you need.
Also, a few notes about your code, if I may.
NSString has many path methods that you should use to make your intent more clear when handling paths.
UIImageJPEGRepresentation already returns an autoreleased NSData instance. It's a common mistake for beginners, but you are wasting code and adding extra memory management work by creating a new NSData instance with the old one.
NSData has a method -writeToFile:options:error: that will let you get rid of all that extra NSFileHandle code. I think it will also save you from having to create the file with NSFileManager first.
Alternatively, you could pass the data from UIImageJPEGRepresentation into the contents parameter of -[NSFileManager createFileAtPath:contents:attributes:]