使用 Tab 键将焦点从数据网格移动到下一个页面元素
Using tab key to move focus from data grid to next page element
使用 AG-Grid,我需要能够按下 tab 键并将焦点元素从当前选择的 grid/cell 更改为页面上网格外的下一个元素。问题是 Tab 键似乎被锁定在网格内,不会移动到数据 table 之外的下一个元素。
我在存储最后一个聚焦单元格的单元格上有一个均匀的监听器(用于存储最后一个位置以便能够切换回网格到先前聚焦的单元格),但需要有下一个聚焦单元格在数据网格之外:
const cells = document.getElementsByClassName('ag-cell');
[...cells].map(cell => {
cell.addEventListener("keydown", function(e) {
if(e.key === "Tab") {
let lastCell = cell.attributes[2].value;
console.log("Last Cell Focused: ", lastCell)
}
})
})
如何将焦点选择从按键时的网格移至下一个可聚焦页面元素?
这是当前网格的 link plnkr:Link
============================================= ========
更新
我已经更新了我的代码,而不是将事件侦听器附加到每个单元格,它现在正在寻找在文档上触发的事件。但是,我仍然 运行 无法获得 last_cell
值并在 hasFocusVisible
.
上看到 focus-visible
class
//on arrow right if last_call === header that has 'focus-visible', set focus to first cell in body
const headerCells = document.getElementsByClassName('ag-header-cell-label');
const last_cell = headerCells[headerCells.length-1].attributes[2];
const hasFocusVisible = document.querySelector('.ag-header-cell-label').classList.contains('focus-visible');
document.addEventListener("keydown", function(e) {
if(e.key === "ArrowRight") {
// if(hasFocusVisible && last_cell) {
console.log("EVENT TRIGGERED FROM: ", event.target, "Last Cell Value: ", last_cell, hasFocusVisible);
//if last_call and 'ag-header-cell-label' has 'focus-visible', set focus to first cell in body
const bodyCell = document.getElementsByClassName('ag-cell')[0];
// }
}
});
更新的 Plnkr:Link
============================================= =======
更新 2
我已将元素选择器更新为以下内容:
const last_cell = document.querySelector('.ag-header-cell:last-child');
const hasFocusVisible = document.querySelector('.ag-header-cell-label').classList.contains('.focus-visible');
document.addEventListener("keydown", function(e) {
console.log('document.activeElement', document.activeElement)
const activeElement = document.activeElement;
if(e.key === "ArrowRight" && activeElement) {
if(last_cell) {
console.log("EVENT TRIGGERED FROM: ", event.target, "Last Cell Value: ", last_cell, hasFocusVisible);
//if last_call and 'ag-header-cell-label' has 'focus-visible', set focus to first cell in body
const bodyCell = document.getElementsByClassName('ag-cell')[0];
}
}
else if(e.key === "ArrowDown"){
//look for first child in first row with same id as header and set focus
document.querySelector('.ag-cell').focus();
}
});
然而,hasFocusVisible
变量总是在注销 div 时出现 false
,该 div 具有焦点可见 class。我不确定我的逻辑是否不正确,或者当事件侦听器被触发时它无法在 ag-header-cell-label
上获得 focus-visible
class。
如果选项卡在单元格内有效,请不要向每个单元格添加侦听器,只需将一个侦听器添加到文档中,然后手动将焦点移至您知道的页面上的下一个内容。例如:
var b = document.querySelector('button');
b.passThrough = true;
b.update = pass => {
b.passThrough = pass;
b.textContent = "click me to " + (b.passThrough ? "block" : "allow") + " tabbing";
}
b.addEventListener('click', e => b.update(!b.passThrough));
b.update(b.passThrough);
var focussable = Array.from(
document.querySelectorAll([
'button',
'[href]',
'input',
'select',
'textarea',
'[tabindex]:not([tabindex="-1"])'
].join(','))
);
// let's pretend this is your last cell.
var p = document.querySelector('p');
// make it kill off keydown events, BUT, also have it redirect focus
// to "the next focussable element", so you can see what that code looks like.
p.addEventListener('keydown', e => e.preventDefault());
document.addEventListener('keydown', e => {
if (b.passThrough && e.target === p) {
var next = focussable.indexOf(p) + 1;
focussable[next % focussable.length].focus();
}
});
<button>toggle</button>
<p tabindex=0>first</p>
<a href="#top">second</a>
<a href="#top">third</a>
运行 这段代码,单击按钮,点击选项卡,注意选项卡事件现在被捕获(就像在您的单元格中一样)。现在,再次单击该按钮,点击 tab,再次点击 tab:注意它 似乎 事件不再被困,而事实是:元素本身的事件正在被杀死关闭,但是 document 的事件侦听器现在明确地为我们移动了焦点。
使用 AG-Grid,我需要能够按下 tab 键并将焦点元素从当前选择的 grid/cell 更改为页面上网格外的下一个元素。问题是 Tab 键似乎被锁定在网格内,不会移动到数据 table 之外的下一个元素。
我在存储最后一个聚焦单元格的单元格上有一个均匀的监听器(用于存储最后一个位置以便能够切换回网格到先前聚焦的单元格),但需要有下一个聚焦单元格在数据网格之外:
const cells = document.getElementsByClassName('ag-cell');
[...cells].map(cell => {
cell.addEventListener("keydown", function(e) {
if(e.key === "Tab") {
let lastCell = cell.attributes[2].value;
console.log("Last Cell Focused: ", lastCell)
}
})
})
如何将焦点选择从按键时的网格移至下一个可聚焦页面元素?
这是当前网格的 link plnkr:Link
============================================= ========
更新
我已经更新了我的代码,而不是将事件侦听器附加到每个单元格,它现在正在寻找在文档上触发的事件。但是,我仍然 运行 无法获得 last_cell
值并在 hasFocusVisible
.
focus-visible
class
//on arrow right if last_call === header that has 'focus-visible', set focus to first cell in body
const headerCells = document.getElementsByClassName('ag-header-cell-label');
const last_cell = headerCells[headerCells.length-1].attributes[2];
const hasFocusVisible = document.querySelector('.ag-header-cell-label').classList.contains('focus-visible');
document.addEventListener("keydown", function(e) {
if(e.key === "ArrowRight") {
// if(hasFocusVisible && last_cell) {
console.log("EVENT TRIGGERED FROM: ", event.target, "Last Cell Value: ", last_cell, hasFocusVisible);
//if last_call and 'ag-header-cell-label' has 'focus-visible', set focus to first cell in body
const bodyCell = document.getElementsByClassName('ag-cell')[0];
// }
}
});
更新的 Plnkr:Link
============================================= =======
更新 2
我已将元素选择器更新为以下内容:
const last_cell = document.querySelector('.ag-header-cell:last-child');
const hasFocusVisible = document.querySelector('.ag-header-cell-label').classList.contains('.focus-visible');
document.addEventListener("keydown", function(e) {
console.log('document.activeElement', document.activeElement)
const activeElement = document.activeElement;
if(e.key === "ArrowRight" && activeElement) {
if(last_cell) {
console.log("EVENT TRIGGERED FROM: ", event.target, "Last Cell Value: ", last_cell, hasFocusVisible);
//if last_call and 'ag-header-cell-label' has 'focus-visible', set focus to first cell in body
const bodyCell = document.getElementsByClassName('ag-cell')[0];
}
}
else if(e.key === "ArrowDown"){
//look for first child in first row with same id as header and set focus
document.querySelector('.ag-cell').focus();
}
});
然而,hasFocusVisible
变量总是在注销 div 时出现 false
,该 div 具有焦点可见 class。我不确定我的逻辑是否不正确,或者当事件侦听器被触发时它无法在 ag-header-cell-label
上获得 focus-visible
class。
如果选项卡在单元格内有效,请不要向每个单元格添加侦听器,只需将一个侦听器添加到文档中,然后手动将焦点移至您知道的页面上的下一个内容。例如:
var b = document.querySelector('button');
b.passThrough = true;
b.update = pass => {
b.passThrough = pass;
b.textContent = "click me to " + (b.passThrough ? "block" : "allow") + " tabbing";
}
b.addEventListener('click', e => b.update(!b.passThrough));
b.update(b.passThrough);
var focussable = Array.from(
document.querySelectorAll([
'button',
'[href]',
'input',
'select',
'textarea',
'[tabindex]:not([tabindex="-1"])'
].join(','))
);
// let's pretend this is your last cell.
var p = document.querySelector('p');
// make it kill off keydown events, BUT, also have it redirect focus
// to "the next focussable element", so you can see what that code looks like.
p.addEventListener('keydown', e => e.preventDefault());
document.addEventListener('keydown', e => {
if (b.passThrough && e.target === p) {
var next = focussable.indexOf(p) + 1;
focussable[next % focussable.length].focus();
}
});
<button>toggle</button>
<p tabindex=0>first</p>
<a href="#top">second</a>
<a href="#top">third</a>
运行 这段代码,单击按钮,点击选项卡,注意选项卡事件现在被捕获(就像在您的单元格中一样)。现在,再次单击该按钮,点击 tab,再次点击 tab:注意它 似乎 事件不再被困,而事实是:元素本身的事件正在被杀死关闭,但是 document 的事件侦听器现在明确地为我们移动了焦点。