Jquery blur works twice - why?

I am working on creating my own book that works like AJAX. It is based on a table with editable cells. The user clicks on the cell to enter a grade, and when they click on the cell, the class is sent to the database via AJAX. While it is working fine, except that I added that the user can press Enter and make him act as if the user had clicked somewhere else to close the editing form.

PROBLEM: when the user accesses return instead of input, the blur part works twice, as evidenced by the warning that appears twice. If they just click somewhere, that's fine. My understanding of jQuery.blur () is that if you call it without a callback or arguments, it acts as an executor and treats it as if the selected element lost focus.

It happens in IE8, Chrome and FF 4.0.1. The current version works on my test site

Can someone explain why it works twice when I try to set the blur on user login?

UPDATE: HTML code cannot be published because in fact the table and the set of table tags are not in the whiteOutflow list. (I'm new here, so there may be a way to do this, but I don't know that.)

In addition, I solved the immediate problem by changing

if(event.keyCode=='13') { $('#gradeUpdate').blur(); } 

to

  if(event.keyCode=='13') { $("#gradeUpdate").parent().focus(); //$('#gradeUpdate').blur(); } 

but I still would like to know why the original line doesn't just make #gradeUpdate blur as I thought.

Everything happens inside this function:

 function clickableCell(){ $("td.assignmentCell").click(function(){ //if a td with an assignment class is clicked, if( clicked == 0) { clicked = 1; currentValue = $(this).text();//get the current value of the entered grade var passable = this; alert("Test: passable is: "+$(passable).text()); //change content to be an editable input form element $(this).html("<input name='gradeUpdate' id='gradeUpdate' size=3 value='"+currentValue+"' type='text' />"); //move the cursor to the new input and highlight the value for easy deletion $('#gradeUpdate').focus().select(); //watch for keystrokes somewhere else and act appropriately $(document).keyup(function(event){ //if they hit Enter, treat it like they clicked somewhere else if(event.keyCode=='13') { $('#gradeUpdate').blur(); } }); $('#gradeUpdate').blur(function(passable){ //reset the clicked counter clicked = 0; //check to see if the value is blank or hasn't changed var inputValue = $('#gradeUpdate').val(); ////////////////////////////////////////////////////////////////////////////////////////// // Here we need to insert a REGEX check for the "exception" values created by the GDST // and check for those values; anything else that not a number will be disallowed // and reset to "" so that it caught in a later step. For now I'm just checking for digits ////////////////////////////////////////////////////////////////////////////////////////// if(!inputValue.match(/^\d+$/)) { alert ("we don't have a match!"); inputValue = ""; } /////////////////////////////////////////////////////////////////////////////////////////// if(currentValue == inputValue || inputValue =="")//hasn't changed or is blank { //DON'T run AJAX call alert("Not a good value, reverting to old value!"); //assign the original, unchanged value to the table $('#gradeUpdate').parent().text(currentValue) $("#gradeUpdate").remove();//close out the input block //make it like they actually clicked on the element they did click on to lose focus $(this).click(); } else //it valid, send the ajax { //send AJAX call here //on success update the td alert("We're all good--entering value!"); $("#gradeUpdate").parent().text(inputValue); $("#gradeUpdate").remove(); } }); }//close of if clicked ==0 }); } 

and here is the full HTML of the source page; it's really just a table with some pre-entered values ​​that you need to use for testing. My next step is to build the table on the fly with the XML returned from the AJAX request.

+4
source share
4 answers

I think you need to switch from $('#gradeUpdate').blur() to $('#gradeUpdate')[0].blur() . In a browser, jQuery blur is different from regular blur. Therefore, it will be activated twice.

+8
source

I had the same thing with me, the line $('input')[0].blur(); somehow fixed it, but I don’t understand how it works. My code is:

 $('h1 input').live('blur', function(){ var text = $('h1 input').val(); if(text == ''){ alert('!'); $('h1').html('<p>' + originalProjectName + '</p><span></span>'); text = originalProjectName; } var id = document.location.hash.split('-')[1]; $('h1').html('<p>' + text + '</p><span></span>'); $.getJSON('json-project.php', { method: 'rename', id: id, name: text }, function(data) { var type = document.location.hash.split('-')[0]; if(type == '#shoot'){ $('#scroller-shoots ul li[data-id=' + id + ']').html(text); } if(type =='#project'){ $('#scroller-projects ul li[data-id=' + id + ']').html(text); } }); }); $('h1 input').live('keydown', function(event) { originalProjectName = $(this).val(); if ( event.which == 13 ) { $(this)[0].blur(); } }); 

This does not make sense, since $(this) should refer to only one selector, and not to several. Does anyone know why this works?

+1
source

Each time you press td.assignmentCell , you restore the blur and keyup . Try linking them only once if that makes sense, or use live or delegate for #gradeUpdate .

Update your questions with your HTML and I can better understand what you are doing.

0
source

I was not able to solve this problem with the proposed solution, because the input blur event occurred before the window blur event (why, I'm not quite sure yet). In doing so, I was able to follow this message and set it up to detect when the user mouse leaves the window area to ignore the blur event.

Code example:

 var isTargetWindow = false; function addEvent(obj, evt, fn) { if (obj.addEventListener) { obj.addEventListener(evt, fn, false); } else if (obj.attachEvent) { obj.attachEvent("on" + evt, fn); } } var isTargetWindow = false; addEvent(window,"load",function(e) { addEvent(window, "mouseout", function(e) { e = e ? e : window.event; var from = e.relatedTarget || e.toElement; if (!from || from.nodeName == "HTML") { // stop your drag event here // for now we can just use an alert isTargetWindow = true; } else { isTargetWindow = false; } }); }); $(document).on( 'blur', 'input', function( e ) { if( isTargetWindow ) { return false; } // ... do something here } 
0
source

All Articles