# Accessibility Extender

Learn how to use Wijmo's Accessibility Extender with FlexGrid in this tutorial

## Content

## Adding App-Specific Accessibility

Wijmo's FlexGrid control has extensive built-in accessibility support, but there may be situations where you want to extend that and provide additional support, specific to your application or user base.

To show how to extend functionality for accessibility support, we'll go through how to notify users when columns are sorted, as well as when a filter is applied:

```javascript
// Extend accessibility features
var acX = new AccessibilityExtender(theGrid);
// Notify users when columns are sorted
theGrid.sortedColumn.addHandler(function(s, e) {
    let col = s.columns[e.col];
    acX.alert('column ' + col.header + ' sorted in ' + (col.currentSort == '+' ? 'ascending' : 'descending') + ' order');
});

// Hook up to filter
var toSearch = null;
document.getElementById('filter').addEventListener('input', function(e) {
    clearTimeout(toSearch);
    toSearch = setTimeout(function () {
        var search = e.target.value, rx = new RegExp(search, 'i');
        theGrid.collectionView.filter = function (item) {
            return !search || JSON.stringify(item).match(rx) != null;
        };
        // notify users that a filter was applied
        setTimeout(function () {
            var msg = search ? 'grid filtered on ' + search : 'filter removed';
            msg += ': ' + theGrid.rows.length + ' items displayed';
            acX.alert(msg);
        }, 200);
    }, 900);
})
```

We create our accessibility extender and tie it to the FlexGrid by creating an **AccessibilityExtender** object and passing our FlexGrid as an arguement. We can then use this object's **alert** method to notify the user when the interact with the grid, whether that be filtering or sorting.

## Keyboard Handling

The FlexGrid uses Microsoft Excel as a model for many operations, including keyboard handling. However, we've made a few changes to keyboard handling logic to better accommodate accessibility:

1. **Ctrl+UP/DOWN**: Excel uses these keys to move the selection to the first/list rows of the grid, however, the control arrows are used extensivel by accessibility tools. So, FlexGrid instead uses **Alt+PAGEUP/DOWN** to navigate to the first and last rows instead.
2. **Tab**: In Excel, the **Tab** key is used to cycle through cells, but this interferes with default browser behavior, which is to move focus to the next element. The default behavior of FlexGrid is to let the browser handle the focus, but have added a `keyActionTab` property so users can revert to the Excel-like behavior.
3. **Enter**: We have added a `keyActionEnter` property that allows users to customize the behavior of the enter key.

The other keyboard commands used by FlexGrid follow the ARIA recommendations and are largely compatible with Excel.

| Keyboard Combination | Action Performed |
| -------------------- | ---------------- |
| Shift + Space | Select row |
| Ctrl + Space | Select column |
| Space | Start editing or toggle checkbox.<br>Expand or collapse the current level group. |
| Ctrl + A | Select the entire grid contents |
| Left/Right | Select the cell to the left/right of the selection |
| Shift + Left/Right | Extend the selection to include the cell to the left/right of the selection |
| Shift + Up/Down | Extend the selection to include the cell above/below the selection |
| Alt + Up/Down | Drop down the listbox editor for the current cell |
| PageUp/Down | Select the cell one page above/below the selection |
| Shift + PageUp/Down | Extend the selection to include the cell one page above/below the selection |
| Alt + PageUp/Down | Move the selection to the first/last row |
| Shift + Alt + PageUp/Down | Extend the selection to include the first/last row |
| Home/End | Move the selection to the first/last column |
| Shift + Home/End | Extend the selection to include the first/last column |
| Ctrl + Home/End | Move the selection to the first/last row and column |
| Shift + Ctrl + Home/End | Extend the selection to include the first/last row and column |
| Escape | Cancel current cell or row editing operation |
| Tab | Move the selection to the next focusable element on the page (can be overridden using the `keyActionTab` property) |
| Enter | Exit editing mode and move selection to the cell below the current one (can be overridden using the `keyActionEnter` property) |
| Delete, Backspace | Delete the currently selected rows (if `allowDelete` property is set to true), or clear content of the selected cells (if values are not required) |
| Ctrl + C or Ctrl + Insert | Copy the selection to the clipboard (if `autoClipboard` property is set to true) |
| Ctrl + V or Shift + Insert | Paste the content of the clipboard into the selected area (if `autoClipboard` property is set to true) |
| Ctrl + X | Copy the selection to the clipboard and clear or delete any selected content that can be modified (if the **autoClipboard** property is set to `true` and the **preventCut** property is set to `false`) |
| Ctrl + + | When `allowAddNew` is true, insert a new blank row above the current active cell (`+` key on numpad) |
| Ctrl + - | When `allowDelete` is true, delete the row where the active cell is located (`-` key on numpad) |
| Ctrl + Shift + P | Pin/unpin the column where the active cell is located |
| Ctrl + Shift + F | Open the column filter where the active cell is located |
| Ctrl + Shift + S | Sort the column where the active cell is located |
| Ctrl + Alt + F | Freeze all rows and columns before the active cell |
| Shift + ←/→ | Move column left/right (focus on column header, requires `allowDragging` and `headersFocusability`) |
| Shift + ↑/↓ | Move row up/down (focus on row header, requires `allowDragging` and `headersFocusability`) |
| Alt + ←/→ | Decrease/increase column width (requires `allowResizing`, default step: 2px, adjust via `FlexGrid`.`SHORTCUT\_KEY\_RESIZE\_GAP`; When `deferResizing` is enabled, enters preview mode — press `Enter` to apply or `Escape` to cancel) |
| Alt + ↑/↓ | Decrease/increase row height (requires `allowResizing`, default step: 2px, adjust via `FlexGrid`.`SHORTCUT\_KEY\_RESIZE\_GAP`; When `deferResizing` is enabled, enters preview mode — press `Enter` to apply or `Escape` to cancel) |

>type=note
> **Built-in Cut Handling Behavior**
> The cut operation performs two steps:
>
> 1. Copies the selected content to the clipboard.
> 2. Clears only the selected content that can be modified.
>
> The following rules apply:
>
> * Read-only or non-editable cells are copied but not cleared.
> * If the copy operation is canceled or does not complete, no content is removed.
> * If both editable and non-editable cells are selected, only editable cell content is cleared.
>
> Set `preventCut` to `true` to disable the built-in cut handling and allow custom shortcut logic.

## Click Event Handling

FlexGrid avoids adding event handlers to child elements, instead attaching them to the grid's host element. It then forwards the commands to the appropriate child elements based on hit-testing logic. This presents some problems in accessibility scenarios that expect to get references to child elements and fire events in code by invoking the child element's "click" methods directly.

To accommodate this scenario, Wijmo now has a new **HitTest** constructor that takes an element as a parameter and builds the necessary hit-test information so the grid can honor click events fires in code. For example, you can generate a "click" event on a column header using the following code:

```javascript
// Get the header cell
var headerCell = grid.columnHeaders.getCellElement(0,0);
// Invoke the “click” event on the header cell
headerCell.click();
```

Or, you could drop down the filter editor for a given column using this code:

```javascript
// Get the filter glyph element using a CSS selector
var selector = '.wj-flexgrid .wj-colheaders .wj-cell .wj-elem-filter'; var filterBtn = grid.hostElement.querySelector(selector);  
columnHeaders.getCellElement(0, 0);  
// Invoke the “click” event on the filter glyph  
filterBtn.click();  
```

You can follow the same approach to simulate clicks and select cells, expand/collapse nodes, drop down list boxes associated with cells, etc.