Connor Price
Connor Price

Reputation: 29

Canvas - bullets to mouse point

So I'm trying to implement shooting, and what I want to do is take the players x and y and use that as the base point where the projectile derives from and then it basically goes to the point pressed in the canvas. The projectile is deriving from the player, but instead of going to the cursor point it strangely ALWAYS goes right, but will go right+up or right+down depending on which direction was pressed; I've looked on-line and can't seem to find the answer.

Inside my javascript here is the shoot function:

function shoot(event){
    bullets[bulletCount] = new Array(4);
    bullets[bulletCount][0] = x;
    bullets[bulletCount][1] = y;
    bullets[bulletCount][2] = window.event.clientX;
    bullets[bulletCount][3] = window.event.clientY;
    bulletCount++;
}

In my javascript here is the bullet part in the update method:

for(var b = 0; b < bullets.length; b++){
        if(bullets[b][0] < bullets[b][2]) bullets[b][0] += 5;
        if(bullets[b][0] > bullets[b][2]) bullets[b][0] -= 5;
        if(bullets[b][1] < bullets[b][3]) bullets[b][1] += 5;
        if(bullets[b][1] > bullets[b][3]) bullets[b][1] -= 5;
        ctx.fillRect(bullets[b][0],bullets[b][1], 8, 8);
    }

and in my index.html page:

<canvas id="gameBoard" onClick="shoot(event)" width="500" height="500" tabindex="1"></canvas>

EDIT: fixed the problem, for anyone else who suffers this problem inside the shoot function change from what was originally up there to this:

function shoot(event){
    var rect = canvas.getBoundingClientRect();
    bullets[bulletCount] = new Array(4);
    bullets[bulletCount][0] = x;
    bullets[bulletCount][1] = y;
    bullets[bulletCount][2] = event.clientX - rect.left;
    bullets[bulletCount][3] = event.clientY - rect.top;
    bulletCount++;
} 

Upvotes: 0

Views: 1068

Answers (2)

NickCortes
NickCortes

Reputation: 111

    var bullets = []; 
    var bullet_speed = 10;   

call this in your init() fucntion: which could have your setInterval.

    window.addEventListener('click', shoot, false);

call this in your draw function:

for (var i = 0; i < bullets.length; i++){
    bullets[i].x += bullets[i].xChange;
    bullets[i].y += bullets[i].yChange;
    context.fillStyle ='black';
    context.fillRect(bullets[i].x,bullets[i].y,4,4)
  }

function shoot(event){
    x = event.offsetX
    y = event.offsetY
    d = Math.sqrt(Math.pow(Math.abs(player.x-x),2)+Math.pow(Math.abs(player.y-y),2))
    bullet = {
        x : player.x,
        y : player.y,
        xChange : (x-player.x)/(d/bullet_speed),
        yChange : (y-player.y)/(d/bullet_speed),
    }; 
    bullets.push(bullet);
} 

Upvotes: 0

assembly_wizard
assembly_wizard

Reputation: 2064

The problem lies within these two lines:

bullets[bulletCount][2] = window.event.clientX;
bullets[bulletCount][3] = window.event.clientY;

It is because that the location you save for the click is not the real location.

You see, event.clientX/Y give you the mouse coordinates relative to the top left corner of the window, but you only want the coordinates relative to the top left corner of your canvas element.

To fix this, first get to know another way to get the mouse coordinates, which is event.pageX/Y.

This will not give you the coordinates relative to the canvas, however you need this instead of event.clientX/Y because it will give you the mouse coordinates relative to the top left corner of the page, not the window, which means it doesn't matter if the user scrolls somewhere, the coordinates are always true to the page.

So, now that you're using event.pageX/Y, how to make it relative to the canvas? Well, we can just take these coordinates and subtract the top left corner coordinates of the canvas:

bullets[bulletCount][2] = window.event.pageX - canvas.offsetLeft;
bullets[bulletCount][3] = window.event.pageY - canvas.offsetTop;
  • Assuming that your canvas element is saved in a variable named canvas

Hope that solves it :D

Upvotes: 1

Related Questions