Question

I'm trying to count the time that player is holding the mouse button down. I tried this but it didn't works:

var Game = cc.Layer.extend({
    count: false,
    countTimer: null,

    init: function () {
        var selfPointer = this;

        this.canvas.addEventListener('mousedown', function(evt) {
            selfPointer.count = true;
            selfPointer.countTimer = window.setTimeout(selfPointer.Count(), 1);
        });

        this.canvas.addEventListener('mouseup', function(evt) {
            selfPointer.count= false;
            window.clearTimeout(selfPointer.countTimer);
        });
    },

    Count: function() {
        if (this.count)
        {
            window.setTimeout(this.Count(), 1);
        }
    }

This is a part of my code(for brevity) that I want to do an action any 1 milisecond if player is holding the button.

This isn't working besides, I presume that is a better way to do this than mine way. Any ideas?

Was it helpful?

Solution

Why do you use timeouts for this simple task? You can just get time of mousedown, time of mouseup and calculate difference of them. Anyway, timer resolution in browsers is less than 1ms. Read this article of Nickolas Zakas to get more info about time resolution.

Code is:

var Game = cc.Layer.extend({
  init: function () {
    var holdStart = null,
        holdTime = null;

    this.canvas.addEventListener('mousedown', function(evt) {
      holdStart = Date.now()
    });

    this.canvas.addEventListener('mouseup', function(evt) {
      holdTime = Date.now() - holdStart;
      // now in holdTime you have time in milliseconds
    });
}

OTHER TIPS

Well if you are targeting newer browsers that are HTML5 compatible you can use web workers for this kind of task. Simply post a message to the web worker on mouse press to start the timer. The web worker can post a message back every 1 ms ish to trigger your in game action and then on mouse release, post another message to the web worker telling it to stop.

Here is just a quick example of how that would work. You would need to run from a local server to have web workers working.

Game.js

function start() {              
    var worker = new Worker("ActionTrigger.js");
    worker.addEventListener('message', function(objEvent) {
        console.log("Holding");
    });
    worker.postMessage("start");

    window.onmousedown = function() {
        console.log("Mouse press");
        worker.postMessage("startTrigger");
    }

    window.onmouseup = function() {
        console.log("Mouse release");
        worker.postMessage("endTrigger");
    }
} 

ActionTrigger.js

var trigger = false;
var interval = 1;

self.addEventListener('message', function(objEvent) {
    if(objEvent.data == 'startTrigger')
        trigger = true;
    else if(objEvent.data == 'endTrigger')
        trigger = false;
    else if(objEvent.data == 'start')
        timerCountdown();
});

function timerCountdown() {
    if(trigger)
        postMessage("");
    setTimeout(timerCountdown,interval);
}

You could use something like this: http://jsfiddle.net/yE8sh/

//Register interval handle
var timer;
$(document).mousedown(function(){
    //Starts interval. Run once every 1 millisecond
    timer=self.setInterval(add,1);
});
$(document).mouseup(function(){
   //Clears interval on mouseup
   timer=window.clearInterval(timer);
});

function add(){
  //The function to run
  $("body").append("a");
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top