我在业余时间制作一个基本的平台游戏,我目前正在尝试添加重力。游戏在画布中运行,因此我使用黑色像素作为实体对象。我正在制作的精灵应该在没有接触到黑色实线时掉落。为此,我使用context.getImageData()
了精灵对象的 x 位置、y 位置、宽度和高度属性。当我创建玩家精灵时,我为其分配了一个 x 位置 10、y 位置 10、宽度 50 和高度 100: var player = new Sprite (10, 10, 50, 100);
我的问题是当我尝试绘制精灵或使用它的 y 位置时context.getImageData()
它说y位置是Nan。下面的代码是一个简化版本,只有相关变量。
//-----------SETUP-------------//
//----GLOBAL VARIABLES---//
var gravityValue = 1; //amount of change that gravity makes per move
var fallBoxThickness = 1; //thickness of fall-box check
var canvas = document.getElementById("canvas"); //get the canvas object
canvas.width = 800; //set the canvas width
canvas.height = 600; //set the canvas height
var context = canvas.getContext("2d"); //get the canvas's context, 2d
//--------OBJECTS---------//
function Sprite (x,y,width,height) { //sprite object
//components
this.x = x; //sprite x position
this.y = y; //sprite y position
this.width = width; //image width
this.height = height; //image height
this.dx = 0; //sprite x movement
this.dy = 0; //sprite y movement
this.gravityEnabled = true; //allows sprite falling, must be manually disabled
//methods
this.draw = function () { //draw method
//context.drawImage(this.src, this.x, this.y);
//draws the sprite to the canvas
//it used to do the above, now it outputs it to the output span
document.getElementById("output").innerHTML = this.y;
};
this.move = function () { //move method
if (this.gravityEnabled === true) { //if the sprite can fall
var hit = false; //a hit is not yet detected
var checkSpace = context.getImageData( //get pixels to see if the sprite ...
this.x, parseInt(this.y + this.height), //... will hit an object below it's lower edge
this.x + this.width, this.y + this.height, + fallBoxThickness);
var i = 0; //set i to 0
while (i < checkSpace.length && hit === false) {
//while the check hasn't finished and a hit isn't detected
if (checkSpace[i] < 5 //
&& checkSpace[i+1] < 5 //if there is a black pixel
&& checkSpace[i+2] < 5) { //
hit = true; //record that there is a hit
}
i = i + 4; //add 4 to i
}
if (hit === false) { //if the check didn't hit
this.dy += gravityValue; //add to the fall of the sprite
} else {
this.dy = 0;
}
}
this.y += this.dy;
};
}
//------------PLAYER CREATION---------//
var player = new Sprite (10, 10, 50, 100); //create the player object
//--------FUNCTIONS--------//
function drawCanvas () { //draw everything on the canvas
player.draw(); //draw the player
}
function moveSprites () {
player.move();
}
//----------MAIN-----------//
function main () {
moveSprites(); //move the sprites
drawCanvas(); //draw the screen
}
setInterval(main,100); //run main 10 times a second,
//start the program
<title>ptf2</title>
<canvas id="canvas" style="border:1px solid black;"></canvas>
there was images here but the javascript never gets far enough to render them because of the y-position error.<br>
Instead I am just outputting the value of the player sprite's y-position to the span below.<br>
:<span id="output">this is to prevent it from occasionally being undefined</span>
另外,我真的不确定为什么这个版本可以代替我以前的版本,所以现在我将包含完整版本:
//-----------SETUP-------------//
//----IMAGES----//
document.getElementById("map").style.display = "none"; //hide the map image
document.getElementById("sprite").style.display = "none"; //hide the sprite image
//----GLOBAL VARIABLES---//
var gravityValue = 1; //amount of change that gravity makes per move
var fallBoxThickness = 1; //thickness of fall-box check
var canvas = document.getElementById("canvas"); //get the canvas object
canvas.width = 800; //set the canvas width
canvas.height = 600; //set the canvas height
var context = canvas.getContext("2d"); //get the canvas's context, 2d
//--------OBJECTS---------//
function Sprite (x,y,src,width,height,dx,dy) { //sprite object
//components
this.x = x; //sprite x position
this.y = y; //sprite y position
this.src = document.getElementById(src); //sprite source image
this.width = width; //image width
this.height = height; //image height
this.dx = dx; //sprite x movement
this.dy = dy; //sprite y movement
this.gravityEnabled = true; //allows sprite movement, must be manually disabled
//methods
this.draw = function () { //draw method
context.drawImage(this.src, this.x, this.y); //draws the sprite to the canvas
};
this.move = function () { //move method
if (this.gravityEnabled === true) { //if the sprite can fall
var hit = false; //a hit is not yet detected
var checkSpace = context.getImageData( //get pixels to see if the sprite ...
this.x, parseInt(this.y + this.height), //... will hit an object below it's lower edge
this.x + this.width, this.y + this.height, + fallBoxThickness);
var i = 0; //set i to 0
while (i < checkSpace.length && hit === false) {
//while the check hasn't finished and a hit isn't detected
if (checkSpace[i] < 5 //
&& checkSpace[i+1] < 5 //if there is a black pixel
&& checkSpace[i+2] < 5) { //
hit = true; //record that there is a hit
}
i = i + 4; //add 4 to i
}
if (hit === false) { //if the check didn't hit
this.dy += gravityValue; //add to the fall of the sprite
} else {
this.dy = 0;
}
}
this.y += this.dy;
};
}
var player = new Sprite (10, 10, "sprite", 50, 100); //create the player object
var map = new Sprite (0, 0, "map", 800, 600); //create the map sprite
map.gravityEnabled = false; //prevents the map from falling
//--------FUNCTIONS--------//
function drawCanvas () { //draw everything on the canvas
map.draw(); //draw the map
player.draw(); //draw the player
}
function moveSprites () {
player.move();
}
//----------MAIN-----------//
function main () {
moveSprites(); //move the sprites
drawCanvas(); //draw the screen
alert("run");
}
setInterval(main,100); //run main 10 times a second,
//start the program
<title>ptf2</title>
<canvas id="canvas" style="border:1px solid black;"></canvas>
<img id="map" src = "assets/map03.png">
<img id="sprite"src = "assets/sprite.png">
<script src = "main.js"></script>
对于为什么不能使用完全相同的值,任何启示都将不胜感激。谢谢你。