@nxgt/material 3.42.1 → 3.44.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.
Files changed (102) hide show
  1. package/CHANGELOG.md +16 -0
  2. package/README.md +2 -2
  3. package/dist/{async-slice-Dj0tAKRI.js → async-slice-D9LAUgth.js} +2 -2
  4. package/dist/{button-CTsT_LqL.js → button-b_kruV_L.js} +1 -1
  5. package/dist/charts.js +3 -3
  6. package/dist/{chip-DP7EyhtT.js → chip-6O3t9GXt.js} +1 -1
  7. package/dist/{code-editor-BWn0AXBf.js → code-editor-BtDOgUET.js} +4 -4
  8. package/dist/code-editor.js +4 -4
  9. package/dist/{code-language-items-CCRuLYpA.js → code-language-items-374m-OK8.js} +2 -2
  10. package/dist/{components-7GE-Nyov.js → components-DMgim3_P.js} +21176 -20576
  11. package/dist/components.js +15 -15
  12. package/dist/{dialog-uQld1gKm.js → dialog-8Ua9uuJW.js} +1 -1
  13. package/dist/dnd.js +1 -1
  14. package/dist/{dropdown-menu-BA70o7HC.js → dropdown-menu-DJEeT1XT.js} +1 -1
  15. package/dist/editor.js +7 -7
  16. package/dist/{empty-state-BzwyRX5J.js → empty-state-CrhrmNqn.js} +1 -1
  17. package/dist/hooks.js +2 -2
  18. package/dist/{i18n-provider-DkeMr5bw.js → i18n-provider-hrtFm9jD.js} +1 -1
  19. package/dist/i18n.js +5 -5
  20. package/dist/{icon-badge-D_z5BGbc.js → icon-badge-Cpke1tCf.js} +1 -1
  21. package/dist/lib/components/ui/collections/page-footer/page-footer.d.ts +7 -3
  22. package/dist/lib/components/ui/dates/now-indicator/now-indicator.d.ts +9 -1
  23. package/dist/lib/components/ui/dates/now-indicator/now-indicator.utils.d.ts +2 -0
  24. package/dist/lib/components/ui/display/event-chip/event-chip.d.ts +3 -1
  25. package/dist/lib/components/ui/feedback/confirm-dialog/confirm-dialog.d.ts +8 -1
  26. package/dist/lib/components/ui/feedback/custom-dialog/custom-dialog.d.ts +6 -1
  27. package/dist/lib/components/ui/fields/contacts/placeholders.d.ts +1 -1
  28. package/dist/lib/components/ui/tone-color.d.ts +2 -0
  29. package/dist/lib/components/ui/widgets/event-calendar/event-calendar-context.d.ts +2 -0
  30. package/dist/lib/components/ui/widgets/event-calendar/event-calendar-events.utils.d.ts +8 -15
  31. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.axis.d.ts +49 -0
  32. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.d.ts +1 -1
  33. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.drop.d.ts +27 -0
  34. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.ids.d.ts +9 -2
  35. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.labels.d.ts +18 -0
  36. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.layout.d.ts +17 -0
  37. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.resources.d.ts +36 -0
  38. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.scroll.d.ts +7 -0
  39. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.slice.d.ts +28 -0
  40. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.utils.d.ts +0 -3
  41. package/dist/lib/components/ui/widgets/event-calendar/event-calendar.zone.d.ts +35 -0
  42. package/dist/lib/components/ui/widgets/event-calendar/index.d.ts +1 -1
  43. package/dist/lib/components/ui/widgets/event-calendar/partials/calendar-event-chip.d.ts +3 -1
  44. package/dist/lib/components/ui/widgets/event-calendar/partials/event-preview-resource.d.ts +6 -0
  45. package/dist/lib/components/ui/widgets/event-calendar/partials/event-preview-title.d.ts +11 -0
  46. package/dist/lib/components/ui/widgets/event-calendar/partials/event-preview.d.ts +3 -2
  47. package/dist/lib/components/ui/widgets/event-calendar/partials/event-resize-handle.d.ts +3 -2
  48. package/dist/lib/components/ui/widgets/event-calendar/partials/resource-all-day-lane.d.ts +6 -0
  49. package/dist/lib/components/ui/widgets/event-calendar/partials/resource-header.d.ts +12 -0
  50. package/dist/lib/components/ui/widgets/event-calendar/partials/resource-switcher.d.ts +9 -0
  51. package/dist/lib/components/ui/widgets/event-calendar/partials/time-column-now.d.ts +10 -0
  52. package/dist/lib/components/ui/widgets/event-calendar/partials/time-column.d.ts +12 -1
  53. package/dist/lib/components/ui/widgets/event-calendar/partials/time-grid-event.d.ts +6 -2
  54. package/dist/lib/components/ui/widgets/event-calendar/partials/time-grid-header-day.d.ts +9 -0
  55. package/dist/lib/components/ui/widgets/event-calendar/partials/time-grid-header.d.ts +4 -1
  56. package/dist/lib/components/ui/widgets/event-calendar/partials/time-grid-hours.d.ts +6 -0
  57. package/dist/lib/components/ui/widgets/event-calendar/partials/time-grid.d.ts +11 -4
  58. package/dist/lib/components/ui/widgets/event-calendar/partials/time-gutter.d.ts +9 -4
  59. package/dist/lib/components/ui/widgets/event-calendar/partials/tone-mark.d.ts +5 -0
  60. package/dist/lib/components/ui/widgets/event-calendar/partials/zone-corner.d.ts +10 -0
  61. package/dist/lib/components/ui/widgets/event-calendar/types.d.ts +42 -0
  62. package/dist/lib/components/ui/widgets/event-calendar/use-calendar-drag.d.ts +3 -0
  63. package/dist/lib/components/ui/widgets/event-calendar/use-calendar-keys.d.ts +3 -0
  64. package/dist/lib/components/ui/widgets/event-calendar/use-calendar-nav.d.ts +15 -0
  65. package/dist/lib/components/ui/widgets/event-calendar/use-chip-event.d.ts +13 -0
  66. package/dist/lib/components/ui/widgets/event-calendar/use-drawn-events.d.ts +9 -0
  67. package/dist/lib/components/ui/widgets/event-calendar/use-event-calendar.d.ts +9 -25
  68. package/dist/lib/components/ui/widgets/event-calendar/use-event-list.d.ts +18 -0
  69. package/dist/lib/components/ui/widgets/event-calendar/use-slot-create.d.ts +5 -4
  70. package/dist/lib/components/ui/widgets/event-calendar/use-time-column.d.ts +22 -0
  71. package/dist/lib/components/ui/widgets/event-calendar/use-time-grid.d.ts +36 -0
  72. package/dist/lib/i18n/resources/en/en.d.ts +3 -0
  73. package/dist/lib/i18n/resources/en/material.json.d.ts +4 -1
  74. package/dist/lib/i18n/resources/fr/fr.d.ts +3 -0
  75. package/dist/lib/i18n/resources/fr/material.json.d.ts +4 -1
  76. package/dist/lib/i18n/resources/resources.d.ts +6 -0
  77. package/dist/lib/i18n/translator.d.ts +1 -1
  78. package/dist/lib.js +1 -1
  79. package/dist/main.js +21 -21
  80. package/dist/map.js +4 -4
  81. package/dist/material.css +1 -1
  82. package/dist/pdf-reader.js +1 -1
  83. package/dist/print.js +2 -2
  84. package/dist/{public-ib0sK0Hr.js → public-DPPmNtZB.js} +6 -6
  85. package/dist/{rich-code-block-D_PTTZWQ.js → rich-code-block-KQYR0qt3.js} +4 -4
  86. package/dist/{sortable-provider-CrS51nKB.js → sortable-provider-hPPTMtJA.js} +632 -631
  87. package/dist/{spinner-DLd_IHev.js → spinner-Dd0os4cb.js} +1 -1
  88. package/dist/{stored-language-B5SMR-W2.js → stored-language-Blyb68vN.js} +8 -2
  89. package/dist/theme-picker.js +2 -2
  90. package/dist/{theme-toggle-wJYmnwgu.js → theme-toggle-BDRRkkiA.js} +1 -1
  91. package/dist/{toolbar-items-BLjrk8uU.js → toolbar-items-D3hw7XZE.js} +2 -2
  92. package/dist/{translate-material-BYRDtSEk.js → translate-material-CdJBbURx.js} +2 -2
  93. package/dist/{translator-C-_M57ZA.js → translator-38JuN_VD.js} +1 -1
  94. package/dist/{use-chat-composer-D_hfO99B.js → use-chat-composer-utGkZQ6X.js} +12 -12
  95. package/dist/{use-heading-spy-wElRpO2G.js → use-heading-spy-bTccmEMF.js} +1 -1
  96. package/dist/{use-material-translation-CFF73jk5.js → use-material-translation-DLsfkMxp.js} +2 -2
  97. package/docs/components/data-table-filter-and-lists.md +10 -2
  98. package/docs/components/date-and-time.md +2 -0
  99. package/docs/components/feedback-and-status.md +5 -1
  100. package/docs/components/rich-widgets.md +105 -2
  101. package/docs/troubleshooting.md +14 -0
  102. package/package.json +1 -1
@@ -1,6 +1,6 @@
1
1
  import { t as e } from "./utils-BLfntITJ.js";
2
2
  import { o as t } from "./tooltip-CkttDIab.js";
3
- import { t as n } from "./use-material-translation-CFF73jk5.js";
3
+ import { t as n } from "./use-material-translation-DLsfkMxp.js";
4
4
  import { jsx as r } from "react/jsx-runtime";
5
5
  //#region lib/components/ui/feedback/spinner/spinner.tsx
6
6
  var i = t("transition-all duration-500", {
@@ -1576,7 +1576,10 @@ var t = {
1576
1576
  delete: "Delete event",
1577
1577
  "delete-confirm": "This event will be removed.",
1578
1578
  "open-day": "Open {date}",
1579
- sidebar: "Calendar navigation"
1579
+ sidebar: "Calendar navigation",
1580
+ unassigned: "Unassigned",
1581
+ resource: "Resource",
1582
+ "time-zone": "Time zone: {zone}"
1580
1583
  },
1581
1584
  dnd: { drag: "Drag" },
1582
1585
  "rich-text-editor": {
@@ -4346,7 +4349,10 @@ var t = {
4346
4349
  delete: "Supprimer l'événement",
4347
4350
  "delete-confirm": "Cet événement sera retiré.",
4348
4351
  "open-day": "Ouvrir le {date}",
4349
- sidebar: "Navigation du calendrier"
4352
+ sidebar: "Navigation du calendrier",
4353
+ unassigned: "Non assigné",
4354
+ resource: "Ressource",
4355
+ "time-zone": "Fuseau horaire : {zone}"
4350
4356
  },
4351
4357
  dnd: { drag: "Déplacer" },
4352
4358
  "rich-text-editor": {
@@ -1,10 +1,10 @@
1
1
  import { t as e } from "./utils-BLfntITJ.js";
2
2
  import { a as t, i as n, n as r, o as i, r as a, t as o } from "./bubble-input-B7BVd9fX.js";
3
- import { t as s } from "./use-material-translation-CFF73jk5.js";
3
+ import { t as s } from "./use-material-translation-DLsfkMxp.js";
4
4
  import { a as c, r as l } from "./icon-sprites-CaYXzOL4.js";
5
5
  import { t as u } from "./use-theme-DMcyJ52N.js";
6
6
  import { a as d, r as f } from "./theme-context-Cofk6vgs.js";
7
- import { t as p } from "./theme-toggle-wJYmnwgu.js";
7
+ import { t as p } from "./theme-toggle-BDRRkkiA.js";
8
8
  import { n as m, t as h } from "./nxgt-theme-ZS945iMP.js";
9
9
  import { Check as g } from "lucide-react";
10
10
  import { useContext as _ } from "react";
@@ -1,4 +1,4 @@
1
- import { t as e } from "./use-material-translation-CFF73jk5.js";
1
+ import { t as e } from "./use-material-translation-DLsfkMxp.js";
2
2
  import { i as t } from "./theme-store-CSl51uNH.js";
3
3
  import { n, t as r } from "./use-theme-DMcyJ52N.js";
4
4
  import { r as i } from "./theme-context-Cofk6vgs.js";
@@ -4,9 +4,9 @@ import { a as i, c as a, i as o, l as s, r as c, s as l } from "./dist-lmHmz_bu.
4
4
  import { b as u, c as d, d as f, f as p, l as m, t as h, u as g, x as _ } from "./tooltip-CkttDIab.js";
5
5
  import { i as v, n as y, r as b, t as x } from "./dist-C4wtXCjf.js";
6
6
  import { a as S, c as C, l as w, o as T, r as ee, s as te, t as E } from "./in-dialog-Vwkyp-M5.js";
7
- import { A as ne, M as re, N as ie, b as ae, d as oe, f as se, i as ce, j as le, l as ue, n as de, o as fe, r as pe, t as me, u as he, y as ge } from "./dropdown-menu-BA70o7HC.js";
7
+ import { A as ne, M as re, N as ie, b as ae, d as oe, f as se, i as ce, j as le, l as ue, n as de, o as fe, r as pe, t as me, u as he, y as ge } from "./dropdown-menu-DJEeT1XT.js";
8
8
  import { a as _e, n as ve, r as ye, t as be } from "./dist-B7RjY7SL.js";
9
- import { t as xe } from "./use-material-translation-CFF73jk5.js";
9
+ import { t as xe } from "./use-material-translation-DLsfkMxp.js";
10
10
  import { t as Se } from "./warn-once-C_e47JM8.js";
11
11
  import { o as Ce } from "./escape-owner-C4W_sOAU.js";
12
12
  import { ChevronLeft as we, ChevronRightIcon as Te, MoreVertical as Ee } from "lucide-react";
@@ -1,5 +1,5 @@
1
- import "./stored-language-B5SMR-W2.js";
2
- import { a as e, r as t } from "./translator-C-_M57ZA.js";
1
+ import "./stored-language-Blyb68vN.js";
2
+ import { a as e, r as t } from "./translator-38JuN_VD.js";
3
3
  //#region lib/i18n/translate-material.ts
4
4
  function n(n, r, i, a) {
5
5
  if (n) for (let e of /* @__PURE__ */ new Set([n, n.split("-")[0]])) {
@@ -1,5 +1,5 @@
1
1
  import { t as e } from "./is-production-GLw59WU8.js";
2
- import { a as t, i as n, r, t as i } from "./stored-language-B5SMR-W2.js";
2
+ import { a as t, i as n, r, t as i } from "./stored-language-Blyb68vN.js";
3
3
  import { t as a } from "./get-CTzJAwfc.js";
4
4
  //#region ../../node_modules/@formatjs/fast-memoize/index.js
5
5
  function o(e, t) {
@@ -7,21 +7,21 @@ import { a as o, c as s, i as c, l, n as u, o as d, r as f, s as p, t as m } fro
7
7
  import { _ as h, a as g, g as _, h as v, m as y, o as b, p as x, t as S, v as C, y as w } from "./tooltip-CkttDIab.js";
8
8
  import { a as T, i as E, n as D, r as O, t as k } from "./dist-C4wtXCjf.js";
9
9
  import { i as A, n as ee, t as j } from "./in-dialog-Vwkyp-M5.js";
10
- import { A as M, C as N, D as te, E as ne, O as P, S as re, T as ie, _ as F, b as ae, f as oe, g as se, k as I, l as ce, m as le, n as ue, o as de, r as fe, s as pe, t as me, u as he, v as ge, w as _e, x as ve, y as ye } from "./dialog-uQld1gKm.js";
10
+ import { A as M, C as N, D as te, E as ne, O as P, S as re, T as ie, _ as F, b as ae, f as oe, g as se, k as I, l as ce, m as le, n as ue, o as de, r as fe, s as pe, t as me, u as he, v as ge, w as _e, x as ve, y as ye } from "./dialog-8Ua9uuJW.js";
11
11
  import { A as be, C as xe, D as Se, E as Ce, O as we, S as Te, T as Ee, _ as De, a as Oe, b as ke, d as Ae, f as je, g as Me, h as Ne, i as Pe, k as Fe, l as Ie, m as Le, n as Re, o as ze, p as Be, r as Ve, s as He, t as Ue, u as We, v as Ge, w as Ke, x as qe, y as Je } from "./floating-ui.dom-KkZSW8_E.js";
12
- import { D as Ye, E as Xe, N as Ze, O as Qe, c as $e, d as et, f as tt, i as nt, k as rt, m as it, n as at, o as ot, p as st, t as ct, u as lt } from "./dropdown-menu-BA70o7HC.js";
12
+ import { D as Ye, E as Xe, N as Ze, O as Qe, c as $e, d as et, f as tt, i as nt, k as rt, m as it, n as at, o as ot, p as st, t as ct, u as lt } from "./dropdown-menu-DJEeT1XT.js";
13
13
  import { a as ut, i as dt, n as ft } from "./field-blur-context-Cft9s7Hg.js";
14
- import { C as pt, S as mt, a as ht, c as gt, d as _t, l as vt, n as yt, o as bt, s as xt, u as St } from "./toolbar-items-BLjrk8uU.js";
14
+ import { C as pt, S as mt, a as ht, c as gt, d as _t, l as vt, n as yt, o as bt, s as xt, u as St } from "./toolbar-items-D3hw7XZE.js";
15
15
  import { a as Ct, i as wt, n as Tt, o as Et, t as Dt } from "./bubble-input-B7BVd9fX.js";
16
16
  import { i as Ot } from "./dist-B7RjY7SL.js";
17
- import "./stored-language-B5SMR-W2.js";
18
- import { a as kt } from "./translator-C-_M57ZA.js";
17
+ import "./stored-language-Blyb68vN.js";
18
+ import { a as kt } from "./translator-38JuN_VD.js";
19
19
  import { h as At } from "./get-CTzJAwfc.js";
20
20
  import { t as jt } from "./isEmpty-F_g3jLf8.js";
21
- import { t as L } from "./use-material-translation-CFF73jk5.js";
22
- import { t as Mt } from "./spinner-DLd_IHev.js";
21
+ import { t as L } from "./use-material-translation-DLsfkMxp.js";
22
+ import { t as Mt } from "./spinner-Dd0os4cb.js";
23
23
  import { a as Nt } from "./button-tones-BwuVvAmd.js";
24
- import { a as Pt, i as Ft, o as It, r as Lt, t as Rt } from "./button-CTsT_LqL.js";
24
+ import { a as Pt, i as Ft, o as It, r as Lt, t as Rt } from "./button-b_kruV_L.js";
25
25
  import { t as R } from "./icon-button-CN9r5TNE.js";
26
26
  import { a as zt, r as Bt } from "./icon-sprites-CaYXzOL4.js";
27
27
  import { t as Vt } from "./use-ssr-media-query-C6M5m8sf.js";
@@ -35,10 +35,10 @@ import { a as tn, i as nn, o as rn } from "./escape-owner-C4W_sOAU.js";
35
35
  import { n as an } from "./use-slice-reducer-BGkeGtML.js";
36
36
  import { t as on } from "./browser-only-DQ94lWF8.js";
37
37
  import { t as sn } from "./compose-refs-DZ0iIVF-.js";
38
- import { n as cn, r as ln, t as un } from "./chip-DP7EyhtT.js";
39
- import { n as dn, t as fn } from "./icon-badge-D_z5BGbc.js";
38
+ import { n as cn, r as ln, t as un } from "./chip-6O3t9GXt.js";
39
+ import { n as dn, t as fn } from "./icon-badge-Cpke1tCf.js";
40
40
  import { r as pn } from "./use-csp-nonce-ZKs9k-ov.js";
41
- import { t as mn } from "./empty-state-BzwyRX5J.js";
41
+ import { t as mn } from "./empty-state-CrhrmNqn.js";
42
42
  import { t as hn } from "./skeleton-DSdtr2qc.js";
43
43
  import { H as gn, V as _n, X as vn, bt as yn, it as bn, lt as xn, n as Sn, t as Cn, xt as wn, yt as Tn } from "./dist-moutbfbd.js";
44
44
  import { t as En } from "./markdown-Dw_uH7j7.js";
@@ -11082,7 +11082,7 @@ var RS = (e = {}) => Dn({
11082
11082
  let [{ default: t }, { lowlight: n }, { richCodeBlock: r }] = await Promise.all([
11083
11083
  import("./dist-CRMFGjng.js"),
11084
11084
  import("./lowlight-OtcjU2Sa.js"),
11085
- import("./rich-code-block-D_PTTZWQ.js")
11085
+ import("./rich-code-block-KQYR0qt3.js")
11086
11086
  ]);
11087
11087
  return [r(t, {
11088
11088
  lowlight: n,
@@ -1,4 +1,4 @@
1
- import { r as e } from "./i18n-provider-DkeMr5bw.js";
1
+ import { r as e } from "./i18n-provider-hrtFm9jD.js";
2
2
  import { _ as t, g as n, h as r, n as i, v as a, y as o } from "./number.utils-BG_eEt5g.js";
3
3
  import { useCallback as s, useEffect as c, useMemo as l, useRef as u } from "react";
4
4
  //#region ../../node_modules/date-fns/locale/fr/_lib/formatDistance.js
@@ -1,5 +1,5 @@
1
- import { r as e } from "./i18n-provider-DkeMr5bw.js";
2
- import { t } from "./translate-material-BYRDtSEk.js";
1
+ import { r as e } from "./i18n-provider-hrtFm9jD.js";
2
+ import { t } from "./translate-material-CdJBbURx.js";
3
3
  import { useCallback as n } from "react";
4
4
  //#region lib/i18n/use-material-translation.ts
5
5
  function r() {
@@ -17,7 +17,7 @@ either can be used alone.
17
17
  | <img src="../previews/data-table-filter-lists-servertable.webp" width="96" alt=""> | [ServerTable](#servertable) | A server-mode `DataTable` driven by the URL, with the Filter in its top band (a title and a description, or neither): sort, cursor paging, the empty page with a scene, an action and removable chips, one count announced |
18
18
  | <img src="../previews/data-table-filter-lists-rowmenu.webp" width="96" alt=""> | [RowMenu](#rowmenu) | A row's "..." button named after its row ("Actions for Ada"), its menu aligned to the end with the destructive item last, and `rowMenuColumn` to drop both in a table |
19
19
  | <img src="../previews/data-table-filter-lists-listempty.webp" width="96" alt=""> | [ListEmpty](#listempty) | A list's empty page: nothing yet, with a scene and an action, or nothing matches and the way out |
20
- | <img src="../previews/data-table-filter-lists-pagefooter.webp" width="96" alt=""> | [PageFooter](#pagefooter) | The page footer of a feed that is not a table (cards, a news feed) under a FilterBar: the range and Previous / Next as links from the URL's cursor trail, `pageControls="icon"` |
20
+ | <img src="../previews/data-table-filter-lists-pagefooter.webp" width="96" alt=""> | [PageFooter](#pagefooter) | The page footer of a feed that is not a table (cards, a news feed) under a FilterBar: the range and Previous / Next as links from the URL's cursor trail, `pageControls="icon"`; no `totalCount` for a feed with no total (no range, Previous / Next only) |
21
21
  | <img src="../previews/data-table-filter-lists-datagrid.webp" width="96" alt=""> | [DataGrid](#datagrid) | An editable grid: spreadsheet keys, paste, a fill handle with series, undo, totals, saving with versions and conflicts (lazy ones fetch theirs on "Keep mine"), `onRefuse` for a refused paste or fill, row selection (`enableRowSelection`), and resizable, hideable and reorderable columns (`columnControls`, `columnLayout`, `DataGridColumnsMenu`) |
22
22
  | <img src="../previews/data-table-filter-lists-daygroupedlist.webp" width="96" alt=""> | [DayGroupedList](#daygroupedlist) | A list split by day under sticky Today / Yesterday / Earlier headings |
23
23
  | <img src="../previews/data-table-filter-lists-filter.webp" width="96" alt=""> | [Filter](#filter) | Schema-driven filters with chips, presets and persistence |
@@ -932,6 +932,8 @@ export default function Students() {
932
932
  },
933
933
  ]}
934
934
  />
935
+ {/* A ConfirmDialog (or ConfirmationDialog, CustomDialog) takes the same
936
+ prop: onCloseAutoFocus={(e) => { e.preventDefault(); confirm?.focus(); }} */}
935
937
  <Dialog open={confirm != null} onOpenChange={(open) => !open && setConfirm(null)}>
936
938
  <DialogContent
937
939
  // Without this, the focus goes back to what Radix remembers, which is
@@ -1237,11 +1239,17 @@ import { FilterBar, PageFooter } from '@nxgt/material/components';
1237
1239
 
1238
1240
  Previous exists when the URL has a trail; Next when `pageInfo` has a next page and an `endCursor`. An end with no page is a disabled button with `aria-disabled`, not a link. Previous and Next are named "Previous" / "Next", or "Previous page" / "Next page" with `pageControls="icon"` (`material.table.pagination.*` keys, as the table's).
1239
1241
 
1242
+ A cursor feed whose API answers `pageInfo` and the items but no total (a news or notifications feed) leaves `totalCount` out: the footer shows no range (never a made-up total), only the controls, usually with `pageControls="icon"`, and still renders nothing for an empty first page.
1243
+
1244
+ ```tsx
1245
+ <PageFooter pageInfo={pageInfo} params={params} pageSize={20} count={items.length} pageControls="icon" />
1246
+ ```
1247
+
1240
1248
  | Prop | Type | Default | Effect |
1241
1249
  | --- | --- | --- | --- |
1242
1250
  | `params` | `URLSearchParams` | — | the page's search params: the trail is read from them and every other param is kept in the hrefs |
1243
1251
  | `pageInfo` | `{ hasNextPage, endCursor? }` | — | the connection's page info |
1244
- | `totalCount` | `number` | — | items matching the query across every page |
1252
+ | `totalCount` | `number` | — | items matching the query across every page; leave it out for a cursor feed with no total: no range, only the Previous / Next controls (Next disabled once `pageInfo.hasNextPage` is false) |
1245
1253
  | `pageSize` | `number` | — | items per page; it places the range from the trail |
1246
1254
  | `count` | `number` | `pageSize` | items on this page, for a short last page |
1247
1255
  | `pageHref` | `(params) => string` | ``?${params}`` | a page's href |
@@ -963,6 +963,8 @@ import { NowIndicator } from '@nxgt/material/components';
963
963
  | `tone` | `'strong' \| 'subtle'` | `'strong'` | a line with a dot, named "Current time: 10:40"; or a faint line, hidden from assistive technology |
964
964
  | `showTime` | `boolean` | `false` | the time in a pill before the line, in the gutter at the parent's left |
965
965
  | `timeFormat` | `string` | `'HH:mm'` | the time's date-fns format |
966
+ | `minutes` | `number` | — | the minute to draw at, counted like `startMinutes`, instead of reading `now`'s clock (a column that keeps its own time, such as a day in another time zone); `now` still gates the line |
967
+ | `timeLabel` | `string` | `now` in `timeFormat` | the text of the `showTime` pill |
966
968
 
967
969
  `useNow()` is the clock behind it (`null` until mounted), and `nowPosition()`
968
970
  the maths.
@@ -226,6 +226,7 @@ function DeleteProject({ onDelete }: { onDelete: () => Promise<void> }) {
226
226
  | `lockOnRefusal` | `boolean` | `false` | once `onConfirm` has refused (thrown), the confirm button stays disabled while its error shows, so a retry that cannot succeed is not invited; Cancel stays enabled. The error clears when the dialog closes |
227
227
  | `confirmLabel` / `cancelLabel` | `string` | "Confirm" / "Cancel", translated (`material.confirm-dialog.confirm` / `.cancel`) | button text |
228
228
  | `cancelVariant` | `ButtonVariant` | `'tonal'` | the Cancel button's variant; `'outlined'` restores the earlier look |
229
+ | `onCloseAutoFocus` | `(event: Event) => void` | — | called as the dialog closes, before the focus goes back; `event.preventDefault()` places it yourself, e.g. `ctx.focusTrigger()` of a `ServerTable` bulk action whose button a redraw replaced |
229
230
 
230
231
  On a phone (below 640 px) the footer stacks. A `destructive` dialog puts Cancel first and the destructive action last; a default one keeps the action on top.
231
232
 
@@ -234,7 +235,9 @@ it hands the focus back to what opened it, or to the menu's trigger when
234
235
  that was a `DropdownMenuItem` (gone by then); `Dialog`, `Sheet` and
235
236
  `Drawer` do the same.
236
237
  `ConfirmationDialog` is a `Dialog` and focuses its first control (its form
237
- field, or its first button).
238
+ field, or its first button). `ConfirmDialog`, `ConfirmationDialog` and
239
+ `CustomDialog` take `onCloseAutoFocus`: opened from a `ServerTable` bulk
240
+ action, pass `onCloseAutoFocus={(e) => { e.preventDefault(); ctx.focusTrigger(); }}`.
238
241
 
239
242
  ![ConfirmationDialog](../previews/feedback-status-confirmationdialog.webp)
240
243
 
@@ -327,6 +330,7 @@ import { Atom } from 'lucide-react';
327
330
  | `title` / `description` | `ReactNode` | — | hidden when empty |
328
331
  | `footer` | `ReactNode` | — | after a separator; omitted when empty |
329
332
  | `open` / `onOpenChange` | Radix `Dialog` props | uncontrolled | control it from outside |
333
+ | `onCloseAutoFocus` | `(event: Event) => void` | — | called as it closes, before the focus goes back; `event.preventDefault()` places it yourself |
330
334
 
331
335
  **Storybook:** `Feedback & status/CustomDialog` · **Vue:** `CustomDialog`
332
336
 
@@ -8,7 +8,7 @@ the app owns the data.
8
8
  | --- | --- | --- |
9
9
  | <img src="../previews/rich-widgets-chat-overview.webp" width="96" alt=""> | [Chat kit](#chat-kit) | Inbox, thread, grouped bubbles with receipts and replies, composer with quick replies, floating widget |
10
10
  | <img src="../previews/rich-widgets-kanban.webp" width="96" alt=""> | [Kanban](#kanban) | Board with columns, swimlanes, WIP limits and drag-and-drop |
11
- | <img src="../previews/rich-widgets-eventcalendar.webp" width="96" alt=""> | [EventCalendar](#eventcalendar) | Month / week / day / agenda calendar, phone to desktop |
11
+ | <img src="../previews/rich-widgets-eventcalendar.webp" width="96" alt=""> | [EventCalendar](#eventcalendar) | Month / week / day / agenda calendar, a day view split by resource, a named time zone, phone to desktop |
12
12
  | <img src="../previews/rich-widgets-native-charts-linechart.webp" width="96" alt=""> | [Charts](#charts) | Native SVG charts (line, area, bar, pie, donut, gauge, radial, funnel, heat map, radar, scatter, combo) with keyboard, summary and View data; the Nivo ones were removed in 3.0 |
13
13
  | <img src="../previews/rich-widgets-drawing.webp" width="96" alt=""> | [Drawing](#drawing) | Vector drawing from a scene of plain data or JSX primitives: theme colours, accessible, focusable nodes, strict-CSP safe |
14
14
  | <img src="../previews/rich-widgets-emojipicker.webp" width="96" alt=""> | [EmojiPicker](#emojipicker) | Shared emoji picker and list |
@@ -243,8 +243,111 @@ function Schedule() {
243
243
  | `phoneView` | `EventCalendarView` | — | the view while 767px or narrower, until one is picked |
244
244
  | `now` | `Date` | the clock | today and the now line — fix it in tests and demos |
245
245
  | `scrollToHour` | `number` | `7` | the hour the week and day views open on when today is not shown |
246
+ | `resources` | `EventCalendarResource[]` | — | the day view draws one column per resource, see [Resources](#eventcalendar-resources) |
247
+ | `timeZone` | `string` | the machine's | an IANA zone the grid, today and the times follow, see [Time zone](#eventcalendar-time-zone) |
246
248
 
247
- **Storybook:** `Rich widgets/EventCalendar`, `Rich widgets/EventCalendar/Layouts` · **Vue:** `EventCalendar` (the new props and layouts: React only for now, #892)
249
+ **Short events.** Events that do not overlap in time share a column and keep the
250
+ full width. An event is drawn at least 24px tall only where there is free space
251
+ below it (up to the next event); back-to-back short events sit flush at their
252
+ true heights, so at 52px an hour a 20-minute event is 17px tall (13px compact).
253
+
254
+ **Accessibility.** Back-to-back short events render as chips 17px tall (13px in
255
+ compact density), under the 24px target size of WCAG 2.5.8. This is an accepted
256
+ trade-off: each event stays reachable by keyboard (Tab and the arrow keys move
257
+ through the events), and the agenda view lists every event in full, which is the
258
+ accessible route.
259
+
260
+ ### EventCalendar resources
261
+
262
+ `resources` splits the **day view** into one column per room, person or team
263
+ (the week, workweek, month and agenda views ignore it: resources are day-view
264
+ only, and a week keeps its days). Give each event a
265
+ `resourceId`:
266
+
267
+ ```tsx
268
+ import { EventCalendar, type CalendarEvent } from '@nxgt/material/components';
269
+
270
+ const resources = [
271
+ { id: 'a', label: 'Room A', description: 'Ground floor' },
272
+ { id: 'b', label: 'Room B' },
273
+ ];
274
+ const events: CalendarEvent[] = [
275
+ { id: '1', title: 'Visit 1', start: '2026-03-12T09:00:00Z', end: '2026-03-12T10:00:00Z', resourceId: 'a' },
276
+ { id: '2', title: 'Visit 2', start: '2026-03-12T09:00:00Z', end: '2026-03-12T09:30:00Z', resourceId: 'b' },
277
+ ];
278
+
279
+ <EventCalendar
280
+ view="day"
281
+ date="2026-03-12"
282
+ events={events}
283
+ resources={resources}
284
+ onChange={({ event }) => save(event.id, event.resourceId)}
285
+ onSlotClick={(slot) => create(slot.start, slot.end, slot.resourceId)}
286
+ />;
287
+ ```
288
+
289
+ - **Columns.** A sticky header names each resource (its `label`, and the
290
+ `description` under it) while the hours scroll; the columns share the width
291
+ and scroll sideways under 11rem each. The all-day lane is per resource too.
292
+ - **Tone.** In the day view, a resource may take a `tone` (one of the library's tones, or one the
293
+ app declared, never a raw colour): a small mark beside its name in the header
294
+ and in the phone switcher, and the colour of that column's events that set no
295
+ `color` of their own.
296
+ - **Unassigned.** An event with no `resourceId`, or one that matches no
297
+ resource, shares a leading "Unassigned" column. It is drawn only while such
298
+ an event exists, so a calendar whose events all have a resource has none.
299
+ - **Moving.** Dragging an event into another column sets its `resourceId` (into
300
+ "Unassigned" removes it) and keeps the time it was dropped at, in the same
301
+ `onChange` as a plain move: `change.event.resourceId` is the new one,
302
+ `change.previous.resourceId` the old. Dragging and resizing inside a column
303
+ keep it. In the day view, the popover that opens on an event also has a
304
+ **Resource** select (the keyboard's way to reassign), and `Ctrl`+arrow moves keep the column.
305
+ `onSlotClick` receives the column's id as `slot.resourceId` (none for
306
+ "Unassigned").
307
+ - **Phone.** At 767px or less a select (named "Resource") shows one resource
308
+ at a time, never squeezed columns; it starts on the first column.
309
+ - **Accessibility.** Each column is a `group` named by the resource and the
310
+ date (`Room A, Thursday, March 12th, 2026`), and an event's name includes
311
+ its resource (`Visit 1, Room A`).
312
+
313
+ ### EventCalendar time zone
314
+
315
+ `timeZone` (an IANA name such as `Africa/Lagos`) makes the calendar read that
316
+ zone's wall clock. Without it, nothing changes: the machine's clock.
317
+
318
+ - **What follows the zone:** the grid's hours, "today" and the date the
319
+ calendar opens on, the now line and its pill, the day boundaries (an event
320
+ that is after midnight in the zone is on the next day), the times on chips,
321
+ in the agenda and in the popover, and the corner of the time grid, which
322
+ names the zone's offset (`UTC+9`; the popover does too).
323
+ - **What stays true:** `start` and `end` are instants and stay so. The `Date`s
324
+ given to `onSlotClick` and the `start` / `end` written by `onChange` are
325
+ real instants too; an all-day slot or event runs from the zone's midnight to
326
+ its next midnight. The week, month and agenda views derive their days from
327
+ the zone the same way.
328
+ - **Clock changes.** The **day view** draws the day's real length: 23 hours of
329
+ axis on the day the clocks go forward (the hour lines skip the missing hour)
330
+ and 25 on the day they go back (the repeated hour is drawn twice). An event
331
+ is placed by elapsed time, so one that crosses the change keeps its real
332
+ duration. The week and workweek views keep **24 wall-clock rows** a day, so
333
+ the hours line up across the columns. Dragging or resizing turns the dropped
334
+ position into an instant with the helpers of `@nxgt/material-core/zone`: a
335
+ moved event keeps its wall-clock time on the other day (09:00 stays 09:00
336
+ across a change, though the offset differs), and a time the day skips lands
337
+ after the gap.
338
+ - **Labels.** The times on chips, the agenda and the popover are read from the
339
+ true instants with the zone's own clock, never through the browser's date
340
+ maths: a wall time the browser's zone skips (its own clock change) still
341
+ reads as it is in the calendar's zone.
342
+ - **Unknown zone.** A name `Intl` does not know reads `UTC`, as the other date
343
+ fields do, with one development warning.
344
+
345
+ ```tsx
346
+ // 09:00 in Tokyo is drawn at 09:00 whatever zone the browser is in.
347
+ <EventCalendar view="day" date="2026-03-12" timeZone="Asia/Tokyo" events={events} />
348
+ ```
349
+
350
+ **Storybook:** `Rich widgets/EventCalendar`, `Rich widgets/EventCalendar/Layouts`, `Rich widgets/EventCalendar/Resources`, `Rich widgets/EventCalendar/Resources on a phone`, `Rich widgets/EventCalendar/Resources a11y`, `Rich widgets/EventCalendar/Time zone`, `Rich widgets/EventCalendar/Back to back`, `Rich widgets/EventCalendar/Resource tone`, `Rich widgets/EventCalendar/Hydration` · **Vue:** `EventCalendar` (the new props and layouts, `resources` and `timeZone`: React only for now, #892 and #1780)
248
351
 
249
352
  ---
250
353
 
@@ -137,6 +137,7 @@ words in your error.
137
137
  - [`defineFilterModel: field "period" scope needs a default operator taking one value`](#definefiltermodel-field-period-scope-needs-a-default-operator-taking-one-value)
138
138
  - [`errors` shows nothing on the filter bar](#errors-shows-nothing-on-the-filter-bar)
139
139
  - [`@nxgt/material-core/filter: unknown time zone "…", using the runtime's`](#nxgtmaterial-corefilter-unknown-time-zone--using-the-runtimes)
140
+ - [`` [@nxgt/material] EventCalendar: unknown timeZone "Mars/Olympus", reading UTC instead. ``](#nxgtmaterial-eventcalendar-unknown-timezone-marsolympus-reading-utc-instead)
140
141
  - [``Filter: the autocomplete field(s) … have neither `options` nor a `search` in `fieldProps`: their editor has nothing to offer.``](#filter-the-autocomplete-fields--have-neither-options-nor-a-search-in-fieldprops-their-editor-has-nothing-to-offer)
141
142
  - [`Filter bar parts must be used inside <Filter variant="bar">`](#filter-bar-parts-must-be-used-inside-filter-variantbar)
142
143
  - [A date preset's count differs between the server and the page](#a-date-presets-count-differs-between-the-server-and-the-page)
@@ -2577,6 +2578,19 @@ const clock = {
2577
2578
  const conditions = resolveDateConditions(effectiveConditions(query, model, locked), model, clock);
2578
2579
  ```
2579
2580
 
2581
+ ### `` [@nxgt/material] EventCalendar: unknown timeZone "Mars/Olympus", reading UTC instead. ``
2582
+
2583
+ **When:** in development, once per name, when `EventCalendar`'s `timeZone` is not
2584
+ an IANA name `Intl` knows (`'Paris'`, `'UTC+2'`, a typo).
2585
+ **Why:** the calendar reads `UTC` instead, as the other date fields and
2586
+ `@nxgt/material-core/zone` do, so a server and a browser draw the same grid; the
2587
+ hours are then off by the zone's offset.
2588
+ **Fix:** pass an IANA name (`'Europe/Paris'`, `'Africa/Lagos'`):
2589
+
2590
+ ```tsx
2591
+ <EventCalendar view="day" timeZone="Europe/Paris" events={events} />
2592
+ ```
2593
+
2580
2594
  ### ``Filter: the autocomplete field(s) … have neither `options` nor a `search` in `fieldProps`: their editor has nothing to offer.``
2581
2595
 
2582
2596
  **When:** in the console in development, when `Filter variant="bar"` or
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nxgt/material",
3
- "version": "3.42.1",
3
+ "version": "3.44.0",
4
4
  "license": "MIT",
5
5
  "bugs": {
6
6
  "email": "stevegires@gmail.com"