sma*_*use 6 accessibility modal-dialog wai-aria semantic-ui wcag2.0
我正在用Angular和开发一个应用程序Semantic-UI.应用程序应该是可访问的,这意味着它应该符合WCAG 2.0.为了达到这个目的,模态应该在对话框中保持焦点,并防止用户走出去或在位于模态下的页面元素之间移动"标签".
我找到了一些工作示例,如下所示:
dialogHTML 5.1元素:https://demo.agektmr.com/dialog这是我尝试用Semantic-UI创建一个可访问的模态:https://plnkr.co/edit/HjhkZg
如您所见,我使用了以下属性:
role="dialog"
aria-labelledby="modal-title"
aria-modal="true"
但他们没有解决我的问题.你有没有办法让我的模态保持专注,只有当用户点击取消/确认按钮时才会失去它?
目前还没有简单的方法来实现这一目标.将惰性属性提出来尝试做任何元素与属性,这一切来解决这个问题的孩子无法访问.但是,采用速度很慢,直到最近它才落在Chrome Canary后面的旗帜上.
另一个提出的解决方案是创建一个本机API,它将跟踪模态堆栈,实质上使当前不是堆栈顶部的所有内容都是惰性的.我不确定提案的状态,但看起来不会很快实施.
不幸的是,没有一个好的解 一种流行的解决方案是创建所有已知可聚焦元素的查询选择器,然后通过向模态中的最后和第一个元素添加keydown事件来将焦点捕获到模态.但是,随着Web组件和shadow DOM的兴起,此解决方案无法再找到所有可聚焦元素.
如果你总是控制对话框中的所有元素(并且你没有创建一个通用的对话框库),那么最简单的方法就是在第一个和最后一个可聚焦元素上为keydown添加一个事件监听器,检查是否为tab或使用了shift选项卡,然后将第一个或最后一个元素聚焦到陷阱焦点.
如果你正在创建一个通用的对话框库,我发现的唯一合理的工作就是使用惰性polyfill或者使模态外的所有东西都有tabindex=-1.
var nonModalNodes;
function openDialog() {
var modalNodes = Array.from( document.querySelectorAll('dialog *') );
// by only finding elements that do not have tabindex="-1" we ensure we don't
// corrupt the previous state of the element if a modal was already open
nonModalNodes = document.querySelectorAll('body *:not(dialog):not([tabindex="-1"])');
for (var i = 0; i < nonModalNodes.length; i++) {
var node = nonModalNodes[i];
if (!modalNodes.includes(node)) {
// save the previous tabindex state so we can restore it on close
node._prevTabindex = node.getAttribute('tabindex');
node.setAttribute('tabindex', -1);
// tabindex=-1 does not prevent the mouse from focusing the node (which
// would show a focus outline around the element). prevent this by disabling
// outline styles while the modal is open
// @see https://www.sitepoint.com/when-do-elements-take-the-focus/
node.style.outline = 'none';
}
}
}
function closeDialog() {
// close the modal and restore tabindex
if (this.type === 'modal') {
document.body.style.overflow = null;
// restore or remove tabindex from nodes
for (var i = 0; i < nonModalNodes.length; i++) {
var node = nonModalNodes[i];
if (node._prevTabindex) {
node.setAttribute('tabindex', node._prevTabindex);
node._prevTabindex = null;
}
else {
node.removeAttribute('tabindex');
}
node.style.outline = null;
}
}
}
Run Code Online (Sandbox Code Playgroud)
不同的“工作示例”在屏幕阅读器中无法正常工作。
它们不会将屏幕阅读器的视觉焦点困在模态中。
为此,您必须:
aria-hidden在任何其他节点上设置属性禁用这些树中的键盘可聚焦元素(链接使用tabindex=-1,控件使用disabled,...)
:focusable伪选择器可用于查找可聚焦元素。在页面上添加一个透明层以禁用鼠标选择。
pointer-events: none在浏览器使用非 SVG 元素处理它时使用 css属性,而不是在 IE 中