IOS: Загрузка изображения с URL-адреса и сохранение на устройстве
Я пытаюсь загрузить изображение с URL http://a3.twimg.com/profile_images/414797877/05052008321_bigger.jpg
Я использую следующий код, но изображение не сохраняется в устройстве. Я хочу знать, что я делаю неправильно.
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:@"http://a3.twimg.com/profile_images/414797877/05052008321_bigger.jpg"]];
[NSURLConnection connectionWithRequest:request delegate:self];
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *localFilePath = [documentsDirectory stringByAppendingPathComponent:@"pkm.jpg"];
NSData *thedata = NULL;
[thedata writeToFile:localFilePath atomically:YES];
UIImage *img = [[UIImage alloc] initWithData:thedata];
Ответы
Ответ 1
Если вы установите theData
на nil
, что вы ожидаете от записи на диск?
Что вы можете использовать, это NSData* theData = [NSData dataWithContentsOfURL:yourURLHere];
, чтобы загрузить данные с диска, а затем сохранить его с помощью writeToFile:atomically:
. Если вам нужно больше контролировать процесс загрузки или иметь его в фоновом режиме, посмотрите документацию NSURLConnection
и связанного с ним руководства.
Ответ 2
У меня точно есть то, что вы ищете.
Получить изображение из URL
-(UIImage *) getImageFromURL:(NSString *)fileURL {
UIImage * result;
NSData * data = [NSData dataWithContentsOfURL:[NSURL URLWithString:fileURL]];
result = [UIImage imageWithData:data];
return result;
}
Сохранить изображение
-(void) saveImage:(UIImage *)image withFileName:(NSString *)imageName ofType:(NSString *)extension inDirectory:(NSString *)directoryPath {
if ([[extension lowercaseString] isEqualToString:@"png"]) {
[UIImagePNGRepresentation(image) writeToFile:[directoryPath stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%@", imageName, @"png"]] options:NSAtomicWrite error:nil];
} else if ([[extension lowercaseString] isEqualToString:@"jpg"] || [[extension lowercaseString] isEqualToString:@"jpeg"]) {
[UIImageJPEGRepresentation(image, 1.0) writeToFile:[directoryPath stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%@", imageName, @"jpg"]] options:NSAtomicWrite error:nil];
} else {
NSLog(@"Image Save Failed\nExtension: (%@) is not recognized, use (PNG/JPG)", extension);
}
}
Загрузить изображение
-(UIImage *) loadImage:(NSString *)fileName ofType:(NSString *)extension inDirectory:(NSString *)directoryPath {
UIImage * result = [UIImage imageWithContentsOfFile:[NSString stringWithFormat:@"%@/%@.%@", directoryPath, fileName, extension]];
return result;
}
How-To
//Definitions
NSString * documentsDirectoryPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0];
//Get Image From URL
UIImage * imageFromURL = [self getImageFromURL:@"http://www.yourdomain.com/yourImage.png"];
//Save Image to Directory
[self saveImage:imageFromURL withFileName:@"My Image" ofType:@"png" inDirectory:documentsDirectoryPath];
//Load Image From Directory
UIImage * imageFromWeb = [self loadImage:@"My Image" ofType:@"png" inDirectory:documentsDirectoryPath];
Ответ 3
Это код для загрузки изображения с URL-адреса и сохранения этого изображения на устройстве, а this является ссылкой ссылки.
NSURLRequest *request = [NSURLRequest requestWithURL:[NSURL URLWithString:@"http://a3.twimg.com/profile_images/414797877/05052008321_bigger.jpg"]];
[NSURLConnection connectionWithRequest:request delegate:self];
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *localFilePath = [documentsDirectory stringByAppendingPathComponent:@"pkm.jpg"];
NSData *thedata = [NSData dataWithContentsOfURL:[NSURL URLWithString:@"http://a3.twimg.com/profile_images/414797877/05052008321_bigger.jpg"]];
[thedata writeToFile:localFilePath atomically:YES];
Ответ 4
Получить изображение из URL
-(UIImage *) getImageFromURL:(NSString *)fileURL {
UIImage * result;
NSData * data = [NSData dataWithContentsOfURL:[NSURL URLWithString:fileURL]];
result = [UIImage imageWithData:data];
return result;
}
Это отлично поработало для меня, но я столкнулся с проблемами памяти с CFData (store). Исправлено это с autoreleasepool:
-(UIImage *) getImageFromURL:(NSString *)fileURL {
@autoreleasepool {
UIImage * result;
NSData * data = [NSData dataWithContentsOfURL:[NSURL URLWithString:fileURL]];
result = [UIImage imageWithData:data];
return result;
}
}
Ответ 5
Привет. Ясно, что вы пишете NULL данные в свой файл.
В вашем кодовом выражении NSData * thedata = NULL; указывает, что вы назначаете значение NULL для своих данных.
Вы также записываете данные NULL в свой файл.
Еще раз проверьте свой код.
Ответ 6
Так как мы сейчас на IOS6, вам больше не нужно писать изображения на диск.
Начиная с iOS5 теперь вы можете установить "разрешить внешнее хранилище" на бинарный атрибут coredata.
Согласно заметкам о выпуске яблок, это означает следующее:
Небольшие значения данных, такие как миниатюры изображений, могут быть эффективно сохранены в базы данных, но фотографии с большими объемами или другие носители лучше всего обрабатывать непосредственно файловой системы. Теперь вы можете указать, что значение управляемого атрибут объекта может быть сохранен как внешняя запись - см. setAllowsExternalBinaryDataStorage:Когда включено, Core Data эвристически решает на основе стоимости, если он должен сохранять данные непосредственно в базе данных или хранить URI для отдельный файл, который он управляет для вас. Вы не можете запрашивать на основе содержимое двоичного свойства данных, если вы используете эту опцию.
Ответ 7
-(IBAction)BtnDwn:(id)sender
{
[self.actvityIndicator startAnimating];
NSURL *URL = [NSURL URLWithString:self.dataaArray];
NSURLRequest *request = [NSURLRequest requestWithURL:URL];
NSURLSession *session = [NSURLSession sharedSession];
NSURLSessionDownloadTask *downloadTask = [session downloadTaskWithRequest:request completionHandler:^(NSURL *location, NSURLResponse *response, NSError *error)
{
NSString *documentsPath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) firstObject];
NSURL *documentsDirectoryURL = [NSURL fileURLWithPath:documentsPath];
NSURL *documentURL = [documentsDirectoryURL URLByAppendingPathComponent:[response suggestedFilename]];
BOOL exists = [[NSFileManager defaultManager] fileExistsAtPath:[documentURL path]];
if (exists)
{
NSLog(@"not created");
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Download"
message:@"sory,file already exists"
delegate:nil
cancelButtonTitle:@"cancel"
otherButtonTitles:nil];
[alert show];
}
else
{
[[NSFileManager defaultManager] moveItemAtURL:location toURL:documentURL error:nil];
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"Download"
message:@"Succesfully downloaded"
delegate:nil
cancelButtonTitle:@"OK"
otherButtonTitles:nil];
[self.actvityIndicator stopAnimating];
NSLog(@"wait downloading......");
[alert show];
}
}];
[downloadTask resume];
}
Ответ 8
Вот пример того, как я загружаю баннеры в свое приложение. Я загружаю изображения в фоновом режиме, и большинство моих приложений не используют подсчет ссылок, поэтому я освобождаю объекты.
- (void)viewDidLoad {
[super viewDidLoad];
[NSThread detachNewThreadSelector:@selector(loadImageInBackground) toTarget:self withObject:nil];
}
- (void) loadImageInBackground {
NSURL *url = [[NSURL alloc] initWithString:@"http://yourImagePath.png"];
NSData *data = [[NSData alloc] initWithContentsOfURL:url];
[url release];
UIImage *result = [[UIImage alloc] initWithData:data];
[data release];
UIImageView *banner_ImageView = [[UIImageView alloc] initWithFrame:CGRectMake(0, 0, 320, 50)];
[self.view addSubview:banner_ImageView];
banner_ImageView.image = result;
[result release];
}
Ответ 9
Вот как вы можете сохранить изображение асинхронно в Swift:
requestImage("http://www.asdf.com/89asdf.gif") { (image) -> Void in
let myImage = image
}
func requestImage(url: String, success: (UIImage?) -> Void) {
requestURL(url, success: { (data) -> Void in
if let d = data {
success(UIImage(data: d))
}
})
}
func requestURL(url: String, success: (NSData?) -> Void, error: ((NSError) -> Void)? = nil) {
NSURLConnection.sendAsynchronousRequest(
NSURLRequest(URL: NSURL (string: url)!),
queue: NSOperationQueue.mainQueue(),
completionHandler: { response, data, err in
if let e = err {
error?(e)
} else {
success(data)
}
})
}
Он включен как стандартная функция в моем репо:
https://github.com/goktugyil/EZSwiftExtensions