ckeditor / ckeditor5

Powerful rich text editor framework with a modular architecture, modern integrations, and features like collaborative editing.
https://ckeditor.com/ckeditor-5
Other
9.66k stars 3.7k forks source link

Discovery: research keyboard handling for grid components #11851

Closed mlewand closed 2 years ago

mlewand commented 2 years ago

Provide a description of the task

Research best practices on how to handle grid navigation using the keyboard.

We have multiple grid-like UI components:

To make it clear: this issue is just discovery. It's meant just to figure out best way to implement it and see why we have it implemented the way we did. We also can make some PoC to see how much effort will it require to fix it.

Once we have figured how this should be solved, we can move on to each separate issue.

mlewand commented 2 years ago

There's a curious thing in how we handle grids as some of them have not predefined columns.

For example, list styles have responsive grid, based only on CSS. However font colors do have predefined columns count.

mlewand commented 2 years ago

As far as the implementation goes we might consider doing it as a helper rather than making this feature a UI component class.

An example of such composition-based approach is click outside handler: https://github.com/ckeditor/ckeditor5/blob/30286f77b39526fce2856b03b9be0ba4cc91d1c7/packages/ckeditor5-ui/src/bindings/clickoutsidehandler.js#L27

oleq commented 2 years ago

For the record, it looks like the table insertion grid should handle keyboard differently because when reaching the right boundary of the grid, the right arrow key should not move focus back to the first column (which would be expected in the color grid).

mmotyczynska commented 2 years ago

Yet another approach could be using a FocusCycler as it's already partly used in grid-based features. We'd have to enhance it for grids so e.g. the next/previous methods would 'know' that at some point a row of elements ends and we have to go to the beginning/end of the row instead of to the next/previous element. And of course we'd have to add vertical navigation as well for handling arrow up/down events.

We'd have to discuss if there should be one FocusCycler for everything or two FocusCyclers at the same time - one for main navigation and the second one for grid only.

Reinmar commented 2 years ago

BTW: https://github.com/ckeditor/ckeditor5/issues/5772

mmotyczynska commented 2 years ago

Navigation (tab vs arrow keys):

There should be two different navigation handled (they shouldnโ€™t be mixed together):

In case we decided using 2 focusCyclers, they will have to operate on two different levels - we cannot mix the levels in one focusCycler, e.g. cycling through sections of the view with tab key should be in a different focusCycler than moving between grid items with arrow keys.

The approaches discussed regarding focusCycler:

  1. Extend focusCycler to support 2D navigation
    • Has to be backward compatible: navigation through a vector and through grid elements
    • No 3D navigation: for sections 1D navigation (with tab) and for grid elements 2D navigation (arrow keys)
    • This extension would require one additional parameter: number of columns - the focusCycler should automatically switch to 2D mode
    • This extension would require 2 additional methods (focusUp and focusDown as focusPrevious and focusNext already exist)
    • Actually focusUp and focusDown are not good names, as focusPrevious and focusNext could actually mean right and left as well as up and down in case of 1D vertical dropdown
  2. Create a class inheriting from FocusCycler (e.g. GridFocusCycler) that adds additional constructor parameter and methods for navigation

3 possible solutions (for this ticket):

Actually we came to the conclusion that there are 3 ways of handling this issue:

  1. Create a helper and make no changes in current grids
  2. Create a helper and change current grids so they work the same
    • Seems a good option to have GridView class and a helper inside (and also we could use this helper for inserting tables) - this would be still flexible solution with not so many changes regarding using this API
    • But there is no such class as GridView - and it could be a good moment to create one (but it would take some time)
  3. Create new component for grids and no helper

We agreed that the best option would be 2 (helper + GridView class).ย 

Notes about the implementation of the GridView class:

Summary:

Decided:

mmotyczynska commented 2 years ago

A follow-up issue for keyboard navigation in color picker in table properties: #12193

mlewand commented 2 years ago

Edit: Extracted to #12224 - let's keep this epic focused on keyboard only.

We focused exclusively on keyboard handling so far - but we need to remember that semantical markup is core requirement for this component.

I started a research on markup that we should produce for accessible grid components. The benefit of semantically marked grid is that it will convey information that this is a 2 dimension widget (has rows and columns).

Other editors

Others simply donโ€™t implement it well. They simple are using options.

Available options

Rejected options