210

I wonder what I'm doing wrong:

$(".s").keypress(function(e) {
   switch (e.keyCode) {
      case 8: // Backspace
      //console.log('backspace');
      case 9: // Tab
      case 13: // Enter
      case 37: // Left
      case 38: // Up
      case 39: // Right
      case 40: // Down
         break;

      default:
         doSearch();
   }
});

I want my doSearch() function also to be fired when I hit the Backspace key. At the moment absolutely nothing happens when I press Backspace in Chrome and Safari.

any ideas?

Cristiano Soares
  • 619
  • 1
  • 9
  • 20
matt
  • 42,713
  • 103
  • 264
  • 397

4 Answers4

360

Use keyup instead of keypress. This gets all the key codes when the user presses something

Jonathon Bolster
  • 15,811
  • 3
  • 43
  • 46
  • 44
    Why would `keyup` fire for Backspace when `keypress` won't? – Aaron Digulla Jan 14 '11 at 11:11
  • 1
    it's the case. Keyup fires backspace, keypress doesn't -> weird. is there a chance to also check if two keys are pressed like cmd-c, or cmd-v, or cmd-a – matt Jan 14 '11 at 11:28
  • 19
    It's actually dependent on key. You want to use `keypress` for `Enter` key, `keydown` for `Backspace` and so forth; otherwise you'll find your events in some browsers don't really work as you expect, especially when you want to prevent the default behavior for the key. When you use the wrong one, what will happen is either your event is not captured at all (as is the case for Backspace) or you can't prevent it; since it already happens before your event handling code gets to it. – srcspider Feb 22 '11 at 13:20
  • 5
    The problem with this answer is that using `keyup` will [break the number pad](http://stackoverflow.com/questions/5630918/get-correct-keycode-for-keypadnumpad-keys). Do you know of an answer that allows correctly detecting any key on a full keyboard? – hughes Apr 04 '13 at 22:12
  • this is not exactly right, because when I use keyup I get completely "wrong" codes for the keys, the same for the keydown, only keypress seemed to work for this issue, until I faced this backspace google chrome problem – dav Feb 08 '14 at 14:46
  • This won't be the solution if you won't to fire the function **before** user release the key! – Andre Figueiredo Apr 01 '14 at 18:35
  • 7
    `keydown` is the better option for all keys – artfuldev Aug 28 '14 at 09:39
  • keydown also works better for when the user holds down the backspace key – Adam Hey Jul 25 '17 at 15:24
  • it does not seem to work with type = tel or type = password – George Jan 29 '18 at 10:09
  • Sometimes it might be too late to listen for `keyup`. Use `keydown` – Roko C. Buljan Jul 29 '18 at 21:30
36

I came across this myself. I used .on so it looks a bit different but I did this:

 $('#element').on('keypress', function() {
   //code to be executed
 }).on('keydown', function(e) {
   if (e.keyCode==8)
     $('element').trigger('keypress');
 });

Adding my Work Around here. I needed to delete ssn typed by user so i did this in jQuery

  $(this).bind("keydown", function (event) {
        // Allow: backspace, delete
        if (event.keyCode == 46 || event.keyCode == 8) 
        {
            var tempField = $(this).attr('name');
            var hiddenID = tempField.substr(tempField.indexOf('_') + 1);
            $('#' + hiddenID).val('');
            $(this).val('')
            return;
        }  // Allow: tab, escape, and enter
        else if (event.keyCode == 9 || event.keyCode == 27 || event.keyCode == 13 ||
        // Allow: Ctrl+A
        (event.keyCode == 65 && event.ctrlKey === true) ||
        // Allow: home, end, left, right
        (event.keyCode >= 35 && event.keyCode <= 39)) {
            // let it happen, don't do anything
            return;
        }
        else 
        {
            // Ensure that it is a number and stop the keypress
            if (event.shiftKey || (event.keyCode < 48 || event.keyCode > 57) &&       (event.keyCode < 96 || event.keyCode > 105)) 
            {
                event.preventDefault();
            }
        }
    });
Jim B
  • 8,344
  • 10
  • 49
  • 77
Rob
  • 361
  • 3
  • 2
  • 1
    this works with firefox if you use event.which instead of event.keyCode http://api.jquery.com/event.which/ – BishopZ Sep 19 '14 at 16:38
11

If you want to fire the event only on changes of your input use:

$('.s').bind('input', function(){
  console.log("search!");
  doSearch();
});
Marcos Nunes
  • 1,265
  • 12
  • 12
8

According to the jQuery documentation for .keypress(), it does not catch non-printable characters, so backspace will not work on keypress, but it is caught in keydown and keyup:

The keypress event is sent to an element when the browser registers keyboard input. This is similar to the keydown event, except that modifier and non-printing keys such as Shift, Esc, and delete trigger keydown events but not keypress events. Other differences between the two events may arise depending on platform and browser. (https://api.jquery.com/keypress/)

In some instances keyup isn't desired or has other undesirable effects and keydown is sufficient, so one way to handle this is to use keydown to catch all keystrokes then set a timeout of a short interval so that the key is entered, then do processing in there after.

jQuery(el).keydown( function() { 
    var that = this; setTimeout( function(){ 
           /** Code that processes backspace, etc. **/ 
     }, 100 );  
 } );
Aminadav Glickshtein
  • 23,232
  • 12
  • 77
  • 117
Halcyon
  • 1,376
  • 1
  • 15
  • 22