fabrica

hanna/fabrica

fix(web): center empty-card notes and two-tone the label selector chips

1820303 · hanna committed on 2026-07-26

Zero a card's last child's bottom margin (mirroring the first-child rule) so a
card holding only an empty-state note ("No open issues.") sits centred instead
of bottom-heavy. In the label dropdown, render a checked scoped label's summary
chip two-tone (scope on a neutral background, value in colour) to match the
static label chips.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Signed by hannaSSH key fingerprint: SHA256:4g9cWhkAAw8gwqhJUcVbSnGEvdGwklW+1Aa/fMUu59k
2 files changed · +18 −4UnifiedSplit
assets/base.css +6 −2
@@ -325,11 +325,15 @@ body.drawer-open .drawer-backdrop {
325325 border-radius: var(--fb-radius);
326326 padding: 1rem;
327327 }
328-/* The first child sits against the card padding, so its own top margin would
329- double the gap (empty-state notes, first form labels, headings). */
328+/* The first/last child sits against the card padding, so its own top/bottom
329+ margin would double the gap — most visibly on a card holding only an
330+ empty-state note ("No open issues."), which would otherwise sit off-centre. */
330331 .card > :first-child {
331332 margin-top: 0;
332333 }
334+.card > :last-child {
335+ margin-bottom: 0;
336+}
333337
334338 .muted {
335339 color: var(--fb-fg-muted);
assets/fabrica.js +12 −2
@@ -77,10 +77,20 @@
7777 return;
7878 }
7979 checked.forEach(function (cb) {
80+ var name = cb.getAttribute("data-label-name") || cb.value;
8081 var chip = document.createElement("span");
81- chip.className = "label-chip";
8282 chip.style.setProperty("--label-color", cb.getAttribute("data-label-color") || "#888");
83- chip.textContent = cb.getAttribute("data-label-name") || cb.value;
83+ var sep = name.indexOf(": ");
84+ if (sep === -1) {
85+ chip.className = "label-chip";
86+ chip.textContent = name;
87+ } else {
88+ // Scoped label: static markup, text set via textContent (escaped).
89+ chip.className = "label-chip label-chip-scoped";
90+ chip.innerHTML = '<span class="label-scope"></span><span class="label-value"></span>';
91+ chip.firstChild.textContent = name.slice(0, sep).trim();
92+ chip.lastChild.textContent = name.slice(sep + 2).trim();
93+ }
8494 summaryLabel.appendChild(chip);
8595 });
8696 }