StudioTime
StudioTime

Reputation: 23979

Enter key for .on() fires twice

I have a system which allows a user to tag an image, they click on the image and box appears for them to enter their friends name, then when chosen from autocomplete they either click save button or click enter

$("#imgtag img").click(function(e){ // make sure the image is clicked
        var imgtag = $(this).parent(); // get the div to append the tagging entry
        mouseX = e.pageX - $(imgtag).offset().left; // x and y axis
        mouseY = e.pageY - $(imgtag).offset().top;
        mouseY = (mouseY-60);
        mouseX = (mouseX-90);
        $('#tagit').remove(); // remove any tagit div first
        $(imgtag).append('<div id="tagit"><div class="box"></div><div class="name"><input type="text" name="name" id="tagName" /><input type="button" name="btnsave" value="Save" id="btnsave" /><input type="button" name="btncancel" value="Cancel" id="btncancel" /></div></div>');
        $('#tagit').css({top:mouseY,left:mouseX});

        $("#tagName").autocomplete({        
            source: data,
            select: function( event, ui ) {
                $( "#tagName" ).val( ui.item.label); 
                return false;
            }
        });

        $('#tagName').focus();

        $('#tagName').keyup(function(event){ // this fires twice
            if(event.keyCode == 13){
                $('#btnsave').trigger('click');
            }
        });
    });

This is the code which saves the data

$(document).on('click', '#btnsave', function() {
        name = $('#tagName').val();
        counter++;
        $('#taglist ol').append('<li rel="'+counter+'"><a>'+name+'</a> (<a class="remove">Remove</a>)</li>');
        $('#imgtag').append('<div class="tagview" id="view_'+counter+'"></div>');
        $('#view_' + counter).css({top:mouseY,left:mouseX});
        $('#tagit').fadeOut();
        // add backend code here, use mouseX and mouseY for the axis and counter.
    });

If I move the $('#tagName').keyup(function(event){ if(event.keyCode == 13){}} out of the #imgtag img scope it doesn't work at all, but with where it is now its like clicking the #btnsave button twice, which should not be possible as the surrounding div is removed when the button is clicked once.

This works perfectly when actually clicking the button it just fires twice if I use the enter button instead.

Any ideas why this would fire it twice on enter?

UPDATE I have now moved the click out of the #imgtag click function - thanks for that, also slightly different enter key code but still firing twice

$("#imgtag img").click(function(e){ // make sure the image is clicked
    var imgtag = $(this).parent(); // get the div to append the tagging entry
    mouseX = e.pageX - $(imgtag).offset().left; // x and y axis
    mouseY = e.pageY - $(imgtag).offset().top;
    mouseY = (mouseY-60);
    mouseX = (mouseX-130);
    $('#tagit').remove(); // remove any tagit div first
    $(imgtag).append('<div id="tagit"><div class="box"></div><div class="name"><input type="text" name="name" id="tagName" /><input type="button" name="btnsave" value="Save" id="btnsave" /><input type="button" name="btncancel" value="Cancel" id="btncancel" /></div></div>');
    $('#tagit').css({top:mouseY,left:mouseX});


$("#tagName").autocomplete({        
    source: "/ajax/fbFriendsAutoC.php",
    select: function( event, ui ) {
    $( "#tagName" ).val( ui.item.name ); // on select place friend name to input
    $( "#uid" ).val( ui.item.uid ); // temp place for uid
    return false;

    }
    }).data( "ui-autocomplete" )._renderItem = function( ul, item ) { // how our list will looks
return $( "<li></li>" )
.append( "<a><img src='" + item.pic_square + "' height=32 /><div class='fbName'>" + item.name + "</div></a>" )
            .data( "item.autocomplete", item ) .appendTo( ul );
        };
    $('#tagName').focus();  
    });

$(document).keyup(function(e) {
    if (e.keyCode == 13) { $('#btnsave').trigger('click'); }     // enter
    if (e.keyCode == 27) { $('#tagit').fadeOut(); }   // esc
});

$(document).on('click', '#btnsave', function() {
    uid = $('#uid').val();  
    var hdnValue = $('#tags').val();
    $('#tags').val(hdnValue + uid + ','+ mouseX + ',' + mouseY + ',');
    name = $('#tagName').val();
    counter++;
    $('#taglist ul').append('<li rel="'+counter+'"><a>'+name+'</a> (<a class="remove">Remove</a>)</li>');
        $('#imgtag').append('<div class="tagview" id="view_'+counter+'"></div>');
    $('#view_' + counter).css({top:mouseY,left:mouseX});
    $('#tagit').fadeOut();      
});

Upvotes: 1

Views: 2883

Answers (2)

adeneo
adeneo

Reputation: 318182

It probably not only fires twice, but as many times as you click the image, as you're binding the keyup event handler inside the click function for the image, rebinding a new keyup event on every click of the image.

Try something like this :

$("#imgtag img").on('click', function(e){
    var imgtag = $(this).parent(),
        mouseX = (e.pageX - $(imgtag).offset().left) - 60,
        mouseY = (e.pageY - $(imgtag).offset().top) - 90,
        tagit  = $('<div />', { style : 'top:'+mouseY+'px; left:'+mouseX+'px;' }),
        html   = '<div class="box"></div><div class="name"><input type="text" name="name" id="tagName" /><input type="button" name="btnsave" value="Save" id="btnsave" /><input type="button" name="btncancel" value="Cancel" id="btncancel" /></div>';

    $('#tagit').remove();
    $(imgtag).append(tagit.html(html));

    $("#tagName").autocomplete({        
        source: data,
        select: function( event, ui ) {
            $( "#tagName" ).val( ui.item.label); 
            return false;
        }
   }).focus();
});

$('#imgtag').on('keyup', '#tagName', function(e) {
    if(e.which == 13){
        $('#btnsave').trigger('click');
    }
});

Upvotes: 3

Animesh Nandi
Animesh Nandi

Reputation: 458

ok, try with .keypress

instead of

.keyup(function(event){ // this fires twice
        if(event.keyCode == 13){

try

.keypress(function(event) {
        if(event.which == 13) {

Upvotes: 2

Related Questions