admin管理员组

文章数量:1315318

Google Chrome is throwing "Uncaught TypeError: Cannot set property 'isDown' of undefined" but it doesn't look like anything is wrong with my code!

Important part of my variable array:

KEY = {
    UP: 38,
    DOWN: 40,
    W: 87,
    S: 83,
    D: 68
}
pingpong = {
    fps: 60,
    pressedKeys: [],
    plete: false,
}

Key listener initialization (this is where the error is thrown):

    for (var keyCode in KEY) {
        if (KEY.hasOwnProperty(keyCode)) {
            pingpong.pressedKeys[KEY[keyCode]] = {
                isDown: false,
                wasDown: false
            };
        }
    }
    $(document).keydown(function(e) {
        pingpong.pressedKeys[e.which].isDown = true;
    });
    $(document).keyup(function(e) {
/* This line is the issue */    pingpong.pressedKeys[e.which].isDown = false;
    });

Any Ideas?

Google Chrome is throwing "Uncaught TypeError: Cannot set property 'isDown' of undefined" but it doesn't look like anything is wrong with my code!

Important part of my variable array:

KEY = {
    UP: 38,
    DOWN: 40,
    W: 87,
    S: 83,
    D: 68
}
pingpong = {
    fps: 60,
    pressedKeys: [],
    plete: false,
}

Key listener initialization (this is where the error is thrown):

    for (var keyCode in KEY) {
        if (KEY.hasOwnProperty(keyCode)) {
            pingpong.pressedKeys[KEY[keyCode]] = {
                isDown: false,
                wasDown: false
            };
        }
    }
    $(document).keydown(function(e) {
        pingpong.pressedKeys[e.which].isDown = true;
    });
    $(document).keyup(function(e) {
/* This line is the issue */    pingpong.pressedKeys[e.which].isDown = false;
    });

Any Ideas?

Share Improve this question asked Jan 16, 2012 at 8:40 rshea0rshea0 12.3k9 gold badges30 silver badges41 bronze badges 1
  • What button do you press when the issue occurs? Perhaps this button is not described in KEY object? – dfsq Commented Jan 16, 2012 at 8:49
Add a ment  | 

2 Answers 2

Reset to default 2

The problem is that you're trying to access an element of the pressedKeys array which does not exist. For example, if we pressed the "a" key:

$(document).keyup(function(e) {
    //Pressed "a" so e.which == 65
    pingpong.pressedKeys[e.which].isDown = false;
});

When you initialize your array you only create elements for the properties of the KEY object:

for (var keyCode in KEY) {
    //Iterating over KEY, which contains 5 properties...
    if (KEY.hasOwnProperty(keyCode)) {
        //Add value to pressedKeys (this happens for each of the 5 properties)
        pingpong.pressedKeys[KEY[keyCode]] = {
            isDown: false,
            wasDown: false
        };
    }
}

So pressedKeys only contains 5 elements, corresponding to the properties of KEY. Note that a TypeError is also thrown in the keydown event handler, as well as keyup.

To fix it, you could check that e.which is in the KEYS object in the event handler functions. If it's not, just ignore it. Something like this perhaps (there may be a better way, this is just what came to mind first):

$(document).keydown(function(e) {
    for(var k in KEY) {
        if(KEY[k] == e.which) {
            break; //Break out of loop and execute last line
        }
        return false; //Key not recognized, last line is not executed
    }
    pingpong.pressedKeys[e.which].isDown = true;
});

e.which is IE only. Real browsers use e.keyCode

jQuery Event Keypress: Which key was pressed?

本文标签: javascriptUncaught TypeError Cannot set property of undefinedStack Overflow