Best Way to Cache Images on iOS App

Best way to cache images on ios app?

Caching just means keeping a copy of the data that you need so that you don't have to load it from some slower source. For example, microprocessors often have cache memory where they keep copies of data so that they don't have to access RAM, which is a lot slower. Hard disks often have memory caches from which the file system can get much quicker access to blocks of data that have been accessed recently.

Similarly, if your app loads a lot of images from the network, it may be in your interest to cache them on your device instead of downloading them every time you need them. There are lots of ways to do that -- it sounds like you already found one. You might want to store the images you download in your app's /Library/Caches directory, especially if you don't expect them to change. Loading the images from secondary storage will be much, much quicker than loading them over the network.

You might also be interested in the little-known NSCache class for keeping the images you need in memory. NSCache works like a dictionary, but when memory gets tight it'll start releasing some of its contents. You can check the cache for a given image first, and if you don't find it there you can then look in your caches directory, and if you don't find it there you can download it. None of this will speed up image loading on your app the first time you run it, but once your app has downloaded most of what it needs it'll be much more responsive.

How to cache images properly in ios

The Code below in your heightForRowAtIndexPath is causing issue:

NSString *filePath = [NSString stringWithFormat:@"%@app/media/access/pictures?p=%@",baseurl,data.picPath];
self.img = [UIImage imageWithData: [NSData dataWithContentsOfURL:[NSURL URLWithString:filePath]]];

Code will executed every time you scroll tableView and it will cause freezing problem since it is not asynchronous call.

Edit:
To avoid that you can do something like this:

when finished downloading you can use,

[tableView reloadRowsAtIndexPaths:[NSArray arrayWithObjects:indexPath, nil] 
withRowAnimation:UITableViewRowAnimationAutomatic];

This will call again

    -(CGFloat)tableView:(UITableView *)tableView
heightForRowAtIndexPath:(NSIndexPath *)indexPath

Like,

[cell.image sd_setImageWithURL:[NSURL URLWithString:[NSMutableString stringWithFormat:@"%@app/media/access/pictures?p=%@",baseurl,data.picPath]]

completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, NSURL *imageURL) {

if (error) {

NSLog(@"error: %@",error.description);


}
else{

//get image height and return this height from HeightForRowAtIndexPath
Height=image.size.height;

//reloading row will call heightForRowAtIndexPath,where now you can return height got above
[tableView reloadRowsAtIndexPaths:[NSArray arrayWithObjects:indexPath, nil] withRowAnimation:UITableViewRowAnimationAutomatic];

NSLog(@"Not an error in image download");
}




}];

Edit1:

to check image already cached, you can use below method of SDWebImage library:

- (BOOL)diskImageExistsWithKey:(NSString *)key;

The cache key is an application unique identifier for the image to cache. It is generally the absolute URL of the image.

Now if image exist in cache,then get image path using below methods of SDWebImage Library:

- (NSString *)defaultCachePathForKey:(NSString *)key;
- (NSString *)cachedFileNameForKey:(NSString *)key;

You can get the path to your image like this:

NSString *ImageKey;//key for the image you want the path for
[[SDImageCache sharedImageCache] defaultCachePathForKey:ImageKey];

in case you do not use the default location, you can use:

- (NSString *)cachePathForKey:(NSString *)key inPath:(NSString *)path;

For more detail check here: SDWebImage

IOS How do I asynchronously download and cache images and videos for use in my app

It is very simple to download and cache. The following code will asynchronously download and cache.

NSCache *memoryCache; //assume there is a memoryCache for images or videos

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_BACKGROUND, 0), ^{

NSString *urlString = @"http://URL";

NSData *downloadedData = [NSData dataWithContentsOfURL:[NSURL URLWithString:urlString]];

if (downloadedData) {

// STORE IN FILESYSTEM
NSString* cachesDirectory = [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0];
NSString *file = [cachesDirectory stringByAppendingPathComponent:urlString];
[downloadedData writeToFile:file atomically:YES];

// STORE IN MEMORY
[memoryCache setObject:downloadedData forKey:urlString];
}

// NOW YOU CAN CREATE AN AVASSET OR UIIMAGE FROM THE FILE OR DATA
});

Now there is something peculiar with UIImages that makes a library like SDWebImage so valuable , even though the asynchronously downloading images is so easy. When you display images, iOS uses a lazy image decompression scheme so there is a delay. This becomes jaggy scrolling if you put these images into tableView cells. The correct solution is to image decompress (or decode) in the background, then display the decompressed image in the main thread.

To read more about lazy image decompression, see this: http://www.cocoanetics.com/2011/10/avoiding-image-decompression-sickness/

My advice is to use SDWebImage for your images, and the code above for your videos.

Best way to cache images on PhoneGap IOS

This blog post should set you on the right track https://www.raymondcamden.com/2012/01/19/Downloading-files-to-a-PhoneGap-application-Part-1/

How to cache images in IOS App with expiry age using swift

As indicated by Fahri, you will need to manage the cache yourself (or using an open source library). You could easily create a cache directory to store your images. Then, at application launch, you parse this image cache directory to check image creation date, check time elapsed and remove those older than the specified age.

The below Swift code will do this parsing/removing job, I set the specified age to 30,000 (seconds)

// We list the stored images in Caches/Images and delete old ones
let cacheDirectory = NSFileManager.defaultManager().URLsForDirectory(.CachesDirectory, inDomains: .UserDomainMask).first! as NSURL
let filelist = try? filemanager.contentsOfDirectoryAtPath(cacheDirectory.path!)
var newDir = cacheDirectory.URLByAppendingPathComponent("Images")
var properties = [NSURLLocalizedNameKey, NSURLCreationDateKey, NSURLLocalizedTypeDescriptionKey]
var URLlist = try? filemanager.contentsOfDirectoryAtURL(newDir, includingPropertiesForKeys: properties, options: [])
if URLlist != nil {
for URLname in URLlist! {
let filePath = URLname.path!
let attrFile: NSDictionary? = try? filemanager.attributesOfItemAtPath(filePath)
let createdAt = attrFile![NSFileCreationDate] as! NSDate
let createdSince = fabs( createdAt.timeIntervalSinceNow )
#if DEBUG
print( "file created at \(createdAt), \(createdSince) seconds ago" )
#endif
if createdSince > 30000 {
let resultDelete: Bool
do {
try filemanager.removeItemAtPath(filePath)
resultDelete = true
} catch _ {
resultDelete = false
}
#if DEBUG
print("purging file =\(filePath), result= \(resultDelete)")
#endif
}
}
}

How to cache images that can change later in IOS?

Get a API service build stating that profile pic has been changed.
Hence for new profile pic since last time (use timestamp) it should return 1 else 0.

If you get 1 download new profile pic and replaces the cached one.

So you new service will include a boolean flag and timestamp.

best way to cache image url from my webservice?

I hope it's can help you. I use SDWebImage with my all projects.

using :

add your viewcontroller : #import "UIImageView+WebCache.h"

[yourImageView setImageWithURL:[NSURL URLWithString:@"ImageUrl"]];

you need to add MapKit and ImageIO to the project. if you didn't add

To do that:

  1. Click on the project at the top of the project navigator in Xcode

  2. Select the 'Build Phases' tab.

  3. Open up the 'Link Binary with Libraries' box.

  4. Click the '+'.
  5. Add MapKit and ImageIO frameworks.

Best image cache for loading numerous images in UITableView for IOS?

AFNetworking has a great UIImage category that does this well and works on iOS9. I too had issues with SDWebimageCache on iOS9.



Related Topics



Leave a reply



Submit