带有溢出自动的Div在Chrome中无法进行制表符聚焦



我有两个具有最大高度和溢出自动的div。一个div不溢出,另一个则溢出。可滚动的div可以用键盘滚动,但Firefox和Chrome的行为不同:

  • Firefox:即使我没有在可滚动的div上指定选项卡索引,它也是可选项卡聚焦的。无法滚动的div无法聚焦。这是我想要的一个很好的默认行为
  • Chrome:除非我添加了tabindex="0"来强制它,否则可滚动的div不能以选项卡为中心。在我的用例中,每个div的内容都是用户生成的,我不知道它是否会溢出,所以我不能只将tabindex="0"应用于所有div,因为它会使不可滚动的divs聚焦,而我不希望这样

请注意,如果您先单击div,然后按上/下箭头,Chrome允许滚动可滚动的div,但这实际上并不能聚焦div(div不会变成document.activeElement(。Chrome似乎记得上次点击哪个元素。这不是一个键盘唯一的解决方案,我正在寻找。

基本上,我希望Chrome在这种情况下能像Firefox一样工作。这可能吗?也许Chrome中有一个可访问性设置可以实现这一点(我找不到(。在Chrome中,只有键盘的用户将如何处理这种情况?

div {
overflow: auto;
max-height: 50px;
border: 1px solid black;
margin: 10px 0;
}
div:focus {
outline: 2px solid blue;
}
<div>
Text does not overflow, not scrollable and should not receive tab focus.
</div>
<div>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.
</div>

假设这些用户只是键盘用户,而不是屏幕阅读器用户(因为他们会使用不同的控件(,最简单的方法是使用一点JavaScript,如果元素有滚动条(垂直和水平(,则添加tabindex="0"

一行JavaScript 就可以计算出一个元素是有垂直滚动条还是水平滚动条

if(el.scrollWidth > el.clientWidth || el.scrollHeight > el.clientHeight){//scrollable}

我在下面包含了一个示例,其中如果容器有滚动条,我会在容器上设置tabindex="0"

如果这些div的内容可能会发生变化,您可能需要使用突变观测器来侦听这些变化。

我在下面的例子中也为您介绍了这一点。

var els = document.querySelectorAll('.isItScrollable');
//observer setup
var observer = new MutationObserver(mutatedDiv);
var objConfig = {
childList: true,
subtree : true,
attributes: false, 
characterData : false
};
//see if the scroll width or height is larger than the client width or height
function isScrollable(el){
if(el.scrollWidth > el.clientWidth || el.scrollHeight > el.clientHeight){
return true;
}
return false;
}

for(var x = 0; x < els.length; x++){
var el = els[x];
//check whether the element is scrollable initially.
if(isScrollable(el)){
el.setAttribute('tabindex', 0);
}
//use an observer to check for a change so we can check if the content updates
observer.observe(el, objConfig);
}
//observer callback function
function mutatedDiv (mutations) {
mutations.forEach(function(mutation) {
if(isScrollable(mutation.target)){
mutation.target.setAttribute('tabindex', 0);
}else{
mutation.target.removeAttribute('tabindex');
}
});
}

////////////not relevant, just for demo
var add1 = document.querySelector('.addone');
add1.addEventListener("click", function(e){
els[0].innerHTML = "Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br> Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br> Text overflows and should be tab focusable so that it can be scrolled with the keyboard.";
});
var remove1 = document.querySelector('.removeone');
remove1.addEventListener("click", function(e){
els[0].innerHTML = "Text does not overflow, not scrollable and should not receive tab focus."
});
var add2 = document.querySelector('.addtwo');
add2.addEventListener("click", function(e){
els[1].innerHTML = "Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br> Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br> Text overflows and should be tab focusable so that it can be scrolled with the keyboard.";
});
var remove2 = document.querySelector('.removetwo');
remove2.addEventListener("click", function(e){
els[1].innerHTML = "Text does not overflow, not scrollable and should not receive tab focus."
});


.isItScrollable {
overflow: auto;
max-height: 50px;
border: 1px solid black;
margin: 10px 0;
}
.isItScrollable:focus {
outline: 2px solid blue;
}
<div class="isItScrollable">
Text does not overflow, not scrollable and should not receive tab focus.
</div>
<div class="isItScrollable">
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.<br>
Text overflows and should be tab focusable so that it can be scrolled with the keyboard.
</div>
<button class="addone">Add Text Div One</button>
<button class="removeone">Reset Text Div One</button>
<button class="addtwo">Add Text Div Two</button>
<button class="removetwo">Remove Text Div Two</button>

最新更新