Reputation: 76
The example for this question is http://jsfiddle.net/4ac5u/
var x = 0;
var y = 0;
$(document).keydown(function(e){
if (e.keyCode == 37) {
$("#left").css( "background-color", "red" );
x = x-1;
$("#ball").css( "margin-left", x*10 );
return false;
}
});
$(document).keyup(function(e){
if (e.keyCode == 37) {
$("#left").css( "background-color", "#fff" );
return false;
}
});
$(document).keydown(function(e){
if (e.keyCode == 38) {
$("#up").css( "background-color", "red" );
y = y-1;
$("#ball").css( "margin-top", y*10 );
return false;
}
});
$(document).keyup(function(e){
if (e.keyCode == 38) {
$("#up").css( "background-color", "#fff" );
return false;
}
});
$(document).keydown(function(e){
if (e.keyCode == 39) {
$("#right").css( "background-color", "red" );
x = x+1;
$("#ball").css( "margin-left", x*10 );
return false;
}
});
$(document).keyup(function(e){
if (e.keyCode == 39) {
$("#right").css( "background-color", "#fff" );
return false;
}
});
$(document).keydown(function(e){
if (e.keyCode == 40) {
$("#down").css( "background-color", "red" );
y = y+1;
$("#ball").css( "margin-top", y*10 );
return false;
}
});
$(document).keyup(function(e){
if (e.keyCode == 40) {
$("#down").css( "background-color", "#fff" );
return false;
}
});
In this example I have different Jquery keydown listeners waiting for a specific key press, and on that keypress I want to move a ball in a certain direction (in this example using the css function to change the margin).
The issue is that you can only move in one direction at a time. Is it possible to have it so that if I have the down arrow and the right arrow down at the same time I move towards the bottom left part of the screen, not just right or down?
I have thought about possibly finding a way to alternate between them if both are pressed, but I'm not sure how that would work. Or if there is some way to do threading.
Also I'm not sure if there is a way to also make it not cancel out on pressing a new button while you are still holding the other down.
Upvotes: 0
Views: 146
Reputation: 13789
Create an Array of Booleans (left, right, up, down) and on a setInterval
check which ones are set to true
Here would be your updated code:
var x = 0;
var y = 0;
var keysDown = [false, false, false, false];
$(document).keydown(function (e) {
switch (e.keyCode) {
case 37:
keysDown[0] = true;
break;
case 38:
keysDown[2] = true;
break;
case 39:
keysDown[1] = true;
break;
case 40:
keysDown[3] = true;
break;
}
});
$(document).keyup(function (e) {
switch (e.keyCode) {
case 37:
keysDown[0] = false;
$("#left").css("background-color", "#fff");
break;
case 38:
keysDown[2] = false;
$("#up").css("background-color", "#fff");
break;
case 39:
keysDown[1] = false;
$("#right").css("background-color", "#fff");
break;
case 40:
keysDown[3] = false;
$("#down").css("background-color", "#fff");
break;
}
});
function checkBallMoving()
{
if (keysDown[0] === true) {
$("#left").css("background-color", "red");
x = x - 1;
$("#ball").css("margin-left", x * 10);
}
if (keysDown[1] === true) {
$("#right").css("background-color", "red");
x = x + 1;
$("#ball").css("margin-left", x * 10);
}
if (keysDown[2] === true) {
$("#up").css("background-color", "red");
y = y - 1;
$("#ball").css("margin-top", y * 10);
}
if (keysDown[3] === true) {
$("#down").css("background-color", "red");
y = y + 1;
$("#ball").css("margin-top", y * 10);
}
}
setInterval(function () {
checkBallMoving();
}, 100);
Upvotes: 0
Reputation: 23268
Please take a look at this code:
var x = 0;
var y = 0;
var dirs = {
left: false,
top: false,
right: false,
bottom: false
};
$(document).keydown(function(e){
switch (e.keyCode) {
case 37: dirs.left = true; return false;
case 38: dirs.top = true; return false;
case 39: dirs.right = true; return false;
case 40: dirs.bottom = true; return false;
}
});
$(document).keyup(function(e){
switch (e.keyCode) {
case 37: dirs.left = false; return false;
case 38: dirs.top = false; return false;
case 39: dirs.right = false; return false;
case 40: dirs.bottom = false; return false;
}
});
var checkLeft = function() {
if (dirs.left) {
$("#left").css( "background-color", "red" );
x--;
} else {
$("#left").css( "background-color", "#fff" );
}
}
var checkRight = function() {
if (dirs.right) {
$("#right").css( "background-color", "red" );
x++;
} else {
$("#right").css( "background-color", "#fff" );
}
}
var checkTop = function() {
if (dirs.top) {
$("#up").css( "background-color", "red" );
y--;
} else {
$("#up").css( "background-color", "#fff" );
}
}
var checkBottom = function() {
if (dirs.bottom) {
$("#down").css( "background-color", "red" );
y++;
} else {
$("#down").css( "background-color", "#fff" );
}
}
var moveBall = function() {
$("#ball").css({
"margin-left": x*10,
"margin-top": y*10
});
}
setInterval(function() {
checkLeft();
checkRight();
checkTop();
checkBottom();
moveBall()
}, 50);
Upvotes: 1
Reputation: 18344
You can handle the keydowns in an array or object and then check for all the ones that were pressed:
Here you have:
Detect multiple keys on single keypress event in jQuery
Cheers
Upvotes: 0
Reputation: 10372
Combine all of your keydowns and keyups into one function with multiple if statements. Check for combinations first, and then check for single arrow presses. That should resolve the issue.
If you want to support users being able to move the ball around fluidly, I'd look into the example given here: http://jsfiddle.net/kzXek/. This example includes handling pressed down arrow keys to provide fluid movement.
// Made by RobseRob.dk
// Please give credit.
// Vars which contains key state
var movLeft = 0;
var movRight = 0;
var movUp = 0;
var movDown = 0;
var score = 0;
$(function() {
// Keydown listener
$("body").keydown(function(e) {
ek = e.keyCode;
if (ek==37) movLeft=1;
if (ek==39) movRight=1;
if (ek==38) movUp=1;
if (ek==40) movDown=1;
});
// Keyuo listener
$("body").keyup(function(e) {
ek = e.keyCode;
if (ek==37) movLeft=0;
if (ek==39) movRight=0;
if (ek==38) movUp=0;
if (ek==40) movDown=0;
});
});
Upvotes: 1