Determining if key is pressed down in Javascript - javascript

I'm writing a platform game for my university project using the canvas element and Javascript. I'm well on my way, but I'm stuck at how to see if a certain key is being pressed in my players update loop.
I was thinking like this:
if(d) {
// move player right
} else if(a) {
// move player left
} else if(w) {
// move player up
} else if(s) {
// move player down
}
That's psudocode, obviously. The only resources to key presses in Javascript that I can find are events, nothing to see if a key is being pressed at a certain point.
Can anyone shed some light on this?

Setup 4 boolean variables if key is up or down. On keydown set it to true, on keyup set it to false. Than you can do if(key_d == true) { // key d is pressed }
That's the best way to do it. Its not "hacky", add event listeners to handle key presses.

I don't think you can get around using keydown, keyup, or keypress for determining which keys are pressed. However, instead of running this code within one of those event handlers, you could set and unset some global flag within them. Then, when this code runs (I'm assuming it'll be on some kind of interval?), it could check for the flag.

You need an event listener.
//function foo, returns keypress
function foo(e){
var evt=(e)?e:(window.event)?window.event:null;
if(evt){
var key=(evt.charCode)?evt.charCode:
((evt.keyCode)?evt.keyCode:((evt.which)?evt.which:0));
return key;
}
//set event listener
//you could also attach this to your canvas, but that will require tricks
//to make the canvas focusable
document.addEventListener('keydown', foo);

Related

Handling multiple keys pressed at once in JavaScript

For context: this is a JavaScript app running in the Xbox One. All of this is happening through the Xbox's virtual keyboard. Keep in mind that since I have figured out how the events are being fired, this shouldn't matter anymore, just how to deal with the two events at once.
It's not really multiple keys, what is happening is when I turn on CAPS for my app, I am getting two events keys at once: shift and whatever key I am actually pressing. The problem this is causing is that shift seems to be overriding whatever I am trying to spell, and no key is displayed in my input boxes.
I currently have a global function which takes care of all special events in the app, and I would like to handle this issue from over there but am not sure how to go about this issue.
Here is what I currently have:
// this is the global function where I would like to solve the issue
onStartup(function () {
var $html = $('html')
$html.on('keydown', function (evt) {
if (evt.isDefaultPrevented()) return
console.warn('key being pressed:', evt.keyCode)
if (evt.keyCode === 16) { // Note: 16 is shift's keycode
// do something to prevent shift from overriding the actual key I want to press.
return
}
})
})
When I press a key without CAPS being turned on, say a, which has the keyCode of 65, we have the following output:
key being pressed: 65
If however I try to do a capital a (or A), this is what happens:
key being pressed: 16
key being pressed: 65
What can I do to stop the shift from preventing me from actually typing the capital keys?
I figured it out! All I had to do was when shift was fired, to call evt.stopImmediatePropagation().
So basically, for my code:
// ...
if (keycodeControls.is('shift', evt)) {
evt.stopImmediatePropagation()
}

Building A Timer in Javascript/jQuery

I'm currently working on a website which would work somewhat like this one:
http://www.keyhero.com/free-typing-test/
I'd like to build a timer which starts on the user's first key press, and ends when the user presses 'Enter'. When the timer ends, I'd want to get the resulting time and push it off to the backend (Django for me) where the WPM will be calculated. However, I have no idea how to get started on this, as I have little experience with jQuery and Javascript and haven't been able to find useful pages.
So my question is, how would I do this? I can post some of my Django files if a better picture of what I am asking is needed.
You manage the key events with .keypress() for know when the person click in the keyboard.
http://api.jquery.com/keypress/
And for key = "ENTER", you just need to validate if is equal to key 13
$('#id_tag').keypress(function (e) {
var key = e.which;
if(key == 13) // the enter key code
{
alert("Clicked on enter");
return false;
}
});
I see that post too, that are using keyup():
JQuery Event for user pressing enter in a textbox?
Well you're going to have to capture the keypress/keydown/keyup event in a jQuery event, then start a setInterval and have that function increment a counter variable of sorts. Then you just reference that variable whenever you want to see how many seconds have passed. A crude example would be:
window.secondsSinceTyped = 0;
$('#textbox').one('keypress', function (e) {
window.setInterval(function () {
window.secondsSinceTyped++;
}, 1000);
});
Then just reference the variable secondsSinceTyped whenever you want to check the time. Note that I used the jquery one binding which will only bind the event once so that every time you type it doesn't rebind the event.

jQuery: avoid checking if the key pressed is 'enter' everytime

In the code below, instead of using on keydown, is there a way I can use on e.which === 13 where the keydown is? This was it wont have to check each time a key is pressed, and will work only when enter is pressed.
Current Code
$('.search').on('keydown', function(e) {
if(e.which === 13) {
// enter key pressed
var value = this.value; // this is the inputs value
console.log(value);
}
});
What I hope to do (pseudo code)
$('.search').(when key === 13 is pressed) { // Only if the enter key pressed
// enter key pressed
var value = this.value; // this is the inputs value
console.log(value);
}
});
Can something like this be done?
You could use a higher-order function to extract that logic for you:
function onlyOnEnter(fn) {
return function(e) {
if(e.which === 13) {
fn.apply(this, arguments);
}
}
}
Usage:
$('.search').on('keydown', onlyOnEnter(function(e) {
var value = this.value; // this is the inputs value
console.log(value);
})
);
That way, your callback function will only be called when the key pressed is an enter.
Not really.
The best you can do is capturing events (you are using on but it could be any other event capturing method). There are many different kind of events (mouse events, keyboard events, control specific events, etc.), you have to look at the event, since each event type will have different properties.
For key pressing, there are some events available for capturing such as keypress, keydown and keyup. You can't expect that one specific key will have an event on its own because you want so save one line of code.
No, this isn't really possible (at least not for the purposes of your code) nor does it make a lot of sense. The keydown event is fired whenever a key is pressed.
Whether you are manually checking to see if it's the enter key or whether the browser or jQuery is doing it internally isn't tremendously relevant - regardless the browser will need to check which key was pressed any time any key is pressed to test whether it was the enter key.
Essentially you're wasting your time. There isn't going to be any measurable performance optimization by trying to do this. No matter how you try to detect the enter key being pressed, it will be tested for every keydown or keypress event regardless of which key is pressed.

save keydown in array and executes

im creating a simple 2d game, and I want save the keydown keys into array, and execute them inisde a loop, so the user can hold a key and make it look like the chartater is moving non stop.
i got a setInterval function that act like a game Timer, and it just loop it self all the time. i added a listener and an array to hold the key.
I checked the keys inside the array and it look fine but, the functions moveRight and moveLeft are not working for some reson.
here is the code:
this.keysPressed = new Array();
InitGameLoop: function () {
var that = this;
setInterval(function () {
$(document).keydown(function (e) {
var key = e.which;
that.keysPressed.push(key);
for (var i = 0; i < that.keysPressed.length; i++) {
if (that.keysPressed[i] == 38) {
that.moveRight(worldWidth, 10);
}
else if (that.keysPressed[i] == 37) {
that.moveLeft(10);
}
log(that.keysPressed, that.yPos);
that.keysPressed.pop();
}
});
}, 60);
my questions are:
what am i doing worng?
is this a good idea? (if not, please feel free to recommend me about another :) )
(sorry for my english)
Registering an eventhandler inside setInterval is always wrong. In your case, every 60 milliseconds you are creating an additional listener, and when you press a key, all of your listeners will fire. Also there is absolutely no need to store them in an array. Just register the listener once, and it will fire each time a key is pressed. If more than one keys are pressed, the listener will fire for each key individually.
$(document).keydown(function (e) {
var key = e.which;
console.log(key);
// call your according functions here
switch (key){
case 37: // moving left
// do stuff
// set a flag to indicate that you are moving left
moveleft = true;
break;
case 39: // moving right
// do stuff
// set a flag to indicate that you are moving right
moveright = true;
break;
}
});
Since you are catching the keydown, you should set flags. This way you can track which keys are pressed currently. On keyup, you are resetting these flags again (need another eventhandler for that).
Instead of storing the pressed keys in an array, make each key code activate a related var in a 'movement' array. e.g. when left is pressed, movement['left']=1. Use keyup to set it back to 0.
Have your loop check the array for each possible movement, and trigger the related functions in corelance to the active movements at that given moment.

Javascript Checking Keyboard State

I am working on making a simple Javascript game and need to be able to check if certain keys are being pressed. I have tried binding to the onkeydown event, but the problem that I am having is twofold: first, it won't let me check to see if more than one key is being pressed at any time. And second, it pauses after holding the key down before it starts spamming the event.
In my code, I could either have an event, or a function that checks every millisecond to see if the key is being pressed. Seeing as this is a game, I would really have no problem with either.
You can use onkeydown and onkeyup together:
var pressed={};
element.onkeydown=function(e){
e = e || window.event;
pressed[e.keyCode] = true;
}
element.onkeyup=function(e){
e = e || window.event;
delete pressed[e.keyCode];
}
with this code you store every pressed key code in the pressed variable and then you delete it when the key is released. So when you need to know which keys are pressed you can loop with a for(..in..) through the pressed object.

Categories

Resources