Skip to content

feat(keyboard-shortcuts): add customizable keyboard shortcuts - #8521

Open
grantfitzsimmons wants to merge 100 commits into
mainfrom
issue-1746
Open

grantfitzsimmons wants to merge 100 commits into
mainfrom
issue-1746

Conversation

@grantfitzsimmons

@grantfitzsimmons grantfitzsimmons commented Sep 14, 2026 •

Copy link
Copy Markdown
Member

Begins to fix #1746.
Rebased #5097 onto main and resolved the resulting conflicts.

This PR adds keyboard shortcuts!!! Major thanks to @maxpatiiuk for doing the heavy lifting here.

image image

There are some WIP docs available here for staff: https://speciforum.org/t/keyboard-shortcuts/4272/1

Basics

There are some pre-configured shortcuts for common actions when working in the form, dialog, query, or tree views in the app.

Cheat Sheet

There is a new 'cheat sheet' (heavily inspired by the one from Apple's iPadOS 18) that shows you all currently usable shortcuts for the particular view you are in.

DynamicCheatSheet.mp4

It is dynamic, so it handles many different resolutions well:

shortcut_cheatsheet.mp4

Actions can be taken on both the main form, within dialogs, record sets, using keyboard shortcuts out of the box:

image

Keyboard Shortcuts appears as a new section in User Preferences. Shortcut mappings for forms, dialogs, trees, query builders, navigation items, user tools, and URLs are covered by the existing preference definitions and automated tests.

Checklist

  • Self-review the PR after opening it to make sure the changes look good and
    self-explanatory (or properly documented)
  • Add relevant issue to release milestone
  • Add pr to documentation list
  • Add automated tests
  • Add a reverse migration if a migration is present in the PR
  • Add migration function to
    def fix_schema_config(stdout: WriteToStdOut | None = None):

Testing instructions

  • Open Preferences → Keyboard Shortcuts. Confirm action groups, User Tools, and configured URL shortcuts are visible.
  • Record, change, and remove a simultaneous key shortcut (combinations can be made by holding down multiple keys simultaneously when setting a shortcut). Confirm it saves when recording ends. Assign a shortcut already used by an available action and check that the warning names both actions; confirm actions available only in mutually exclusive views can share a shortcut without a warning.
  • In a form, try Save, Carry Forward, and Clone. Open a dialog and verify its configured close shortcut works when available.
  • Add shortcuts for an internal Specify path (including a path such as Choose Collection) and an external URL. Confirm internal navigation stays in the app and respects unsaved changes, while the external URL opens as expected (in a new tab).
  • Verify that keyboard shortcuts do not conflict with browser defaults.

Summary by CodeRabbit

Summary

  • New Features
    • Added configurable keyboard shortcuts for forms, dialogs, record navigation, saving, queries, tree actions, search, and URL navigation.
    • Added preferences to edit shortcuts and assign them to pages, overlays, tools, and custom URLs.
    • Shortcut labels appear on relevant controls; hold Control or Meta to view active shortcuts.
    • Search fields in supported views can receive focus automatically, and record selectors and paginators support keyboard navigation.
  • Accessibility
    • External links now have accessible labels or titles.
  • Bug Fixes
    • Improved handling of malformed URLs and route titles.

maxpatiiuk and others added 30 commits July 26, 2025 08:07
"Keyboard" is a bit too generic/ambiguous
- Replace "show nodes with children only" checkbox with a toggle button.
  Reasons:
  - The checkbox was the only thing below the tree viewer - occupying
    an entire line of horizontal space.
  - Because of how Tab and Shift+Tab keys are used in the tree viewer,
    moving focus to elements below the tree viewer is not possible - you
    can only move above the tree viewer. That made this checkbox
    inaccessible from keyboard
  - The label for this checkbox is long, adding visual noise - it's
    cleaner as a small tidy button
- Don't display split view controls if split view is not enabled to
  reduce visual clutter
@grantfitzsimmons
grantfitzsimmons requested a review from a team October 2, 2026 21:06

@JDAM2k4 JDAM2k4 left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Testing instructions

  • Open Preferences and select the Keyboard Shortcuts submenu.
  • Confirm the shortcut groups have descriptive headings and descriptions:
    • Form Actions
    • Dialog Actions
    • Tree Editor Actions
    • Query Builder Actions
  • In the 'User Tools' section, confirm that navigation-menu items and user tools are listed with their corresponding icons and that a shortcut can be assigned directly to each item.
  • Confirm that 'Keyboard Shortcuts to URLs' appears as a separate section beneath User Tools, includes its description, and still opens the URL editor with the Edit button. Test these shortcuts to specific URLs (even those outside of Specify).
  • Assign and use shortcuts for form actions such as Save, Carry Forward, and Clone.
  • Open dialogs that show Close or Save actions (most) and verify that their configured shortcuts work only when the corresponding action is available.
  • Open a tree and a query builder and verify that their configured shortcuts trigger the expected actions. If not, report what is not working!
  • Navigate using shortcuts assigned to menu items or user tools. Confirm that navigation stays in the app and that unsaved-change prompts still appear.
  • Verify that the shortcuts to things like the 'About Specify 7' dialog and other internal navigation actions also use the in-app router and respect unsaved changes.
  • Check default shortcuts on a non-Specify page for browser or operating-system conflicts. Test on Firefox and Chrome on macOS, Windows, and Linux (name what you test on!).

The formatting seems a little weird to me, because it's all pushed to the left side of the screen and leaves a lot of empty space between the keyboard shortcuts and the User Preference Menu options. This could be used to have descriptions for the options, because as of now, I have no idea what the option Trees is supposed to do. Does it open the Trees tab? Does it take me to the Taxon tree? Does it create a new Tree entirely?

Technically the User Tools Header appears outside of all of the categories, so it's a bit difficult to tell what specifically you are referring to in the third instruction, because the label for that category is Main.

The Save button that appears after you add a keyboard shortcut could be confusing as if you leave the page without selecting the button at the bottom of the page, it does not save the shortcut. It also will not keep the changes unless you click this button first, which seems oddly redundant.

There is no warning/indicator if you have multiple shortcuts that use the same key, which would be good for a future update. The addition of default keyboard shortcuts would also be nice, because it feels cumbersome to have to create these preferences for every user in a database.

Specify does not acknowledge when I press the tab key. It also doesn't recognize when I press either shift key by itself. You also can't use multiple keys at once (ex. Shift + D + V for Data Views). I'm not sure if this is a problem that warrants addressing as I only find issue with it due to personal preference, but I am bringing it up regardless.

When I try to add a custom URL, it defaults to adding /specify/user-preferences/ before it, which does not allow outside URLs to be usable with this. So trying to use google.com/ as a custom URL becomes /specify/user-preferences/google.com which leads to a 404 page in Specify, because that does not exist.

The keyboard shortcut options for Form Actions do not exist. Honestly, as of now, the options for keyboard shortcuts are only really to do administrative tasks or to open a specific tab from the main menu, which I find severely lacking.

The above testing was done on Edge. I didn't find any new errors when I tested on Chrome though.

@kwhuber kwhuber left a comment •

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • Open Preferences and select the Keyboard Shortcuts submenu.
  • Confirm the shortcut groups have descriptive headings and descriptions:
    • Form Actions
    • Dialog Actions
    • Tree Editor Actions
    • Query Builder Actions
  • In the 'User Tools' section, confirm that navigation-menu items and user tools are listed with their corresponding icons and that a shortcut can be assigned directly to each item.
  • Confirm that 'Keyboard Shortcuts to URLs' appears as a separate section beneath User Tools, includes its description, and still opens the URL editor with the Edit button. Test these shortcuts to specific URLs (even those outside of Specify).
  • Assign and use shortcuts for form actions such as Save, Carry Forward, and Clone.
  • Open dialogs that show Close or Save actions (most) and verify that their configured shortcuts work only when the corresponding action is available.
  • Open a tree and a query builder and verify that their configured shortcuts trigger the expected actions. If not, report what is not working!
  • Navigate using shortcuts assigned to menu items or user tools. Confirm that navigation stays in the app and that unsaved-change prompts still appear.
  • Verify that the shortcuts to things like the 'About Specify 7' dialog and other internal navigation actions also use the in-app router and respect unsaved changes.
  • Check default shortcuts on a non-Specify page for browser or operating-system conflicts. Test on Firefox and Chrome on macOS, Windows, and Linux (name what you test on!).

Tested on uw_geo with Chrome and Firefox (any issues appeared on both the same).

  • Confirm the shortcut groups have descriptive headings and descriptions:

I don't see any section but the User Tools one.

  • Confirm that 'Keyboard Shortcuts to URLs' appears as a separate section beneath User Tools, includes its description, and still opens the URL editor with the Edit button. Test these shortcuts to specific URLs (even those outside of Specify).

When the URL is not entered in its entirety (like when copying it from a browser window), this will not work correctly. It might be a good idea to have some sort of warning/ability to detect when this might happen and not just prefix it with Specify slugs.

I also tested adding a shortcut to the /accounts/choose_collection (Choose Collection) URL and received unexpected behavior after typing my shortcut (my database had 3 collections):

Image
  • Navigate using shortcuts assigned to menu items or user tools. Confirm that navigation stays in the app and that unsaved-change prompts still appear.
  • Verify that the shortcuts to things like the 'About Specify 7' dialog and other internal navigation actions also use the in-app router and respect unsaved changes.

In my testing, I had unsaved changes in a CO form and used a shortcut to open 'About Specify 7.' Upon closing the about page, I was prompted the unsaved changes dialog, which I assume is behavior you want. However, I am returned to my form to resume any changes and if I don't save and then click out of this CO form I am prompted with the unsaved changes dialog again (existing functionality). I guess I just don't see the purpose of the first dialog when I know I am being returned to the CO form by clicking close on the 'About Specify 7' dialog...it's the same thing twice and not super relevant in the first case because I'm not making changes to the 'About Specify 7' documentation.

@g1rly-c0d3r g1rly-c0d3r left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Testing instructions

  • Open Preferences and select the Keyboard Shortcuts submenu.
  • Confirm the shortcut groups have descriptive headings and descriptions:
    • Form Actions
    • Dialog Actions
    • Tree Editor Actions
    • Query Builder Actions
  • In the 'User Tools' section, confirm that navigation-menu items and user tools are listed with their corresponding icons and that a shortcut can be assigned directly to each item.
  • Confirm that 'Keyboard Shortcuts to URLs' appears as a separate section beneath User Tools, includes its description, and still opens the URL editor with the Edit button. Test these shortcuts to specific URLs (even those outside of Specify).
  • Assign and use shortcuts for form actions such as Save, Carry Forward, and Clone.
  • Open dialogs that show Close or Save actions (most) and verify that their configured shortcuts work only when the corresponding action is available.
  • Open a tree and a query builder and verify that their configured shortcuts trigger the expected actions. If not, report what is not working!
  • Navigate using shortcuts assigned to menu items or user tools. Confirm that navigation stays in the app and that unsaved-change prompts still appear.
  • Verify that the shortcuts to things like the 'About Specify 7' dialog and other internal navigation actions also use the in-app router and respect unsaved changes.
  • Check default shortcuts on a non-Specify page for browser or operating-system conflicts. Test on Firefox and Chrome on macOS, Windows, and Linux (name what you test on!).

I agree with @JDAM2k4 on several points:

  • The User Tools heading is broken:
Image
  • The double save is redundant and does not align with any other keyboard shortcut editor I have ever used, which makes it un-intuitive
  • No indication of having duplicate shortcuts
  • There are keys missing, like escape that we use for closing overlays, but that is in a different section and not re-assignable, I would like to see that integrated into the keyboard shortcuts section
    • If you press fast enough you can have multiple keys for a single shortcut but the timing is way to fast (I was able to assign Shift+:+q for logout)

I was able to assign an external URL to a shortcut without issue, though.

  • Check default shortcuts on a non-Specify page for browser or operating-system conflicts. Test on Firefox and Chrome on macOS, Windows, and Linux (name what you test on!).

I tested this on linux (using the Sway wm), where all of my system keyboard shortcuts are prefixed with Super, so there were no conflicts there, but zen browser, which is a firefox fork has a few issues.

  • Ctrl+Shift+C copies the current url to the clipboard
    • conflicts with carry-forward
  • Ctrl+S toggles the visibility of the tab/url/navigation bar
    • conflicts with saving

@grantfitzsimmons

grantfitzsimmons commented Oct 21, 2026 •

Copy link
Copy Markdown
Member Author

@kwhuber @g1rly-c0d3r @JDAM2k4

Thanks for testing! I've tried my best to address all your points, but note that this is not a high priority feature compared to our other commitments, so I feel we are at a reasonable point for a version 1 (assuming all claimed functionality is operational):

  • c6231e177a groups shortcuts by action area, and c764a7ad fixes the Preferences layout.
  • c5bdd0e577 lists URL shortcuts on the main Keyboard Shortcuts page. 0ab2a01e3e improves custom URL handling, and beeaaddd00 fixes the "Choose Collection" route.
  • 4027a3d2a8 saves a shortcut as soon as recording ends, without a separate Save step. b601f600c8 adds duplicate warnings, with exceptions for actions that cannot be active together (e.g., tree viewer actions, query builder, dialog, forms, etc.)
  • 883537001d removes the redundant unsaved-changes prompt when opening internal pages.
  • 60a5b021db makes dialog closing configurable as a shortcut (so if Esc doesn't work for you?)
  • 5ba7240abe changes the default Save and Carry Forward shortcuts to avoid the browser conflicts reported with Ctrl+S and Ctrl+Shift+C (though I will miss ⌘+S for saving as a default).

If you press fast enough you can have multiple keys for a single shortcut but the timing is way to fast (I was able to assign Shift+:+q for logout)

You should hold the keys simultaneously while setting the shortcut instead of pressing them one at a time! No time limit in that case and you can combo a ton of keys at once.

@g1rly-c0d3r g1rly-c0d3r left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Testing instructions

  • Open Preferences → Keyboard Shortcuts. Confirm action groups, User Tools, and configured URL shortcuts are visible.
  • Record, change, and remove a simultaneous key shortcut (combinations can be made by holding down multiple keys simultaneously when setting a shortcut). Confirm it saves when recording ends. Assign a shortcut already used by an available action and check that the warning names both actions; confirm actions available only in mutually exclusive views can share a shortcut without a warning.
  • In a form, try Save, Carry Forward, and Clone. Open a dialog and verify its configured close shortcut works when available.
  • Add shortcuts for an internal Specify path (including a path such as Choose Collection) and an external URL. Confirm internal navigation stays in the app and respects unsaved changes, while the external URL opens as expected (in a new tab).
  • Verify that keyboard shortcuts do not conflict with browser defaults.

Much better! I still have some issues with the defaults, but users that care can customize those. I think this is very good, and the functionality is there.

@grantfitzsimmons

Copy link
Copy Markdown
Member Author

Much better! I still have some issues with the defaults, but users that care can customize those. I think this is very good, and the functionality is there.

@g1rly-c0d3r Please feel free to suggest changes to the defaults! I am open to modifying those before release

@g1rly-c0d3r

Copy link
Copy Markdown
Contributor

@grantfitzsimmons The concrete one is for carry forward. Three modifire keys plus c feels like a lot, but I think that is just from my muscle memory when it comes to keyboard-driven navigation. I like the Tree Editor Actions, one keystroke per action.

My suggestion would be something like:
c -> clone
Shift+C -> Carry forward

@kwhuber kwhuber left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  • Open Preferences → Keyboard Shortcuts. Confirm action groups, User Tools, and configured URL shortcuts are visible.
  • Record, change, and remove a simultaneous key shortcut (combinations can be made by holding down multiple keys simultaneously when setting a shortcut). Confirm it saves when recording ends. Assign a shortcut already used by an available action and check that the warning names both actions; confirm actions available only in mutually exclusive views can share a shortcut without a warning.
  • In a form, try Save, Carry Forward, and Clone. Open a dialog and verify its configured close shortcut works when available.
  • Add shortcuts for an internal Specify path (including a path such as Choose Collection) and an external URL. Confirm internal navigation stays in the app and respects unsaved changes, while the external URL opens as expected (in a new tab).
  • Verify that keyboard shortcuts do not conflict with browser defaults.

@JDAM2k4 JDAM2k4 left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Testing instructions

  • Open Preferences → Keyboard Shortcuts. Confirm action groups, User Tools, and configured URL shortcuts are visible.
  • Record, change, and remove a simultaneous key shortcut (combinations can be made by holding down multiple keys simultaneously when setting a shortcut). Confirm it saves when recording ends. Assign a shortcut already used by an available action and check that the warning names both actions; confirm actions available only in mutually exclusive views can share a shortcut without a warning.
  • In a form, try Save, Carry Forward, and Clone. Open a dialog and verify its configured close shortcut works when available.
  • Add shortcuts for an internal Specify path (including a path such as Choose Collection) and an external URL. Confirm internal navigation stays in the app and respects unsaved changes, while the external URL opens as expected (in a new tab).
  • Verify that keyboard shortcuts do not conflict with browser defaults.

Some sort of prompt to indicate if a "custom" internal page within Specify already exists could be a good future update, because I tried to add the internal path to choose a collection and it took me a little too long to realize it was already a default page.

Specify still doesn't recognize if I press the tab key, but again, this is personal preference so it does not need to be implemented at this time.

Overall, this works much better than it did before!

@JDAM2k4
JDAM2k4 self-requested a review October 23, 2026 16:32
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

Status: Dev Attention Needed

Development

Successfully merging this pull request may close these issues.

Add keyboard shortcuts for common actions

6 participants