How would I detect clicks in javascript? - javascript

I'm building a little web game in node.js, and I've been using event listeners for input, and it's worked fine for things like key presses and mouse movement.
window.addEventListener("keydown", onKeyDown);
window.addEventListener("keyup", onKeyUp);
window.removeEventListener("mousemove", onMouseInput);
(all of these have worked perfectly)
But when I tried using the mouseup/mousedown events (and also pointerup/pointerdown), they won't register. Is there something I'm doing wrong? Does it have to click on something?
window.addEventListener("pointerdown", changeShooting(true));
window.addEventListener("pointerup", changeShooting(false));
(doesn't work)

You have to pass a function to addEventListener, while you are passing the result of the call to changeShooting (which I assume does not return a function).
In order to do that, you can define an inline function like:
window.addEventListener("pointerdown", function() {
changeShooting(true)
});
If you need to remove the listener later, you have to define it explicitly:
function onPointerDown() {
changeShooting(true);
}
window.addEventListener("pointerdown", onPointerDown);
// later somewhere
window.removeEventListener("pointerdown", onPointerDown);

Related

Should I / how do I clear a mousemove JQuery event listener?

When I use
$(".page").mousemove(function(event){});
As soon as the mouseup event comes, I no longer need this listener. Since I'll be applying the listener repetitively for different actions, it seems to me that these listeners might stick around and build up (needlessly wasting CPU) as the user activates the function many times. I'm not really sure how this works internally, that's just my guess.
Should I / how do I clear a mousemove JQuery event listener?
Here is the code:
$('.page').off('mousemove');
But please note that the following approach turns off all functions firing on mousemove. If you want to turn off a prticular function then you should do the following:
// Define function that fires on mousemove
function anyFunctionName () {
// Some code
}
// Set listener
$('.page').on('mousemove', anyFunctionName);
// Turn off only function called funcionName
$('.page').off('mousemove', anyFunctionName);
Another way for turning off a particular function would is defining a name for the event:
// Define function that fires on mousemove
function anyFunctionName () {
// Some code
}
// Set listener
$('.page').on('mousemove.anyEventName', anyFunctionName);
// Turn off only function fired on event called anyEventName
$('.page').off('mousemove.anyEventName');
I was able to get a working example using the more general .on and .off JQuery functions instead of their explicit handlers. Here is the code I used:
$('.page').on('mousedown', function() {
$(this).on('mousemove', function(event) {
// Do something meaningful
});
});
$('.page').on('mouseup', function() {
$(this).off('mousemove');
});
Here is a JFiddle Demo of it.

Removing event listeners

I have a canvas element in which I draw something using WebGL.
Depending on what is drawn I am adding an event listener.
Now when I am redrawing the canvas, I want to remove the old event listener and add a new one.
Simply doing this will not work:
canvas.removeEventListener("click", function(event){
colorbarClicked(event, viewdata);
}, false);
canvas.addEventListener("click", function(event){
colorbarClicked(event, viewdata);
}, false);
I think it is because the colorbarClicked function has already changed (maybe because its parameters have different values?) and not matching the old one which I want to remove any more.
So my problem is that each time I am redrawing event listeners get added and therefore doubled. But the colorbarClicked function depends on what is drawn in the canvas, so I definitely need to change it.
You need to remember the function you used when adding, and use that same function again when removing:
// Somewhere *outside* the code doing the adding/removing (in containing code)
var listener = null;
// In the code adding/removing
if (listener) {
canvas.removeEventListener("click", listener, false);
}
listener = function(event){ colorbarClicked(event, viewdata); };
canvas.addEventListener("click", listener, false);
Side note: Adding and removing a handler every time seems awkward. Normally, you'd want to just add the handler the once, and have it respond to whatever changes you make.
You can use named functions. Take the example below:
function foo(){
alert("this comes only once");
this.removeEventListener('click', foo);
}
dude.addEventListener('click', foo);
<button id="dude">Click Me</button>
What is happening here is that the function foo is defined in the global scope. It has a unique identity of it's own. What the function basically does is that it creates an alert, and then removes itself from the click event for the button. So when you click it, the listener is removed, and thus, you no longer see it.
Your code doesn't work as intended because the function you pass as callback to addEventListener has no unique identity, and Javascript doesn't know what to remove.
This method also prevents things like callback hell :)

Why does mousedown event listener run through function?

I drew a canvas, and then with the code
canvas.addEventListener("mousedown", clicked(event), false);
I added an event listener to run clicked whenever I click the mouse.
But when I went through the code line by line on chrome, the moment it adds the event listener it automatically runs the function clicked anyway, but I only want it to run the function when I click.
Am I doing something wrong?
You need to just pass the function reference and not actually call it like this:
canvas.addEventListener("mousedown", clicked, false);
Then, the function should be defined like this:
function clicked(event) {
// code here
}
When you include parens after the function name, it is immediately executed and it's return value is what is passed to addEventListener() which is probably not what you wanted at all. Leave off the parens to just pass a function reference.
canvas.addEventListener("mousedown", clicked,false);

Can't get keydown / keyup to work with pointer lock / fullscreen

My problem is that I recently started to change my HTML5 webapp to use fullscreen + pointer lock instead of dragging the mouse in the window. The app uses keyboard in addition to mouse, and everything was working fine previously. However, now I can't get any kind of keypresses to work. Pointer locked mouse works perfectly.
Previously I listened to keypresses like this:
document.onkeydown = handleKeyDown;
document.onkeyup = handleKeyUp;
where handleKeyDown and Up are functions, for example:
function handleKeyUp(event) {
doStuffWith(event.keyCode);
}
Now, I have added keyboard listeners right next to my mousemove listener:
document.addEventListener('keyup', handleKeyUp(event), false);
document.addEventListener('keydown', handleKeyDown(event), false);
where handleKey* are the same as above, but doStuffWith doesn't do anything. It seems to get some undefined events and nothing else. This is probably a fairly elementary problem, but I have a hard time solving it. Most examples and tutorials I found with Google don't use addEventListener but instead the old style like I used previously.
I am very grateful for any help.
edit // A clarification: since events are undefined, doStuffWith doesn't get called at all, because the execution stops when trying to read .keyCode of undefined
The main problem is that, according to the following MDN page, alphanumeric keys are disabled in full-screen mode:
https://developer.mozilla.org/en/DOM/Using_full-screen_mode#Things_your_users_want_to_know
There are also a couple of issues with your code. In the the line
document.addEventListener('keyup', handleKeyUp(event), false);
... you have two problems: first, the second parameter need to be a reference to a function. It's actually a reference to undefined because you're calling the function immediately and passing in the result rather than passing in a function. Second, in browsers that support addEventListener, the Event object is automatically passed into the event listener function. What you want, therefore, is:
function handleKeyUp(e) {
doStuffWith(e.keyCode);
}
document.addEventListener('keyup', handleKeyUp, false);

How to change all onClick events to TouchStart on iOS?

OnClick event has a timeout ~400ms before executing on iOS-browser (demo). And I want to change it to TouchStart event for all DOM-elements who have onClick. How can i make it?
I use jQuery and i tried check all elements for click function:
$('*').each(function() {
if($(this).click != null) {
// BUT all elements in DOM has click
}
})
I don't have an exact answer, but I think you should be able to make this do what you want.
For every element on your page that has an OnClick, add a class - say TouchTarget. Then use this in your startup function.
$('.TouchTarget').bind('touchstart', function (e) {
e.preventDefault();
touchStart(e, this);
});
Create a handler function that looks like this:
function touchStart(pEvent, pElement) {
//Do something with the touch.
}
If you only want to register if touch is available, then you can protect the bind call with
if (Modernizr.touch) {
}
I believe the reason for the delay in OnClick is because Safari is waiting to see if the touch is really a click or a drag, or some other gesture. This will recognize a simple touch quickly. I normally bind both touchstart and touchend when I need quick touches so that touchstart provides visual feedback and then touchend does something with the "click". This method does not have a delay built in.
Use a product like http://www.jqtouch.com/ or the code snipped provided here: http://cubiq.org/remove-onclick-delay-on-webkit-for-iphone.

Categories

Resources