Javascript Pac-Man碰撞检测

时间:2016-06-02 10:41:48

标签: javascript html canvas

背景信息:我是Canvas,javascript和jQuery的初学者,以及整体游戏开发。这是我的第一部非文字游戏。

我已经在这个问题上工作了几天,并打了2个墙,我认为这是相互关联的。我将在这里描述问题,然后给你代码;

  1. 当我将瓷砖绘制到画布上时,电路板似乎是镜像的。我不确定为什么会这样,但我似乎无法修复它。

  2. 我已经为我的角色制定了可用的路线,但碰撞检测只能上下移动,但不能左右移动。

  3. 以下是代码:

    var TILE_WIDTH = 32, TILE_HEIGHT = 32, TICK_SPEED = 1000/30;
    var playerimg = new Image(), ghostimg = new Image(), walkableimg = new Image(), wallimg = new Image(); 
    
    playerimg.src = "player.png";
    ghostimg.src = "ghost.png";
    walkableimg.src = "walkable.png";
    wallimg.src = "wall.png";
    
    
    var map = [
    [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1],
    [1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1]
    
    
    
    ]
    
    var spawnx = 128, spawny = 128;
    
    
    var player = {direction: "right",image: playerimg, x:spawnx, y: spawny, xdir: spawnx, ydir: spawny}, ghost = {image:ghostimg, x:128 , y:128}, wall = {walkable: false,image: wallimg}, walkable = {walkable: true, image: walkableimg}; 
    
    
    function main(){
        setInterval(
    
            function(){
    
                tick();
            }, TICK_SPEED)
    
    }
    
    
    function collisionDetect(direction){
        if(direction = "up" && map[(player.ydir/32)][(player.xdir/32)] == 0){
            player.y = player.ydir; //up    
            console.log("moved up");
    
    
        } else if(direction = "down" && map[(player.ydir/32)][(player.xdir32)] == 0){
            player.y = player.ydir; //down
            console.log("moved down");
    
    
        } else if(direction = "left" && map[player.ydir/32][(player.xdir/32)] == 0){
            player.x = player.xdir; //left
            console.log("moved left");
    
        } else if(direction = "right" && map[player.ydir/32][(player.xdir/32)] == 0){
            player.x = player.xdir; //right
            console.log("moved right ");
        } 
    
        player.xdir = player.x;
        player.ydir = player.y;
    }
    
    function solidDetect(block){
    
    }
    
    
    
    function render(){
        var field = document.getElementById("draw");
        var ctx = field.getContext("2d");
        renderField();
        renderPlayer();
    
    }  
    
    function renderPlayer(){
        var field = document.getElementById("draw");
        var ctx = field.getContext("2d");
        console.log(player.x,player.y,player.xdir,player.ydir);
        ctx.drawImage(player.image,player.x,player.y);
        ctx.rect(player.x,player.y,10,10);
        ctx.stroke();
    }
    
    function renderField(){
        var field = document.getElementById("draw");
        var ctx = field.getContext("2d");
    
        for(var i = 0; i < 20; i++){
            for(var j = 0; j<20; j++){
    
                    if(map[i][j] == 1){
                        ctx.drawImage(wall.image,TILE_HEIGHT*i,TILE_HEIGHT*j);
    
                    } else if(map[i][j] == 0){
                        ctx.drawImage(walkable.image,TILE_HEIGHT*i,TILE_HEIGHT*j);
    
                    }
    
    
    
            }
        }
    }
    
    function tick(){
    
        render();
    
    }
    
    
    
    
    
    //key listener
    
    
    
    $(document).keypress(function (eventObject) {
            var key = eventObject.keyCode;
            console.log(key);
    
            if (key == 115) {
            // up arrow
            console.log("Key pressed");
            player.ydir += 32;
            player.direction = "up";
            collisionDetect(player.direction);
            }
            else if (key == 119) {
                // down arrow
                console.log("Key pressed");
                player.ydir -= 32;
                player.direction = "down";
                collisionDetect(player.direction);
            }
            else if (key == 97) {
               // left arrow
               console.log("Key pressed");
               player.xdir -= 32;
               player.direction = "left";
               collisionDetect(player.direction);
            }
            else if (key == 100) {
               // right arrow
               console.log("Key pressed");
               player.xdir += 32;
               player.direction = "right";
               collisionDetect(player.direction);
            } else {
                return 1;
            }
    })
    
    
    
    
    main();
    

1 个答案:

答案 0 :(得分:1)

我不明白你所反映的董事会是什么意思。无论map包含什么内容都会在我的屏幕上呈现。

首先,应手动分配画布宽度和高度:

function render(){
    var field = document.getElementById("draw");
    var ctx = field.getContext("2d");
    field.height = TILE_HEIGHT*map.length;
    field.width = TILE_WIDTH*map[0].length;
    renderField();
    renderPlayer();
}

我更新了您的密钥检测功能以注册箭头键(必须使用onkeydown)。请注意,y坐标是从Canvas的左上角计算的。

window.onkeydown = function (eventObject) {
    var key = eventObject.keyCode;
    if (key == 38) {
        // up arrow
        console.log("Key pressed");
        player.ydir -= 32;
        player.direction = "up";
        collisionDetect(player.direction);
    }
    else if (key == 40) {
        // down arrow
        console.log("Key pressed");
        player.ydir += 32;
        player.direction = "down";
        collisionDetect(player.direction);
    }
    else if (key == 37) {
       // left arrow
       console.log("Key pressed");
       player.xdir -= 32;
       player.direction = "left";
       collisionDetect(player.direction);
    }
    else if (key == 39) {
       // right arrow
       console.log("Key pressed");
       player.xdir += 32;
       player.direction = "right";
       collisionDetect(player.direction);
    }
    else {
        return 1;
    }
};

collisionDetect函数中有两个错误:

  1. 分配而不是比较if(direction = "up" &&...)
  2. 缺少向下方向的除法运算符(player.xdir32)
  3. 这是固定功能:

    function collisionDetect(direction){
    
        if(direction == "up" && map[(player.ydir/32)][(player.xdir/32)] == 0){
            player.y = player.ydir; //up    
            console.log("moved up");
    
    
        } else if(direction == "down" && map[(player.ydir/32)][(player.xdir/32)] == 0){
            player.y = player.ydir; //down
            console.log("moved down");
    
    
        } else if(direction == "left" && map[player.ydir/32][(player.xdir/32)] == 0){
            player.x = player.xdir; //left
            console.log("moved left");
    
        } else if(direction == "right" && map[player.ydir/32][(player.xdir/32)] == 0){
            player.x = player.xdir; //right
            console.log("moved right ");
        } 
    
        player.xdir = player.x;
        player.ydir = player.y;
    }
    

    瞧!运动和墙壁碰撞在各个方向都有效。