@jirawatpyk/aura-react 5.1.1 → 5.3.0

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.
@@ -360,6 +360,12 @@ var STRINGS = {
360
360
  page: function(p, total) {
361
361
  return "Page " + p + " of " + total;
362
362
  },
363
+ rangeOpen: function(a, b) {
364
+ return a + "\u2013" + b + " of many";
365
+ },
366
+ pageOpen: function(p) {
367
+ return "Page " + p;
368
+ },
363
369
  prevPage: "Previous page",
364
370
  nextPage: "Next page",
365
371
  totals: "Totals",
@@ -373,6 +379,7 @@ var STRINGS = {
373
379
  timeOutOfRange: function(a, b) {
374
380
  return "Choose a time between " + a + " and " + b;
375
381
  },
382
+ timeUnavailable: "That time isn't available. Choose another.",
376
383
  dropFiles: "Drag files here or",
377
384
  browse: "Choose files",
378
385
  browseOne: "Choose a file",
@@ -474,6 +481,12 @@ var STRINGS = {
474
481
  page: function(p, total) {
475
482
  return "\u0E2B\u0E19\u0E49\u0E32 " + p + " / " + total;
476
483
  },
484
+ rangeOpen: function(a, b) {
485
+ return a + "\u2013" + b + " \u0E08\u0E32\u0E01\u0E2B\u0E25\u0E32\u0E22\u0E23\u0E32\u0E22\u0E01\u0E32\u0E23";
486
+ },
487
+ pageOpen: function(p) {
488
+ return "\u0E2B\u0E19\u0E49\u0E32 " + p;
489
+ },
477
490
  prevPage: "\u0E2B\u0E19\u0E49\u0E32\u0E01\u0E48\u0E2D\u0E19\u0E2B\u0E19\u0E49\u0E32",
478
491
  nextPage: "\u0E2B\u0E19\u0E49\u0E32\u0E16\u0E31\u0E14\u0E44\u0E1B",
479
492
  totals: "\u0E23\u0E27\u0E21",
@@ -487,6 +500,7 @@ var STRINGS = {
487
500
  timeOutOfRange: function(a, b) {
488
501
  return "\u0E40\u0E25\u0E37\u0E2D\u0E01\u0E40\u0E27\u0E25\u0E32\u0E23\u0E30\u0E2B\u0E27\u0E48\u0E32\u0E07 " + a + "\u2013" + b + " \u0E19.";
489
502
  },
503
+ timeUnavailable: "\u0E40\u0E27\u0E25\u0E32\u0E19\u0E35\u0E49\u0E44\u0E21\u0E48\u0E27\u0E48\u0E32\u0E07 \u0E40\u0E25\u0E37\u0E2D\u0E01\u0E40\u0E27\u0E25\u0E32\u0E2D\u0E37\u0E48\u0E19",
490
504
  dropFiles: "\u0E25\u0E32\u0E01\u0E44\u0E1F\u0E25\u0E4C\u0E21\u0E32\u0E27\u0E32\u0E07 \u0E2B\u0E23\u0E37\u0E2D",
491
505
  browse: "\u0E40\u0E25\u0E37\u0E2D\u0E01\u0E44\u0E1F\u0E25\u0E4C",
492
506
  browseOne: "\u0E40\u0E25\u0E37\u0E2D\u0E01\u0E44\u0E1F\u0E25\u0E4C",
@@ -588,6 +602,12 @@ var STRINGS = {
588
602
  page: function(p, total) {
589
603
  return "Sida " + p + " av " + total;
590
604
  },
605
+ rangeOpen: function(a, b) {
606
+ return a + "\u2013" + b + " av m\xE5nga";
607
+ },
608
+ pageOpen: function(p) {
609
+ return "Sida " + p;
610
+ },
591
611
  prevPage: "F\xF6reg\xE5ende sida",
592
612
  nextPage: "N\xE4sta sida",
593
613
  totals: "Summa",
@@ -601,6 +621,7 @@ var STRINGS = {
601
621
  timeOutOfRange: function(a, b) {
602
622
  return "V\xE4lj en tid mellan " + a + " och " + b;
603
623
  },
624
+ timeUnavailable: "Den tiden \xE4r inte ledig. V\xE4lj en annan.",
604
625
  dropFiles: "Dra filer hit eller",
605
626
  browse: "V\xE4lj filer",
606
627
  browseOne: "V\xE4lj en fil",
@@ -1185,7 +1206,52 @@ var Textarea = React12.forwardRef(function Textarea2(props, ref) {
1185
1206
 
1186
1207
  // src/Select.tsx
1187
1208
  var React13 = __toESM(require("react"), 1);
1209
+ var import_react_dom2 = require("react-dom");
1188
1210
  var h3 = React13.createElement;
1211
+ var FORM_KEYS = ["name", "form", "value", "defaultValue", "disabled", "autoComplete", "onInput", "onInvalid"];
1212
+ var HANDLED_KEYS = FORM_KEYS.concat([
1213
+ "onChange",
1214
+ "onBlur",
1215
+ "onFocus",
1216
+ "onKeyDown",
1217
+ "onClick",
1218
+ "autoFocus",
1219
+ "tabIndex",
1220
+ "aria-label",
1221
+ "aria-labelledby",
1222
+ "aria-describedby",
1223
+ "multiple",
1224
+ "size"
1225
+ ]);
1226
+ function pick(o, keys) {
1227
+ const r = {};
1228
+ for (const k of keys) if (k in o) r[k] = o[k];
1229
+ return r;
1230
+ }
1231
+ function readItems(el) {
1232
+ if (!el) return [];
1233
+ return Array.prototype.map.call(el.options, function(o, i) {
1234
+ const g = o.parentElement && o.parentElement.tagName === "OPTGROUP" ? o.parentElement : null;
1235
+ return {
1236
+ value: o.value,
1237
+ label: o.textContent || "",
1238
+ disabled: o.disabled || !!(g && g.disabled),
1239
+ group: g ? g.label : null,
1240
+ index: i
1241
+ };
1242
+ });
1243
+ }
1244
+ function initialLabel(props) {
1245
+ const opts = (props.options || []).map(function(o) {
1246
+ return typeof o === "object" ? o : { value: o, label: o };
1247
+ });
1248
+ const v = props.value !== void 0 && props.value !== null ? String(props.value) : props.defaultValue !== void 0 && props.defaultValue !== null ? String(props.defaultValue) : props.placeholder ? "" : opts[0] ? opts[0].value : "";
1249
+ const hit = opts.filter(function(o) {
1250
+ return o.value === v;
1251
+ })[0];
1252
+ if (hit) return { label: hit.label, empty: false };
1253
+ return { label: props.placeholder || "", empty: true };
1254
+ }
1189
1255
  var Select = React13.forwardRef(function Select2(props, ref) {
1190
1256
  const auto = uid(), id = props.id || auto;
1191
1257
  const rest = omit(props, FIELD_KEYS.concat(["children"]));
@@ -1198,10 +1264,259 @@ var Select = React13.forwardRef(function Select2(props, ref) {
1198
1264
  /* @__PURE__ */ React13.createElement("option", { key: "__ph", value: "", disabled: true }, props.placeholder)
1199
1265
  );
1200
1266
  const extra = props.value === void 0 && props.defaultValue === void 0 && props.placeholder ? { defaultValue: "" } : {};
1201
- return /* @__PURE__ */ React13.createElement(
1267
+ const native = !!props.multiple || props.size != null && props.size > 1;
1268
+ const mounted = useMounted();
1269
+ const live = !native && mounted;
1270
+ const density = useDensity();
1271
+ const selRef = React13.useRef(null), trigRef = React13.useRef(null), listRef = React13.useRef(null);
1272
+ const shown = React13.useState(function() {
1273
+ return initialLabel(props);
1274
+ });
1275
+ const openState = React13.useState(false), open = openState[0];
1276
+ const activeState = React13.useState(-1), active = activeState[0];
1277
+ const items2 = React13.useState([]);
1278
+ const pos = React13.useState(null);
1279
+ const typed = React13.useRef({ text: "", at: 0 });
1280
+ const sync = React13.useCallback(function() {
1281
+ const el = selRef.current;
1282
+ if (!el) return;
1283
+ const o = el.selectedIndex >= 0 ? el.options[el.selectedIndex] : null;
1284
+ const next = o ? { label: o.textContent || "", empty: o.value === "" } : { label: "", empty: true };
1285
+ shown[1](function(cur) {
1286
+ return cur.label === next.label && cur.empty === next.empty ? cur : next;
1287
+ });
1288
+ }, []);
1289
+ const hook = React13.useCallback(
1290
+ function(el) {
1291
+ selRef.current = el;
1292
+ if (!el || native || el.__auraHooked) return;
1293
+ el.__auraHooked = true;
1294
+ const proto = HTMLSelectElement.prototype;
1295
+ const pv = Object.getOwnPropertyDescriptor(proto, "value"), pi = Object.getOwnPropertyDescriptor(proto, "selectedIndex");
1296
+ if (pv && pv.set && pv.get)
1297
+ Object.defineProperty(el, "value", {
1298
+ configurable: true,
1299
+ get: function() {
1300
+ return pv.get.call(el);
1301
+ },
1302
+ set: function(v) {
1303
+ pv.set.call(el, v);
1304
+ sync();
1305
+ }
1306
+ });
1307
+ if (pi && pi.set && pi.get)
1308
+ Object.defineProperty(el, "selectedIndex", {
1309
+ configurable: true,
1310
+ get: function() {
1311
+ return pi.get.call(el);
1312
+ },
1313
+ set: function(v) {
1314
+ pi.set.call(el, v);
1315
+ sync();
1316
+ }
1317
+ });
1318
+ el.focus = function(o) {
1319
+ if (trigRef.current) trigRef.current.focus(o);
1320
+ else proto.focus.call(el, o);
1321
+ };
1322
+ },
1323
+ [native, sync]
1324
+ );
1325
+ const selMerged = useMergedRef(ref, hook);
1326
+ React13.useEffect(
1327
+ function() {
1328
+ const f = selRef.current && selRef.current.form;
1329
+ if (!f || native) return;
1330
+ function onReset() {
1331
+ setTimeout(sync, 0);
1332
+ }
1333
+ f.addEventListener("reset", onReset);
1334
+ return function() {
1335
+ f.removeEventListener("reset", onReset);
1336
+ };
1337
+ },
1338
+ [native, sync]
1339
+ );
1340
+ const focusedOnce = React13.useRef(false);
1341
+ React13.useEffect(
1342
+ function() {
1343
+ if (!live || focusedOnce.current || !trigRef.current) return;
1344
+ focusedOnce.current = true;
1345
+ if (props.autoFocus || selRef.current && document.activeElement === selRef.current) trigRef.current.focus();
1346
+ },
1347
+ [live]
1348
+ );
1349
+ useIsoLayoutEffect(function() {
1350
+ if (!live) return;
1351
+ sync();
1352
+ if (!open) return;
1353
+ const now = readItems(selRef.current), was = items2[0];
1354
+ const same2 = now.length === was.length && now.every(function(it, i) {
1355
+ const w = was[i];
1356
+ return w.value === it.value && w.label === it.label && w.disabled === it.disabled && w.group === it.group;
1357
+ });
1358
+ if (same2) return;
1359
+ items2[1](now);
1360
+ if (!choices(now).length) {
1361
+ close(false);
1362
+ return;
1363
+ }
1364
+ const hv = was[active] ? was[active].value : null;
1365
+ const again = now.filter(function(it) {
1366
+ return !it.disabled && it.value === hv;
1367
+ })[0];
1368
+ const cur = selRef.current ? selRef.current.selectedIndex : -1;
1369
+ activeState[1](again ? again.index : now[cur] && !now[cur].disabled ? cur : choices(now)[0].index);
1370
+ });
1371
+ function choices(list) {
1372
+ return list.filter(function(i) {
1373
+ return !i.disabled;
1374
+ });
1375
+ }
1376
+ function choose(it) {
1377
+ const el = selRef.current;
1378
+ if (!el || it.disabled) return;
1379
+ if (el.value !== it.value) {
1380
+ el.value = it.value;
1381
+ el.dispatchEvent(new Event("input", { bubbles: true }));
1382
+ el.dispatchEvent(new Event("change", { bubbles: true }));
1383
+ }
1384
+ sync();
1385
+ close(true);
1386
+ }
1387
+ function openList(at) {
1388
+ if (props.disabled || trigRef.current && trigRef.current.disabled) return;
1389
+ const list = readItems(selRef.current);
1390
+ const ok = choices(list);
1391
+ if (!ok.length) return;
1392
+ items2[1](list);
1393
+ const cur = selRef.current ? selRef.current.selectedIndex : -1;
1394
+ let a = at === "first" ? ok[0].index : at === "last" ? ok[ok.length - 1].index : cur;
1395
+ if (typeof at === "number") a = at;
1396
+ if (a < 0 || !list[a] || list[a].disabled) a = ok[0].index;
1397
+ activeState[1](a);
1398
+ openState[1](true);
1399
+ }
1400
+ function close(focus) {
1401
+ openState[1](false);
1402
+ pos[1](null);
1403
+ if (focus && trigRef.current) trigRef.current.focus();
1404
+ }
1405
+ function step(from, dir, list) {
1406
+ for (let i = from + dir; i >= 0 && i < list.length; i += dir) if (!list[i].disabled) return i;
1407
+ return from;
1408
+ }
1409
+ function typing() {
1410
+ return !!typed.current.text && Date.now() - typed.current.at < 500;
1411
+ }
1412
+ function typeahead(ch, list, from) {
1413
+ const now = Date.now(), t = typed.current;
1414
+ t.text = now - t.at < 500 ? t.text + ch : ch;
1415
+ t.at = now;
1416
+ const q = t.text.toLocaleLowerCase();
1417
+ for (let k = 1; k <= list.length; k++) {
1418
+ const i = (from + (t.text.length > 1 ? 0 : 1) + k - 1 + list.length) % list.length;
1419
+ if (!list[i].disabled && list[i].label.toLocaleLowerCase().indexOf(q) === 0) return i;
1420
+ }
1421
+ t.text = "";
1422
+ return -1;
1423
+ }
1424
+ function onKeyDown(e) {
1425
+ const k = e.key;
1426
+ const printable = k.length === 1 && !e.ctrlKey && !e.metaKey && !e.altKey;
1427
+ const search = printable && (k !== " " || typing());
1428
+ if (!open) {
1429
+ if (search) {
1430
+ const list2 = readItems(selRef.current);
1431
+ const i = typeahead(k, list2, selRef.current ? selRef.current.selectedIndex : -1);
1432
+ e.preventDefault();
1433
+ if (i >= 0) openList(i);
1434
+ } else if (k === "ArrowDown" || k === "ArrowUp" || k === "Enter" || k === " ") {
1435
+ e.preventDefault();
1436
+ openList(k === "ArrowUp" && !(selRef.current && selRef.current.value) ? "last" : void 0);
1437
+ }
1438
+ return;
1439
+ }
1440
+ const list = items2[0];
1441
+ if (search) {
1442
+ e.preventDefault();
1443
+ const i = typeahead(k, list, active);
1444
+ if (i >= 0) activeState[1](i);
1445
+ } else if (k === "ArrowDown") {
1446
+ e.preventDefault();
1447
+ activeState[1](step(active, 1, list));
1448
+ } else if (k === "ArrowUp") {
1449
+ e.preventDefault();
1450
+ activeState[1](step(active, -1, list));
1451
+ } else if (k === "Home" || k === "PageUp") {
1452
+ e.preventDefault();
1453
+ activeState[1](k === "Home" ? step(-1, 1, list) : Math.max(step(-1, 1, list), step(active - 9, 1, list)));
1454
+ } else if (k === "End" || k === "PageDown") {
1455
+ e.preventDefault();
1456
+ activeState[1](
1457
+ k === "End" ? step(list.length, -1, list) : Math.min(step(list.length, -1, list), step(active + 9, -1, list))
1458
+ );
1459
+ } else if (k === "Enter" || k === " ") {
1460
+ e.preventDefault();
1461
+ if (list[active]) choose(list[active]);
1462
+ } else if (k === "Escape") {
1463
+ e.preventDefault();
1464
+ e.stopPropagation();
1465
+ close(true);
1466
+ } else if (k === "Tab") {
1467
+ close(false);
1468
+ }
1469
+ }
1470
+ useIsoLayoutEffect(
1471
+ function() {
1472
+ if (!open) return;
1473
+ function place() {
1474
+ const t = trigRef.current && trigRef.current.parentElement;
1475
+ if (!t) return;
1476
+ const r = t.getBoundingClientRect(), below2 = window.innerHeight - r.bottom - 8, above = r.top - 8, want = listRef.current ? listRef.current.scrollHeight : 320, up = below2 < Math.min(want, 200) && above > below2;
1477
+ pos[1]({
1478
+ left: r.left,
1479
+ width: r.width,
1480
+ top: up ? void 0 : r.bottom + 4,
1481
+ bottom: up ? window.innerHeight - r.top + 4 : void 0,
1482
+ maxHeight: Math.min(320, (up ? above : below2) - 4)
1483
+ });
1484
+ }
1485
+ place();
1486
+ function outside(e) {
1487
+ const n2 = e.target;
1488
+ if (listRef.current && listRef.current.contains(n2)) return;
1489
+ if (trigRef.current && trigRef.current.contains(n2)) return;
1490
+ close(false);
1491
+ }
1492
+ function onScroll(e) {
1493
+ if (!listRef.current || !listRef.current.contains(e.target)) place();
1494
+ }
1495
+ document.addEventListener("pointerdown", outside, true);
1496
+ window.addEventListener("scroll", onScroll, true);
1497
+ window.addEventListener("resize", place);
1498
+ return function() {
1499
+ document.removeEventListener("pointerdown", outside, true);
1500
+ window.removeEventListener("scroll", onScroll, true);
1501
+ window.removeEventListener("resize", place);
1502
+ };
1503
+ },
1504
+ [open]
1505
+ );
1506
+ React13.useEffect(
1507
+ function() {
1508
+ if (!open || !listRef.current || active < 0) return;
1509
+ const el = listRef.current.querySelector('[data-idx="' + active + '"]');
1510
+ if (el && el.scrollIntoView) el.scrollIntoView({ block: "nearest" });
1511
+ },
1512
+ [open, active, pos[0] != null]
1513
+ );
1514
+ const described = [describedBy(id, props), rest["aria-describedby"]].filter(Boolean).join(" ") || void 0;
1515
+ const field = (child) => /* @__PURE__ */ React13.createElement(
1202
1516
  Field,
1203
1517
  {
1204
1518
  id,
1519
+ labelId: native ? void 0 : id + "-label",
1205
1520
  label: props.label,
1206
1521
  hint: props.hint,
1207
1522
  error: props.error,
@@ -1210,19 +1525,180 @@ var Select = React13.forwardRef(function Select2(props, ref) {
1210
1525
  disabled: props.disabled,
1211
1526
  className: props.className
1212
1527
  },
1213
- /* @__PURE__ */ React13.createElement("div", { className: cx("aura-input aura-select", props.icon && "has-icon") }, props.icon ? /* @__PURE__ */ React13.createElement(Icon, { name: props.icon, className: "aura-input__icon" }) : null, h3(
1214
- "select",
1215
- Object.assign(extra, rest, {
1216
- ref,
1217
- id,
1218
- className: "aura-input__control",
1219
- required: props.required,
1220
- "aria-invalid": props.error ? true : void 0,
1221
- "aria-describedby": describedBy(id, props)
1222
- }),
1223
- opts,
1224
- props.children
1225
- ), /* @__PURE__ */ React13.createElement(Icon, { name: "chevron-down", className: "aura-select__chevron" }))
1528
+ child
1529
+ );
1530
+ if (!live)
1531
+ return field(
1532
+ /* @__PURE__ */ React13.createElement("div", { className: cx("aura-input aura-select", props.icon && "has-icon") }, props.icon ? /* @__PURE__ */ React13.createElement(Icon, { name: props.icon, className: "aura-input__icon" }) : null, h3(
1533
+ "select",
1534
+ Object.assign(extra, rest, {
1535
+ ref: native ? ref : selMerged,
1536
+ id,
1537
+ className: "aura-input__control",
1538
+ required: props.required,
1539
+ "aria-invalid": props.error ? true : void 0,
1540
+ "aria-describedby": described
1541
+ }),
1542
+ opts,
1543
+ props.children
1544
+ ), /* @__PURE__ */ React13.createElement(Icon, { name: "chevron-down", className: "aura-select__chevron" }))
1545
+ );
1546
+ const listId = id + "-list", labelId = id + "-label";
1547
+ const optId = function(i) {
1548
+ return id + "-opt-" + i;
1549
+ };
1550
+ const labelledBy = rest["aria-labelledby"] || (props.label ? labelId : void 0);
1551
+ const selIndex = selRef.current ? selRef.current.selectedIndex : -1;
1552
+ const option = function(it) {
1553
+ const sel = selIndex === it.index;
1554
+ return /* @__PURE__ */ React13.createElement(
1555
+ "div",
1556
+ {
1557
+ key: it.index,
1558
+ id: optId(it.index),
1559
+ role: "option",
1560
+ "data-idx": it.index,
1561
+ "aria-selected": sel,
1562
+ "aria-disabled": it.disabled || void 0,
1563
+ className: cx(
1564
+ "aura-combo__option",
1565
+ it.index === active && "is-active",
1566
+ sel && "is-selected",
1567
+ it.disabled && "is-disabled"
1568
+ ),
1569
+ onPointerDown: function(e) {
1570
+ e.preventDefault();
1571
+ },
1572
+ onPointerMove: function() {
1573
+ if (!it.disabled && active !== it.index) activeState[1](it.index);
1574
+ },
1575
+ onClick: function() {
1576
+ choose(it);
1577
+ }
1578
+ },
1579
+ /* @__PURE__ */ React13.createElement("span", { className: "aura-combo__text" }, /* @__PURE__ */ React13.createElement("span", { className: "aura-combo__label" }, it.label)),
1580
+ sel ? /* @__PURE__ */ React13.createElement(Icon, { name: "check", className: "aura-combo__check" }) : null
1581
+ );
1582
+ };
1583
+ const runs = [];
1584
+ items2[0].forEach(function(it) {
1585
+ if (it.value === "" && it.disabled) return;
1586
+ const last = runs[runs.length - 1];
1587
+ if (last && last.group === it.group) last.items.push(it);
1588
+ else runs.push({ group: it.group, items: [it] });
1589
+ });
1590
+ const popup = open ? (0, import_react_dom2.createPortal)(
1591
+ /* @__PURE__ */ React13.createElement(
1592
+ "div",
1593
+ {
1594
+ ref: listRef,
1595
+ "data-density": density,
1596
+ className: "aura-combo__popover aura-select__popover",
1597
+ style: pos[0] ? {
1598
+ left: pos[0].left,
1599
+ minWidth: pos[0].width,
1600
+ top: pos[0].top,
1601
+ bottom: pos[0].bottom,
1602
+ maxHeight: pos[0].maxHeight
1603
+ } : { left: -9999, top: -9999 }
1604
+ },
1605
+ /* @__PURE__ */ React13.createElement(
1606
+ "div",
1607
+ {
1608
+ id: listId,
1609
+ role: "listbox",
1610
+ "aria-labelledby": labelledBy,
1611
+ "aria-label": labelledBy ? void 0 : rest["aria-label"],
1612
+ className: "aura-combo__list"
1613
+ },
1614
+ runs.map(function(r, n2) {
1615
+ if (r.group === null) return /* @__PURE__ */ React13.createElement(React13.Fragment, { key: "r" + n2 }, r.items.map(option));
1616
+ const gid = id + "-group-" + n2;
1617
+ return /* @__PURE__ */ React13.createElement("div", { key: "r" + n2, role: "group", "aria-labelledby": gid }, /* @__PURE__ */ React13.createElement("div", { id: gid, className: "aura-select__group" }, r.group), r.items.map(option));
1618
+ })
1619
+ )
1620
+ ),
1621
+ document.body
1622
+ ) : null;
1623
+ const userFocus = rest.onFocus, userBlur = rest.onBlur, userKey = rest.onKeyDown, userClick = rest.onClick;
1624
+ return field(
1625
+ /* @__PURE__ */ React13.createElement(
1626
+ "div",
1627
+ {
1628
+ className: cx("aura-input aura-select aura-select--custom", props.icon && "has-icon", open && "is-open"),
1629
+ "data-invalid": props.error ? "" : void 0
1630
+ },
1631
+ props.icon ? /* @__PURE__ */ React13.createElement(Icon, { name: props.icon, className: "aura-input__icon" }) : null,
1632
+ h3(
1633
+ "select",
1634
+ Object.assign(extra, pick(rest, FORM_KEYS), {
1635
+ ref: selMerged,
1636
+ id: id + "-select",
1637
+ className: "aura-select__native",
1638
+ tabIndex: -1,
1639
+ "aria-hidden": true,
1640
+ required: props.required,
1641
+ onChange: function(e) {
1642
+ sync();
1643
+ if (props.onChange) props.onChange(e);
1644
+ },
1645
+ /* A browser focusing the <select> (the required bubble, a label click) hands focus to the button. */
1646
+ onFocus: function() {
1647
+ if (trigRef.current) trigRef.current.focus();
1648
+ },
1649
+ /* Only the blur the button reports (below): the <select>'s own, while it hands focus over, is not one. */
1650
+ onBlur: function(e) {
1651
+ if (!e.nativeEvent.isTrusted && userBlur) userBlur(e);
1652
+ }
1653
+ }),
1654
+ opts,
1655
+ props.children
1656
+ ),
1657
+ /* @__PURE__ */ React13.createElement(
1658
+ "button",
1659
+ {
1660
+ ...omit(rest, HANDLED_KEYS),
1661
+ ref: trigRef,
1662
+ type: "button",
1663
+ role: "combobox",
1664
+ form: id + "-no-form",
1665
+ className: "aura-input__control aura-select__trigger",
1666
+ disabled: props.disabled,
1667
+ tabIndex: rest.tabIndex,
1668
+ "aria-haspopup": "listbox",
1669
+ "aria-expanded": open,
1670
+ "aria-controls": open ? listId : void 0,
1671
+ "aria-activedescendant": open && active >= 0 ? optId(active) : void 0,
1672
+ id,
1673
+ "aria-label": rest["aria-label"],
1674
+ "aria-labelledby": rest["aria-labelledby"],
1675
+ "aria-required": props.required || void 0,
1676
+ "aria-invalid": props.error ? true : void 0,
1677
+ "aria-describedby": described,
1678
+ onFocus: function(e) {
1679
+ if (userFocus) userFocus(e);
1680
+ },
1681
+ onClick: function(e) {
1682
+ if (userClick) userClick(e);
1683
+ if (e.defaultPrevented) return;
1684
+ if (open) close(true);
1685
+ else openList();
1686
+ },
1687
+ onKeyDown: function(e) {
1688
+ if (userKey) userKey(e);
1689
+ if (!e.defaultPrevented) onKeyDown(e);
1690
+ },
1691
+ onBlur: function(e) {
1692
+ if (listRef.current && e.relatedTarget && listRef.current.contains(e.relatedTarget)) return;
1693
+ if (open) close(false);
1694
+ if (selRef.current) selRef.current.dispatchEvent(new FocusEvent("focusout", { bubbles: true }));
1695
+ }
1696
+ },
1697
+ /* @__PURE__ */ React13.createElement("span", { id: id + "-value", className: cx("aura-select__value", shown[0].empty && "is-placeholder") }, shown[0].label || " ")
1698
+ ),
1699
+ /* @__PURE__ */ React13.createElement(Icon, { name: "chevron-down", className: "aura-select__chevron" }),
1700
+ popup
1701
+ )
1226
1702
  );
1227
1703
  });
1228
1704
 
@@ -1321,7 +1797,7 @@ var Switch = React15.forwardRef(function Switch2(props, ref) {
1321
1797
 
1322
1798
  // src/Combobox.tsx
1323
1799
  var React16 = __toESM(require("react"), 1);
1324
- var import_react_dom2 = require("react-dom");
1800
+ var import_react_dom3 = require("react-dom");
1325
1801
  function norm(s) {
1326
1802
  return String(s == null ? "" : s).normalize("NFC").toLocaleLowerCase("th");
1327
1803
  }
@@ -1341,6 +1817,7 @@ var Combobox = React16.forwardRef(
1341
1817
  const multi = all.multiple === true;
1342
1818
  const mp = all;
1343
1819
  const t = useStrings();
1820
+ const density = useDensity();
1344
1821
  const auto = uid(), id = props.id || auto, listId = id + "-list";
1345
1822
  const options = (props.options || []).map(toOpt);
1346
1823
  const st = useMaybeControlled(
@@ -1503,8 +1980,8 @@ var Combobox = React16.forwardRef(
1503
1980
  const optId = function(i) {
1504
1981
  return id + "-opt-" + i;
1505
1982
  };
1506
- const list = open && mounted && posState[0] ? (0, import_react_dom2.createPortal)(
1507
- /* @__PURE__ */ React16.createElement("div", { ref: listRef, className: "aura-combo__popover", style: posState[0] }, live.length ? /* @__PURE__ */ React16.createElement(
1983
+ const list = open && mounted && posState[0] ? (0, import_react_dom3.createPortal)(
1984
+ /* @__PURE__ */ React16.createElement("div", { ref: listRef, "data-density": density, className: "aura-combo__popover", style: posState[0] }, live.length ? /* @__PURE__ */ React16.createElement(
1508
1985
  "ul",
1509
1986
  {
1510
1987
  id: listId,
@@ -1664,7 +2141,7 @@ var Combobox = React16.forwardRef(
1664
2141
 
1665
2142
  // src/DatePicker.tsx
1666
2143
  var React17 = __toESM(require("react"), 1);
1667
- var import_react_dom3 = require("react-dom");
2144
+ var import_react_dom4 = require("react-dom");
1668
2145
 
1669
2146
  // src/dates.ts
1670
2147
  var ERA = /^พ\.ศ\.\s?|\s?(BE|พ\.ศ\.)$/g;
@@ -1672,20 +2149,29 @@ var pad = function(n2) {
1672
2149
  return (n2 < 10 ? "0" : "") + n2;
1673
2150
  };
1674
2151
  function toISO(d) {
1675
- return d ? d.getFullYear() + "-" + pad(d.getMonth() + 1) + "-" + pad(d.getDate()) : null;
2152
+ if (!d) return null;
2153
+ const y = String(d.getFullYear());
2154
+ return ("000" + y).slice(-Math.max(4, y.length)) + "-" + pad(d.getMonth() + 1) + "-" + pad(d.getDate());
2155
+ }
2156
+ function makeDate(y, monthIndex2, day) {
2157
+ const d = new Date(2e3, 0, 1);
2158
+ d.setFullYear(y, monthIndex2, day);
2159
+ return d;
1676
2160
  }
1677
2161
  function fromISO(s) {
1678
2162
  if (!s) return null;
1679
2163
  const m = /^(\d{4})-(\d{2})-(\d{2})$/.exec(s);
1680
- return m ? new Date(+m[1], +m[2] - 1, +m[3]) : null;
2164
+ if (!m) return null;
2165
+ const d = makeDate(+m[1], +m[2] - 1, +m[3]);
2166
+ return d.getMonth() === +m[2] - 1 && d.getDate() === +m[3] ? d : null;
1681
2167
  }
1682
2168
  function addDays(d, n2) {
1683
- return new Date(d.getFullYear(), d.getMonth(), d.getDate() + n2);
2169
+ return makeDate(d.getFullYear(), d.getMonth(), d.getDate() + n2);
1684
2170
  }
1685
2171
  function addMonths(d, n2) {
1686
- const t = new Date(d.getFullYear(), d.getMonth() + n2, 1);
1687
- const last = new Date(t.getFullYear(), t.getMonth() + 1, 0).getDate();
1688
- return new Date(t.getFullYear(), t.getMonth(), Math.min(d.getDate(), last));
2172
+ const t = makeDate(d.getFullYear(), d.getMonth() + n2, 1);
2173
+ const last = makeDate(t.getFullYear(), t.getMonth() + 1, 0).getDate();
2174
+ return makeDate(t.getFullYear(), t.getMonth(), Math.min(d.getDate(), last));
1689
2175
  }
1690
2176
  function same(a, b) {
1691
2177
  return !!a && !!b && a.getFullYear() === b.getFullYear() && a.getMonth() === b.getMonth() && a.getDate() === b.getDate();
@@ -1793,7 +2279,15 @@ function monthIndex(word) {
1793
2279
  return MONTHS[k] != null ? MONTHS[k] : -1;
1794
2280
  }
1795
2281
  function parseDate(text) {
1796
- const s = String(text || "").trim();
2282
+ const raw = String(text || "").trim();
2283
+ const gregorian = /ค\.ศ\.|\d\s*(AD|CE)\b|^\s*(AD|CE)\s/i.test(raw);
2284
+ let s = raw.replace(/พ\.ศ\.|ค\.ศ\./g, " ").replace(/(\d)\s*(BE|AD|CE)\b/gi, "$1 ").replace(/^\s*(BE|AD|CE)\s+/i, " ").replace(/\s+/g, " ").trim();
2285
+ const eight = /^(\d{2})(\d{2})(\d{4})$/.exec(s);
2286
+ if (eight) {
2287
+ const a = +eight[3] >= 1e3 ? parseDate(eight[1] + "/" + eight[2] + "/" + eight[3] + (gregorian ? " \u0E04.\u0E28." : "")) : null;
2288
+ if (a) return a;
2289
+ s = s.slice(0, 4) + "-" + s.slice(4, 6) + "-" + s.slice(6);
2290
+ }
1797
2291
  let m = /^(\d{4})-(\d{1,2})-(\d{1,2})$/.exec(s), y, mo, d;
1798
2292
  if (m) {
1799
2293
  y = +m[1];
@@ -1803,13 +2297,13 @@ function parseDate(text) {
1803
2297
  d = +m[1];
1804
2298
  mo = +m[2];
1805
2299
  y = +m[3];
1806
- } else if ((m = /^(\d{1,2})\s+(\S+)\s+(\d{4})$/.exec(s.replace(ERA, "").trim())) && monthIndex(m[2]) >= 0) {
2300
+ } else if ((m = /^(\d{1,2})\s+(\S+)\s+(\d{4})$/.exec(s)) && monthIndex(m[2]) >= 0) {
1807
2301
  d = +m[1];
1808
2302
  mo = monthIndex(m[2]) + 1;
1809
2303
  y = +m[3];
1810
2304
  } else return null;
1811
- if (y >= 2400) y -= 543;
1812
- const dt = new Date(y, mo - 1, d);
2305
+ if (y >= 2400 && !gregorian) y -= 543;
2306
+ const dt = makeDate(y, mo - 1, d);
1813
2307
  return dt.getMonth() === mo - 1 && dt.getDate() === d ? toISO(dt) : null;
1814
2308
  }
1815
2309
  function todayIn(timeZone) {
@@ -2100,16 +2594,16 @@ function useCalendarPopover(boxRef) {
2100
2594
  const pos = React17.useState(null), popRef = React17.useRef(null), mounted = useMounted();
2101
2595
  function place() {
2102
2596
  if (!boxRef.current) return;
2103
- const r = boxRef.current.getBoundingClientRect(), H = 380;
2104
- const up = window.innerHeight - r.bottom < H && r.top > H;
2105
- const left = Math.max(8, Math.min(r.left, window.innerWidth - 320 - 8));
2597
+ const el = popRef.current, r = boxRef.current.getBoundingClientRect(), W = el ? el.offsetWidth : 320, H = el ? el.offsetHeight : 380;
2598
+ const up = window.innerHeight - r.bottom < H + 12 && r.top > H + 12;
2599
+ const left = Math.max(8, Math.min(r.left, window.innerWidth - W - 8));
2106
2600
  pos[1](up ? { left, bottom: window.innerHeight - r.top + 4 } : { left, top: r.bottom + 4 });
2107
2601
  }
2108
2602
  useIsoLayoutEffect(
2109
2603
  function() {
2110
2604
  if (open) place();
2111
2605
  },
2112
- [open]
2606
+ [open, !!pos[0]]
2113
2607
  );
2114
2608
  React17.useEffect(
2115
2609
  function() {
@@ -2252,7 +2746,7 @@ var DatePicker = React17.forwardRef(function DatePicker2(props, ref) {
2252
2746
  pop.setOpen(false);
2253
2747
  if (inputRef.current) inputRef.current.focus();
2254
2748
  }
2255
- const cal = pop.open && pop.mounted && pop.pos ? (0, import_react_dom3.createPortal)(
2749
+ const cal = pop.open && pop.mounted && pop.pos ? (0, import_react_dom4.createPortal)(
2256
2750
  /* @__PURE__ */ React17.createElement(
2257
2751
  "div",
2258
2752
  {
@@ -2377,7 +2871,7 @@ var DateRangePicker = React17.forwardRef(
2377
2871
  draft[1](null);
2378
2872
  if (inputRef.current) inputRef.current.focus();
2379
2873
  }
2380
- function pick(iso) {
2874
+ function pick2(iso) {
2381
2875
  if (!draft[0]) {
2382
2876
  draft[1](iso);
2383
2877
  return;
@@ -2387,7 +2881,7 @@ var DateRangePicker = React17.forwardRef(
2387
2881
  st[1](a <= b ? { start: a, end: b } : { start: b, end: a });
2388
2882
  close();
2389
2883
  }
2390
- const cal = pop.open && pop.mounted && pop.pos ? (0, import_react_dom3.createPortal)(
2884
+ const cal = pop.open && pop.mounted && pop.pos ? (0, import_react_dom4.createPortal)(
2391
2885
  /* @__PURE__ */ React17.createElement(
2392
2886
  "div",
2393
2887
  {
@@ -2421,7 +2915,7 @@ var DateRangePicker = React17.forwardRef(
2421
2915
  start: draft[0] || v.start,
2422
2916
  end: draft[0] ? null : v.end,
2423
2917
  focus: draft[0] || v.start,
2424
- onSelect: pick
2918
+ onSelect: pick2
2425
2919
  }
2426
2920
  )
2427
2921
  ),
@@ -2491,7 +2985,7 @@ var Alert = React18.forwardRef(function Alert2(props, ref) {
2491
2985
 
2492
2986
  // src/Toaster.tsx
2493
2987
  var React19 = __toESM(require("react"), 1);
2494
- var import_react_dom4 = require("react-dom");
2988
+ var import_react_dom5 = require("react-dom");
2495
2989
  var MAX_VISIBLE = 3;
2496
2990
  var toastState = {
2497
2991
  list: [],
@@ -2652,7 +3146,7 @@ function Toaster(props) {
2652
3146
  };
2653
3147
  }, []);
2654
3148
  if (!mounted) return null;
2655
- return (0, import_react_dom4.createPortal)(
3149
+ return (0, import_react_dom5.createPortal)(
2656
3150
  /* @__PURE__ */ React19.createElement(
2657
3151
  "div",
2658
3152
  {
@@ -2933,7 +3427,7 @@ var FilterBar = React23.forwardRef(function FilterBar2(props, ref) {
2933
3427
 
2934
3428
  // src/Command.tsx
2935
3429
  var React25 = __toESM(require("react"), 1);
2936
- var import_react_dom5 = require("react-dom");
3430
+ var import_react_dom6 = require("react-dom");
2937
3431
 
2938
3432
  // src/useModal.tsx
2939
3433
  var React24 = __toESM(require("react"), 1);
@@ -3137,7 +3631,7 @@ function Command(props) {
3137
3631
  }
3138
3632
  if (!modal.ready) return null;
3139
3633
  let i = -1;
3140
- return (0, import_react_dom5.createPortal)(
3634
+ return (0, import_react_dom6.createPortal)(
3141
3635
  /* @__PURE__ */ React25.createElement(
3142
3636
  "div",
3143
3637
  {
@@ -3246,7 +3740,7 @@ function Command(props) {
3246
3740
 
3247
3741
  // src/Tooltip.tsx
3248
3742
  var React26 = __toESM(require("react"), 1);
3249
- var import_react_dom6 = require("react-dom");
3743
+ var import_react_dom7 = require("react-dom");
3250
3744
  var Tooltip = React26.forwardRef(function Tooltip2(props, ref) {
3251
3745
  const id = uid(), st = React26.useState(false), open = props.open !== void 0 ? props.open : st[0], set = st[1];
3252
3746
  const anchor = React26.useRef(null), anchorMerged = useMergedRef(ref, anchor), tip = React26.useRef(null), timer = React26.useRef(void 0);
@@ -3344,7 +3838,7 @@ var Tooltip = React26.forwardRef(function Tooltip2(props, ref) {
3344
3838
  },
3345
3839
  React26.cloneElement(child, { "aria-describedby": open ? id : child.props["aria-describedby"] })
3346
3840
  );
3347
- return /* @__PURE__ */ React26.createElement(React26.Fragment, null, trigger, open && mounted ? (0, import_react_dom6.createPortal)(
3841
+ return /* @__PURE__ */ React26.createElement(React26.Fragment, null, trigger, open && mounted ? (0, import_react_dom7.createPortal)(
3348
3842
  /* @__PURE__ */ React26.createElement(
3349
3843
  "div",
3350
3844
  {
@@ -3366,7 +3860,7 @@ var Tooltip = React26.forwardRef(function Tooltip2(props, ref) {
3366
3860
 
3367
3861
  // src/Dialog.tsx
3368
3862
  var React27 = __toESM(require("react"), 1);
3369
- var import_react_dom7 = require("react-dom");
3863
+ var import_react_dom8 = require("react-dom");
3370
3864
  var Dialog = React27.forwardRef(function Dialog2(props, ref) {
3371
3865
  const t = useStrings();
3372
3866
  const density = useDensity();
@@ -3381,7 +3875,7 @@ var Dialog = React27.forwardRef(function Dialog2(props, ref) {
3381
3875
  footSelector: ".aura-dialog__foot"
3382
3876
  });
3383
3877
  if (!modal.ready) return null;
3384
- return (0, import_react_dom7.createPortal)(
3878
+ return (0, import_react_dom8.createPortal)(
3385
3879
  /* @__PURE__ */ React27.createElement("div", { className: "aura-dialog-layer", "data-density": density, onKeyDown: modal.onKeyDown }, /* @__PURE__ */ React27.createElement("div", { className: "aura-scrim", onClick: close, "aria-hidden": true }), /* @__PURE__ */ React27.createElement(
3386
3880
  "div",
3387
3881
  {
@@ -3416,7 +3910,7 @@ var Drawer = React27.forwardRef(function Drawer2(props, ref) {
3416
3910
  });
3417
3911
  if (!modal.ready) return null;
3418
3912
  const side = props.side === "left" ? "left" : "right";
3419
- return (0, import_react_dom7.createPortal)(
3913
+ return (0, import_react_dom8.createPortal)(
3420
3914
  /* @__PURE__ */ React27.createElement("div", { className: "aura-dialog-layer aura-drawer-layer", "data-density": density, onKeyDown: modal.onKeyDown }, /* @__PURE__ */ React27.createElement("div", { className: "aura-scrim", onClick: close, "aria-hidden": true }), /* @__PURE__ */ React27.createElement(
3421
3915
  "div",
3422
3916
  {
@@ -3440,7 +3934,7 @@ var Drawer = React27.forwardRef(function Drawer2(props, ref) {
3440
3934
 
3441
3935
  // src/DataTable.tsx
3442
3936
  var React28 = __toESM(require("react"), 1);
3443
- var import_react_dom8 = require("react-dom");
3937
+ var import_react_dom9 = require("react-dom");
3444
3938
  var BP = { sm: 640, md: 768, lg: 1024, xl: 1280 };
3445
3939
  var DEFAULT_COLUMNS = [
3446
3940
  { key: "id", label: "ID", width: 96, mono: true },
@@ -3597,7 +4091,7 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
3597
4091
  function hideFull() {
3598
4092
  setTip(null);
3599
4093
  }
3600
- const tipEl = tip && typeof document !== "undefined" ? (0, import_react_dom8.createPortal)(
4094
+ const tipEl = tip && typeof document !== "undefined" ? (0, import_react_dom9.createPortal)(
3601
4095
  /* @__PURE__ */ React28.createElement(
3602
4096
  "div",
3603
4097
  {
@@ -3678,11 +4172,12 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
3678
4172
  if (lv && boxWidth[0] == null) hideTerms += " + " + w + "px * var(--aura-h" + lv + "-on, 1)";
3679
4173
  else fixedSum += w;
3680
4174
  });
3681
- let pinOffsets = {}, acc = 0;
4175
+ let pinOffsets = {}, acc = "0px";
3682
4176
  vis.forEach(function(c) {
3683
4177
  if (isPinned(c)) {
3684
4178
  pinOffsets[c.key] = acc;
3685
- acc += widthOf(c);
4179
+ const lv = hideLevel(c);
4180
+ acc += " + " + widthOf(c) + "px" + (lv && boxWidth[0] == null ? " * var(--aura-h" + lv + "-on, 1)" : "");
3686
4181
  }
3687
4182
  });
3688
4183
  const selW = selectable ? " + var(--aura-table-select-width)" : "";
@@ -3697,7 +4192,7 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
3697
4192
  s["--aura-cell-flex"] = !hasFlex && i === vis.length - 1 ? "1 0 auto" : "none";
3698
4193
  s["--aura-cell-w"] = w + "px";
3699
4194
  }
3700
- if (isPinned(c)) s["--aura-cell-left"] = "calc(var(--aura-space-6)" + selW + " + " + pinOffsets[c.key] + "px)";
4195
+ if (isPinned(c)) s["--aura-cell-left"] = "calc(var(--aura-space-6)" + selW + " + " + pinOffsets[c.key] + ")";
3701
4196
  return s;
3702
4197
  }
3703
4198
  const sortCol = sort && sort.key ? byKey[sort.key] : void 0;
@@ -3743,6 +4238,20 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
3743
4238
  const pageRows = pageSize && !manual ? view.slice(first, first + pageSize) : view;
3744
4239
  const canSortAny = !busy && (manual ? total > 1 : rows.length > 1);
3745
4240
  const shownTotal = manual && props.totalRows == null ? first + rows.length : total;
4241
+ const prevCount = React28.useRef(pageCount);
4242
+ React28.useEffect(
4243
+ function() {
4244
+ if (busy) return;
4245
+ const before = prevCount.current;
4246
+ prevCount.current = pageCount;
4247
+ const asked = pageState[0] || 1;
4248
+ if (asked === page || pageCount >= before || asked > before) return;
4249
+ if (props.getPageHref && !props.onPageChange && !props.onStateChange) return;
4250
+ pageState[1](page);
4251
+ emit(sort, page);
4252
+ },
4253
+ [pageState[0], page, busy, pageCount]
4254
+ );
3746
4255
  const linkPaging = !!props.getPageHref && !props.onPageChange && !oneCallback;
3747
4256
  const prevLink = React28.useRef(null), nextLink = React28.useRef(null), jumpLink = React28.useRef(null);
3748
4257
  const jumpState = React28.useState(null);
@@ -3811,9 +4320,10 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
3811
4320
  const visibleRows = Math.max(1, Math.floor(bodyH / ROW_H));
3812
4321
  const nCols = vis.length + (selectable ? 1 : 0);
3813
4322
  const nRows = loading ? 0 : pageRows.length;
4323
+ const hasTotal = !!(props.footer && rows.length && !loading), T = nRows + 1, lastR = nRows + (hasTotal ? 1 : 0);
3814
4324
  const active = activeState[0];
3815
- const ar = Math.min(active.r, nRows), ac = Math.min(active.c, nCols - 1);
3816
- const activeRendered = ar === 0 || ar - 1 >= start && ar - 1 < end;
4325
+ const ar = Math.min(active.r, lastR), ac = Math.min(active.c, nCols - 1);
4326
+ const activeRendered = ar === 0 || hasTotal && ar === T || ar - 1 >= start && ar - 1 < end;
3817
4327
  function colAt(ci) {
3818
4328
  return selectable ? ci === 0 ? null : vis[ci - 1] : vis[ci];
3819
4329
  }
@@ -3844,12 +4354,33 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
3844
4354
  }
3845
4355
  });
3846
4356
  function focusCell(r, c) {
3847
- r = Math.max(0, Math.min(r, nRows));
4357
+ r = Math.max(0, Math.min(r, lastR));
3848
4358
  c = Math.max(0, Math.min(c, nCols - 1));
3849
4359
  if (stacked && r === 0 && nRows > 0 && !(selectable && c === 0)) r = 1;
4360
+ if (gridRef.current && r === T && hasTotal) {
4361
+ const shown2 = function(cc) {
4362
+ const e = gridRef.current.querySelector('[data-rc="' + r + ":" + cc + '"]');
4363
+ return !!e && e.getClientRects().length > 0;
4364
+ };
4365
+ if (!shown2(c))
4366
+ for (let d = 1; d < nCols; d++) {
4367
+ if (c + d < nCols && shown2(c + d)) {
4368
+ c = c + d;
4369
+ break;
4370
+ }
4371
+ if (c - d >= 0 && shown2(c - d)) {
4372
+ c = c - d;
4373
+ break;
4374
+ }
4375
+ }
4376
+ }
3850
4377
  activeState[1]({ r, c });
3851
4378
  pending.current = { r, c };
3852
- if (virtual && r > 0) {
4379
+ if (virtual && hasTotal && r === T && !props.stickyFooter) {
4380
+ const sc = scrollRef.current;
4381
+ sc.scrollTop = sc.scrollHeight;
4382
+ setScrollTop(sc.scrollTop);
4383
+ } else if (virtual && r > 0 && r <= nRows) {
3853
4384
  const sc = scrollRef.current, top = (r - 1) * ROW_H;
3854
4385
  if (top < sc.scrollTop) sc.scrollTop = top;
3855
4386
  else if (top + ROW_H > sc.scrollTop + bodyH) sc.scrollTop = top + ROW_H - bodyH;
@@ -4092,7 +4623,7 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
4092
4623
  return;
4093
4624
  }
4094
4625
  const p = rc.split(":"), r = +p[0], c = +p[1], k = e.key, col = colAt(c);
4095
- const row = r > 0 ? pageRows[r - 1] : null;
4626
+ const row = r > 0 && r <= nRows ? pageRows[r - 1] : null, isTotal = hasTotal && r === T;
4096
4627
  let handled = true;
4097
4628
  if (r === 0 && col && e.altKey && (k === "ArrowLeft" || k === "ArrowRight") && canResize(col))
4098
4629
  setW(col, widthOf(col) + (k === "ArrowLeft" ? -1 : 1) * (e.shiftKey ? 48 : 16), true);
@@ -4103,21 +4634,23 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
4103
4634
  else if (k === "ArrowRight") focusCell(r, c + 1);
4104
4635
  else if (k === "ArrowLeft") focusCell(r, c - 1);
4105
4636
  else if (k === "ArrowDown") {
4106
- if (r < nRows) focusCell(r + 1, c);
4637
+ if (r < lastR) focusCell(r + 1, c);
4107
4638
  else if (pageSize && page < pageCount && goPage(page + 1, { r: 1, c })) activeState[1]({ r: 1, c });
4108
4639
  } else if (k === "ArrowUp") {
4109
4640
  if (r > 1 || r === 1 && !(pageSize && page > 1)) focusCell(r - 1, c);
4110
4641
  else if (r === 1 && goPage(page - 1, { r: pageSize, c })) activeState[1]({ r: pageSize, c });
4111
4642
  } else if (k === "Home") focusCell(e.ctrlKey ? 1 : r, 0);
4112
- else if (k === "End") focusCell(e.ctrlKey ? nRows : r, nCols - 1);
4643
+ else if (k === "End") focusCell(e.ctrlKey ? lastR : r, nCols - 1);
4113
4644
  else if (k === "PageDown") {
4114
4645
  if (pageSize) {
4115
4646
  if (goPage(page + 1, { r: 1, c })) activeState[1]({ r: 1, c });
4116
- } else focusCell(Math.min(nRows, r + visibleRows), c);
4647
+ } else focusCell(Math.min(lastR, r + visibleRows), c);
4117
4648
  } else if (k === "PageUp") {
4118
4649
  if (pageSize) {
4119
4650
  if (goPage(page - 1, { r: 1, c })) activeState[1]({ r: 1, c });
4120
4651
  } else focusCell(Math.max(1, r - visibleRows), c);
4652
+ } else if (isTotal && (k === " " || k === "Enter" || k === "F2")) {
4653
+ handled = false;
4121
4654
  } else if (k === "F2" && r > 0) {
4122
4655
  const inner = target.querySelector("button, a[href], input, select, textarea");
4123
4656
  if (inner) inner.focus();
@@ -4488,9 +5021,10 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
4488
5021
  }
4489
5022
  );
4490
5023
  }
5024
+ const openTotal = manual && props.totalRows == null && !!pageSize && rows.length >= pageSize;
4491
5025
  if (pageSize && (rows.length || busy || page > 1)) {
4492
5026
  const from = rows.length ? first + 1 : 0, to = manual ? first + rows.length : Math.min(first + pageSize, view.length);
4493
- foot = /* @__PURE__ */ React28.createElement("div", { className: "aura-table__foot" }, /* @__PURE__ */ React28.createElement("span", { "aria-live": "polite" }, busy ? t.loading : t.range(from, to, shownTotal)), /* @__PURE__ */ React28.createElement("span", { className: "aura-table__pager" }, /* @__PURE__ */ React28.createElement("span", null, t.page(page, pageCount)), pagerButton(-1), pagerButton(1)));
5027
+ foot = /* @__PURE__ */ React28.createElement("div", { className: "aura-table__foot" }, /* @__PURE__ */ React28.createElement("span", { "aria-live": "polite" }, busy ? t.loading : openTotal ? t.rangeOpen(from, to) : t.range(from, to, shownTotal)), /* @__PURE__ */ React28.createElement("span", { className: "aura-table__pager" }, /* @__PURE__ */ React28.createElement("span", null, openTotal ? t.pageOpen(page) : t.page(page, pageCount)), pagerButton(-1), pagerButton(1)));
4494
5028
  } else if (height && rows.length && !loading) {
4495
5029
  foot = /* @__PURE__ */ React28.createElement("div", { className: "aura-table__foot" }, /* @__PURE__ */ React28.createElement("span", null, t.rowCount(shownTotal)), selectable && selected.length ? /* @__PURE__ */ React28.createElement("span", null, t.selectedCount(selected.length)) : /* @__PURE__ */ React28.createElement("span", null));
4496
5030
  }
@@ -4504,15 +5038,32 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
4504
5038
  style: rowStyle
4505
5039
  },
4506
5040
  /* @__PURE__ */ React28.createElement("span", { className: "aura-table__gutter", "aria-hidden": true }),
4507
- selectable ? /* @__PURE__ */ React28.createElement("span", { className: cx("aura-table__sel", nPinned && "is-pinned"), "aria-hidden": true }) : null,
5041
+ selectable ? /* @__PURE__ */ React28.createElement(
5042
+ "span",
5043
+ {
5044
+ role: "gridcell",
5045
+ "aria-colindex": 1,
5046
+ className: cx("aura-table__sel", nPinned && "is-pinned"),
5047
+ tabIndex: tabFor(T, 0),
5048
+ "data-rc": T + ":0",
5049
+ onFocus: function() {
5050
+ activeState[1]({ r: T, c: 0 });
5051
+ }
5052
+ }
5053
+ ) : null,
4508
5054
  vis.map(function(c, j) {
4509
- const pin = isPinned(c);
5055
+ const pin = isPinned(c), ci = j + (selectable ? 1 : 0);
4510
5056
  return /* @__PURE__ */ React28.createElement(
4511
5057
  "span",
4512
5058
  {
4513
5059
  key: c.key,
4514
5060
  role: "gridcell",
4515
5061
  "aria-colindex": j + (selectable ? 2 : 1),
5062
+ tabIndex: tabFor(T, ci),
5063
+ "data-rc": T + ":" + ci,
5064
+ onFocus: function() {
5065
+ if (activeState[0].r !== T || activeState[0].c !== ci) activeState[1]({ r: T, c: ci });
5066
+ },
4516
5067
  className: cx(
4517
5068
  "aura-table__td",
4518
5069
  c.mono && "aura-table__mono",
@@ -4538,7 +5089,7 @@ var DataTable = React28.forwardRef(function DataTable2(props, ref) {
4538
5089
  )
4539
5090
  ) : null;
4540
5091
  const scrollStyle = {
4541
- scrollPaddingLeft: "calc(var(--aura-space-6)" + selW + " + " + acc + "px)",
5092
+ scrollPaddingLeft: "calc(var(--aura-space-6)" + selW + " + " + acc + ")",
4542
5093
  scrollPaddingTop: ROW_H + "px",
4543
5094
  scrollPaddingBottom: stickyTotal ? ROW_H + "px" : void 0
4544
5095
  };
@@ -4790,7 +5341,7 @@ var Tabs = React30.forwardRef(function Tabs2(props, ref) {
4790
5341
 
4791
5342
  // src/SideNav.tsx
4792
5343
  var React31 = __toESM(require("react"), 1);
4793
- var import_react_dom9 = require("react-dom");
5344
+ var import_react_dom10 = require("react-dom");
4794
5345
  function contains(it, id) {
4795
5346
  return !!id && !!it.children && it.children.some(function(c) {
4796
5347
  return c.id === id || contains(c, id);
@@ -4983,7 +5534,7 @@ var SideNav = React31.forwardRef(function SideNav2(props, ref) {
4983
5534
  }
4984
5535
  }
4985
5536
  )) : null,
4986
- tip && typeof document !== "undefined" ? (0, import_react_dom9.createPortal)(
5537
+ tip && typeof document !== "undefined" ? (0, import_react_dom10.createPortal)(
4987
5538
  /* @__PURE__ */ React31.createElement(
4988
5539
  "div",
4989
5540
  {
@@ -5427,7 +5978,7 @@ var Stat = React44.forwardRef(function Stat2(props, ref) {
5427
5978
 
5428
5979
  // src/TimePicker.tsx
5429
5980
  var React45 = __toESM(require("react"), 1);
5430
- var import_react_dom10 = require("react-dom");
5981
+ var import_react_dom11 = require("react-dom");
5431
5982
 
5432
5983
  // src/text.ts
5433
5984
  function formatBytes(n2) {
@@ -5450,6 +6001,7 @@ function parseTime(text) {
5450
6001
  const m = /^(\d{1,2})(?:[:.](\d{2}))?$/.exec(s) || /^(\d{1,2})(\d{2})$/.exec(s);
5451
6002
  if (!m) return null;
5452
6003
  let hh = +m[1], mm = m[2] ? +m[2] : 0;
6004
+ if ((am || pm) && (hh < 1 || hh > 12)) return null;
5453
6005
  if (pm && hh < 12) hh += 12;
5454
6006
  if (am && hh === 12) hh = 0;
5455
6007
  if (hh > 23 || mm > 59) return null;
@@ -5564,7 +6116,8 @@ var TimePicker = React45.forwardRef(function TimePicker2(props, ref) {
5564
6116
  return true;
5565
6117
  }
5566
6118
  if (blocked(v)) {
5567
- errState[1](t.timeOutOfRange(fromMin(lo), fromMin(hi)));
6119
+ const n2 = toMin(v);
6120
+ errState[1](n2 != null && n2 >= lo && n2 <= hi ? t.timeUnavailable : t.timeOutOfRange(fromMin(lo), fromMin(hi)));
5568
6121
  return false;
5569
6122
  }
5570
6123
  errState[1](null);
@@ -5641,7 +6194,7 @@ var TimePicker = React45.forwardRef(function TimePicker2(props, ref) {
5641
6194
  }
5642
6195
  }
5643
6196
  const error = errState[0] || props.error;
5644
- const list = open && mounted && pos[0] ? (0, import_react_dom10.createPortal)(
6197
+ const list = open && mounted && pos[0] ? (0, import_react_dom11.createPortal)(
5645
6198
  /* @__PURE__ */ React45.createElement("div", { ref: listRef, className: "aura-combo__popover aura-time__popover", style: pos[0] }, /* @__PURE__ */ React45.createElement("ul", { id: listId, role: "listbox", "aria-label": props.label, className: "aura-combo__list" }, slots.map(function(s, i) {
5646
6199
  const dis = blocked(s), sel = s === value;
5647
6200
  return /* @__PURE__ */ React45.createElement(
@@ -5823,6 +6376,7 @@ var FileUpload = React46.forwardRef(function FileUpload2(props, ref) {
5823
6376
  [items2, props.name]
5824
6377
  );
5825
6378
  function thumb(it) {
6379
+ if (!it.file && it.url && /^image\//.test(it.type || "")) return it.url;
5826
6380
  if (!it.file || !/^image\//.test(it.type || "") || typeof URL === "undefined" || !URL.createObjectURL) return null;
5827
6381
  if (!urls.current[it.id]) urls.current[it.id] = URL.createObjectURL(it.file);
5828
6382
  return urls.current[it.id];
@@ -5928,7 +6482,7 @@ var FileUpload = React46.forwardRef(function FileUpload2(props, ref) {
5928
6482
  ),
5929
6483
  items2.length ? /* @__PURE__ */ React46.createElement("ul", { className: "aura-upload__list", "aria-live": "polite" }, items2.map(function(it) {
5930
6484
  const src = thumb(it);
5931
- return /* @__PURE__ */ React46.createElement("li", { key: it.id, className: cx("aura-upload__item", it.error && "is-error") }, src ? /* @__PURE__ */ React46.createElement("img", { className: "aura-upload__thumb", src, alt: "" }) : /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__thumb is-icon", "aria-hidden": true }, /* @__PURE__ */ React46.createElement(Icon, { name: /^image\//.test(it.type || "") ? "image" : "file", size: "md" })), /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__meta" }, /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__name" }, it.name), /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__sub" }, it.error ? /* @__PURE__ */ React46.createElement(React46.Fragment, null, /* @__PURE__ */ React46.createElement(Icon, { name: "circle-alert", size: 12 }), it.error) : it.status === "uploading" ? t.uploading + (it.progress != null ? " " + Math.round(it.progress) + "%" : "") : it.status === "done" ? /* @__PURE__ */ React46.createElement(React46.Fragment, null, /* @__PURE__ */ React46.createElement(Icon, { name: "circle-check", size: 12 }), formatBytes(it.size)) : formatBytes(it.size)), it.status === "uploading" ? /* @__PURE__ */ React46.createElement(
6485
+ return /* @__PURE__ */ React46.createElement("li", { key: it.id, className: cx("aura-upload__item", it.error && "is-error") }, src ? /* @__PURE__ */ React46.createElement("img", { className: "aura-upload__thumb", src, alt: "" }) : /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__thumb is-icon", "aria-hidden": true }, /* @__PURE__ */ React46.createElement(Icon, { name: /^image\//.test(it.type || "") ? "image" : "file", size: "md" })), /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__meta" }, it.url && !it.error ? /* @__PURE__ */ React46.createElement("a", { className: "aura-upload__name", href: it.url, target: "_blank", rel: "noreferrer" }, it.name) : /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__name" }, it.name), /* @__PURE__ */ React46.createElement("span", { className: "aura-upload__sub" }, it.error ? /* @__PURE__ */ React46.createElement(React46.Fragment, null, /* @__PURE__ */ React46.createElement(Icon, { name: "circle-alert", size: 12 }), it.error) : it.status === "uploading" ? t.uploading + (it.progress != null ? " " + Math.round(it.progress) + "%" : "") : it.status === "done" ? /* @__PURE__ */ React46.createElement(React46.Fragment, null, /* @__PURE__ */ React46.createElement(Icon, { name: "circle-check", size: 12 }), formatBytes(it.size)) : formatBytes(it.size)), it.status === "uploading" ? /* @__PURE__ */ React46.createElement(
5932
6486
  "span",
5933
6487
  {
5934
6488
  className: "aura-upload__bar",
@@ -6631,15 +7185,22 @@ var Accordion = React54.forwardRef(function Accordion2(props, ref) {
6631
7185
 
6632
7186
  // src/Popover.tsx
6633
7187
  var React55 = __toESM(require("react"), 1);
6634
- var import_react_dom11 = require("react-dom");
7188
+ var import_react_dom12 = require("react-dom");
6635
7189
  function position(anchor, pop, placement) {
6636
- const r = anchor.getBoundingClientRect(), pw = pop.offsetWidth, ph = pop.offsetHeight, vw = window.innerWidth, vh = window.innerHeight, gap = 6;
7190
+ const r = anchor.getBoundingClientRect(), pw = pop.offsetWidth, ph = pop.scrollHeight, vw = window.innerWidth, vh = window.innerHeight, gap = 6;
6637
7191
  let side = (placement || "bottom-start").split("-")[0], align = (placement || "bottom-start").split("-")[1] || "start";
6638
7192
  if (side === "bottom" && r.bottom + gap + ph > vh - 8 && r.top - gap - ph > 8) side = "top";
6639
7193
  else if (side === "top" && r.top - gap - ph < 8 && r.bottom + gap + ph < vh - 8) side = "bottom";
6640
- const top = side === "top" ? r.top - gap - ph : r.bottom + gap;
7194
+ const below2 = vh - r.bottom - gap - 8, above = r.top - gap - 8;
7195
+ let maxHeight;
7196
+ if (ph > below2 && ph > above) {
7197
+ side = above > below2 ? "top" : "bottom";
7198
+ maxHeight = Math.max(120, side === "top" ? above : below2);
7199
+ }
7200
+ const h9 = maxHeight ? Math.min(ph, maxHeight) : ph;
7201
+ const top = side === "top" ? r.top - gap - h9 : r.bottom + gap;
6641
7202
  const left = align === "end" ? r.right - pw : align === "center" ? r.left + r.width / 2 - pw / 2 : r.left;
6642
- return { top: Math.max(8, top), left: Math.max(8, Math.min(left, vw - pw - 8)), side };
7203
+ return { top: Math.max(8, top), left: Math.max(8, Math.min(left, vw - pw - 8)), side, maxHeight };
6643
7204
  }
6644
7205
  var Popover = React55.forwardRef(function Popover2(props, ref) {
6645
7206
  const t = useStrings();
@@ -6702,7 +7263,7 @@ var Popover = React55.forwardRef(function Popover2(props, ref) {
6702
7263
  [open, mounted]
6703
7264
  );
6704
7265
  const child = React55.Children.only(props.trigger);
6705
- const panel = open && mounted ? (0, import_react_dom11.createPortal)(
7266
+ const panel = open && mounted ? (0, import_react_dom12.createPortal)(
6706
7267
  /* @__PURE__ */ React55.createElement(
6707
7268
  "div",
6708
7269
  {
@@ -6719,7 +7280,11 @@ var Popover = React55.forwardRef(function Popover2(props, ref) {
6719
7280
  },
6720
7281
  className: cx("aura-popover", pos[0] && "is-" + pos[0].side, props.className),
6721
7282
  style: Object.assign(
6722
- { top: pos[0] ? pos[0].top : -9999, left: pos[0] ? pos[0].left : -9999 },
7283
+ {
7284
+ top: pos[0] ? pos[0].top : -9999,
7285
+ left: pos[0] ? pos[0].left : -9999,
7286
+ maxHeight: pos[0] && pos[0].maxHeight ? pos[0].maxHeight : void 0
7287
+ },
6723
7288
  props.width ? { width: props.width } : null
6724
7289
  ),
6725
7290
  onKeyDown: function(e) {