feat(member): condense the overview into composite name and address cells
This commit is contained in:
parent
b79d7ac9ea
commit
af2cc2e0d4
17 changed files with 716 additions and 93 deletions
|
|
@ -678,6 +678,78 @@
|
|||
|
||||
/* This file is for your main application CSS */
|
||||
|
||||
/* ============================================
|
||||
Table header density scaling
|
||||
============================================ */
|
||||
|
||||
/*
|
||||
* DaisyUI table size modifiers (table-xs, table-sm, etc.) scope their font-size
|
||||
* rule to ":not(thead, tfoot) tr", so the header row stays at the base 0.875 rem
|
||||
* regardless of the chosen density. We extend each modifier to thead so the
|
||||
* header scales together with the body.
|
||||
*/
|
||||
.table.table-xs thead tr { font-size: 0.6875rem; }
|
||||
.table.table-sm thead tr { font-size: 0.75rem; }
|
||||
.table.table-lg thead tr { font-size: 1.125rem; }
|
||||
.table.table-xl thead tr { font-size: 1.375rem; }
|
||||
|
||||
/*
|
||||
* Density-tracking badges and sort icons in the member overview.
|
||||
*
|
||||
* The member table renders its rows via LiveView streams, so toggling density
|
||||
* only swaps the <table> size class (table-xs <-> table-md); it does NOT
|
||||
* re-render the streamed rows. A per-row `size=` conditional therefore bakes a
|
||||
* stale badge size into the streamed DOM. To make badges (and, for visual
|
||||
* consistency, the header sort glyphs) follow the density toggle without any
|
||||
* row re-render, their size is driven purely from the table size class here.
|
||||
*
|
||||
* Badge values mirror daisyUI's own .badge-xs / .badge-md (font-size, --size
|
||||
* which the base .badge uses for height, and padding-inline). Scoped to the
|
||||
* member overview via #members-keyboard so unrelated badges are unaffected.
|
||||
*/
|
||||
#members-keyboard .table.table-xs .badge {
|
||||
--size: calc(var(--size-selector, 0.25rem) * 4);
|
||||
font-size: 0.625rem;
|
||||
padding-inline: calc(0.25rem * 2 - var(--border));
|
||||
}
|
||||
#members-keyboard .table.table-md .badge {
|
||||
--size: calc(var(--size-selector, 0.25rem) * 6);
|
||||
font-size: 0.875rem;
|
||||
padding-inline: calc(0.25rem * 3 - var(--border));
|
||||
}
|
||||
|
||||
/* Sort glyphs scale with the header text (11px compact / 14px comfortable). */
|
||||
#members-keyboard .table.table-md thead .sort-icon {
|
||||
width: 1.5rem;
|
||||
height: 1.5rem;
|
||||
}
|
||||
#members-keyboard .table.table-xs thead .sort-icon {
|
||||
width: 1.125rem;
|
||||
height: 1.125rem;
|
||||
}
|
||||
|
||||
/*
|
||||
* Infinite-scroll loading row.
|
||||
*
|
||||
* The loading indicator must read like a full, accented data row rather than a
|
||||
* narrow pinned bar. The accent (base-200 background + a top separator) and the
|
||||
* padding live on the full-width footer cell, which spans every column via
|
||||
* colspan, so the accent is visible edge-to-edge even while the table is scrolled
|
||||
* horizontally. The spinner + label inside stay pinned to the visible viewport
|
||||
* width (StickyViewportWidth hook) and transparent, so they remain centered on
|
||||
* horizontal scroll while the cell accent shows through behind them.
|
||||
*
|
||||
* The row height tracks the active density (table-xs compact / table-md
|
||||
* comfortable) so it matches a normal data row in each mode.
|
||||
*/
|
||||
#members-footer > tr > td {
|
||||
background-color: var(--color-base-200);
|
||||
border-top: 1px solid var(--color-base-300);
|
||||
padding: 0;
|
||||
}
|
||||
.table.table-xs #members-loading-bar { min-height: 3.375rem; }
|
||||
.table.table-md #members-loading-bar { min-height: 4.1875rem; }
|
||||
|
||||
/* ============================================
|
||||
SortableList: drag-and-drop table rows
|
||||
============================================ */
|
||||
|
|
@ -773,3 +845,115 @@
|
|||
[data-sticky-first-col-rows="true"] .table.table-zebra tbody tr input.checkbox:focus:not(:focus-visible) {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
/*
|
||||
* Sticky checkbox column: border-collapse: separate avoids the Chromium artifact
|
||||
* where a collapsed row border is repainted (a spurious 1px line) under a
|
||||
* position: sticky cell. The row separators are moved onto the cells so they
|
||||
* still render in the separate model (matching DaisyUI's faint divider color).
|
||||
*/
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra {
|
||||
border-collapse: separate;
|
||||
border-spacing: 0;
|
||||
}
|
||||
[data-sticky-first-col-rows="true"]
|
||||
.table.table-zebra
|
||||
:where(thead tr, tbody tr:not(:last-child))
|
||||
> :where(th, td) {
|
||||
border-bottom: var(--border) solid color-mix(in oklch, var(--color-base-content) 5%, #0000);
|
||||
}
|
||||
|
||||
/*
|
||||
* Horizontal-scroll fade for the pinned checkbox column: instead of hiding the
|
||||
* scrolled-away content behind a hard opaque block, a gradient on the right edge
|
||||
* of the sticky cell fades the incoming content, signalling there is more behind
|
||||
* it. overflow: visible lets the ::after gradient extend past the cell; the cell
|
||||
* keeps its own (zebra) background so the checkbox stays legible.
|
||||
*/
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra td.sticky-first-col-cell {
|
||||
overflow: visible;
|
||||
}
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra td.sticky-first-col-cell::after,
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra thead th.sticky-first-col-th::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
left: 100%;
|
||||
width: 1.25rem;
|
||||
pointer-events: none;
|
||||
}
|
||||
[data-sticky-first-col-rows="true"]
|
||||
.table.table-zebra
|
||||
tbody
|
||||
tr:nth-child(odd)
|
||||
> td.sticky-first-col-cell::after {
|
||||
background: linear-gradient(to right, var(--color-base-100), transparent);
|
||||
}
|
||||
[data-sticky-first-col-rows="true"]
|
||||
.table.table-zebra
|
||||
tbody
|
||||
tr:nth-child(even)
|
||||
> td.sticky-first-col-cell::after {
|
||||
background: linear-gradient(to right, var(--color-base-200), transparent);
|
||||
}
|
||||
[data-sticky-first-col-rows="true"]
|
||||
.table.table-zebra
|
||||
tbody
|
||||
tr[data-row-interactive="true"]:is(:hover, :has(:focus-visible))
|
||||
> td.sticky-first-col-cell::after {
|
||||
background: linear-gradient(to right, var(--color-base-300), transparent);
|
||||
}
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra thead th.sticky-first-col-th::after {
|
||||
background: linear-gradient(to right, var(--color-base-100), transparent);
|
||||
}
|
||||
/* Compact density: narrower fade so the gradient does not visually reach into the
|
||||
checkbox column's own content area in the tighter table-xs cell. */
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra.table-xs td.sticky-first-col-cell::after,
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra.table-xs thead th.sticky-first-col-th::after {
|
||||
width: 0.5rem;
|
||||
}
|
||||
|
||||
/*
|
||||
* Sort-header tooltip. Rendered via the native Popover API (see the SortTooltip
|
||||
* JS hook), so it lives in the browser TOP LAYER: it is not clipped by the
|
||||
* members table's overflow (overflow-x:auto forces overflow-y:auto, which used
|
||||
* to clip a CSS pseudo-tooltip below the header) and paints above the sticky
|
||||
* header, neighbor cells, and the pinned checkbox column's fade — without any
|
||||
* z-index hacks. This block only resets the popover UA defaults and gives it a
|
||||
* small daisyUI-flavoured tooltip look; the JS hook sets top/left each show.
|
||||
*/
|
||||
.sort-tooltip {
|
||||
position: fixed;
|
||||
inset: auto;
|
||||
margin: 0;
|
||||
border: 0;
|
||||
padding: 0.25rem 0.5rem;
|
||||
width: max-content;
|
||||
max-width: 16rem;
|
||||
overflow: visible;
|
||||
background: var(--color-neutral, oklch(0.2 0 0));
|
||||
color: var(--color-neutral-content, oklch(0.98 0 0));
|
||||
font-size: 0.75rem;
|
||||
line-height: 1rem;
|
||||
border-radius: 0.25rem;
|
||||
box-shadow: 0 1px 3px rgb(0 0 0 / 0.3);
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
/*
|
||||
* Vertically center the row checkbox in the sticky first column using the
|
||||
* table-native vertical-align: middle. This keeps display: table-cell intact so
|
||||
* the cell background fills the full row height (no white gap at the bottom).
|
||||
* The fieldset margin-bottom reset removes the mb-2 from the shared input
|
||||
* component so no residual margin shifts the checkbox off-center.
|
||||
*/
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra td.sticky-first-col-cell,
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra thead th.sticky-first-col-th {
|
||||
vertical-align: middle;
|
||||
}
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra td.sticky-first-col-cell fieldset,
|
||||
[data-sticky-first-col-rows="true"] .table.table-zebra thead th.sticky-first-col-th fieldset {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue