使用SKAaction的无限水平背景ios

时间:2014-11-05 16:15:27

标签: ios animation sprite-kit skaction

我有一个很长的图像,我想设置为" Rollable"背景 。 我试图使用精灵的2个实例,一旦图像到达(frame - imageHeight),就可以添加上面的第二个并保持平滑运动。

但是,我得到了一个意想不到的行为 - 在动画的最后部分,屏幕重叠 - 第二个屏幕与第一个屏幕重叠。

这是我的代码:

- (void) repositionBackground{

SKSpriteNode *currentBackground = self.backgroundArray[self.currentBackgoundIndex];
if(!currentBackground.parent && !self.currentBackgoundIndex) //First time running
{
    SKAction *imageMinusFrameAnimation = [SKAction moveToY:-currentBackground.size.height+self.frame.size.height/2.0f duration:self.backgroundAnimationLength];
    SKAction *sequence = [SKAction sequence:@[imageMinusFrameAnimation, [SKAction runBlock:^{
        [self repositionBackground];
    }]]];
    [currentBackground runAction:sequence];
    [self addChild:currentBackground];

    NSLog(@"Calling Reposition for the first time");
}
else
{
    self.currentBackgoundIndex = (self.currentBackgoundIndex + 1) % [self.backgroundArray count];
    SKSpriteNode *newBackground = self.backgroundArray[self.currentBackgoundIndex];
    //Reposition th enew backfround on top of the current one
    [newBackground setPosition:CGPointMake(0, self.frame.size.height/2.0f)];

    //Add actions to backfround - the top backgound to be vanished from the screen and the new one to appear and start scrolling down
    SKAction *imageMinusFrameAnimation = [SKAction moveToY:-currentBackground.size.height+self.frame.size.height/2.0f duration:self.backgroundAnimationLength];
    SKAction *sequence = [SKAction sequence:@[imageMinusFrameAnimation, [SKAction runBlock:^{
        [self repositionBackground];
    }]]];
    [newBackground runAction:sequence];


    if(!newBackground.parent)
    {
        [self addChild:newBackground];
    }
    float newBackgroundAnimationLength = self.frame.size.height / BACKGROUND_ANIMATION_VELOCITY;
    SKAction *frameLengthAnimation = [SKAction moveByX:0 y:-self.frame.size.height duration:newBackgroundAnimationLength];

    [currentBackground runAction:frameLengthAnimation];


}

}

1 个答案:

答案 0 :(得分:0)

我自己弄清楚了。 这是算法中的一个错误。 我在这里发布解决方案:(SpriteKit)

//creating 2 background - positioning one above the screen and one to stand on the (0.5,0} axis
SKSpriteNode *firstBackground = [SKSpriteNode spriteNodeWithImageNamed:@"mtImage.jpeg"];
firstBackground.anchorPoint = CGPointMake(0.5f,0);
firstBackground.zPosition = 1;
SKSpriteNode *secondBackground =[firstBackground copy];
self.backgroundArray = @[firstBackground,secondBackground];
[firstBackground setPosition:CGPointMake(0, -self.frame.size.height/2)];
[secondBackground setPosition:CGPointMake(0, self.frame.size.height/2)];
self.currentBackgoundIndex = 0;
self.backgroundAnimationLength = firstBackground.size.height / BACKGROUND_ANIMATION_VELOCITY;

[self repositionBackground];


- (void) repositionBackground{

  SKSpriteNode *currentBackground = self.backgroundArray[self.currentBackgoundIndex];
  SKAction *majorPartAnimation;
  //First time running
  if(!currentBackground.parent && !self.currentBackgoundIndex)
  {
      float firstAnimationDuration = (currentBackground.size.height - self.frame.size.height) / BACKGROUND_ANIMATION_VELOCITY;
      majorPartAnimation = [SKAction moveToY:-currentBackground.size.height+self.frame.size.height/2.0f duration:firstAnimationDuration];
      SKAction *sequence = [SKAction sequence:@[majorPartAnimation, [SKAction runBlock:^{
        [self repositionBackground];
      }]]];
      [currentBackground runAction:sequence];
      [self addChild:currentBackground];
  }
  else
  {
      //current background needs to move by frameHeight and the new one has to be set above him and start its animation
      majorPartAnimation = [SKAction moveToY:-currentBackground.size.height+self.frame.size.height/2.0f duration:self.backgroundAnimationLength];
      self.currentBackgoundIndex = (self.currentBackgoundIndex + 1) % [self.backgroundArray count];
      SKSpriteNode *newBackground = self.backgroundArray[self.currentBackgoundIndex];
      //Reposition th enew backfround on top of the current one
      [newBackground setPosition:CGPointMake(0, self.frame.size.height/2.0f)];

      //Add actions to backfround - the top backgound to be vanished from the screen and the new one to appear and start scrolling down
      SKAction *sequence = [SKAction sequence:@[majorPartAnimation, [SKAction runBlock:^{
          [self repositionBackground];
      }]]];
      [newBackground runAction:sequence];
      if(!newBackground.parent)
      {
          [self addChild:newBackground];
      }
      float currentBackgroundAnimationLength = self.frame.size.height / BACKGROUND_ANIMATION_VELOCITY;
      SKAction *minorPartAniamiton = [SKAction moveByX:0 y:-self.frame.size.height duration:currentBackgroundAnimationLength];
      [currentBackground runAction:minorPartAniamiton];
  }

}