Make list-rows.js answer both the old and new row hooks
Missed in the card rewrite: <x-card> now renders data-md-list-row, data-md-list-open and data-md-list-actionable, but list-rows.js still queried only the unprefixed data-list-row/-open/-actionable, so a card's row press and its actionable Enter/Space stopped working. <x-list-item>, still unrewritten until the next commit, keeps rendering the old names, so the script answers both for now (the same transition interaction.css already makes for data-md-dragged), and the fallback comes out once list-item moves too. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Qwx5USif3wFFmxtHg5U1g9
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
f04e31b3aa
commit
5cb11cd127
+24
-13
@@ -1,26 +1,37 @@
|
|||||||
/**
|
/**
|
||||||
* A row opens from anywhere on it.
|
* A row opens from anywhere on it.
|
||||||
*
|
*
|
||||||
* A row is `data-list-row` — an `<x-list-item>`, an `<x-card>`, a table row — and exactly one
|
* A row is `data-md-list-row` (or the older, unprefixed `data-list-row`, while a component that
|
||||||
* control inside it is its opener, `data-list-open`: the title button that opens a sheet, or the
|
* has not yet moved off it still renders it) — an `<x-list-item>`, an `<x-card>`, a table row —
|
||||||
* link that goes to the item's page. A click anywhere else on the row is handed to the opener, so
|
* and exactly one control inside it is its opener, `data-md-list-open` (or `data-list-open`): the
|
||||||
* the whole row is the target while the opener stays a real control — the tab stop, the name a
|
* title button that opens a sheet, or the link that goes to the item's page. A click anywhere else
|
||||||
* screen reader reads, and the owner of the `wire:click` or the `href`. The row's other controls
|
* on the row is handed to the opener, so the whole row is the target while the opener stays a real
|
||||||
* keep their own clicks. How a row looks while that happens is resources/css/components/list.css.
|
* control — the tab stop, the name a screen reader reads, and the owner of the `wire:click` or the
|
||||||
|
* `href`. The row's other controls keep their own clicks. How a row looks while that happens is
|
||||||
|
* resources/css/components/card.css and list.css.
|
||||||
*
|
*
|
||||||
* Not a stretched link (`::after { inset: 0 }`): Safari makes no containing block of a <tr>, so in
|
* Not a stretched link (`::after { inset: 0 }`): Safari makes no containing block of a <tr>, so in
|
||||||
* a table every overlay would cover the whole table; and not one <button> around the row, which
|
* a table every overlay would cover the whole table; and not one <button> around the row, which
|
||||||
* could hold no other buttons. The listeners sit on `document` and are added once.
|
* could hold no other buttons. The listeners sit on `document` and are added once.
|
||||||
*
|
*
|
||||||
* A row that is also `data-list-actionable` is M3's **directly actionable card** (`<x-card
|
* A row that is also `data-md-list-actionable` (or `data-list-actionable`) is M3's **directly
|
||||||
* actionable>`): the card is the one tab stop, so Enter and Space on the card reach the opener,
|
* actionable card** (`<x-card actionable>`): the card is the one tab stop, so Enter and Space on
|
||||||
* and the card's other actions follow it in the tab order with their own keys. The opener itself
|
* the card reach the opener, and the card's other actions follow it in the tab order with their
|
||||||
* carries `tabindex="-1"`, which the card's caller writes.
|
* own keys. The opener itself carries `tabindex="-1"`, which the card's caller writes.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/** Anything that answers a click itself — the row's own controls, and the opener. */
|
/** Anything that answers a click itself — the row's own controls, and the opener. */
|
||||||
const CONTROLS = 'a, button, input, select, textarea, label, summary, [contenteditable]'
|
const CONTROLS = 'a, button, input, select, textarea, label, summary, [contenteditable]'
|
||||||
|
|
||||||
|
/** A row, under either its current or its older hook. */
|
||||||
|
const ROW = '[data-md-list-row], [data-list-row]'
|
||||||
|
|
||||||
|
/** A row's opener, under either its current or its older hook. */
|
||||||
|
const OPENER = '[data-md-list-open], [data-list-open]'
|
||||||
|
|
||||||
|
/** A directly actionable row, under either its current or its older hook. */
|
||||||
|
const ACTIONABLE = '[data-md-list-actionable], [data-list-actionable]'
|
||||||
|
|
||||||
/** How far a pointer may travel between press and release and still be a click. */
|
/** How far a pointer may travel between press and release and still be a click. */
|
||||||
const DRAG_PX = 6
|
const DRAG_PX = 6
|
||||||
|
|
||||||
@@ -45,7 +56,7 @@ const openerFor = (event) => {
|
|||||||
return null
|
return null
|
||||||
}
|
}
|
||||||
|
|
||||||
const opener = event.target.closest('[data-list-row]')?.querySelector('[data-list-open]')
|
const opener = event.target.closest(ROW)?.querySelector(OPENER)
|
||||||
|
|
||||||
if (!opener) {
|
if (!opener) {
|
||||||
return null
|
return null
|
||||||
@@ -111,11 +122,11 @@ document.addEventListener('keydown', (event) => {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
if (event.defaultPrevented || !(event.target instanceof Element) || !event.target.matches('[data-list-actionable]')) {
|
if (event.defaultPrevented || !(event.target instanceof Element) || !event.target.matches(ACTIONABLE)) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
const opener = event.target.querySelector('[data-list-open]')
|
const opener = event.target.querySelector(OPENER)
|
||||||
|
|
||||||
if (!opener) {
|
if (!opener) {
|
||||||
return
|
return
|
||||||
|
|||||||
Reference in New Issue
Block a user