Question

I am making a snake game but when I try and instantiate my snake object I get "Uncaught TypeError: undefined is not a function".

function draw(){
var canvas = document.getElementById("canvas");
    if (canvas.getContext){
        var ctx = canvas.getContext('2d');
}
drawSnake();    

}

This is where I instantiate the snake object and draw it and where i get the error more specifically line 13.

function drawSnake(){
    var Snake = new Snake(250,250,-1,0);
    Snake.create();
    ctx.fillStyle = "white";
    for(i=Snake.snakeBlock.length(); i>=0;i--){
        var s = Snake.snakeBlock[i].block;
        ctx.fillRect(s.xPos,s.xPos,s.height,s.width);
    }
}    

function Block(x,y,w,h){
    var xPos = x;
    var yPos = y;
    var width = w;
    var height = h;
}

This is where I define the snake object yet I still get an error.

function Snake(x,y,dY,dX){
    var snakeBlock = [];
    var length = 20;
    var xPos = x;
    var yPos = y;
    var dirX = dX;
    var dirX = dY;
    Snake.prototype.create = function(){
        for (var i = 0; i <= length; i++) {
        snakeBlock.push(new Block((xPos-(i*10))*dirX, (yPos-(i*10))*dirY,10,10));
    };
}
}

Is there something that I am ignoring in the creation of objects as I can't figure out what is wrong with the code.

Was it helpful?

Solution 2

var Snake = new Snake(250,250,-1,0);

Are you trying to overwrite the Snake constructor here? Anyway, the declaration of the local variable is shadowing the global Snake constructor reference, and Snake is undefined when you try to call it. Use a different variable name - usually instance names are lowercased:

var snake = new Snake(250, 250, -1, 0);
for(i=Snake.snakeBlock.length(); i>=0;i--){
  • use a local variable: var i
  • .length is indeed not a function: it is a plain, numeric property.
  • snakeBlock is a local variable in the Snake constructor, not a property.
    var s = Snake.snakeBlock[i].block;

snakeBlock[i] does already reference the Block instance you put there. It does not have a .block property.

    var snakeBlock = [];

As already mentioned, this does declare a local variable. You want to access it from the outside, though (in prototype methods, in your drawSnake call), so you should create a property instead:

this.snakeBlock = [];

Read more on the differences in Javascript: Do I need to put this.var for every variable in an object?.

    Snake.prototype.create = function(){

Never put an assignment to the prototype inside the constructor! Your indentation is also screwed up.

snakeBlock.push(…)

Now, access it as a property:

this.snakeBlock.push(…)

Also see @MattWay's fiddle for a fixed up version :-)

OTHER TIPS

There are quite a few things wrong with the code you have pasted. I have created a really quick fiddle, and adjusted your code so that it doesn't give errors (although it's likely not the best way to write it anyway).

http://jsfiddle.net/62VDC/

Some of the things I found were related to not using this. Trying to use a variable name Snake at the same time as an object named Snake. Referencing things like snakeBlock[i].block when there is no block component. Using length(), when you should simply use .length. Putting prototype functions inside the construtor.

If you need more help, you might have to elaborate.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top