We want to download image and data async to our tableview and we want to cache it not to download it again. We found a code for caching.Here is our code. It works asynchronously but when we scroll table view, images gone and come back(we cant see image for a while). Sometimes wrong image come to wrong cell. What might be the reasons and how can we solve it ?
NSURL *imageURL = [NSURL URLWithString:[NSString stringWithFormat:@"%@%@",[userInfo[0] serverUrl],[estateList[indexPath.row] imgUrl]]];
NSString *key = [imageURL absoluteString];
NSData *data = [FTWCache objectForKey:key];
if (data) {
UIImage *image = [UIImage imageWithData:data];
cell.imageView.image = image;
} else {
cell.imageView.image = [UIImage imageNamed:@"yukleniyor"];
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0ul);
dispatch_async(queue, ^{
NSData *data = [NSData dataWithContentsOfURL:imageURL];
[FTWCache setObject:data forKey:key];
UIImage *image = [UIImage imageWithData:data];
dispatch_async(dispatch_get_main_queue(), ^{
cell.imageView.image = image;
});
});
}
Here is that code we found for caching
Header is like this
#import <Foundation/Foundation.h>
@interface FTWCache : NSObject
+ (void) resetCache;
+ (void) setObject:(NSData*)data forKey:(NSString*)key;
+ (id) objectForKey:(NSString*)key;
@end
And .m file is like this
#import "FTWCache.h"
static NSTimeInterval cacheTime = (double)604800;
@implementation FTWCache
+ (void) resetCache {
[[NSFileManager defaultManager] removeItemAtPath:[FTWCache cacheDirectory] error:nil];
}
+ (NSString*) cacheDirectory {
NSArray* paths = NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES);
NSString *cacheDirectory = [paths objectAtIndex:0];
cacheDirectory = [cacheDirectory stringByAppendingPathComponent:@"FTWCaches"];
return cacheDirectory;
}
+ (NSData*) objectForKey:(NSString*)key {
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *filename = [self.cacheDirectory stringByAppendingPathComponent:key];
if ([fileManager fileExistsAtPath:filename])
{
NSDate *modificationDate = [[fileManager attributesOfItemAtPath:filename error:nil] objectForKey:NSFileModificationDate];
if ([modificationDate timeIntervalSinceNow] > cacheTime) {
[fileManager removeItemAtPath:filename error:nil];
} else {
NSData *data = [NSData dataWithContentsOfFile:filename];
return data;
}
}
return nil;
}
+ (void) setObject:(NSData*)data forKey:(NSString*)key {
NSFileManager *fileManager = [NSFileManager defaultManager];
NSString *filename = [self.cacheDirectory stringByAppendingPathComponent:key];
BOOL isDir = YES;
if (![fileManager fileExistsAtPath:self.cacheDirectory isDirectory:&isDir]) {
[fileManager createDirectoryAtPath:self.cacheDirectory withIntermediateDirectories:NO attributes:nil error:nil];
}
NSError *error;
@try {
[data writeToFile:filename options:NSDataWritingAtomic error:&error];
}
@catch (NSException * e) {
//TODO: error handling maybe
}
}
@end