多个 Jquery 动作同时运行

Posted

技术标签:

【中文标题】多个 Jquery 动作同时运行【英文标题】:Multiple Jquery actions running at the same time 【发布时间】:2014-01-24 07:41:45 【问题描述】:

这个问题的例子是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;
    
);

在此示例中,我有不同的 Jquery keydown 侦听器等待特定的按键,并且在该按键上我想将球沿某个方向移动(在此示例中使用 css 函数来更改边距)。

问题是您一次只能朝一个方向移动。是否有可能让如果我同时有向下箭头和向右箭头,我会向屏幕的左下角移动,而不仅仅是向右或向下?

我曾考虑过如果两者都被按下,可能会找到一种在它们之间交替的方法,但我不确定这会如何工作。或者如果有一些方法可以做线程。

此外,我不确定是否有一种方法可以使它在按下新按钮时也不会取消,而您仍然按住另一个按钮。

【问题讨论】:

为什么不让e.keyCode 在同一个事件处理函数的else-if 中检查呢? Example in a JSFiddle here 你为什么要大量基于使用 jquery 的用户交互来编写任何东西?移动球的目的是什么?写游戏?用别的东西。 你有什么建议@tenub? 这里有:***.com/questions/10655202/… Cheers 我在想可能是一个简单的游戏,但更多的是一般的键盘控制 【参考方案1】:

将您的所有 keydowns 和 keyups 组合成一个带有多个 if 语句的函数。首先检查组合,然后检查单箭头按压。这应该可以解决问题。

如果您想支持用户流畅地移动球,我会查看此处给出的示例:http://jsfiddle.net/kzXek/。此示例包括处理按下的箭头键以提供流畅的移动。

// 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;
    );
);

【讨论】:

这可以通过使用$(document)、委派事件并链接它们来进一步改进。 ;-)【参考方案2】:

请看一下这段代码:

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);

http://jsfiddle.net/26XWw/

【讨论】:

【参考方案3】:

您可以处理数组或对象中的按键,然后检查所有被按下的按键:

这里有:

Detect multiple keys on single keypress event in jQuery

干杯

【讨论】:

【参考方案4】:

创建一个布尔数组(左、右、上、下)并在setInterval 上检查哪些设置为true

这是您更新后的代码:

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);

DEMO

【讨论】:

有趣,我试过了,但似乎没有用。 $(document).keyup(function(e) if (e.keyCode == 39 && e.keyCode == 40) y = y+1; x = x+1; $("#ball").css( "margin-top", y*10 ); $("#ball").css( "margin-left", x*10 ); ); 把它放在keydown 而不仅仅是keyup 这个例子在很多层面上都是错误的(没有缓存变量,没有委托事件,使用 setInterval)并且没有解决手头的问题(我可以在 500 毫秒内按下多个键而没有问题) .相反,它使阅读、理解和调试变得更加困难! 减少setInterval 持续时间并没有改善任何东西。请查看其他答案以获得更好的解决方案。

以上是关于多个 Jquery 动作同时运行的主要内容,如果未能解决你的问题,请参考以下文章

jQuery - 链(Chaining):把动作/方法链接在一起

如何同时调度多个 ngrx 动作

jQuery对于链和捕获的实战研究

React Hooks 在设置状态的同时处理多个动作的方式是啥?

jQuery小试牛刀

cocos2dx的runAction: 反复运行,多个动作连接运行,多个动作同一时候运行的实现