Javascript NVDA屏幕阅读器未按预期切换到聚焦模式
我有一个简单的代码块,在使用NVDA屏幕阅读器时,我试图让键盘可以访问 具体来说,我有一个角色为“button”的div,另一个角色为“button”的div嵌套在其中。每个div都有一个不同的onkeydown事件,当用户点击该div并按下“enter”时,该事件将被触发 当我没有打开NVDA屏幕阅读器时,这个键盘功能可以正常工作 但是,当我打开屏幕阅读器时,嵌套的keydown事件不再触发。相反,即使嵌套事件具有焦点,也只会激发父事件 但是,如果我手动将NVDA从“浏览模式”更改为“焦点模式”(通过按NVDA键+空格键),则按键事件将再次按需要工作 不幸的是,我不能期望使用NVDA的人知道手动切换到“聚焦模式”。它要么需要自动切换到“焦点模式”,要么需要在“浏览模式”下工作 代码如下: HTML:Javascript NVDA屏幕阅读器未按预期切换到聚焦模式,javascript,accessibility,nvda,Javascript,Accessibility,Nvda,我有一个简单的代码块,在使用NVDA屏幕阅读器时,我试图让键盘可以访问 具体来说,我有一个角色为“button”的div,另一个角色为“button”的div嵌套在其中。每个div都有一个不同的onkeydown事件,当用户点击该div并按下“enter”时,该事件将被触发 当我没有打开NVDA屏幕阅读器时,这个键盘功能可以正常工作 但是,当我打开屏幕阅读器时,嵌套的keydown事件不再触发。相反,即使嵌套事件具有焦点,也只会激发父事件 但是,如果我手动将NVDA从“浏览模式”更改为“焦点模式
外分区
内分区
JavaScript:
function outerDivAction(event) {
event.stopPropagation();
console.log('outer div');
$('.result').html('<p>outer div!</p>');
}
function innerDivAction(event) {
event.stopPropagation();
console.log('inner div')
$('.result').html('<p>inner div!</p>');
}
function keyEvent(event, callback) {
event.stopPropagation();
if (event.which === 13) {
callback(event);
}
}
$('.outerDiv').click(outerDivAction);
$('.innderDiv').click(innerDivAction);
功能输出(事件){
event.stopPropagation();
控制台日志(“外部分区”);
$('.result').html('outerdiv!');
}
函数innerDivAction(事件){
event.stopPropagation();
console.log('internaldiv')
$('.result').html('内部div!');
}
函数keyEvent(事件,回调){
event.stopPropagation();
if(event.which==13){
回调(事件);
}
}
$('.outerDiv')。单击(outerDivAction);
$('.innderDiv')。单击(innerDivAction);
您也可以在此处查看代码笔:
任何人能提供的任何帮助都将不胜感激
p、 美国。
我知道,如果我取下嵌套的div并将其移动,使其不再嵌套,而是成为第一个div的兄弟,那么一切都会按预期工作。不幸的是,这不是一个选择。div需要嵌套。这不是NVDA中的错误 首先,不能有嵌套的可单击元素。明确地不能嵌套链接和按钮。不能在按钮中嵌套链接,也不能在链接中嵌套按钮。还有其他类型的值得研究,以供将来参考 您可能会发现您的代码在技术上是有效的,但这只是因为您编写的是一个谎言 您没有使用正确的元素(
),而是选择将角色=按钮
置于
上。HTML验证器将传递您的代码,因为它可以有效地嵌套
但是,通过给它们每个role=button
,您已经指示用户代理将它们视为
(减去它们带来的所有好处,如可访问性、键处理程序、语义等)
现在,让我们返回并再次验证该代码,因为用户代理将看到它(作为嵌套的
s)。W3C Nu HTML检查器将失败(我知道,因为我运行了一个测试):
错误:已看到开始标记按钮
,但相同类型的元素已打开
我的建议是:
- 为了不让它们筑巢
- 将它们转换为
s - 删除无效的
(您不需要)tabindex=1
- 取消对密钥代码的检查,因为
免费提供密钥代码(包括字符32) - 把你的
变成一个(有) - 并在按钮周围放置一个包装,以提供所需的视觉效果
<div class="wrapper">
<button class="outerDiv">
Outer Div
</button>
<button class="innderDiv">
Inner Div
</button>
</div>
<div class="result" role="alert" aria-live="assertive"></div>
外分区
内分区
如果您感兴趣,则(APG)提供了如何使各种设计模式可访问的指导。它还包括一个关于您所描述内容的示例:其中包括带有子菜单的菜单的代码示例。感谢您花时间提供如此全面的解释。不幸的是,这将很难实现,因为我正在开发的实际规范是一个导航,其中一些项具有与其关联的下拉菜单,然后这些下拉项具有一个显示为弹出菜单的附加子菜单。这些项目中的每一项有时都可以是按钮(打开子菜单)或链接,因此目前我使用JavaScript将它们从role=“button”动态更改为role=“link”。元素嵌套的原因是因为子菜单是父项的子项。为了避免嵌套按钮,您是否可以重新构造代码以使用带有嵌套子列表(包含按钮)的列表?根据列表项的焦点(或按钮切换)控制可见性需要更多的努力,但它避免了@aardrian提到的嵌套交互内容。这里有一个代码笔来说明我的意思:@jennEDVT,你可能除了重构之外别无选择,因为你总是会遇到辅助技术的问题。Skerrvy提供了一个很好的快速演示,展示了您可以尝试的功能。另外,寻找可以修改的现有模式。例如,Adobe有一个复杂的大菜单,虽然对大多数网站来说太多了,但可能是一个合适的选择?感谢所有的建议和资源。听起来重构已经准备好了。请编辑一些代码,以帮助OP理解您的答案。只有链接的答案(指解决方案本身作为链接呈现,而不在帖子中解释的任何答案,即使存在其他非链接文本)通常不受欢迎,因为如果链接断开,这些答案可能会失效,并且在过去被用于自我推广。感谢您提供的资源!
<div class="wrapper">
<button class="outerDiv">
Outer Div
</button>
<button class="innderDiv">
Inner Div
</button>
</div>
<div class="result" role="alert" aria-live="assertive"></div>