--- title: Shortcut Keys order: 5 layout: page --- [[advanced.shortcuts]] = Shortcut Keys Vaadin provides simple ways to define shortcut keys for field components, as well as to a default button, and a lower-level generic shortcut API based on actions. A __shortcut__ is an action that is executed when a key or key combination is pressed within a specific scope in the UI. The scope can be the entire [classname]#UI# or a [classname]#Window# inside it. [[advanced.shortcuts.defaultbutton]] == Shortcut Keys for Default Buttons You can add a __click shortcut__ to a button to set it as "default" button; pressing the defined key, typically kbd:[Enter], in any component in the scope (sub-window or UI) causes a click event for the button to be fired. You can define a click shortcut with the [methodname]#setClickShortcut()# shorthand method: [source, java] ---- // Have an OK button and set it as the default button Button ok = new Button("OK"); ok.setClickShortcut(KeyCode.ENTER); ok.addStyleName(ValoTheme.BUTTON_PRIMARY); ---- The [methodname]#setClickShortcut()# is a shorthand method to create, add, and manage a [classname]#ClickShortcut#, rather than to add it with [methodname]#addShortcutListener()#. Themes offer special button styles to show that a button is special. In the Valo theme, you can use the [literal]#++BUTTON_PRIMARY++# style name. The result can be seen in <>. [[figure.advanced.shortcuts.defaultbutton]] .Default Button with Click Shortcut image::img/shortcut-defaultbutton.png[] [[advanced.shortcuts.focus]] == Field Focus Shortcuts You can define a shortcut key that sets the focus to a field component (any component that inherits [classname]#AbstractField#) by adding a [classname]#FocusShortcut# as a shortcut listener to the field. The constructor of the [classname]#FocusShortcut# takes the field component as its first parameter, followed by the key code, and an optional list of modifier keys, as listed in <>. [source, java] ---- // A field with Alt+N bound to it TextField name = new TextField("Name (Alt+N)"); name.addShortcutListener( new AbstractField.FocusShortcut(name, KeyCode.N, ModifierKey.ALT)); layout.addComponent(name); ---- You can also specify the shortcut by a shorthand notation, where the shortcut key is indicated with an ampersand ( [literal]#++&++#). [source, java] ---- // A field with Alt+A bound to it, using shorthand notation TextField address = new TextField("Address (Alt+A)"); address.addShortcutListener( new AbstractField.FocusShortcut(address, "&Address")); ---- This is especially useful for internationalization, so that you can determine the shortcut key from the localized string. [[advanced.shortcuts.actions]] == Generic Shortcut Actions Shortcut keys can be defined as __actions__ using the [classname]#ShortcutAction# class. It extends the generic [classname]#Action# class that is used for example in [classname]#Tree# and [classname]#Table# for context menus. Currently, the only classes that accept [classname]##ShortcutAction##s are [classname]#Window# and [classname]#Panel#. To handle key presses, you need to define an action handler by implementing the [classname]#Handler# interface. The interface has two methods that you need to implement: [methodname]#getActions()# and [methodname]#handleAction()#. The [methodname]#getActions()# method must return an array of [classname]#Action# objects for the component, specified with the second parameter for the method, the [parameter]#sender# of an action. For a keyboard shortcut, you use a [classname]#ShortcutAction#. The implementation of the method could be following: [source, java] ---- // Have the unmodified Enter key cause an event Action action_ok = new ShortcutAction("Default key", ShortcutAction.KeyCode.ENTER, null); // Have the C key modified with Alt cause an event Action action_cancel = new ShortcutAction("Alt+C", ShortcutAction.KeyCode.C, new int[] { ShortcutAction.ModifierKey.ALT }); Action[] actions = new Action[] {action_cancel, action_ok}; public Action[] getActions(Object target, Object sender) { if (sender == myPanel) return actions; return null; } ---- The returned [classname]#Action# array may be static or you can create it dynamically for different senders according to your needs. The constructor of [classname]#ShortcutAction# takes a symbolic caption for the action; this is largely irrelevant for shortcut actions in their current implementation, but might be used later if implementors use them both in menus and as shortcut actions. The second parameter is the key code and the third a list of modifier keys, which are listed in <>. The following example demonstrates the definition of a default button for a user interface, as well as a normal shortcut key, kbd:[Alt+C] for clicking the [guibutton]#Cancel# button. [source, java] ---- public class DefaultButtonExample extends CustomComponent implements Handler { // Define and create user interface components Panel panel = new Panel("Login"); FormLayout formlayout = new FormLayout(); TextField username = new TextField("Username"); TextField password = new TextField("Password"); HorizontalLayout buttons = new HorizontalLayout(); // Create buttons and define their listener methods. Button ok = new Button("OK", event -> okHandler()); Button cancel = new Button("Cancel", event -> cancelHandler()); // Have the unmodified Enter key cause an event Action action_ok = new ShortcutAction("Default key", ShortcutAction.KeyCode.ENTER, null); // Have the C key modified with Alt cause an event Action action_cancel = new ShortcutAction("Alt+C", ShortcutAction.KeyCode.C, new int[] { ShortcutAction.ModifierKey.ALT }); public DefaultButtonExample() { // Set up the user interface setCompositionRoot(panel); panel.addComponent(formlayout); formlayout.addComponent(username); formlayout.addComponent(password); formlayout.addComponent(buttons); buttons.addComponent(ok); buttons.addComponent(cancel); // Set focus to username username.focus(); // Set this object as the action handler panel.addActionHandler(this); } /** * Retrieve actions for a specific component. This method * will be called for each object that has a handler; in * this example just for login panel. The returned action * list might as well be static list. */ public Action[] getActions(Object target, Object sender) { System.out.println("getActions()"); return new Action[] { action_ok, action_cancel }; } /** * Handle actions received from keyboard. This simply directs * the actions to the same listener methods that are called * with ButtonClick events. */ public void handleAction(Action action, Object sender, Object target) { if (action == action_ok) { okHandler(); } if (action == action_cancel) { cancelHandler(); } } public void okHandler() { // Do something: report the click formlayout.addComponent(new Label("OK clicked. " + "User=" + username.getValue() + ", password=" + password.getValue())); } public void cancelHandler() { // Do something: report the click formlayout.addComponent(new Label("Cancel clicked. User=" + username.getValue() + ", password=" + password.getValue())); } } ---- Notice that the keyboard actions can currently be attached only to [classname]##Panel##s and [classname]##Window##s. This can cause problems if you have components that require a certain key. For example, multi-line [classname]#TextField# requires the kbd:[Enter] key. There is currently no way to filter the shortcut actions out while the focus is inside some specific component, so you need to avoid such conflicts. [[advanced.shortcuts.keycodes]] == Supported Key Codes and Modifier Keys The shortcut key definitions require a key code to identify the pressed key and modifier keys, such as kbd:[Shift], kbd:[Alt], or kbd:[Ctrl], to specify a key combination. The key codes are defined in the [classname]#ShortcutAction.KeyCode# interface and are: Keys [parameter]#A# to [parameter]#Z#:: Normal letter keys [parameter]#F1# to [parameter]#F12#:: Function keys [parameter]#BACKSPACE#, [parameter]#DELETE#, [parameter]#ENTER#, [parameter]#ESCAPE#, [parameter]#INSERT#, [parameter]#TAB#:: Control keys [parameter]#NUM0# to [parameter]#NUM9#:: Number pad keys [parameter]#ARROW_DOWN#, [parameter]#ARROW_UP#, [parameter]#ARROW_LEFT#, [parameter]#ARROW_RIGHT#:: Arrow keys [parameter]#HOME#, [parameter]#END#, [parameter]#PAGE_UP#, [parameter]#PAGE_DOWN#:: Other movement keys Modifier keys are defined in [classname]#ShortcutAction.ModifierKey# and are: [parameter]#ModifierKey.ALT#:: kbd:[Alt] key [parameter]#ModifierKey.CTRL#:: kbd:[Ctrl] key [parameter]#ModifierKey.SHIFT#:: kbd:[Shift] key All constructors and methods accepting modifier keys take them as a variable argument list following the key code, separated with commas. For example, the following defines a kbd:[Ctrl+Shift+N] key combination for a shortcut. [source, java] ---- TextField name = new TextField("Name (Ctrl+Shift+N)"); name.addShortcutListener( new AbstractField.FocusShortcut(name, KeyCode.N, ModifierKey.CTRL, ModifierKey.SHIFT)); ---- === Supported Key Combinations The actual possible key combinations vary greatly between browsers, as most browsers have a number of built-in shortcut keys, which can not be used in web applications. For example, Mozilla Firefox allows binding almost any key combination, while Opera does not even allow binding kbd:[Alt] shortcuts. Other browsers are generally in between these two. Also, the operating system can reserve some key combinations and some computer manufacturers define their own system key combinations.