(NO.00004)iOS实现打砖块游戏(十):砖块!更多的砖块!

时间:2021-11-05 01:22:19

大熊猫猪·侯佩原创或翻译作品.欢迎转载,转载请注明出处.

如果觉得写的不好请告诉我,如果觉得不错请多多支持点赞.谢谢! hopy ;)


到目前为止游戏基本可玩,但是砖块数量是不变的,等玩家打光所有的砖块就会觉得没啥意思了,所以我们必须想办法添加更多的砖块进来.

创建循环保持颜色的实例变量

我们想要按行添加砖块,为了美观,每行砖块的颜色应该都是不同的.所以我们先来建立一个保持当前砖块颜色的实例变量:

NSInteger _currentBrickColor;

当然还有一个更新其值的方法:

-(void)updateCurrentBrickColor:(NSInteger)incVal{
    _currentBrickColor += incVal;
    _currentBrickColor %= brkColorMax;
    if (_currentBrickColor == brkColorUnknown) {
        _currentBrickColor++;
    }
}

很简单,就是在所有brick颜色中不断循环着.

在指定Y轴位置创建一行砖块

接下来我们写一个在指定Y坐标高度位置创建一行砖块的帮助方法:

//在rowY位置创建新的一行砖块
-(void)createOneBrickRow:(NSInteger)rowY{
    [self updateCurrentBrickColor:1];
    [self createOneBrickRow:rowY withColor:_currentBrickColor];
}

其中调用了另一个方法,我们马上实现它:

//在rowY位置用指定color创建新的一行砖块
-(void)createOneBrickRow:(NSInteger)rowY withColor:(BrickColor)color{
    Brick *brick;
    //如果rowY为0,则从屏幕砖块最高可码到的高度开始创建
    if (rowY == 0) {
        rowY = MAX_BRICK_HIGHT;
    }

    for (int i = 0; i < 4; i++) {
        brick = [Brick brickWithColor:color];
        brick.position = ccp(i * (_brickWidth - BRICK_SHADOW_OFFSET_X), rowY);
        [_physicsWorld addChild:brick];
        //将新加的砖块放到_bricks数组的头部
        [_bricks insertObject:brick atIndex:0];
    }
}

一般的,我们在指定的rowY位置建立一行砖块,但可能出现这么一种情况:当前所有砖块都被打光了,屏幕中没有砖块了.这时我们就从屏幕最高的位置建立一行砖块.

下沉一行砖

如果当前砖块保持不动,那么新的砖块就无法添加进来.所以我们得想办法让砖块向下移动,以便在空出的位置新添加一行.

我们先实现下沉一块砖的方法,借此再实现下沉一行砖块的方法.

首先是下沉一块砖:

//下沉一个指定的砖块
-(void)sinkOneBrick:(Brick*)brick{
    CCPhysicsBody *physBody = brick.physicsBody;
    physBody.type = CCPhysicsBodyTypeDynamic;
    CGPoint brickPosition = brick.position;
    brick.position = ccp(brickPosition.x,brickPosition.y - (_brickHeight - BRICK_SHADOW_OFFSET_Y));
    [self scheduleBlock:^(CCTimer *timer){
        physBody.type = CCPhysicsBodyTypeKinematic;
    } delay:0];
}

上面代码中,我们先是将砖块类型改为动态,最后又恢复为混合态.这是因为避免静态物理对象在移动时碰到动态物体时将其弹开的不恰当行为.

有了上面的方法,下沉一行砖块就好实现了:

//将Level中的所有砖块下沉step级,然后在上方创建新的step行砖块.
-(void)sinkBricksAndCreateNewRows:(NSInteger)step{
    //保存当前Level中最高行砖块的Y值
    NSInteger highestRowBrickY = 0;
        for (int i = 0; i < step; i++) {
            for (Brick *brick in _bricks) {
                if (highestRowBrickY == 0) {
                    highestRowBrickY = brick.position.y;
                }
                [self sinkOneBrick:brick];
            }
            //在原来最高的那一行中创建新的一行砖块
            [self createOneBrickRow:highestRowBrickY];
            highestRowBrickY = 0;
    }
}

以上代码完成了下沉一行砖块,然后在空出的位置新建一行砖块的功能.

定时下沉砖块

好了,最后写一个定时器方法,在指定间隔后调用以上方法即可:

-(void)doWithBricks{
    [self sinkBricksAndCreateNewRows:1];
}

然后在初始化方法中调用该定时器方法:

[self schedule:@selector(doWithBricks) interval:3];

现在编译运行app,我们已经实现了我们想要的添加砖块的效果:

(NO.00004)iOS实现打砖块游戏(十):砖块!更多的砖块!