@muten/shadcn 0.1.0 → 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/kit.css CHANGED
@@ -1302,7 +1302,7 @@ html.cx-locked { overflow: hidden; }
1302
1302
  .cx-day b { font-size: 16px; font-weight: 600; font-variant-numeric: tabular-nums; }
1303
1303
  .cx-day i { width: 4px; height: 4px; border-radius: 99px; background: var(--success); }
1304
1304
  .cx-day[data-full] i, .cx-day:disabled i { background: transparent; }
1305
- .cx-day[aria-pressed="true"] small { color: inherit; opacity: .8; }
1305
+ .cx-day[aria-pressed="true"] small { color: inherit; }
1306
1306
  .cx-day[aria-pressed="true"] i { background: currentColor; }
1307
1307
  .cx-hour-grid .cn-button { width: 100%; font-variant-numeric: tabular-nums; }
1308
1308
  .cx-hour-skel { height: 28px; }
@@ -2761,3 +2761,7 @@ a.cx-bc-item:hover { color: var(--foreground); }
2761
2761
  /* ── Press: anything you press gives way a little (0.97), so the page feels it heard you ── */
2762
2762
  .style-nova .cn-button { transition-property: color, background-color, border-color, box-shadow, transform; transition-duration: 160ms; transition-timing-function: cubic-bezier(.23, 1, .32, 1); }
2763
2763
  .style-nova .cn-button:active:not(:disabled) { transform: scale(0.97); }
2764
+
2765
+ /* contrast: the label of the hour groups (Mañana, Tarde) and an appointment's second line read at 4.5:1 */
2766
+ .cx-hours-h { margin: 0; font-size: 12px; font-weight: 600; color: var(--muted-foreground); }
2767
+ .cx-ag-ev .cx-text[data-variant="caption"], .cx-ag-ev .cx-text[data-variant="muted"] { color: color-mix(in srgb, var(--foreground) 78%, var(--tone)); }
package/motion.css CHANGED
@@ -60,7 +60,7 @@
60
60
 
61
61
  /* Drift: a strip that slides by itself (put its items twice, so it loops without a seam). */
62
62
  @keyframes mu-drift { to { transform: translateX(-50%); } }
63
- .drift { display: flex; width: max-content; animation: mu-drift var(--drift, 60s) linear infinite; }
63
+ .drift { display: flex; flex-direction: row; width: max-content; animation: mu-drift var(--drift, 60s) linear infinite; }
64
64
  .drift:hover { animation-play-state: paused; }
65
65
 
66
66
  /* Photo-in: a picture settles from a soft zoom as it appears. */
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@muten/shadcn",
3
- "version": "0.1.0",
3
+ "version": "0.1.1",
4
4
  "description": "shadcn-style component registry for muten - own-the-source parts you add with `muten add`.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -2,6 +2,6 @@
2
2
  # It is the adaptive Modal forced to drawer. The page owns open.
3
3
  # Drawer(open: picking, onClose: done, title: "Elige la hora") { … ModalFooter { … } }
4
4
  # shadcn-for-muten · part over Modal.
5
- part Drawer(open: bool, onClose: action, title: text, description: text = "", size: text = "") {
5
+ part Drawer(open: bool, onClose: action, title: text = "", description: text = "", size: text = "") {
6
6
  Modal(open: $open, onClose: $onClose, title: $title, description: $description, mode: "drawer", size: $size) { slot }
7
7
  }
@@ -91,7 +91,7 @@ export function orderBoard(root, i, core, on) {
91
91
  const groups = GROUP_ORDER.filter((k) => c[k]).map((k) => GROUPS[k](c[k], c));
92
92
  const next = c.actions.find(([a]) => a === 'advance');
93
93
  return `<div data-slot="card-header" class="cn-card-header">${person}</div>`
94
- + (groups.length ? `<div data-slot="card-content" class="cn-card-content"><div data-slot="item-group" class="cn-item-group" role="list">${groups.join(ui.itemSeparator())}</div></div>` : '')
94
+ + (groups.length ? `<div data-slot="card-content" class="cn-card-content"><div data-slot="item-group" class="cn-item-group">${groups.join(ui.itemSeparator())}</div></div>` : '')
95
95
  + (next ? `<div data-slot="card-footer" class="cn-card-footer">${ui.button({ label: `${next[1]}<svg><use href="#right"/></svg>`, variant: 'default', size: 'default', attrs: 'data-bact="advance"', cls: 'cx-fill' })}</div>` : '');
96
96
  };
97
97
 
@@ -297,7 +297,8 @@ export function booking(root, i, core, on) {
297
297
  b.className = 'cn-button cn-button-variant-outline cx-size-tile cx-day'; b.disabled = s === null;
298
298
  if (s && !s.length) b.dataset.full = '';
299
299
  b.setAttribute('aria-pressed', !!picked.day && key(d) === key(picked.day));
300
- b.setAttribute('aria-label', `${DAYLONG[d.getDay()]} ${d.getDate()}${s === null ? ', cerrado' : s.length ? `, ${s.length} horarios` : ', sin horarios'}`);
300
+ // the name starts with what the tile shows («vie 9»), so a voice user can say it; the long day and the state follow
301
+ b.setAttribute('aria-label', `${key(d) === key(today) ? 'hoy' : DAY[d.getDay()]} ${d.getDate()}, ${DAYLONG[d.getDay()]}${s === null ? ', cerrado' : s.length ? `, ${s.length} horarios` : ', sin horarios'}`);
301
302
  b.innerHTML = `<small>${key(d) === key(today) ? 'hoy' : DAY[d.getDay()]}</small><b>${d.getDate()}</b><i></i>`;
302
303
  b.onclick = () => pickDay(d);
303
304
  weekEl.appendChild(b);
@@ -312,7 +313,8 @@ export function booking(root, i, core, on) {
312
313
  return;
313
314
  }
314
315
  const am = s.filter((h) => h < '13:00'), pm = s.filter((h) => h >= '13:00');
315
- const grid = (label, hs) => hs.length ? `<h4>${label}</h4><div class="cx-hour-grid">${hs.map((h) => `<button class="cn-button cn-button-variant-outline cn-button-size-sm cx-hour" aria-pressed="${h === picked.hour}">${h}</button>`).join('')}</div>` : '';
316
+ // the part of the day is a label, not a heading: the picker sits inside pages whose outline it must not break
317
+ const grid = (label, hs) => hs.length ? `<p class="cx-hours-h">${label}</p><div class="cx-hour-grid">${hs.map((h) => `<button class="cn-button cn-button-variant-outline cn-button-size-sm cx-hour" aria-pressed="${h === picked.hour}">${h}</button>`).join('')}</div>` : '';
316
318
  hours.innerHTML = `<div class="cx-panel" style="display:flex;flex-direction:column;gap:10px">${grid('Mañana', am)}${grid('Tarde', pm)}</div>`;
317
319
  $$('.cx-hour', hours).forEach((b) => b.onclick = () => { picked.hour = b.textContent; $$('.cx-hour', hours).forEach((x) => x.setAttribute('aria-pressed', x === b)); sum(); });
318
320
  };
@@ -10,7 +10,7 @@
10
10
  # mode: auto | dialog | drawer | sheet (a panel from a side) · side: right | left | top | bottom (for sheet)
11
11
  # role: dialog | alertdialog · dismiss: on | off (off: no ✕ and the backdrop does not close it; only its buttons do)
12
12
  # size: "" | tall (a list that pages) · shadcn-for-muten · part + Custom (ModalBehavior) · kit.css (.cx-modal).
13
- part Modal(open: bool, onClose: action, title: text, description: text = "", mode: text = "auto", size: text = "", side: text = "right", role: text = "dialog", dismiss: text = "on") {
13
+ part Modal(open: bool, onClose: action, title: text = "", description: text = "", mode: text = "auto", size: text = "", side: text = "right", role: text = "dialog", dismiss: text = "on") {
14
14
  Stack class("cx-modal-root") data(open: $open) {
15
15
  when $dismiss != "off" { Button "" -> $onClose class("cx-overlay") aria(label: "Cerrar", hidden: "true") data(closes: "true") }
16
16
  when $dismiss == "off" { Stack class("cx-overlay") aria(hidden: "true") }