React:可访问的无序列表按钮

React: accessible unordered list of buttons

我正在创建一个无序列表的按钮,并且想让它易于访问。 (注意: 我找到了 ,但它没有回答我的问题。)

我的代码(经过简化,在 React 中)如下所示:

import React from "react";
import "./styles.css";

const items = [1,2,3,4,5];

const renderListItem = (_, index) => (
  <li key={index}>
    <button>Button {index}</button>
  </li>
);

export default function App() {
  return (
    <main className="App">
      <button>Foo</button>
      <button>Bar</button>

      <ul tabIndex="0">
        {items.map(renderListItem)}
      </ul>

      <button>Baz</button>
    </main>
  );
}

我能够通过将 tabIndex 设为 0 来使 ul 可制表。

我的问题是用户仍然可以通过选项卡浏览每个列表项。在我的实际应用程序中,该列表由几十个按钮组成,我觉得对于依赖 a11y 必须通过所有按钮切换的人来说,这将是一个糟糕的用户体验。我读过,最佳做法是使 ul 成为可选项卡(就像我所做的那样),然后允许他们使用“space”进入列表并使用箭头键导航列表,以便他们可以随时跳出到下一个元素。

我怎么能在 React 中做这样的事情?我想学习如何:

  1. 使用“space”输入列表。
  2. 将按钮设置为“untabbable”,而不是...
  3. 使用箭头键在按钮之间导航焦点。

如果您有几个这样的长组案例,您可能还应该提供其他导航方式。例如,标题允许屏幕 reader 用户跳过此类组或针对特定组。

关于选项卡导航:我偶然发现了一种称为 roving tabindex 的模式,在 MDN's Keyboard-navigable JavaScript widgets page

上有很好的解释

技术实现如下:

  • 不要使容器可聚焦
  • 通过将所有其他项目赋予 tabindex="-1"
  • ,仅使列表(菜单)中的第一项可聚焦
  • 添加 React 逻辑以通过箭头键在项目之间移动(隐式)tabindex="0" 属性

似乎 npm package react-roving-tabindex 已经实现了该逻辑,即使 grid-navigation。

否则 quick-fix 可能会在允许跳过它们的按钮列表之前提供一个隐藏的 skip link。我假设您正在为列表提供标题?

<hX>Title explaining the group</hX>
<p><a href="#skip-buttons">Skip group</a></p>
<ul>
<li><button>Button 1</button></li>
…
</ul>

<button id="skip-buttons">Baz</button>