event preventDefault apparently not working properly in Meteor - javascript

For some odd reason event.PrventDefault is not working properly in meteor events.
I try this on jsFiddle and it works as expected (The enter doesn't go to the new line).
Here is a link
However, similar code in meteor events is not working, the enter is registering a break in the textarea.
'keyup #add_comment_content' : function(event) {
if (event.keyCode == 13) { // When the enter key is pressed
event.preventDefault();
//var content = $(this).val();
//var id = $(this).parent().find('comment_content_id').val();
//console.log(content);
//console.log(id);
console.log("Hey");
}
}

I got it to work by using the keypress event instead of the keyup event. I tried this because the docs mentioned:
keypress is most useful for catching typing in text fields, while keydown and keyup can be used for arrow keys or modifier keys.

Related

How to disable enter key in input field

I am trying to stop the enter key from triggering all actions from other scripts on input fields.
Here is the code I am using:
$(document).bind("keydown", function(e) {
var code = e.keyCode || e.which;
if (code == 13) {
// alert('enter pressed');
e.preventDefault();
return false;
}
});
An example of the code in action is here http://jsfiddle.net/8SJYn/ ,
It should be disabling enter but it is not.
Opinions?
You can do it by turning off the keydown and blur events for the input created by the tagit for this element alone.
Try this:
$('#myTags + ul .ui-autocomplete-input').off('keydown').off('blur');
http://jsfiddle.net/JzJRY/
Go into tag-it.js, and on line 245, find this part and remove it:
event.which === $.ui.keyCode.ENTER
JavaScript events have a "bubbling" phase, where they fire first on the inner-most DOM element, and then work their way up to the top-level document. If you try to stop the event at the document level, as in your example code, it is too late.
In some browsers (Firefox, for one) there is a "capturing" phase that occurs before the bubbling phase, and it works in the opposite direction: from top down. You cannot add a capturing phase event handler using jQuery. You must use the native addEventListener function and pass true as the third parameter. If you add the code below into your jsfiddle, it will prevent the Enter keydown event in some browsers.
document.addEventListener('keydown', function (e) {
if (e.keyCode === 13) {
// alert('Enter keydown');
e.stopPropagation();
}
}, true);
Be aware that the tag-it control in your jsfiddle also performs its text-to-tag conversions on blur, so if you uncomment the alert statement above, it will perform its text-to-tag conversion anyway, because of the blur event that occurs when the alert message is displayed.
Lastly, if you want to prevent not just other scripts from processing the Enter keydown, but also the browser itself, add an e.preventDefault(); line to the above.

Keyup event listener fires when enter is pressed on Chrome's Ominbox

In chrome browser, when using this snippet:
$(document).on('keyup', function(){
alert("Hey");
});
Every time I press enter in the url bar (for example when I cut and paste the url of the page itself) the event listener fires.
Why does it happen?
EDIT:
It surprised me because url bar is not in document (maybe in window?) and firefox does not have this behaviour. When I look for e.target, Chrome Inspector shows body.
I thought this could be caused by event bubbling so I tried this:
$(document).on('keyup', function(e){
e.stopPropagation();
alert("Hey");
});
But it doesn't work.
How can I prevent it from being triggered?
This happens because once you hit enter in the omnibox, the focus turns to the page. If you tried the same thing with onkeydown, the omnibox would change nothing, because as you said, it isn't a part of the document. One way to filter the omnibox's false event out would be to check that every keyup has a pair keydown.
<script>
var down = false;
document.addEventListener('keydown', function (){
down = true;
}, false);
document.addEventListener('keyup', function (){
if(down === true){
alert('It was from the page!');
}
else{
alert('Omnibox. Ignore it.');
}
down = false;
}, false);
</script>
Demo.
Make your own HTML page and try it preferably, because PasteHTML.com stuffs it into an iframe. For it to work correctly there, click on the text first to give the iframe focus.
Demo.
Remember to use your mouse to focus on the omnibox and type, not a keyboard shortcut. (That fires the onkeydown event, creating a false positive)
Update: As of Chrome 35, this doesn't happen anymore. I don't know which version they fixed it on, however.
The solution for Chrome is simple: use keypress instead of keyup. This doesn't work in all cases (IE), so you may have to add a conditional to switch the type depending on the browser. However, this will solve your issue.
Note that looking for a specific keycode may negate your issue. Good luck.
You could filter for the keycode ...if that helps...13 is enter key
$(document).on('keyup', function(event){
if( parseInt(event.keyCode,10) !== 13 ){
alert("Hey");
}
});​
A possible solution is to slightly delay the "keyup" event handler registration. This will skip the first "spurious" trigger that seems to happen in Chrome and Safari.
$(function() {
setTimeout(
function() {
console.log("Delayed event attachment");
$(document).bind('keyup', log);
}, 10);
});
function log(e) {
console.log(e.target.localName);
}

Prevent both blur and keyup events to fire after pressing enter in a textbox

After pressing enter I would like that only the keyup event be fired but blur is fired first. How to cancel blur when keyup is fired with enter?
Please don't suggest to bind both blur and keyup into a single live() method.
$(".textbox").on("blur",function () {
alert("blur Event fired");
});
$(".textbox").on("keyup",function (event) {
if(event.keyCode == 13){ // Detect Enter
alert("KeyUp fired after pressing Enter");
}
});
Edit
To prevent both events from firing, you'll have to somehow mark the element before causing it to lose focus. That way, your blur event handler can tell if the event is the subject of a keyup, or if it legitimately lost focus. Something like this:
$(".textbox").live("blur",function (event) {
if (!$(this).hasClass('keyupping'))
alert("blur Event fired");
});
$(".textbox").live("keyup",function (event) {
$(this).addClass('keyupping');
if(event.keyCode == 13){ // Detect Enter
alert("KeyUp fired after pressing Enter");
}
$(this).removeClass('keyupping');
});
Try it out: http://jsfiddle.net/GRMule/sR6zm/
Original answer
When the event for keyup fires, it prepares to draw the browser alert dialog, which takes focus from the document and applies it to the modal dialog. This causes the blur event to fire.
The blur event is then jumping in and finishing its execution context before keyup knows what hit it.
This is demonstrated by using something that does not take the focus off the element, like console.log: http://jsfiddle.net/GRMule/7vRLW/
The order that events fire is implementation-specific, meaning that you can't rely on Firefox acting like IE. See the spec: http://www.w3.org/TR/2000/REC-DOM-Level-2-Events-20001113/events.html#Events-eventgroupings. Try the fiddle with alerts in IE, and in this case you'll see that blur does hit before keyup in IE 7 -- and blur doesn't fire in Chrome!
I had a similar problem. I'm allowing the user to edit a single field and when they press Enter or move off that field, I send an Ajax request to update it. I found that when I pressed Enter the Ajax request was sent twice.
So rather than calling my request on Enter, I tried calling $input.blur() instead, and that worked! Which got me to thinking... If the Enter key causes a blur do I even need to try to capture it?
In my case, I did not need to. I found that all I needed was the blur because the Enter key triggered it anyway. I'm not sure if that's 100% across all browsers, but I did test on current versions of Chrome, Firefox, IE and Safari, all of which worked fine.
So, I suggest that you either just don't capture the Enter at all, or you simply call blur() to trigger the actions you need.
I have an input where a user can change it, focus out or press enter.
But when you press enter both keydown and blur is triggered, so myFunction() gets triggered twice.
So instead of writing two separate functions for keydown and blur, you can instead put them into a single function:
my_input.on('keydown blur', function (e) {
// was it the Enter key?
if (e.which == 13) {
$(this).blur();
}
if (e.type == 'blur') {
myFunction();
}
});
Try the following. Adding a class -- added in this example, in the keyup event handler and modifying the selector for the blur event will prevent the blur event handler from firing.
$(".textbox:not(.added)").on("blur", function () {
alert("blur Event fired");
});
$(".textbox").on("keyup", function (event) {
if (event.keyCode == 13) {
$(event.currentTarget).addClass('added');
alert("KeyUp fired after pressing Enter");
}
});
The below code worked for me, in primefaces 5.2.5
<p:inputText onkeydown="if (event.keyCode === 13) {return false; }" value="#{myForm.name}">
<p:ajax event="blur" update="#this" listener="#{bean.func()}" />
</p:inputText>
Blur event was not triggered even though Enter key was pressed.
Basically, keyup is a trigger for blur event. You should add a flag when keyup fires:
$('#exemple').keyup(function (e) {
if (e.which == 13) {
$('#exemple').addClass('keyupfired');
alert('whatever');
}
});
Then, when blur is fired, it should ask if keyup has already been fired too. Remember to remove the flag if you want the event to be fired when the user get off the textbox:
$('#exemple').on("blur", function () {
if (!$('#exemple').hasClass('keyupfired')) {
alert('whatever');
}
$('#exemple').removeClass('keyupfired');
});
I Couldn't alter class attribute so i'd ended up with,
$(".textbox").on("blur",function () {
if($(this).attr('flag')!='1')
alert("blur Event fired");
});
$(".textbox").on("keyup",function (event) {
$(this).attr('flag','1');
if(event.keyCode == 13){ // Detect Enter
alert("KeyUp fired after pressing Enter");
}
$(this).attr('flag','0');
});
It has been brought to my attention than rather then providing hints I should give more complete explanations and code examples, so here it is:
there is always the cheap way of setting a external variable:
var triggerBlur = true;
$(".textbox")
.live({
blur : function () {
if (triggerBlur) {// if not preceded by keyup 'Enter' event
alert("blur Event fired");
}
// reset variable to true to allow the blur event to be triggered subsequently when not preceded by keyup 'Enter' event
triggerBlur = true;
},
keyup : function (event) {
if(event.which === 13){ // Detect Enter
alert("KeyUp fired after pressing Enter");
triggerBlur = false;
}
});
Also it's preferable to use event.which rather than event.keyCode (see http://api.jquery.com/event.which/ to understand why), and it is recommended to use the identity operator '===' rather than the equality '==' in javascript, as the latter is broken (see Which equals operator (== vs ===) should be used in JavaScript comparisons?)

Javascript/JQuery: how to add keypress/blur event that doesn't trigger twice with alert box? IE only

I have an input field that I would like to validate on when the user either presses enter or clicks away from it, for this I use the events keypress and blur. If the input fails validation, an alert box is called.
I noticed that in IE (all versions), if I press enter with invalid input, for some reason both the keypress and blur events are fired (I suspect it's the alert box, but it doesn't do this on FF/Chrome) and it shows two of the same alert box. How can I have it so only one is shown?
EDIT: In FF/Chrome, I now noticed that a second alert box appears when I click anywhere after I try to validate with enter.
Simplified code:
$("#input-field").keypress(function(event) {
if (event.keycode == 13) {
event.stopPropagation();
validate();
return false;
}
});
$("#input-field").blur(function() {
validate();
});
function validate() {
if ($("#input-field").val() == '') {
alert("Invalid input");
}
}
EDIT: Ah-ha. Not really a fix but a separate detail I forgot - I need to restore the invalid input to its previously valid value, so when the validate function checks the value again it doesn't fail twice.
I ended up just checking for an IE UserAgent and skipping the keypress event for IE (binding keypress and blur to the same function, as below). Not a direct or terrific solution, tragically, but I've been looking to solve the same problem to no avail. Some minor notes that might be helpful: jQuery normalizes which, so you can confidently use e.which == 13 with keypress. I'd also combine the functions into one bind, e.g.
$("#input-field").bind('blur keypress', function(e) {
if(e.which == 13) {
// keypress code (e.g. check for IE and return if so)
}
validate();
});
I've tried setting globals and using jQuery's data() to assign arbitrary flags to indicate whether (in your case) validation has already been triggered for the element, but the events trigger simultaneously or at least, if sequentially, rapidly enough that even with an opening line setting some flag to true did not do the trick. I'd read that putting in a tiny callback delay might help, but that is hella dirty and I wouldn't do it even as a workaround so I've not tested it. stopPropagation() and preventDefault() also did not help.
Firefox does not get the keypress event right. Those events are only triggered when a key combination that produces a character is pressed (which is not the same as pressing any key).
Use keydown instead (as this is probably the only event IE handles correctly - as it should, since MS "invented" it ;-) ).
See http://www.quirksmode.org/dom/events/keys.html.

Remap Enter keydown to trigger Shift+Enter in JavaScript

I'm using Mootools, but a generic answer is fine.
I would like to remap the 'Enter' key in a web application.
When they hit 'Enter' it should react as though the 'Shift-Enter' has been pressed.
I would just stop the enter event, and use exec.insertHTML or its ilk, but FF's implementation is buggy on many elements.
I imagine that I could fire a key event, same as I could fire a click or other event:
click: $('myElement').fireEvent('click', arg1);
keyevent: $('myElement').fireEvent('keydown' ???);
But I can't figure out how.
I don't know exactly what you're looking for, but the following fires the 'shiftenter' event when the enter-key is pressed. Notice that you have to specify the 'shiftenter' event yourself.
$('element').addEvent('keydown', function(e) {
new Event(e).stop();
if (e.key == 'enter') {
this.fireEvent('shiftenter');
}
});

Categories