Files
AtreidesAssetsFree/tests/ui/table-focus.test.mjs
T

107 lines
4.7 KiB
JavaScript
Raw Permalink Normal View History

2026-10-29 11:57:29 +01:00
// Generated, do not edit. sha256:2fdb7171652c771313af8580672b3d94500711ca104d4251cc8f2c61d162cd16
import { describe, it } from 'node:test';
import assert from 'node:assert/strict';
import { installDom } from '../helpers/mini-dom.mjs';
const dom = installDom();
const { captureFocus, restoreFocus, focusFirstField } = await import('../../client/ui/table-focus.js');
const ROW = '<table><tbody><tr data-edit-row="1">'
+ '<td><input data-field="name" value="abcdef"></td>'
+ '<td><input type="date" data-field="day" value="2026-10-18"></td>'
+ '<td><div class="conv-field"><input data-field="amount"><button data-convert="amount">c</button></div></td>'
+ '<td><button data-save="1">s</button></td>'
+ '</tr></tbody></table>';
const table = (html = ROW) => { const el = dom.host(); el.innerHTML = html; return el; };
describe('captureFocus', () => {
it('a text field: its selector and the caret', () => {
const el = table();
const f = el.querySelector('[data-field="name"]');
f.focus();
f.setSelectionRange(2, 4);
assert.deepEqual(captureFocus(el, true), { sel: '[data-field="name"]', start: 2, end: 4 });
});
it('a date field: the selector without a caret, which a browser would refuse to read', () => {
const el = table();
el.querySelector('[data-field="day"]').focus();
assert.deepEqual(captureFocus(el, true), { sel: '[data-field="day"]', start: null, end: null });
});
it('the convert button next to an amount is an anchor of its own, and so is save', () => {
const el = table();
el.querySelector('[data-convert]').focus();
assert.deepEqual(captureFocus(el, true), { sel: '[data-convert="amount"]', start: null, end: null });
el.querySelector('[data-save]').focus();
assert.equal(captureFocus(el, true).sel, '[data-save="1"]');
});
it('nothing outside editing, nothing when the focus is in another table, nothing without an anchor', () => {
const el = table();
el.querySelector('[data-field="name"]').focus();
assert.equal(captureFocus(el, false), null);
const other = table();
assert.equal(captureFocus(other, true), null);
const plain = table('<span tabindex="0">x</span>');
plain.querySelector('span').focus();
assert.equal(captureFocus(plain, true), null);
});
});
describe('restoreFocus', () => {
it('finds the field back in the NEW markup and restores the caret', () => {
const el = table();
const f = el.querySelector('[data-field="name"]');
f.focus();
f.setSelectionRange(1, 3);
const snap = captureFocus(el, true);
el.innerHTML = ROW;
restoreFocus(el, snap);
const again = el.querySelector('[data-field="name"]');
assert.ok(dom.document.activeElement === again, 'focus on the new field');
assert.deepEqual([again.selectionStart, again.selectionEnd], [1, 3]);
});
it('a field that disappeared, or no snapshot, leaves the focus alone', () => {
const el = table();
const before = dom.document.activeElement;
restoreFocus(el, { sel: '[data-field="gone"]', start: null, end: null });
restoreFocus(el, null);
assert.ok(dom.document.activeElement === before);
});
it('a field whose type changed gets the focus without the caret, and does not throw', () => {
const el = table();
const f = el.querySelector('[data-field="name"]');
f.focus();
const snap = captureFocus(el, true);
el.innerHTML = '<input type="date" data-field="name">';
restoreFocus(el, snap);
assert.equal(dom.document.activeElement.getAttribute('type'), 'date');
});
});
describe('focusFirstField', () => {
it('the first enabled, visible field of the edit row', () => {
const el = table('<table><tbody><tr data-edit-row="1"><td><input type="hidden" data-field="h"><input disabled data-field="d"><select data-field="s"></select></td></tr></tbody></table>');
focusFirstField(el);
assert.equal(dom.document.activeElement.dataset.field, 's');
});
it('falls back to the drawer row only when the row itself has nothing', () => {
const el = table('<table><tbody><tr data-edit-row="1"><td></td></tr><tr class="edit-expand-row"><td><textarea data-field="note"></textarea></td></tr></tbody></table>');
focusFirstField(el);
assert.equal(dom.document.activeElement.dataset.field, 'note');
const both = table('<table><tbody><tr data-edit-row="1"><td><input data-field="a"></td></tr><tr class="edit-expand-row"><td><textarea data-field="note"></textarea></td></tr></tbody></table>');
focusFirstField(both);
assert.equal(dom.document.activeElement.dataset.field, 'a');
});
it('no edit row: nothing happens', () => {
const el = table('<p>x</p>');
const before = dom.document.activeElement;
focusFirstField(el);
assert.ok(dom.document.activeElement === before);
});
});