Domanda

I am working on a game. My event handlers are using JQuery, and the game is written in JavaScript, and I've been trying to find the best way to set time before a method can be called again from my event listeners.

Here is my current event listener:

function shootingHandler(key){
    switch(parseInt(key.which, 10)){
        case UpArrow:
        case Spacebar:
            setTimeout(player.shoot(), 1000);
            break;
    }
}

The setTimeout() method doesn't work for this, because it just calls the method, then waits for specified time, then fires it. So in my example code, I'm trying to make it so the player can only fire a shot every second, but if the player holds down spacebar it auto shoots thousands of times.

What is a good way to make a method only able to be called once at a time, only only once every few seconds or so?

È stato utile?

Soluzione

var disabled = false;
var shootOnEnabled = false;
function shootingHandler(key){
    switch(parseInt(key.which, 10)){
        case UpArrow:
        case Spacebar:
            if (disabled) { 
                shootOnEnabled = true;
                break; 
            }
            shoot();
            disabled = true;
            setTimeout(function () {
                disabled = false;
                if (shootOnEnabled) {
                    shootOnEnabled = false;
                    shootingHandler(key);  
                }
            }, 1000);
            break;
    }
}

Altri suggerimenti

Check this fiddle

var timerActive;
function shootingHandler(key){
  switch(parseInt(key.which, 10)){
    case UpArrow:
    case Spacebar:
            if (timerActive){
                clearTimeout(timerActive);
             }
            timerActive= setTimeout(player.shoot(), 1000);
            };
        break;
    }
}

here, if the function shootingHandler is called again before 1 second of previous call, the timer will be reset back to 0. so only if the player releases the space bar for 1 second the function will be triggered. This is an old trick used to prevent window resize from triggering hundreds of times while dragging.

if you are allowed to use other third party libraries check out Underscore

http://underscorejs.org/

It has a pretty nice function that does exactly what you need.

var throttled = _.throttle(updatePosition, 100);
$(window).scroll(throttled);

In this example updatePosition will be called not before every 100 milliseconds.

In player.shoot(), check first to see if the player is allowed to shoot. Something like if(allowedToShoot) { ... }.

And in shootingHandler, call a function that sets the flag to true, calls the player.shoot(), and then sets the flag back to false. Something like setTimeout(allowShooting(), 1000);.

function allowShooting(){
    allowedToShoot = true;
    player.shoot();
    allowedToShoot = false;
}
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top