2016-04-25 71 views
0

所以我已經經歷了幾乎所有關於SO的問題,我已經把它們放在一起來創建一個接受兩個參數的方法,首先是要下載並顯示在UIImageView中的圖像的URL其次是那個UIImageView的佔位符圖像。我想保存圖像,以便它不會每次都下載。我已經使用SDWebImage來下載圖像,但是在使用SDWebImage將圖像保存到文檔目錄時,我有些困惑,所以我決定不使用它。我用dispatch_sync(dispatch_get_main_queue(),我的方法現在看起來像:異步保存圖像

- (void)saveImageFromURL:(UIImage*)image:(NSURL*)imageURL { 

NSString *url = [imageURL absoluteString]; 
NSArray *parts = [url componentsSeparatedByString:@"/"]; 
NSString *filename = [parts lastObject]; 

NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); 
NSString *documentsDirectory = [paths objectAtIndex:0]; 

NSString *fullPath = [documentsDirectory stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.png", filename]]; 
BOOL fileExists = [[NSFileManager defaultManager] fileExistsAtPath:fullPath]; 

if (fileExists) { 
    NSLog(@"File already exists"); 
    _myUIImage.image = [UIImage imageNamed:fullPath]; 
    return; 
} 

else { 
    dispatch_async(dispatch_get_main_queue(), ^{ 
     [self.myUIImage sd_setImageWithURL:imageURL placeholderImage:image]; 
     UIImage *imageFromURL = [UIImage imageWithData:[NSData dataWithContentsOfURL:imageURL]]; 
     NSData *imageDataNew = UIImagePNGRepresentation(imageFromURL); 
     NSFileManager *fileManager = [NSFileManager defaultManager]; 
     [fileManager createFileAtPath:fullPath contents:imageDataNew attributes:nil]; 
    }); 
    } 
} 

我有幾個問題,這是落實不夠好,因爲我是在一個應用程序,會在應用程序商店的工作?從URL下載圖像是否會異步完成? (我知道我使用dispatch_async,但只需要確認)。如果是的話,那麼這不會阻止我的用戶界面,對吧?

+0

很難。因爲您在dispatch_get_main_queue中執行此操作 – heximal

+0

您的意思是輸入:dispatch_sync(dispatch_get_main_queue()'''沒有最後一個括號,或者是一個拼寫錯誤嗎? –

+0

dispatch_sync - 正如您可以期望的那樣 - 它會這意味着如果你從主線程調用saveImageFromURL - 它將被阻塞。更多dispatch_get_main_queue() - 實際上是一個主線程。 因此,你的實現將阻止UI。 – DoN1cK

回答

0
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^(void){ 

// *** Load Image from URL Asynchronously without blocking Main thread ***  
UIImage *imageFromURL = [UIImage imageWithData:[NSData dataWithContentsOfURL:imageURL]]; 

    dispatch_async(dispatch_get_main_queue(), ^(void){ 

     // *** Create file path to DocumentDirectory *** 
     NSString * docDirPath = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES)[0]; 
     NSString *filePath = [docDirPath stringByAppendingPathComponent:@"myImage.jpg"] 

     // *** Write Image to disk *** 
     BOOL isSaved = [UIImageJPEGRepresentation(image, 1.0f) writeToFile:dirPath atomically:YES]; 
     if(isSaved) 
     { 
      NSLog(@"Image write to disc successfully."); 
     } 
    }); 
}); 
+0

而不是像我這樣做,我可以不像異步保存圖像,兩者之間有什麼區別。對不起,我是iOS開發新手。 – TKutal

+0

你可以這樣做,但是當你有下載圖像的情況時,保存並顯示在'UIImageView'中,那麼你需要在'dispatch_async(dispatch_get_main_queue(),^(void)'中更新它,否則它會不在屏幕上反映所有UI操作必須在主線上執行 –

+0

對不起,但我沒有得到你想表達的意思,你的意思是說如果圖像不在我的目錄中,那麼我的代碼不會工作? – TKutal