1

为了保存 ScrollingBackground 对象,我将 CCSprite 子类化为符合 NSCoding。ScrollingBackground 不显示。请参阅下面的相关代码。我不太确定出了什么问题。请帮忙。

ScrollingBackground.h:(CCBackgroundSprite的界面)

@interface CCBackgroundSprite: NSObject <NSCoding>

@property (nonatomic, assign) float xValue;
@property (nonatomic, assign) float yValue;
@property (nonatomic, retain) NSString* backgroundStringName;

@end

ScrollingBackground.m:(CCBackgroundSprite 的实现)

@implementation CCBackgroundSprite

-(id)init
{
    if((self = [super init])){
    }

   return self;
}

-(id) initWithCoder:(NSCoder *) aDecoder {

self = [super init];
if(self != nil) {
    self.xValue = [aDecoder decodeFloatForKey:@"xValue"];
    self.yValue = [aDecoder decodeFloatForKey:@"yValue"];
    self.backgroundStringName = [aDecoder decodeObjectForKey:@"backgroundStringName"];
  }
  return self;
}

-(void) encodeWithCoder:(NSCoder *)aCoder {

   [aCoder encodeFloat:self.xValue forKey:@"xValue"];
   [aCoder encodeFloat:self.yValue forKey:@"yValue"];
   [aCoder encodeObject:self.backgroundStringName forKey:@"backgroundStringName"];
}

@end

为 CCSprite 属性设置 CCBackgroundSprite 的实例:

-(void)spriteProperties {
   background1 = [[CCBackgroundSprite alloc] init];
   [background1 setXValue:bg.position.x];
   [background1 setYValue:bg.position.y];
   [background1 setBackgroundStringName:@"bg"];

   background2 = [[CCBackgroundSprite alloc] init];
   [background2 setXValue:bgSwap.position.x];
   [background2 setYValue:bgSwap.position.y];
   [background2 setBackgroundStringName:@"bgSwap"];

   background3 = [[CCBackgroundSprite alloc] init];
   [background3 setXValue:bgSwap2.position.x];
   [background3 setYValue:bgSwap2.position.y];
   [background3 setBackgroundStringName:@"bgSwap2"];
}

ScrollingBackground 的其他非 Sprite 相关属性的编码/解码:

-(void) encodeWithCoder:(NSCoder *)aCoder {
   [aCoder encodeInt:self.backgroundCount forKey:@"backgroundCount"];
   [aCoder encodeInt:self.backgroundRepeatCount forKey:@"backgroundRepeatCount"];
   [aCoder encodeFloat:self.scrollSpeed forKey:@"scrollSpeed"];
   [aCoder encodeObject:self.backgroundArray forKey:@"backgroundArray"];
   [aCoder encodeObject:self.changeArray forKey:@"changeArray"];
              .
              .
              .
} 

-(id) initWithCoder:(NSCoder *) aDecoder {

self = [super init];
if(self != nil) {
        self.backgroundCount = [aDecoder decodeIntForKey:@"backgroundCount"];
        self.backgroundRepeatCount = [aDecoder decodeIntForKey:@"backgroundRepeatCount"];
        self.scrollSpeed = [aDecoder decodeFloatForKey:@"scrollSpeed"];
        self.backgroundArray = [aDecoder decodeObjectForKey:@"backgroundArray"];
        self.changeArray = [aDecoder decodeObjectForKey:@"changeArray"];
           .
           .
           .
     }
 }

ScrollingBackground 对象的保存和加载:

- (void)saveBackgroundObject:(ScrollingBackground *)object key:(NSString *)key {
   [self spriteProperties];
   NSData *encodedObject = [NSKeyedArchiver archivedDataWithRootObject:object];
   NSString *dataToString = [NSString stringWithFormat:@"%@", encodedObject];
   CCLOG(@"encodedObject = %@ \n", dataToString);

   NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
   [defaults setObject:encodedObject forKey:key];
   [defaults synchronize];
}

-(ScrollingBackground *)loadBackgroundWithKey:(NSString *)key {
   NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
   NSData *encodedObject = [defaults objectForKey:key];
   NSString *dataToString = [NSString stringWithFormat:@"%@", encodedObject];
   CCLOG(@"encodedObject = %@ \n", dataToString);
   ScrollingBackground *object = [NSKeyedUnarchiver unarchiveObjectWithData:encodedObject];
   return object;
 }

更新:

我对 spriteProperties 方法进行了以下更改:

-(void)spriteProperties {
  background1 = [[CCBackgroundSprite alloc] init];
  [background1 setXValue:bg.position.x];
  [background1 setYValue:bg.position.y];
  [background1 setBackgroundImageName:bg.displayFrame.textureFilename];
  [self addChild:background1];

  background2 = [[CCBackgroundSprite alloc] init];
  [background2 setXValue:bgSwap.position.x];
  [background2 setYValue:bgSwap.position.y];
  [background2 setBackgroundImageName:bgSwap.displayFrame.textureFilename];
  [self addChild:background2];

  background3 = [[CCBackgroundSprite alloc] init];
  [background3 setXValue:bgSwap2.position.x];
  [background3 setYValue:bgSwap2.position.y];
  [background3 setBackgroundImageName:bgSwap2.displayFrame.textureFilename];
  [self addChild:background3];
  }

我在上面使用的主要原因displayFrame.textureFilename是因为我一直在重用精灵。还要设置我所做的背景图像:

-(void)startingSprites  //change later to setupInitialBackground
{

    CGSize s = [[CCDirector sharedDirector] winSize];
    bg = [CCSprite spriteWithSpriteFrameName:@"bgImage1.png"];
    bg.position = ccp(s.width/2, s.height/2);
    [currentBackgroundBatchNode addChild:bg];


    swapbg = [CCSprite spriteWithSpriteFrameName:@"bgImage2.png"];
    swapbg.position = ccp(s.width/2, 3*s.height/2 -1.0);
    [currentBackgroundBatchNode addChild: swapbg];

    swapbg2 = [CCSprite spriteWithSpriteFrameName:@"bgImage3.png"];
    swapbg2.position = ccp(s.width/2, 5*s.height/2 - 2.0);
    [currentBackgroundBatchNode addChild: swapbg2];

    CCLOG(@"bg background is %@", bg.displayFrame.textureFilename);
    CCLOG(@"bgSwap background is %@", swapbg.displayFrame.textureFilename);
    CCLOG(@"bgSwap2 background is %@", swapbg2.displayFrame.textureFilename);
}

我刚刚意识到一些事情:

  1. CCLOG 的输入startingSprites为空
  2. 我沿途重复使用currentBackgroundBatchNode(这是 a ),这意味着我必须对其进行编码/解码。CCSpriteBatchNode我如何子类化它以及具有哪些属性?不太确定它会如何工作。
4

2 回答 2

1

我已经阅读了您的许多帖子,也与此有关。我建议不要尝试将几个 cocos2d 类子类化以符合 NSCoding,而应该使用更简单的解决方法。我相信你的背景有它自己的层,所以你为什么不保存各种背景参数并为你的背景创建另一个初始化来处理重新加载背景状态的情况。

于 2013-12-03T03:48:24.873 回答
1

你说你已经子类化了CCSprite,但你实际上是子类化了NSObject。尝试:

@interface CCBackgroundSprite: CCSprite <NSCoding>
...
于 2013-11-10T23:51:09.690 回答