1

Basically my code heavily uses [UIImage imageNamed] which by default fetches image from app bundle.

Now I want the images to be returned from a directory deep within Documents (or library or whatever) - instead of main bundle. And since there are so many instances of imageNamed calls, I am considering to extend (read replace) UIImage ImageNamed implementation for this purpose.

I already went through this but can't quite make up what should I do, and what is best:

  1. Make a category of UIImage
  2. Create a subclass of UIImage
  3. Method swizzling

I also do not know if I have to take care of @2x images. My current bundle includes bunch of them, and I suppose my implementation will also have to take care of it. But not sure how.

Community
  • 1
  • 1
Nirav Bhatt
  • 6,940
  • 5
  • 45
  • 89

3 Answers3

5

The cleanest, most elegant and easiest to maintain long term solution is to use a category on UIImage. Define a custom method on UIImage, and then use a Find & Replace to replace all your imageNamed calls to your new method.

Don't use swizzling (it will introduce weird, undocumented bugs) and is very difficult to maintain or debug. (Also, if you swizzle, it will break in places where you do want to use the default implementation of imageNamed).

There's no need to subclass UIImage for what you're trying to do because you don't need an instance method.

melsam
  • 4,947
  • 1
  • 22
  • 23
  • What you are suggesting is not to replace default imageNamed. But going by that I don't even need a category on UIImage, because imageNamed is class method, not an instance method. All I want from it is a UIImage from a specific path, which can be returned even from my own class method. Doesn't have to be on UIImage. But I am looking for somewhat more elegant approach that will squeeze OOPS for the best. As I have also shown in links posted, it isn't quite uncommon. Thanks anyway for your inputs. – Nirav Bhatt Feb 28 '13 at 05:29
  • You are right. There are really undocumented bugs in imageNamed if swizzling. I get crashes on dealloc. – mafonya Aug 28 '14 at 11:08
1

If it's the only problem to retrive image from document directory try:

[UIimage imageWithContentsOfFile:yourFilePath];

//you can use these method to retrieve file path

- (NSString *) rootPath{
    return [NSSearchPathForDirectoriesInDomains(NSDocumentationDirectory, NSUserDomainMask, YES) lastObject];
}

- (NSString *) pathFoResourse : (NSString *) resourseName ofType: (NSString *)type{
    NSString *path = [[self rootPath] stringByAppendingPathComponent:[NSString stringWithFormat:@"%@.%@", resourseName, type]];
    if (![[NSFileManager defaultManager] fileExistsAtPath:path]) {
        path = [[NSBundle mainBundle] pathForResource:resourseName ofType:type];
    }
    NSLog(@"**path:%@**", path);
    return path;
}
rptwsthi
  • 10,094
  • 10
  • 68
  • 109
  • 1
    While I knew of imageWithContentsOfFile solution and was considering it as my last resort, you still kindof resolved the issue for me, and upvoted you for that. However I am still curious about possible UIImage extension. So keeping this question open. – Nirav Bhatt Feb 28 '13 at 07:45
0

The best and easiest way is to use Category. It makes the code readable. Subclass may confuse you during the work This Question will explain to you why no to use Method Swizzling

Community
  • 1
  • 1
Hossam Ghareeb
  • 7,063
  • 3
  • 53
  • 64