imageWithContentsOfFile vs imageNamed (imageWithCo

2019-07-04 08:34发布

问题:

Once, I placed all my pictures in APP Bundle. I used imageNamed function to get an image. Later, I decided to copy some pictures to the Document when app start. So, I could not use imageNamed function to get an image any more. I used imageWithContentsOfFile to get an image:

NSString* documentsDirectoryPath =[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,NSUserDomainMask, YES) objectAtIndex:0];
UIImage* result =[UIImage imageWithContentsOfFile:[NSString stringWithFormat:@"%@/%@.%@", documentsDirectoryPath, fileName, extension]];

However, imageWithContentsOfFile return a low quality image (very fuzzy). all of my image are 128*128. I used following code the detect the size of the picture:

NSData * imgData = UIImagePNGRepresentation(image);
NSLog(@"size : %d",[imgData length]);

I found that size of the image returned by imageNamed is 3 times than imageWithContentsOfFile. I got crazy ... Help me ! Thanks a lot ...

回答1:

In the UIImage reference documentation you can see a couple of differences between imageNamed and imageWithContentsOfFile.

  • imageWithContentsOfFile doesn't cache the image, nor it looks for retina display version (@2x.png).
  • imageNamed instead does cache the image and also checks to see if there is a @2x version, to load that one when in a retina enabled device.

Knowing this, the most logical explanation that I can think of for your problem is that you are using a retina device and have a retina version of that same image (@2x). That would explain why the image



回答2:

I use + (UIImage *)imageWithContentsOfFile:(NSString *)path in order to load images from disk without caching them, to reduce memory footprint.

It seems that this method has changed since iOS 8x. In order to maintain functionality on each iOS version (7x to 9x), I use this simple category on UIImage :

#import <UIKit/UIKit.h>

@interface UIImage (ImageNamedNoCache)

+ (UIImage *)imageNamedNoCache:(NSString *)imageName;

@end

And .m

#import "UIImage+ImageNamedNoCache.h"

#define MAIN_SCREEN                     [UIScreen mainScreen]
#define SYSTEM_VERSION_LESS_THAN(v)     ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] == NSOrderedAscending)

@implementation UIImage (ImageNamedNoCache)

static NSString *bundlePath = nil;

+ (UIImage *)imageNamedNoCache:(NSString *)imageName
{
    if (!bundlePath)
    {
        bundlePath = [[NSBundle mainBundle] bundlePath];
    }

    NSString *imgPath = [bundlePath stringByAppendingPathComponent:imageName];

    if (SYSTEM_VERSION_LESS_THAN(@"8.0"))
    {
        imgPath = [imgPath stringByAppendingFormat:@"@%ldx.png", (long)[MAIN_SCREEN scale]];
    }
    return [UIImage imageWithContentsOfFile:imgPath];
}

@end

Hope that helps ;)



标签: ios ios6