2

I am currently making a Flappy Bird-copy. Relax, its just for me and the learningpart, im not going to publish it, so dont hate.

The bird is locked at:

self.size.width/3

The pipes are generated like this:

- (void)generatePipes {
    for (NSInteger i = 0; i < 3; i++) {
        pipeNode = [SKNode node];

        [pipeNode setName:@"pipe"];
        [pipeNode setPosition:CGPointMake(self.size.width + 100.0 + (200.0 * i), 0.0)];

        [self addChild:pipeNode];

       **BLABLABLA. Some code**

        [pipeTop setPosition:CGPointMake(0.0, arc4random_uniform(250) + 460.0)];
        [pipeBottom setPosition:CGPointMake(0.0, pipeTop.position.y - (550.0 + arc4random_uniform(10)))];

        [pipeTop setPhysicsBody:[SKPhysicsBody bodyWithRectangleOfSize:pipeTop.size]];
        [pipeBottom setPhysicsBody:[SKPhysicsBody bodyWithRectangleOfSize:pipeBottom.size]];

        [pipeTop.physicsBody setDynamic:NO];
        [pipeBottom.physicsBody setDynamic:NO];

        pipeTop.physicsBody.categoryBitMask = blockBitMask;
        pipeBottom.physicsBody.categoryBitMask = blockBitMask;
        pipeNode.physicsBody.categoryBitMask = blockBitMask;

        [pipeNode addChild:pipeTop];
        //[pipeTop attachDebugRectWithSize:pipeTop.size];
        //[pipeBottom attachDebugRectWithSize:pipeBottom.size];
        [pipeNode addChild:pipeBottom];
    }
}

THis is the only thing i have made somewhat work, and yes, i am new to game-development. FirstDistance is the distance before the first pipe arrive:

        firstDistance += -moveAmount.x;

    if(touchBegan > 0 && firstDistance > (self.size.width -(self.size.width/3)- 60)){
        distanceSinceLastPipe += -moveAmount.x;


        if (distanceSinceLastPipe >= 140.0) {
            distanceSinceLastPipe = 0.0;

            score += 1;

            [_scoreLabel setText:[NSNumberFormatter localizedStringFromNumber:@(score)
                                                                  numberStyle:NSNumberFormatterDecimalStyle]];
            [self runAction:[SKAction playSoundFileNamed:@"pipe.mp3" waitForCompletion:NO]];
        }
    }

How do i tell the update-method that the pipes are passing the bird most efficent? Count pixels between pipes and reset it? Or is it any way to detect when they pass?

CodeSmile
  • 64,284
  • 20
  • 132
  • 217
simonkaspers1
  • 616
  • 4
  • 16

1 Answers1

1

If you know the horizontal position of the bird you could use some "simple" math to calculate how long it will take the pipe to reach the position that means it has passed the bird. Some pseudoCode:

CGFloat totalDistanceForPipeToMove = pipe.position.x - endPosition.x; // endPosition == the final destination for the pipe.
CGFloat relativeSpeed = totalDistanceForPipeToMove / duration; // duration being the SKAction's duration
CGFloat distanceToBird = pipe.position.x - birdPosition.x; 
CGFloat timeThePipeReachesTheBird = distanceToBird / relativeSpeed;

Then you can create an SKActionSequence, firing it at the same time as the pipe begins to move:

SKAction *wait = [SKAction waitForDuration: timeThePipeReachesTheBird];
SKAction *addToScore = [SKAction performSelector:@selector(addToScore) onTarget:self]; // performing the addToScore method
SKAction *sequence = [SKAction sequence:@[wait, addToScore]];

Another way to achieve what you are looking for is by having an invincible sprite trailing the birdSprite. Whenever this "scoreSprite" collides with a pipe you know the pipe has passed the bird...

T. Benjamin Larsen
  • 6,373
  • 4
  • 22
  • 32
  • **On this:** CGFloat totalDistanceForPipeToMove = pipe.position.x - endPosition.x; What is endPosition.x? 0? @nickfalk – simonkaspers1 Feb 17 '14 at 15:10
  • 1
    It's the end-position the pipe is heading to probably a negative value, `pipe.size.width/2` if your anchorPoint is `0.5, 0.5`... – T. Benjamin Larsen Feb 17 '14 at 15:41
  • Okey, i tried and loved the idea of a ghost-sprite. I have implemented it and it follows, but when i use contactBitMask it collides in the pipe and disappears. Shouldnt this just report back to contact-method: `_scoreSprite.physicsBody.categoryBitMask = scoreBitMask; _scoreSprite.physicsBody.contactTestBitMask = blockBitMask;` – simonkaspers1 Feb 17 '14 at 15:49
  • How are you setting up the ghost-sprite? A bit hard to comment without the details, but, yes: The general idea is that you use the `didBeginContact:` to handle the logic. The nodes shouldn't simply vanish on their own without you telling them to... – T. Benjamin Larsen Feb 17 '14 at 16:15