¿Cómo evito que un evento keyup interrumpa un evento keydown en jQuery? [duplicar]

Posible duplicado:
Forma de navegador cruzado para obtener eventos de pulsación de tecla que se repiten automáticamente cuando se mantiene pulsada la tecla

Estoy tratando de crear un juego simple en JavaScript/CSS/HTML, y estoy usando jQuery (y un poco de guión bajo) para manejar las pulsaciones de teclas. El jugador controla un bloque usando las teclas de flecha. Me encontré con un problema al manejar varias pulsaciones de teclas al mismo tiempo. Tengo un sistema en el lugar donde un cierre realiza un seguimiento de todas las teclas de flecha que se presionan. Esto funciona bien si el jugador presiona las teclas en la siguiente secuencia:

  1. El jugador presiona Abajo (el bloque se mueve hacia abajo)
  2. El jugador presiona Izquierda (el bloque se mueve en diagonal hacia abajo a la izquierda)
  3. El jugador suelta hacia abajo (el bloque se mueve hacia la izquierda)
  4. El jugador suelta a la izquierda (el bloque se detiene

Sin embargo, el bloque se detiene si se invierten los pasos 3 y 4. Esto es lo que realmente sucede en ese caso:

  1. El jugador presiona Abajo (el bloque se mueve hacia abajo)
  2. El jugador presiona Izquierda (el bloque se mueve en diagonal hacia abajo a la izquierda)
  3. El jugador suelta a la izquierda (el bloque se detiene)

El comportamiento esperado es que en el paso 3, el bloque continúe moviéndose hacia abajo, en lugar de detenerse por completo.

De los rastros que he puesto en el código, parece que un evento de pulsación de tecla en realidad detiene la propagación de más eventos de pulsación de tecla, incluso cuando mi dedo sigue manteniendo pulsada una de las teclas de flecha.

Aquí hay un fragmento de código relevante. Alguien me puede decir donde puede estar el problema?

// Creates an animation handler for a specific element.
// Animation reacts to any changes as they are submitted
var getMovementAnimator = function(element) {
    var params = {},
        $element = $(element);
    return function(changes) {
        _.each(changes, function(val, key) {
            // Remove null or zeroish keys from animation params
            if ( (val == 0 || !val) && _.has(params, key)) {
                delete params[key];
            } else {
                params[key] = '+=' + val + 'px';
            }
        });
        $element.animate(params, {duration: 0, queue: false});
        console.log(params);
    };
};

// Determines direction and speed of movement for an element
// after a keypress event
var getMovementChange = function(keyEvent, keydown) {
    var isMoving = !!keydown,
        params   = {},
        dir      = '',
        speed    = keydown ? 5 : 0,
        arrows   = {left: 37, up: 38, right: 39, down: 40};
    switch (keyEvent.which) {
        case arrows.left:
            dir = 'left';
            speed = -speed;
            break;
        case arrows.up:
            dir = 'top';
            speed = -speed;
            break;
        case arrows.right:
            dir = 'left';
            break;
        case arrows.down:
            dir = 'top';
            break;
    }
    // If key hit not one of above, do nothing
    if (!dir) {
        return false;
    }
    if (!speed) {
        console.log('key up: ', dir);
    }
    params[dir] = speed;
    return params;
}

// Sets up key handlers
$(document).ready(function() {
    var board = $('#board'),
        animatePlayer = getMovementAnimator('.player');
    $(document).keydown(function(e) {
        e.preventDefault();
        var changes = getMovementChange(e, true);
        animatePlayer(changes);
    }).keyup(function(e) {
        e.preventDefault();
        var changes = getMovementChange(e, false);
        animatePlayer(changes);
    });
});

preguntado el 03 de enero de 13 a las 19:01

1 Respuestas

La búsqueda adicional en Stack Overflow (usando las palabras clave correctas) me mostró que el problema que estoy viendo no es en realidad un error en mi código. Bastante, este es el comportamiento esperado para el sistema operativo.

Sin embargo, encontré una solución que creo que resolverá el problema.

contestado el 23 de mayo de 17 a las 12:05

No es la respuesta que estás buscando? Examinar otras preguntas etiquetadas or haz tu propia pregunta.