Phaser Js 로 Runner 게임 만들기 Part - 4

움직임 제작하기

아마 우리가 지금 추측 한 것처럼, 우리는 달리기의 착시를 만들지 만 실제로 블록을 움직일 것입니다. 템플레이션은 업데이트 기능에서 하나의 그룹으로 이동하는 것입니다.
update:function()
{
  this.blockGroup.x--;
}

그러나 우리가 그렇게 했다면 Phaser가 제공해야 하는 내장 된 물리기능을 이용할 수 없었습니다. 아케이드 물리 충돌 탐지가 작동하려면 그룹 내부의 블록을 물리기능에 사용할 수 있어야 하고 속도를 설정해야합니다.

그래서 이것을 하기 위해 그룹을 반복하고 각각에 물리기능을 적용하여 makeBlocks 함수를 수정했습니다. 또한 블록 사이의 거리를 25에서 50으로 늘렸습니다. 이전 값은 실수 였기 때문에 wallHeight 변수를 1-6에서 1-4로 조정했습니다.
makeBlocks: function() {
        //그룹에서 모든 블록을 제거하십시오.
        this.blocks.removeAll();
        var wallHeight = game.rnd.integerInRange(1, 4);
        for (var i = 0; i < wallHeight; i++) {
            var block = game.add.sprite(0, -i * 50, "block");
            this.blocks.add(block);
        }
        this.blocks.x = game.width - this.blocks.width
        this.blocks.y = this.ground.y - 50;
        //각 블록을 반복하고 물리기능 적용
        this.blocks.forEach(function(block) {
            //물리엔진 시작
            game.physics.enable(block, Phaser.Physics.ARCADE);
            //x 속도를 -160으로 설정한다.
            block.body.velocity.x = -150;
            //블록에 약간의 중력을 가하지 마십시오. //그렇지 않으면 블록이 서로에 대해 튀어 오릅니다.
            block.body.gravity.y = 4;
            //블록이 러너에 반응하도록 바운스를 설정하십시오.
            block.body.bounce.set(1,1);
        });
    }
이제 우리는 3 가지 일이 필요합니다.
- 지상을 빠져 나갈 수없는 블록들
- 서로 떨어지지 않는 블록들
- 그들이 플레이어를 때 때 반응하는 블록
그렇게 하기 위해서 우리는 플레이어가 지상에 머물렀음을 확인하기 위해 했던 것과 똑같이 합니다. 우리는 각각에 대해 충돌을 설정했습니다. 이것을 업데이트 기능에 배치하십시오.

        //영웅과 블록을 충돌시키다.
        game.physics.arcade.collide(this.hero, this.blocks);
        //블록을 땅에 충돌시키다.
        game.physics.arcade.collide(this.ground, this.blocks);
         //하나의 그룹 만 지정하면 해당 그룹의 모든 자식이 서로 충돌합니다.
        game.physics.arcade.collide(this.blocks);

- 작업 결과물 입니다 -

블록 재설정하기

마지막으로 해야 할 일은 플레이어가 성공적으로 블록을 건너 뛰면 블록을 재설정 하는 것입니다. 그룹을 움직이면 그룹의 x 위치를 확인하고 그 수가 0보다 작은 지 확인할 수 있습니다. 블록을 대신 움직이기 때문에 블록의 x 위치는 그룹과 관련이 있습니다. 즉, 시작시 x 위치가 0이고 게임이 진행됨에 따라 부정적인 속도로 이동합니다. 따라서 블록이 화면 왼쪽에서 벗어난다면 게임의 음수 값 이어야합니다. width (-game.width);

모든 블록을 검사하는 대신, 모든 블록이 맞지 않으면 게임 x 위치에 있어야 하므로 그룹의 첫 번째 자식을 확인할 수 있습니다.
//get the first child
var fchild = this.blocks.getChildAt(0);
//화면이 꺼져 있으면 블록을 재설정합니다.
if (fchild.x < -game.width) {
    this.makeBlocks();
}

지금까지 StateMain.js의 전체 코드가 있습니다.
var StateMain = {
    preload: function() {
        game.load.image("ground", "images/ground.png");
        game.load.image("hero", "images/hero.png");
        game.load.image("bar", "images/powerbar.png");
        game.load.image("block", "images/block.png");
    },
    create: function() {
        this.power = 0;
        //배경을 하늘색으로 바꾸다.
        game.stage.backgroundColor = "#00ffff";
        //땅을 추가
        this.ground = game.add.sprite(0, game.height * .9, "ground");
        //영웅을 안으로 추가하십시오.
        this.hero = game.add.sprite(game.width * .2, this.ground.y - 25, "hero");
        //영웅의 머리 바로 위에 파워 바 추가
        this.powerBar = game.add.sprite(this.hero.x + 25, this.hero.y - 25, "bar");
        this.powerBar.width = 0;
        //물리 엔진을 시작하십시오.
        game.physics.startSystem(Phaser.Physics.ARCADE);
        //주인공에 물리엔진을 가능하게하다.
        game.physics.enable(this.hero, Phaser.Physics.ARCADE);
        game.physics.enable(this.ground, Phaser.Physics.ARCADE);
        //game.physics.arcade.gravity.y = 100;
        this.hero.body.gravity.y = 200;
        this.hero.body.collideWorldBounds = true;
        //this.hero.body.bounce.set(0, .2);
        this.ground.body.immovable = true;
        //초기 위치를 기록하다
        this.startY = this.hero.y;
        //입력 확인 설정
        game.input.onDown.add(this.mouseDown, this);
        this.blocks = game.add.group();
        this.makeBlocks();
    },
    mouseDown: function() {
        if (this.hero.y != this.startY) {
            return;
        }
        game.input.onDown.remove(this.mouseDown, this);
        this.timer = game.time.events.loop(Phaser.Timer.SECOND / 1000, this.increasePower, this);
        game.input.onUp.add(this.mouseUp, this);
    },
    mouseUp: function() {
        game.input.onUp.remove(this.mouseUp, this);
        this.doJump();
        game.time.events.remove(this.timer);
        this.power = 0;
        this.powerBar.width = 0;
        game.input.onDown.add(this.mouseDown, this);
    },
    increasePower: function() {
        this.power++;
        this.powerBar.width = this.power;
        if (this.power > 50) {
            this.power = 50;
        }
    },
    doJump: function() {
        this.hero.body.velocity.y = -this.power * 12;
    },
    makeBlocks: function() {
        this.blocks.removeAll();
        var wallHeight = game.rnd.integerInRange(1, 4);
        for (var i = 0; i < wallHeight; i++) {
            var block = game.add.sprite(0, -i * 50, "block");
            this.blocks.add(block);
        }
        this.blocks.x = game.width - this.blocks.width
        this.blocks.y = this.ground.y - 50;
         //블록에 대해 반복 물리엔진 적용.
        this.blocks.forEach(function(block) {
            //물리엔진을 가능하게하다
            game.physics.enable(block, Phaser.Physics.ARCADE);
            //x 속도를 -160으로 설정한다.
            block.body.velocity.x = -150;
             //블록에 약간의 중력을 가하지 마라. 그렇지 않으면 블록이 서로 반동 할 것이다.
            block.body.gravity.y = 4;
             //블록이 러너에 반응하도록 바운스를 설정하십시오.
            block.body.bounce.set(1, 1);
        });
    },
    update: function() {
        game.physics.arcade.collide(this.hero, this.ground);
        //주인공과 블록을 충돌시키다.
        game.physics.arcade.collide(this.hero, this.blocks);
        //블록을 땅에 충돌시키다.
        game.physics.arcade.collide(this.ground, this.blocks);
         //하나의 그룹 만 지정하면 해당 그룹의 모든 자식이 서로 충돌합니다.
        game.physics.arcade.collide(this.blocks);
        //get the first child
        var fchild = this.blocks.getChildAt(0);
        //if off the screen reset the blocks
        if (fchild.x < -game.width) {
            this.makeBlocks();
        }
    }
}

지금까지의 결과물입니다. 
https://phasergames.com/phaser/examples/games/endlessRunner4/index.html


댓글 없음:

댓글 쓰기