views:

133

answers:

3

Not entirely sure I posed the question in the best way but here goes...

I have been playing around with the HTML5 canvas API and have got as far as drawing a shape in the canvas and getting it to move around with the arrow keys.

I then tried to move my various variables and functions to a template so I could spawn multiple shapes (that would eventually be controlled by different keys).

This is what I have:

function player(x, y, z, colour, speed){
    this.lx = x;
    this.ly = y;
    this.speed = 10;
    this.playerSize = z;
    this.colour = colour;
}

playerOne = new player(100, 100, 10, "#F0F");

function persona(z, colour){ 
    zone.fillStyle = colour;
    offset = 0 - (z / 2);
    zone.fillRect(offset, offset, z, z);
}

function move(x, y){
    playerOne.lx = playerOne.lx + x;
    playerOne.ly = playerOne.ly + y;

    zone.clearRect(0, 0, 500, 500);

    zone.save();
        zone.translate(playerOne.lx, playerOne.ly);
        persona(playerOne.playerSize, playerOne.colour);
    zone.restore();
}

window.onkeydown = function() {

    var direction = this.event.keyCode;

    var s = playerOne.speed;

    // Arrow Keys
    if( direction == 38 && playerOne.ly >= 10){ // Up
        move(0,-s);
    }

    if( direction == 40 && playerOne.ly <= 490){    // Down
        move(0,s);
    }

    if( direction == 37 && playerOne.lx >= 10){ // Left
        move(-s,0);
    }

    if( direction == 39 && playerOne.lx <= 490){    // Right
        move(s,0);
    }
};

window.onload = function() {
    zone = document.getElementById('canvas').getContext('2d');
    zone.save();
        zone.translate(playerOne.lx, playerOne.ly);
        persona(playerOne.playerSize, playerOne.colour);
    zone.restore();
};

So what I tried to do was move the persona function into the player template like this:

function player(x, y, z, colour, speed){
    this.lx = x;
    this.ly = y;
    this.speed = 10;

    function persona(){ 
        zone.fillStyle = colour;
        var offset = 0 - (z / 2);
        zone.fillRect(offset, offset, z, z);
    }

}

And then where before it said

persona(playerOne.playerSize, playerOne.colour);

it now just says

playerOne.persona();

But this is just totally flaking out and not working and I can't figure out why.

I'm probably going about it all the wrong way and I think the problem is that I'm trying to manipulate the canvas.context (call zone in my script) from within a object/template.

Perhaps its nothing to do with that at all and I an just not declaring my persona functions properly in the context of the template.

Documentation for the canvas API is very thin on the ground and any hint in the right direction will be very much appreciated.

A: 

First, you need the "zone" variable to be global, so declare it in the global scope to be able to access it from anywhere.

But I suggest you to use a framework to make animations really easier, like CakeJS or RaphaelJS.

Fabien Ménager
A: 

Been hacking away at this for a few more minutes and got the following which is basically what I was trying to achieve from the start. I went in a slightly different direction with this but I would still like any feedback anyone may want to give.

function Player(x, y, z, colour, speed){
    this.lx = x;
    this.ly = y;
    this.speed = speed;
    this.it = false; 
    this.playerSize = z;
    this.colour = colour;

    this.move = move;
    this.draw = persona;
}

function move(dx, dy){
    this.lx = this.lx + (dx * this.speed);
    this.ly = this.ly + (dy * this.speed);
}

function persona(){ 
    zone.fillStyle = this.colour;
    var offset = 0 - (this.playerSize / 2);
    zone.fillRect(offset, offset, this.playerSize, this.playerSize);
}

playerOne = new Player(400,400, 10, "#F0F", 10);
playerTwo = new Player(100,100, 10, "#0F0", 10);

function drawPlayers(){
    zone.clearRect(0, 0, 500, 500);

    zone.save();
     zone.translate(playerOne.lx, playerOne.ly);
     playerOne.draw();
    zone.restore();

    zone.save();
     zone.translate(playerTwo.lx, playerTwo.ly);
     playerTwo.draw();
    zone.restore();
}

window.onkeydown = function() {

    var direction = this.event.keyCode;

    // Arrows
    if( direction == 38 && playerOne.ly >= 10){  // Up
     playerOne.move(0,-1);
    }
    if( direction == 40 && playerOne.ly <= 490){ // Down
     playerOne.move(0,1);
    }
    if( direction == 37 && playerOne.lx >= 10){  // Left
     playerOne.move(-1,0);
    }
    if( direction == 39 && playerOne.lx <= 490){ // Right
     playerOne.move(1,0);
    }

    // WASD
    if( direction == 87 && playerTwo.ly >= 10){  // Up
     playerTwo.move(0,-1);
    }
    if( direction == 83 && playerTwo.ly <= 490){ // Down
     playerTwo.move(0,1);
    }
    if( direction == 65 && playerTwo.lx >= 10){  // Left
     playerTwo.move(-1,0);
    }
    if( direction == 68 && playerTwo.lx <= 490){ // Right
     playerTwo.move(1,0);
    }

    drawPlayers();

};

window.onload = function() {
    zone = document.getElementById('canvas').getContext('2d');
    drawPlayers();
};
Binarytales
A: 

Just commenting that your Player.draw method should be able to handle positioning your sprites on the canvas. This code behaves the same way as your solution, but hopefully is clearer and more compact.

function Player(x, y, z, colour, speed){
    this.lx = x;
    this.ly = y;
    this.speed = speed;
    this.it = false; 
    this.playerSize = z;
    this.colour = colour;
}
Player.prototype = {
    move: function(dx, dy){
        this.lx = this.lx + (dx * this.speed);
        this.ly = this.ly + (dy * this.speed);
    },
    draw: function(){ 
        var size = this.playerSize,
            offset = size / 2;
        zone.fillStyle = this.colour;
        zone.fillRect(playerTwo.lx - offset, playerTwo.ly - offset, size, size);
    }
};

playerOne = new Player(400,400, 10, "#F0F", 10);
playerTwo = new Player(100,100, 10, "#0F0", 10);

function drawPlayers(){
    zone.clearRect(0, 0, 500, 500);

    playerOne.draw();
    playerTwo.draw();
}
Prestaul