iPhone refactoring with ivar names
Could anyone tell me how I can dynamically specify an ivar name within my method? l2 is the ivar I'm trying to target.
//this works
if (maxunlocked > 1) {
filename = [NSString stringWithFormat:@"level%d.png", [[fliesArray objectAtIndex:2] intValue]];
filenameHi = [NSString stringWithFormat:@"level%dHi.png", [[fliesArray objectAtIndex:2] intValue]];
l2 = [SoundMenuItem itemF开发者_StackOverflow社区romNormalSpriteFrameName:filename selectedSpriteFrameName:filenameHi target:self selector:@selector(level:)];
}
//this doesn't
for (int i = 0; i<11; i++) {
if (maxunlocked > i) {
filename = [NSString stringWithFormat:@"level%d.png", [[fliesArray objectAtIndex:i] intValue]];
filenameHi = [NSString stringWithFormat:@"level%dHi.png", [[fliesArray objectAtIndex:i] intValue]];
//this is where I'm attempting to dynamically specify the SoundMenuItem instance name.
sndMenuItem = [NSString stringWithFormat:@"l%d", i];
sndMenuItem = [SoundMenuItem itemFromNormalSpriteFrameName:filename selectedSpriteFrameName:filenameHi target:self selector:@selector(level:)];
sndMenuItem.userData = (id)i;
}
}
Thanks,
Mark
If you have it declared as a property, you may be able to use KVC to get it.
float h1 = [object height];
float h2 = [[object valueForKey:@"height"] floatValue];
[EDIT]
I didn't understand what you're saying. The answer is no. You can't specify a variable name dynamically. What you can do is this:
// if `l2` is a member of self. (as in self.l2)
for (int i = 0; i<11; i++) {
if (maxunlocked > i) {
filename = [NSString stringWithFormat:@"level%d.png", [[fliesArray objectAtIndex:i] intValue]];
filenameHi = [NSString stringWithFormat:@"level%dHi.png", [[fliesArray objectAtIndex:i] intValue]];
//this is where I'm attempting to dynamically specify the SoundMenuItem instance name.
key = [NSString stringWithFormat:@"l%d", i];
tmp = [SoundMenuItem itemFromNormalSpriteFrameName:filename selectedSpriteFrameName:filenameHi target:self selector:@selector(level:)];
tmp.userData = (id)i;
[self setValue:tmp forKey:key];
}
}
[EDIT]
You should probably re-structure your entire class.
@interface myViewController: NSViewController {
UIButton *sound1;
UIButton *sound2;
SoundMenuItem *l1;
SoundMenuItem *l2;
}
@property (assign) IBOutlet UIButton *sound1; // connect up in IB
@property (assign) IBOutlet UIButton *sound2;
- (IBAction) clickSoundButton: (id)sender; // connect up to sound1 and sound2 in IB
- (SoundMenuItem) getSoundMenuItem: (int) i;
@end
@implementation myViewController
- (IBAction) clickSoundButton: (id)sender
{
if (sender == (id)sound1) l1 = [self getSoundMenuItem: 1];
if (sender == (id)sound2) l2 = [self getSoundMenuItem: 2];
}
- (SoundMenuItem) getSoundMenuItem: (int) i
{
if (maxunlocked <= i) return
NSString *filename = [NSString stringWithFormat:@"level%d.png", [[fliesArray objectAtIndex:i] intValue]];
NSString *filenameHi = [NSString stringWithFormat:@"level%dHi.png", [[fliesArray objectAtIndex:i] intValue]];
SoundMenuItem *sndMenuItem = [SoundMenuItem itemFromNormalSpriteFrameName:filename selectedSpriteFrameName:filenameHi target:self selector:@selector(level:)];
sndMenuItem.userData = (id)i;
return sndMenuItem; //(assuming it is auto-released)
}
@end
Sorry about the lack of info and thanks for your patience. I was struggling to add it all into the comments area due to the character limit.
This is what I'm attempting...
In my header file:
//SoundMenuItem is a class SoundMenuItem *l1; SoundMenuItem *l2; (I actually have 20 buttons, one for each game level)
In my .m file
//here I set up the l1 button which is never locked
l1 = [SoundMenuItem itemFromNormalSpriteFrameName:filename selectedSpriteFrameName:filenameHi target:self selector:@selector(level:)];
//and here I set the l2 button to be locked by default
l2 = [SoundMenuItem itemFromNormalSpriteFrameName:@"levellock.png" selectedSpriteFrameName:@"levellockHi.png" target:self selector:@selector(doNothing:)];
//now I check to see if level2 has been unlocked (maxunlocked > 1) and if so I reset the l2 instance to use different images.
if (maxunlocked > 1) {
filename = [NSString stringWithFormat:@"level%d.png", [[fliesArray objectAtIndex:2] intValue]]; filenameHi = [NSString stringWithFormat:@"level%dHi.png", [[fliesArray objectAtIndex:2] intValue]];
l2 = [SoundMenuItem itemFromNormalSpriteFrameName:filename selectedSpriteFrameName:filenameHi target:self selector:@selector(level:)];
}
So rather than having 20 iterations of the above if statement, one for each button I'm wanting to refactor it into one.
I hope I've made myself clearer.
After the question was clarified my first answer was not valid. The answer by @stephen with the suggestion for using a dictionary to keeping all the SoundMenuItem is what I would have proposed as well.
精彩评论