標籤:dma info view 添加 clear sdi 常用 memory err
一、SDWebImage內部實現過程
1, 入口 setImageWithURL:placeholderImage:options: 會先把 placeholderImage 顯示,然後 SDWebImageManager 根據 URL 開始處理圖片。
2, 進入 SDWebImageManager-downloadWithURL:delegate:options:userInfo:,交給 SDImageCache 從緩衝尋找圖片是否已經下載 queryDiskCacheForKey:delegate:userInfo:.
3, 先從記憶體配置圖片緩衝尋找是否有圖片,如果記憶體中已經有圖片緩衝,SDImageCacheDelegate 回調 imageCache:didFindImage:forKey:userInfo: 到 SDWebImageManager。
4, SDWebImageManagerDelegate 回調 webImageManager:didFinishWithImage: 到 UIImageView+WebCache 等前端展示圖片。
5, 如果記憶體緩衝中沒有,產生 NSInvocationOperation 添加到隊列開始從硬碟尋找圖片是否已經緩衝。
6, 根據 URLKey 在硬碟緩衝目錄下嘗試讀取圖片檔案。這一步是在 NSOperation 進行的操作,所以回主線程進行結果回調 notifyDelegate:。
7, 如果上一操作從硬碟讀取到了圖片,將圖片添加到記憶體緩衝中(如果空閑記憶體過小,會先清空記憶體緩衝)。SDImageCacheDelegate 回調 imageCache:didFindImage:forKey:userInfo:。進而回調展示圖片。
8, 如果從硬碟緩衝目錄讀取不到圖片,說明所有緩衝都不存在該圖片,需要下載圖片,回調 imageCache:didNotFindImageForKey:userInfo:。
9, 共用或重建一個下載器 SDWebImageDownloader 開始下載圖片。
10, 圖片下載由 NSURLConnection 來做,實現相關 delegate 來判斷圖片下載中、下載完成和下載失敗。
11, connection:didReceiveData: 中利用 ImageIO 做了按圖片下載進度載入效果。
12, connectionDidFinishLoading: 資料下載完成後交給 SDWebImageDecoder 做圖片解碼處理。
13, 圖片解碼處理在一個 NSOperationQueue 完成,不會拖慢主線程 UI。如果有需要對下載的圖片進行二次處理,最好也在這裡完成,效率會好很多。
14, 在主線程 notifyDelegateOnMainThreadWithInfo: 宣告解碼完成,imageDecoder:didFinishDecodingImage:userInfo: 回調給 SDWebImageDownloader。
15, imageDownloader:didFinishWithImage: 回調給 SDWebImageManager 告知圖片下載完成。
16, 通知所有的 downloadDelegates 下載完成,回調給需要的地方展示圖片。
17, 將圖片儲存到 SDImageCache 中,記憶體緩衝和硬碟緩衝同時儲存。寫檔案到硬碟也在以單獨 NSInvocationOperation 完成,避免拖慢主線程。
18, SDImageCache 在初始化的時候會註冊一些訊息通知,在記憶體警告或退到背景時候清理記憶體配置圖片緩衝,應用結束的時候清理到期圖片。
19, SDWI 也提供了 UIButton+WebCache 和 MKAnnotationView+WebCache,方便使用。
20, SDWebImagePrefetcher 可以預先下載圖片,方便後續使用。
二, SDWebImage 使用
1.使用IImageView+WebCache category來載入UITableView中cell的圖片
[cell.imageView sd_setImageWithURL:[NSURL URLWithString:@"http://www.domain.com/path/to/image.jpg"] placeholderImage:[UIImage imageNamed:@"placeholder.png"]];
2.使用Blocks,採用這個方案可以在網狀圖片載入過程中得知圖片的下載進度和圖片載入成功與否
[cell.imageView sd_setImageWithURL:[NSURL URLWithString:@"http://www.domain.com/path/to/image.jpg"] placeholderImage:[UIImage imageNamed:@"placeholder.png"] completed:^(UIImage image, NSError error, SDImageCacheType cacheType, NSURL *imageURL) { ... completion code here ... }];
3.使用SDWebImageManager,SDWebImageManager為UIImageView+WebCache category的實現提供介面。
SDWebImageManager manager = [SDWebImageManager sharedManager] ;
[manager downloadImageWithURL:imageURL options:0 progress:^(NSInteger receivedSize, NSInteger expectedSize) { // progression tracking code } completed:^(UIImage image, NSError error, SDImageCacheType cacheType, BOOL finished, NSURL imageURL) { if (image) { // do something with image } }];
4.載入圖片還有使用SDWebImageDownloader和SDImageCache方式,但那個並不是我們經常用到的。基本上面所講的3個方法都能滿足需求。
SDWebImage 介面
SDWebImage是一個成熟而且比較龐大的架構,但是在使用過程中並不需要太多的介面,這算是一種代碼封裝程度的體現。這裡就介紹比較常用的幾個介面。
1, 給UIImageView設定圖片的介面,SDWebImage有提供多個給UIImageView設定圖片的介面,最終所有的介面都會調用的這個介面,這是大多數架構的做法。
2, 擷取SDWebImage的磁碟緩衝大小,在項目中有時候會需要統計應用的磁碟緩衝內容大小,那麼擷取圖片的緩衝大小就是使用這個介面來實現
[SDImageCache sharedImageCache] getSize];
3, 清理記憶體緩衝,清理記憶體中緩衝的圖片資源,釋放記憶體資源。
[[SDImageCache sharedImageCache] clearMemory];
4, 有了清理記憶體緩衝,自然也有清理磁碟緩衝的介面
[[SDImageCache sharedImageCache] clearDisk];
iOS圖片載入-SDWebImage