Objective-C类别和新的iVar

geb*_*bel 9 iphone objective-c cocos2d-iphone ios

我尝试扩展cocos2d的SimpleAudioEngine的功能,能够一个接一个地播放几种音效作为某种链.我尝试使用扩展程序执行此操作.但是我现在意识到我可能还需要一个iVar来记住所有声音文件的名称,还有一个要记住当前播放的声音.

但似乎我无法在类别中添加iVars.相反,我尝试使用扩展,但似乎它们需要在类的原始.m文件中,这样也无法工作.还有另一种方式,允许我这样做吗?

带有类别的标题

#import <Foundation/Foundation.h>
@interface SimpleAudioEngine(SoundChainHelper)<CDLongAudioSourceDelegate>
-(void)playSoundChainWithFileNames:(NSString*) filename, ...;
@end
Run Code Online (Sandbox Code Playgroud)

和.m文件扩展名为:

#import "SoundChainHelper.h"

@interface SimpleAudioEngine() {
    NSMutableArray* soundsInChain;
    int currentSound;
}
@end

@implementation SimpleAudioEngine(SoundChainHelper)

// read in all filenames and start off playing process
-(void)playSoundChainWithFileNames:(NSString*) filename, ... {
    soundsInChain = [[NSMutableArray alloc] initWithCapacity:5];

    va_list params;
    va_start(params,filename);

    while (filename) {
        [soundsInChain addObject:filename];
        filename = va_arg(params, NSString*);
    }
    va_end(params);
    currentSound = 0;
    [self cdAudioSourceDidFinishPlaying:nil];
}

// play first file, this will also always automatically be called as soon as the previous sound has finished playing
-(void)cdAudioSourceDidFinishPlaying:(CDLongAudioSource *)audioSource {
    if ([soundsInChain count] > currentSound) {
        CDLongAudioSource* mySound = [[CDAudioManager sharedManager] audioSourceForChannel:kASC_Right];
        [mySound load:[soundsInChain objectAtIndex:0]];
        mySound.delegate = self;
        [mySound play];
        currentSound++;
    }
}

@end
Run Code Online (Sandbox Code Playgroud)

或者,我尝试将iVars定义为属性,将进行编译.但是,我既不能合成它们,也没有任何其他可能性将它们绑定到任何方法.

我尝试将功能实现为SimpleAudioEngine的一个类别,这样我只需要记住一个处理我所有声音问题的类.所以我可以像这样简单地创建一个链:

[[SimpleAudioEngine sharedEngine] playSoundChainWithFileNames:@"6a_loose1D.mp3", @"6a_loose2D.mp3", @"6a_loose3D.mp3", @"6a_loose4D.mp3", @"6b_won1D.mp3", nil];
Run Code Online (Sandbox Code Playgroud)

如果有另一种产生相同/类似结果的方法,我也会非常感激.

And*_*sen 22

你是不对的,你不能将实例变量(或合成的@properties)添加到一个类别.您可以使用Objective-C运行时对关联引用的支持来解决此限制

像这样的东西:

在你的.h:

@interface SimpleAudioEngine (SoundChainHelper)
    @property (nonatomic, retain) NSMutableArray *soundsInChain;
@end
Run Code Online (Sandbox Code Playgroud)

在你的.m:

#import <objc/runtime.h>
static char soundsInChainKey;

@implementation SimpleAudioEngine (SoundChainHelper)

- (NSMutableArray *)soundsInChain
{
   return objc_getAssociatedObject(self, &soundsInChainKey);
}

- (void)setSoundsInChain:(NSMutableArray *)array
{
    objc_setAssociatedObject(self, &soundsInChainKey, array, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
}

@end
Run Code Online (Sandbox Code Playgroud)

(标准免责声明适用.我在浏览器中输入了这个,并没有测试它,但我之前使用过这种技术.)

我链接到的文档有关于关联引用如何工作的更多信息.