2016-08-16 74 views
3

我正在编写一个突破游戏JavaScript,并且在碰撞检测中遇到了问题。Javascript帆布突破碰撞检测问题

在运行程序时,球与桨之间的所有碰撞都很好,直到第一次碰撞为止。此时程序将球重新放回中间并再次发送。然而,这次桨叶表面被忽略了,但超出该点的代码确定球已经离开边界,就像在球下一次仍然重置时离开屏幕一样。有一个jsFiddle的代码是here

我已经尝试了几个if/else变体来修补它,但无法弄清楚为什么后面的代码被忽略。

代码片断

var canvas = document.querySelector("canvas"); 
 
var surface = canvas.getContext("2d"); 
 
var button = document.querySelector("button"); 
 

 
button.addEventListener("click", playGame, false); 
 

 
//Game results 
 
var score = 0; 
 
var lives = 4; 
 
var gameOver = false; 
 

 
//Create a ball object 
 
var ball = { 
 
\t radius: 10, 
 
\t x: canvas.height - 30, 
 
\t y: canvas.width/2, 
 
\t dx: 3, 
 
\t dy: -3, 
 
}; 
 

 
//Create a paddle object 
 
var paddle = { 
 
\t width: 75, 
 
\t height: 10, 
 
\t x: (canvas.width -75)/2, 
 
\t y: canvas.height - 10 
 
}; 
 

 
//add key controls 
 
document.addEventListener("keydown", keydownHandler, false); 
 
document.addEventListener("keyup", keyupHandler, false); 
 
var moveLeft = false; 
 
var moveRight = false; 
 

 
function playGame() { 
 
\t requestAnimationFrame (playGame, canvas); 
 

 
\t \t render(); 
 
\t \t moveBall(); 
 
\t \t movePaddle(); 
 

 
} 
 

 

 

 
function render() { 
 
\t //Clear the canvas surface 
 
\t surface.clearRect(0,0,canvas.width,canvas.height); 
 
\t 
 
\t drawBall(); 
 
\t drawPaddle(); 
 
\t 
 
\t //Keep ball within boundary 
 
\t if(ball.x + ball.dx < 0 + ball.radius || ball.x + ball.dx > canvas.width - ball.radius) { 
 
\t \t //Reverse the direction of the ball in x direction 
 
\t \t ball.dx = -ball.dx; 
 
\t } 
 
\t if(ball.y + ball.dy < 0 + ball.radius) { 
 
\t \t //Reverse the direction of the ball in the y direction 
 
\t \t ball.dy = -ball.dy; 
 
\t } 
 
\t 
 
\t //Make ball bounce of top surface of paddle 
 
\t if(Math.floor(ball.y) === Math.floor(canvas.height - ball.radius - paddle.height) && 
 
\t \t ball.x + ball.radius > paddle.x && ball.x - ball.radius < paddle.x + paddle.width) { 
 
\t \t \t //ball has hit paddle 
 
\t \t \t ball.dy = -ball.dy; 
 
\t } 
 
\t 
 
\t if (ball.y + ball.dy > canvas.height + ball.radius) { 
 
\t \t \t //ball has gone outside area 
 
\t \t \t console.log('Out of Bounds'); 
 
\t \t \t 
 
\t \t \t //Set new ball position 
 
\t \t \t ball.y = canvas.height -30; 
 
\t \t \t ball.x = canvas.width/2; 
 
\t \t \t ball.dy = -ball.dy; 
 
\t } 
 
\t 
 
} 
 
\t 
 

 
function drawBall() { 
 
\t surface.beginPath(); 
 
\t surface.arc(ball.x,ball.y,ball.radius,0, Math.PI*2); 
 
\t surface.fillStyle = "yellow"; 
 
\t surface.fill(); 
 
\t surface.closePath(); 
 
} 
 

 
function drawPaddle() { 
 
\t surface.beginPath(); 
 
\t surface.rect(paddle.x, paddle.y, paddle.width, paddle.height); 
 
\t surface.fillStyle = "lightblue"; 
 
\t surface.fill(); 
 
\t surface.closePath(); 
 
} 
 

 
function movePaddle() { 
 
\t if (moveLeft && paddle.x > 0) { 
 
\t \t paddle.x -= 7; 
 
\t } 
 
\t if (moveRight && paddle.x + paddle.width < canvas.width) { 
 
\t \t paddle.x +=7; 
 
\t } 
 
} 
 

 
function moveBall() { 
 
\t //Give ball a starting velocity 
 
\t ball.x += ball.dx; 
 
\t ball.y += ball.dy; 
 
} 
 

 
function keydownHandler(event) { 
 
\t if(event.keyCode === 37) { 
 
\t \t moveLeft = true; 
 
\t } 
 
\t if(event.keyCode === 39) { 
 
\t \t moveRight = true; 
 
\t } 
 
} 
 

 
function keyupHandler(event) { 
 
\t if(event.keyCode === 37) { 
 
\t \t moveLeft = false; 
 
\t } 
 
\t if(event.keyCode === 39) { 
 
\t \t moveRight = false; 
 
\t } 
 
} 
 

 
function scoreboard() { 
 
\t surface.font = "20px Arial"; 
 
\t surface.fillStyle = "#00FF00"; 
 
\t surface.fillText("Score: " + score, 8, 20); 
 
\t surface.fillText("Lives: " + lives, 730, 20); 
 
}
canvas { 
 
\t background-color: #000; 
 
\t border: 3px solid green; 
 
}
<canvas id="myCanvas" width="800" height="480"></canvas> 
 

 
<button>Run</button>

回答

0

我到底到了那里。

我的代码期望桨表面上的球表面精确匹配。但是,由于增量一次是3个像素,所以球表面刚好在桨表面之上,而在下一个框架上它恰好超过了它。

我通过修改为“大于桨面且小于画布区域”条件来修复。

更新小提琴https://jsfiddle.net/Geejayz/bnLbzgg0/6/

var canvas = document.querySelector("canvas"); 
 
var surface = canvas.getContext("2d"); 
 
var button = document.querySelector("button"); 
 

 
button.addEventListener("click", playGame, false); 
 

 
//Game results 
 
var score = 0; 
 
var lives = 4; 
 
var gameOver = false; 
 

 
//Create a ball object 
 
var ball = { 
 
\t radius: 10, 
 
\t x: canvas.height - 30, 
 
\t y: canvas.width/2, 
 
\t dx: 3, 
 
\t dy: -3, 
 
}; 
 

 
//Create a paddle object 
 
var paddle = { 
 
\t width: 75, 
 
\t height: 10, 
 
\t x: (canvas.width -75)/2, 
 
\t y: canvas.height - 10 
 
}; 
 

 
//add key controls 
 
document.addEventListener("keydown", keydownHandler, false); 
 
document.addEventListener("keyup", keyupHandler, false); 
 
var moveLeft = false; 
 
var moveRight = false; 
 

 
function playGame() { 
 
\t requestAnimationFrame (playGame, canvas); 
 

 
\t \t render(); 
 
\t \t moveBall(); 
 
\t \t movePaddle(); 
 

 
} 
 

 

 

 
function render() { 
 
\t //Clear the canvas surface 
 
\t surface.clearRect(0,0,canvas.width,canvas.height); 
 
\t 
 
\t drawBall(); 
 
\t drawPaddle(); 
 
\t 
 
\t //Keep ball within boundary 
 
\t if(ball.x + ball.dx < 0 + ball.radius || ball.x + ball.dx > canvas.width - ball.radius) { 
 
\t \t //Reverse the direction of the ball in x direction 
 
\t \t ball.dx = -ball.dx; 
 
\t } 
 
\t if(ball.y + ball.dy < 0 + ball.radius) { 
 
\t \t //Reverse the direction of the ball in the y direction 
 
\t \t ball.dy = -ball.dy; 
 
\t } 
 
\t 
 
\t //Make ball bounce of top surface of paddle 
 
\t if(ball.y > canvas.height - ball.radius - paddle.height && 
 
\t \t ball.y < canvas.height - ball.radius && 
 
\t \t ball.x + ball.radius > paddle.x && ball.x - ball.radius < paddle.x + paddle.width) { 
 
\t \t \t //ball has hit paddle 
 
\t \t \t ball.dy = -ball.dy; 
 
\t } 
 
\t 
 
\t if (ball.y + ball.dy > canvas.height + ball.radius) { 
 
\t \t \t //ball has gone outside area 
 
\t \t \t console.log('Out of Bounds'); 
 
\t \t \t 
 
\t \t \t //Set new ball position 
 
\t \t \t ball.y = canvas.height -30; 
 
\t \t \t ball.x = canvas.width/2; 
 
\t \t \t ball.dy = -ball.dy; 
 
\t } 
 
\t 
 
} 
 
\t 
 

 
function drawBall() { 
 
\t surface.beginPath(); 
 
\t surface.arc(ball.x,ball.y,ball.radius,0, Math.PI*2); 
 
\t surface.fillStyle = "yellow"; 
 
\t surface.fill(); 
 
\t surface.closePath(); 
 
} 
 

 
function drawPaddle() { 
 
\t surface.beginPath(); 
 
\t surface.rect(paddle.x, paddle.y, paddle.width, paddle.height); 
 
\t surface.fillStyle = "lightblue"; 
 
\t surface.fill(); 
 
\t surface.closePath(); 
 
} 
 

 
function movePaddle() { 
 
\t if (moveLeft && paddle.x > 0) { 
 
\t \t paddle.x -= 7; 
 
\t } 
 
\t if (moveRight && paddle.x + paddle.width < canvas.width) { 
 
\t \t paddle.x +=7; 
 
\t } 
 
} 
 

 
function moveBall() { 
 
\t //Give ball a starting velocity 
 
\t ball.x += ball.dx; 
 
\t ball.y += ball.dy; 
 
} 
 

 
function keydownHandler(event) { 
 
\t if(event.keyCode === 37) { 
 
\t \t moveLeft = true; 
 
\t } 
 
\t if(event.keyCode === 39) { 
 
\t \t moveRight = true; 
 
\t } 
 
} 
 

 
function keyupHandler(event) { 
 
\t if(event.keyCode === 37) { 
 
\t \t moveLeft = false; 
 
\t } 
 
\t if(event.keyCode === 39) { 
 
\t \t moveRight = false; 
 
\t } 
 
} 
 

 
function scoreboard() { 
 
\t surface.font = "20px Arial"; 
 
\t surface.fillStyle = "#00FF00"; 
 
\t surface.fillText("Score: " + score, 8, 20); 
 
\t surface.fillText("Lives: " + lives, 730, 20); 
 
}
canvas { 
 
\t background-color: #000; 
 
\t border: 3px solid green; 
 
}
<canvas id="myCanvas" width="800" height="480"></canvas> 
 

 
<button>Run</button>

(也感谢AgataB和ZOW的编辑 - 它一直以来我张贴了一段时间我可能还是没有得到这个职位完美无缺)。

+0

请注意,jsfiddles实际上需要与他们的代码。学习阅读系统给你的信息,当它阻止你发布时,请。 – Blubberguy22