Extended the SDImageCache `queryDiskCacheForKey:done:` so it also returns the NSData (we will need it later for the GIF images).

- had to add an NSData param to `SDWebImageQueryCompletedBlock`, so to make it simpler see this change for users, renamed the block type to `SDCacheQueryCompletedBlock`
- pass the NSData when getting the image from disk cache
This commit is contained in:
Bogdan Poplauschi 2016-06-01 09:35:36 +03:00
parent b4659f7648
commit e775b444ef
3 changed files with 22 additions and 26 deletions

View File

@ -24,7 +24,7 @@ typedef NS_ENUM(NSInteger, SDImageCacheType) {
SDImageCacheTypeMemory
};
typedef void(^SDWebImageQueryCompletedBlock)(UIImage *image, SDImageCacheType cacheType);
typedef void(^SDCacheQueryCompletedBlock)(UIImage *image, NSData *data, SDImageCacheType cacheType);
typedef void(^SDWebImageCheckCacheCompletionBlock)(BOOL isInCache);
@ -148,7 +148,7 @@ typedef void(^SDWebImageCalculateSizeBlock)(NSUInteger fileCount, NSUInteger tot
*
* @param key The unique key used to store the wanted image
*/
- (NSOperation *)queryDiskCacheForKey:(NSString *)key done:(SDWebImageQueryCompletedBlock)doneBlock;
- (NSOperation *)queryDiskCacheForKey:(NSString *)key done:(SDCacheQueryCompletedBlock)doneBlock;
/**
* Query the memory cache synchronously.

View File

@ -385,20 +385,20 @@ FOUNDATION_STATIC_INLINE NSUInteger SDCacheCostForImage(UIImage *image) {
return SDScaledImageForKey(key, image);
}
- (NSOperation *)queryDiskCacheForKey:(NSString *)key done:(SDWebImageQueryCompletedBlock)doneBlock {
- (NSOperation *)queryDiskCacheForKey:(NSString *)key done:(SDCacheQueryCompletedBlock)doneBlock {
if (!doneBlock) {
return nil;
}
if (!key) {
doneBlock(nil, SDImageCacheTypeNone);
doneBlock(nil, nil, SDImageCacheTypeNone);
return nil;
}
// First check the in-memory cache...
UIImage *image = [self imageFromMemoryCacheForKey:key];
if (image) {
doneBlock(image, SDImageCacheTypeMemory);
doneBlock(image, nil, SDImageCacheTypeMemory);
return nil;
}
@ -409,6 +409,7 @@ FOUNDATION_STATIC_INLINE NSUInteger SDCacheCostForImage(UIImage *image) {
}
@autoreleasepool {
NSData *diskData = [self diskImageDataBySearchingAllPathsForKey:key];
UIImage *diskImage = [self diskImageForKey:key];
if (diskImage && self.shouldCacheImagesInMemory) {
NSUInteger cost = SDCacheCostForImage(diskImage);
@ -416,7 +417,7 @@ FOUNDATION_STATIC_INLINE NSUInteger SDCacheCostForImage(UIImage *image) {
}
dispatch_async(dispatch_get_main_queue(), ^{
doneBlock(diskImage, SDImageCacheTypeDisk);
doneBlock(diskImage, diskData, SDImageCacheTypeDisk);
});
}
});

View File

@ -154,7 +154,7 @@
}
NSString *key = [self cacheKeyForURL:url];
operation.cacheOperation = [self.imageCache queryDiskCacheForKey:key done:^(UIImage *image, SDImageCacheType cacheType) {
operation.cacheOperation = [self.imageCache queryDiskCacheForKey:key done:^(UIImage *cachedImage, NSData *cachedData, SDImageCacheType cacheType) {
if (operation.isCancelled) {
@synchronized (self.runningOperations) {
[self.runningOperations removeObject:operation];
@ -163,12 +163,12 @@
return;
}
if ((!image || options & SDWebImageRefreshCached) && (![self.delegate respondsToSelector:@selector(imageManager:shouldDownloadImageForURL:)] || [self.delegate imageManager:self shouldDownloadImageForURL:url])) {
if (image && options & SDWebImageRefreshCached) {
if ((!cachedImage || options & SDWebImageRefreshCached) && (![self.delegate respondsToSelector:@selector(imageManager:shouldDownloadImageForURL:)] || [self.delegate imageManager:self shouldDownloadImageForURL:url])) {
if (cachedImage && options & SDWebImageRefreshCached) {
dispatch_main_sync_safe(^{
// If image was found in the cache but SDWebImageRefreshCached is provided, notify about the cached image
// AND try to re-download it in order to let a chance to NSURLCache to refresh it from server.
completedBlock(image, nil, cacheType, YES, url);
completedBlock(cachedImage, nil, cacheType, YES, url);
});
}
@ -181,20 +181,19 @@
if (options & SDWebImageHandleCookies) downloaderOptions |= SDWebImageDownloaderHandleCookies;
if (options & SDWebImageAllowInvalidSSLCertificates) downloaderOptions |= SDWebImageDownloaderAllowInvalidSSLCertificates;
if (options & SDWebImageHighPriority) downloaderOptions |= SDWebImageDownloaderHighPriority;
if (image && options & SDWebImageRefreshCached) {
if (cachedImage && options & SDWebImageRefreshCached) {
// force progressive off if image already cached but forced refreshing
downloaderOptions &= ~SDWebImageDownloaderProgressiveDownload;
// ignore image read from NSURLCache if image if cached but force refreshing
downloaderOptions |= SDWebImageDownloaderIgnoreCachedResponse;
}
id subOperation = [self.imageDownloader downloadImageWithURL:url options:downloaderOptions progress:progressBlock completed:^(UIImage *downloadedImage, NSData *data, NSError *error, BOOL finished) {
id subOperation = [self.imageDownloader downloadImageWithURL:url options:downloaderOptions progress:progressBlock completed:^(UIImage *downloadedImage, NSData *downloadedData, NSError *error, BOOL finished) {
__strong __typeof(weakOperation) strongOperation = weakOperation;
if (!strongOperation || strongOperation.isCancelled) {
// Do nothing if the operation was cancelled
// See #699 for more details
// if we would call the completedBlock, there could be a race condition between this block and another completedBlock for the same object, so if this one is called second, we will overwrite the new data
}
else if (error) {
} else if (error) {
dispatch_main_sync_safe(^{
if (strongOperation && !strongOperation.isCancelled) {
completedBlock(nil, error, SDImageCacheTypeNone, finished, url);
@ -222,16 +221,15 @@
BOOL cacheOnDisk = !(options & SDWebImageCacheMemoryOnly);
if (options & SDWebImageRefreshCached && image && !downloadedImage) {
if (options & SDWebImageRefreshCached && cachedImage && !downloadedImage) {
// Image refresh hit the NSURLCache cache, do not call the completion block
}
else if (downloadedImage && (!downloadedImage.images || (options & SDWebImageTransformAnimatedImage)) && [self.delegate respondsToSelector:@selector(imageManager:transformDownloadedImage:withURL:)]) {
} else if (downloadedImage && (!downloadedImage.images || (options & SDWebImageTransformAnimatedImage)) && [self.delegate respondsToSelector:@selector(imageManager:transformDownloadedImage:withURL:)]) {
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{
UIImage *transformedImage = [self.delegate imageManager:self transformDownloadedImage:downloadedImage withURL:url];
if (transformedImage && finished) {
BOOL imageWasTransformed = ![transformedImage isEqual:downloadedImage];
[self.imageCache storeImage:transformedImage recalculateFromImage:imageWasTransformed imageData:(imageWasTransformed ? nil : data) forKey:key toDisk:cacheOnDisk];
[self.imageCache storeImage:transformedImage recalculateFromImage:imageWasTransformed imageData:(imageWasTransformed ? nil : downloadedData) forKey:key toDisk:cacheOnDisk];
}
dispatch_main_sync_safe(^{
@ -240,10 +238,9 @@
}
});
});
}
else {
} else {
if (downloadedImage && finished) {
[self.imageCache storeImage:downloadedImage recalculateFromImage:NO imageData:data forKey:key toDisk:cacheOnDisk];
[self.imageCache storeImage:downloadedImage recalculateFromImage:NO imageData:downloadedData forKey:key toDisk:cacheOnDisk];
}
dispatch_main_sync_safe(^{
@ -272,19 +269,17 @@
}
}
};
}
else if (image) {
} else if (cachedImage) {
dispatch_main_sync_safe(^{
__strong __typeof(weakOperation) strongOperation = weakOperation;
if (strongOperation && !strongOperation.isCancelled) {
completedBlock(image, nil, cacheType, YES, url);
completedBlock(cachedImage, nil, cacheType, YES, url);
}
});
@synchronized (self.runningOperations) {
[self.runningOperations removeObject:operation];
}
}
else {
} else {
// Image not in cache and download disallowed by delegate
dispatch_main_sync_safe(^{
__strong __typeof(weakOperation) strongOperation = weakOperation;