Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Trap the enter key, but not when choosing the browser's autocomplete suggestion

I have some textboxes on a page and I want to click a link when the user presses enter in any of them.

I can easily trap the enter button using javascript (by looking for 13 in event.keyCode and event.which), but I hit an issue when the browser's autocomplete feature kicks in and suggests what the user might want to type. We're finding the users often press enter to accept the browser's suggestion, rather than tab. This confuses the users as the link is clicked immediately, whereas they still intended to enter text into some of the other fields.

I know it would be better to use a form and a submit button here, but for various reasons that's not practical.

I'm using jQuery, so feel free to offer jQuery solutions.

like image 367
teedyay Avatar asked Oct 30 '09 10:10

teedyay


4 Answers

Using tuanvt's idea in the accepted answer, I wrote a jQuery plugin that does the job.

I track when the user presses the up, down, page-up and page-down keys to tell when they're in the autocomplete box. All other keys imply they've left it.

I ensure that we only apply these rules to textboxes: all other input elements behave normally.

Opera already does a pretty good job of what I was trying to achieve, so I don't enforce my rules in that browser - otherwise the user would have to press enter twice.

Tested in IE6, IE7, IE8, Firefox 3.5.5, Google Chrome 3.0, Safari 4.0.4, Opera 10.00.

It's available on jquery.com as the SafeEnter plugin. For your convenience, the code for release 1.0 is as follows:

// jQuery plugin: SafeEnter 1.0
// http://plugins.jquery.com/project/SafeEnter
// by teedyay
//
// Fires an event when the user presses Enter, but not whilst they're in the browser's autocomplete suggestions

//codesnippet:2e23681e-c3a9-46ce-be93-48cc3aba2c73
(function($)
{
    $.fn.listenForEnter = function()
    {
        return this.each(function()
        {
            $(this).focus(function()
            {
                $(this).data('safeEnter_InAutocomplete', false);
            });
            $(this).keypress(function(e)
            {
                var key = (e.keyCode ? e.keyCode : e.which);
                switch (key)
                {
                    case 13:
                        // Fire the event if:
                        //   - we're not currently in the browser's Autocomplete, or
                        //   - this isn't a textbox, or
                        //   - this is Opera (which provides its own protection)
                        if (!$(this).data('safeEnter_InAutocomplete') || !$(this).is('input[type=text]') || $.browser.opera)
                        {
                            $(this).trigger('pressedEnter', e);
                        }
                        $(this).data('safeEnter_InAutocomplete', false);
                        break;

                    case 40:
                    case 38:
                    case 34:
                    case 33:
                        // down=40,up=38,pgdn=34,pgup=33
                        $(this).data('safeEnter_InAutocomplete', true);
                        break;

                    default:
                        $(this).data('safeEnter_InAutocomplete', false);
                        break;
                }
            });
        });
    };

    $.fn.clickOnEnter = function(target)
    {
        return this.each(function()
        {
            $(this)
                .listenForEnter()
                .bind('pressedEnter', function()
                {
                    $(target).click();
                });
        });
    };
})(jQuery);
like image 166
teedyay Avatar answered Oct 22 '22 22:10

teedyay


User always have to press the down key if they choose to select one of the auto complete text right, why not set a variable to something when they press the down key, and then if they do the enter press afterwards you check the variable. You should not do the link click function if the variable is set, otherwise do it as normal.

like image 38
tuanvt Avatar answered Oct 23 '22 00:10

tuanvt


Try setting the autocomplete off on your check box, though this is not standard for all browser but it works on the common browsers.

<input type="text" autocomplete="off" />
like image 41
jerjer Avatar answered Oct 22 '22 23:10

jerjer


JQuery is nice and all but why not use simple JavaScript?

function submit_on_enter(e) {
    var keycode;
    if (window.event) keycode = window.event.keyCode;
    else if (e) keycode = (e.keyCode ? e.keyCode : e.which);
    else return true;

    if (keycode == 13) {
        if (window.previousKeyCode) {
            // down=40,up=38,pgdn=34,pgup=33
            if (window.previousKeyCode == 33 || window.previousKeyCode == 34 ||
                window.previousKeyCode == 39 || window.previousKeyCode == 40) {
                    window.previousKeyCode = keycode;
                    return true;
            }
        }
        submit_form();
        return false;
    } else {
        window.previousKeyCode = keycode;
        return true;
    }
}
like image 42
Nicolas Bouvrette Avatar answered Oct 22 '22 22:10

Nicolas Bouvrette