Avoid multiple events on keyup, keydown when used simultaneously - javascript

I have the below code. If I press enter key, it triggers click twice. How to avoid multiple triggering of event?(Kepping keyup keydown together). Note: This situation is occuring in chrome not in IE
$(document).on('keyup keydown','#txtbox', function (event) { if(event.which == 13 )$('#btnEnter').click(); return false;}});

I got the most easiest solution. Use event.type property.
if(event.which == 13 && event.type == 'keyup')
{
// Do some stuff. You can use event.type = 'keydown' also
}

Remove one of the events:
$(document).on('keyup', function (event) {
if(event.which == 13 ) $('#btnEnter').click();
});
Every keypress (now, that's another event by the way), triggers both keydown and keyup events, doesn't it?

Extending this snippet, this works when the AJAX Calls are completed:
$(document).on('keyup keydown', function (event) {
if(event.which === 13 ) {
$('#btnEnter').click();
}
});
$('#btnEnter').click(function() {
if ( $(this).hasClass("keydown") ) {
return;
}
$("div").append("I'm clicked on keydown only!<br/>");
$(this).is(".keydown") || $(this).addClass("keydown");
$.ajaxComplete(function() {
$('#btnEnter').removeClass("keydown");
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button id="btnEnter">I'd be clicked on enter key down</button>
<div></div>

This is what I quickly came up with. Is this what you're after?
$(document).on('keyup keydown', function (event) {
if(event.which === 13 ) {
$('#btnEnter').click();
}
});
$('#btnEnter').click(function() {
if ( $(this).hasClass("keydown") ) {
return;
}
$("div").append("I'm clicked on keydown only!<br/>");
$(this).is(".keydown") || $(this).addClass("keydown");
setTimeout(function() {
$('#btnEnter').removeClass("keydown");
}, 150);
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<button id="btnEnter">I'd be clicked on enter key down</button>
<div></div>
Edit: To support my comment, you could do something like the following.
$.ajax({
method: "GET", // Or POST
url: "yourURL"
//other settings
}).done(function(data) {
//Do your stuff
//And then, do:
$('#btnEnter').removeClass("keydown");
});

Create var triggered = false; and add
&& !triggered
To your if condition, and
triggered = true;
To your function and make it false again whenever your event is ready to be triggered again

Related

Listener for keydown is triggered multiple times instead of once

I have the following code:
undoButton.onclick = undoFunction;
document.addEventListener("keydown", (e) => {
if ((e.ctrlKey || e.metaKey) && e.code === "KeyZ") {
e.preventDefault();
undoFunction();
}
});
function undoFunction() {
console.log("undo function...");
}
When I click the button, as excepted, the function code runs once, and so does the console.log, but when I use the key stroke, the function is running a multiple times, up to hundreds of so-called loops at some scenarios. Any suggestion why? I tried to used e.repeat = false but had no luck. Thanks!
Use keyup instead. The keydown event triggers as long a key is hold down. keyup only triggers when a key is released.
var undoButton = document.getElementById('undoButton');
undoButton.onclick = undoFunction;
document.addEventListener("keyup", (e) => {
if ((e.ctrlKey || e.metaKey) && e.code === "KeyZ") {
e.preventDefault();
undoFunction();
}
});
function undoFunction() {
console.log("undo function...");
}
<input id="undoButton" type="button" value="Undo" />

Understanding how many times the jquery events are called and right handling of keyup event

I am trying to develop my webpage where I have a simple input field where I can type something. I want that when I type something and press "enter", a function gets called. The code I am using is:
$(document).ready(function(){
$("#searchBar").click(function(){
$("#searchBar").keyup(function (e) {
if (e.keyCode == 13) {
$(this).trigger("enterKey");
}
});
$("#searchBar").bind("enterKey", function (e) {
searchFunction();
});
})
})
Something is not working well. I have 2 questions:
First of all by debugging on the browser I realize that the event "keyup" is called whenever I type any kind of character, but not when I press "enter" and I don't know why.
By always debugging and using a breakpoint on the keyup handler, it happens that when I press a key, in order to get out from the breakpoint I have to resume the script execution once.. then if I type another character and I go again at the breakpoint, I have to resume the script exectuion twice instead of once to continue debugging.. and so on incresing.. why do I have this kind of behavior?
Thanks in advance!
Two problems:
#searchBar only listens to keyUp and Enter if you have clicked on it at least once
#searchBar adds a new keyUp and Enter listener for each time it receives a click event
I'd just bind the events once like so:
$(document).ready(function(){
$("#searchBar").keyup(function (e) {
if (e.keyCode == 13) {
$(this).trigger("enterKey");
}
});
$("#searchBar").bind("enterKey", function (e) {
searchFunction();
});
});
I can't come up with a valid reason to stop listening to the events, but if that's what you want, then I'd unbind just before or after the call to your searchFunction();
$(document).ready(function(){
$("#searchBar").click(function(e){
$(this).keyup(function (e) {
if (e.keyCode == 13) {
$(this).trigger("enterKey");
}
});
$(this).bind("enterKey", function (e) {
searchFunction();
$(this).unbind("enterKey");
$(this).unbind("keyup");
});
});
// but you'd also need to unbind the events if the user clicks somewhere else in the document, otherwise, these events would still get attached every time the user clicks #searchBar
});
But it's unnecessary, as the events are only fired when #searchBar has focus. All these events also detach if you delete #searchBar
Also, why fire "enterKey" when you already are listening for keystrokes?
$(document).ready(function(){
$("#searchBar").keyup(function (event) {
var keycode = event.keyCode || event.which; //this for cross-browser compatibility
if (keycode == 13) {
searchFunction();
}
});
});
I have to resume the script exectuion twice instead of once to
continue debugging.. and so on incresing.. why do I have this kind of
behavior?
You are attaching a new keyup and enterKey event at each click on element.
Remove click event or use .one() to attach click event
$(document).ready(function() {
var search = $("#searchBar").keyup(function (e) {
if (e.keyCode == 13) {
search.trigger("enterKey");
}
})
.on("enterKey", function (e) {
searchFunction();
});
})
or, if one click is intended to begin process
$(document).ready(function(){
var search = $("#searchBar").one("click", function() {
search.keyup(function (e) {
if (e.keyCode == 13) {
search.trigger("enterKey");
}
})
.on("enterKey", function (e) {
searchFunction();
});
})
})

bind click and keyup of different target to do same function

I have a submit button, I use $("#submit") to perform "myAction function", but in the same time I also want if the user pressed enter, it perform "myAction function"..
I can't do like this
$("#submit").on('click keyup', function(){
//myAction function
});
because I have to attach the keyup event to my input field instead of #submit..
Give a name to your function and bind both event on the selector. Then add a special condition:
function send(e){
if(e.type == 'click' || (e.type == 'keyup' && e.wich == 13))
}
$('[type=text]').on('keyup', send);
$('[type=submit]').on('click', send);
Write your my action as a separate function and use it as below
function myAction() {
console.log('act');
//do your stuff here
}
$("#submit").on('click', myAction);
$("input.enter").on('keypress', function (e) {
//enter key code is 13
if (e.which == 13) {
myAction()
}
});
Demo: Fiddle

press 'Enter' key to invoke a function

In my page there is a button and a text box.
Originally I invoke a function by click the button. Now I also want to implement it by press Enter key as well. But it is not working. Press Enter key doesn't reach myFunction.
<script type="text/javascript">
$(document).ready(function () {
$("#txt1").keyup(function (event) {
if (event.keyCode == 13) {
$("#btn1").click(myFunction);
}
});
$('#btn1').click(myFunction);
});
function myFunction() {
// do something, press enter key doesn't reach here.
})
}
</script>
You are almost right: Just invoke the handler with .click() or .trigger('click')
$(document).ready(function () {
$("#txt1").keyup(function (event) {
if (event.which== 13) {
$("#btn1").click(); // Just do a click.
}
});
$('#btn1').click(myFunction); //Your handler is already registered here.
});
function myFunction() {
// do something, press enter key doesn't reach here.
}
Also use event.which instead of event.keyCode when inside jquery event handler as it normalizes event.keyCode and event.charCode.
Instead of
$("#btn1").click(myFunction);
I reccommend to use:
$("#btn1").on("click", function () {
myFunction();
});
And then:
if (event.keyCode == 13) {
$("#btn1").click(); //click the button
}
JSFIDDLE

Avoid multiple event listeners from .focus

I currently have a textbox that I am invoking a keyboard stroke on focus:
$myTextBox.on('focus', function(e){
$(document).keydown(function(e){
if(e.which==13)
e.preventDefault()
});
$(document).keyup(function(e){
if(e.which ==13)
alert("hey");
});
});
If I click on this multiple times pressing 'enter' once will cause many alerts, how can I avoid this so that only it is only invoked once.
You're adding the event listener every time the field gets focus.
Just add the keydown, keyup listener on the document ready function...
$(function() {
$("#myTextBox").keydown(function(e){
if(e.which==13)
e.preventDefault()
});
$("#myTextBox").keyup(function(e){
if(e.which ==13)
alert("hey");
});
});​
http://jsfiddle.net/ShHkP/
Like others have said, you don't have to keep adding the event on focus. As well, you should just attach the event to the textbox itself because that is in fact what you're trying to do when you add the event on focus.
$myTextBox.on({
'keydown': keyDown,
'keyup': keyUp
});​
So that your application doesn't go into an enter-alert-ok loop, you have to turn off the keyup listener before the alert() call, and then turn it back on after hitting ok.
Here's a fiddle.
I see what you're trying to do (or not?). You could just attach the event to the form and exclude the textarea instead of adding it to the document everytime the input gets focused.
$('form').on('keydown', function( e ) {
// Prevent submit when pressing enter but exclude textareas
if ( e.which == 13 && e.target.nodeName != 'TEXTAREA' ) {
e.preventDefault();
}
}
var alreadyPressed = false;
$("textarea").keypress(function (e) {
if (e.which == 13) {
e.preventDefault();
alreadyPressed = true
}
});
$("textarea").keyup(function (e) {
if (e.which == 13 && !alreadyPressed) {
alert("hey");
alreadyPressed = false;
}
});
http://jsfiddle.net/DerekL/Dr6t2/

Categories