Reputation: 955
I need to get the value of a UIImage's image as a string.
Previously I was doing:
if(images[imageNo].image == [UIImage imageNamed:@"image1.png"])
{
But now I have a lot more conditions so I would like to use a switch, doing:
switch(images[imageNo].image)
{
case @"image1.png":
break;
}
Is there a way to achieve this? Thanks!
Upvotes: 0
Views: 13771
Reputation: 28349
The answer provided by H2C03
is appropriate. Use a dictionary to associate the names.
However, an alternative is using associative objects. Note that there is a cost in both space and time using associative objects, but they are convenient for just this type of case (adding a category-property).
@interface UIImage (MyImageLabel)
@property (nonatomic, copy) NSString *label;
@end
#import <objc/runtime.h>
@implementation UIImage (MyImageLabel)
static char const kImageLabelKey[1];
- (NSString*)label {
return objc_getAssociatedObject(self, kImageLabelKey);
}
- (void)setLabel:(NSString *)label {
objc_setAssociatedObject(self, kImageLabelKey, label, OBJC_ASSOCIATION_COPY_NONATOMIC);
}
@end
Now, you can have a label property on your UIImage instances, like so:
myImage.label = someLabelStringCouldEvenBeFilename;
and
if ([myImage.label isEqualToString:someString]) {
}
The typical caveats apply regarding anything in a category. Most will encourage you to use a unique prefix or postfix to differentiate your category methods from potential future Apple names.
Note, that you could add another method to the category, like this...
+ (UIImage)myImageNamed:(NSString*)name {
id result = [self imageNamed:name];
[result setLabel:name];
return result;
}
and now you automatically set the label.
Of course, you could do this as a subclass, if you will always be creating your own image, and avoid the "nastiness" associated with associative objects (though all your images need to be MyUIImages).
@interface MyUIImage : UIImage
@property (nonatomic, copy) NSString *label;
@end
@implementation MyUIImage
// Now, you override imageNamed:
+ (UIImage*)imageNamed:(NSString*)name {
UIImage *image = [super imageNamed:name];
self.label = name;
return image;
}
@end
Upvotes: 1
Reputation:
Both of your approaches are incorrect. The first one relies on caching (which is not documented), meanwhile the second is a syntax error - the 'case' keywords expect a compile-time constant expression.
As far as I know, there's no such a method in the iOS SDK that would return an image's filename - simply because it's not a property of the image (what would it return for a programmatically created image?). You should instead try to operate on an NSDictionary, storing the UIImage objects associated with the filenames as keys, and comparing the keys using isEqualToString:
.
So you should create your images only once, and store them in a dictionary:
// assuming `images` is an already created instance variable of your class
[images setObject:[UIImage imageNamed:@"ImgOne.png"] forKey:@"ImgOne.png"];
// and so on, with every image you need
// then once you have to check against a file name, use:
UIImage *img = [images objectForKey:@"FileName.png"];
if ([someImage isEqual:img]) {
// you can now be sure that the image set to the object was once named "FileName"
}
Upvotes: 0
Reputation: 18488
Mmm I am not sure what you want to accomplish here but using [UIImage imageNamed:@"image1.png"]
, is definitely a very bad way to do the comparison as you are creating a new UIImage object on the fly for no reason at all, furthermore you are using the == operator when you should be using isEqual since they are objects.
I believe what you want to do is convert it to a base 64 string perhaps?. If so you an use this:
NSData *imageData = UIImageJPEGRepresentation(myImage, 1.0);
NSString *encodedString = [imageData base64Encoding];
Upvotes: 2