@jirawatpyk/aura-react 5.13.0 → 5.14.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.
- package/README.md +13 -0
- package/dist/aura.bundle.js +138 -85
- package/dist/cjs/index.cjs +138 -85
- package/dist/esm/AppShell.js +69 -24
- package/dist/esm/Avatar.js +4 -32
- package/dist/esm/Button.js +4 -2
- package/dist/esm/Stat.js +2 -30
- package/dist/esm/Tabs.js +1 -1
- package/dist/esm/display.js +75 -2
- package/dist/index.d.cts +11 -1
- package/dist/index.d.ts +11 -1
- package/dist/server/index.cjs +78 -1
- package/dist/server/index.d.cts +48 -1
- package/dist/server/index.d.ts +48 -1
- package/dist/server/index.js +78 -1
- package/dist/styles.css +29 -5
- package/dist/styles.layer.css +29 -5
- package/package.json +1 -1
package/dist/esm/AppShell.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
import * as React from "react";
|
|
3
3
|
import { Drawer } from "./Dialog.js";
|
|
4
4
|
import { IconButton } from "./IconButton.js";
|
|
5
|
-
import { cx } from "./internal.js";
|
|
5
|
+
import { cx, useIsoLayoutEffect, useMergedRef } from "./internal.js";
|
|
6
6
|
import { useStrings } from "./locale.js";
|
|
7
7
|
import { useBreakpoint } from "./responsive.js";
|
|
8
8
|
import { IconMenu } from "./icons.js";
|
|
@@ -24,6 +24,27 @@ const AppShell = React.forwardRef(function AppShell2(props, ref) {
|
|
|
24
24
|
if (shared) navState[1](id);
|
|
25
25
|
if (navEl && navEl.props.onChange) navEl.props.onChange(id);
|
|
26
26
|
}
|
|
27
|
+
const rootRef = React.useRef(null);
|
|
28
|
+
const barRef = React.useRef(null);
|
|
29
|
+
const mergedRef = useMergedRef(ref, rootRef);
|
|
30
|
+
const hasBar = !!(props.header || props.nav);
|
|
31
|
+
useIsoLayoutEffect(
|
|
32
|
+
function() {
|
|
33
|
+
const root = rootRef.current, bar = barRef.current;
|
|
34
|
+
if (!root || !bar) return;
|
|
35
|
+
function sync() {
|
|
36
|
+
root.style.setProperty("--aura-shell-bar-height", bar.getBoundingClientRect().height + "px");
|
|
37
|
+
}
|
|
38
|
+
sync();
|
|
39
|
+
const ro = typeof ResizeObserver === "undefined" ? null : new ResizeObserver(sync);
|
|
40
|
+
if (ro) ro.observe(bar);
|
|
41
|
+
return function() {
|
|
42
|
+
if (ro) ro.disconnect();
|
|
43
|
+
root.style.removeProperty("--aura-shell-bar-height");
|
|
44
|
+
};
|
|
45
|
+
},
|
|
46
|
+
[hasBar]
|
|
47
|
+
);
|
|
27
48
|
const deskNav = navEl && shared ? React.cloneElement(navEl, { value: navState[0], onChange: onNav }) : props.nav;
|
|
28
49
|
const drawerNav = navEl ? React.cloneElement(navEl, {
|
|
29
50
|
value: shared ? navState[0] : navEl.props.value,
|
|
@@ -35,32 +56,56 @@ const AppShell = React.forwardRef(function AppShell2(props, ref) {
|
|
|
35
56
|
collapsed: false,
|
|
36
57
|
collapsible: false
|
|
37
58
|
}) : props.nav;
|
|
38
|
-
return /* @__PURE__ */ React.createElement(
|
|
39
|
-
|
|
59
|
+
return /* @__PURE__ */ React.createElement(
|
|
60
|
+
"div",
|
|
40
61
|
{
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
62
|
+
ref: mergedRef,
|
|
63
|
+
className: cx(
|
|
64
|
+
"aura-shell",
|
|
65
|
+
props.bottomNav && "aura-shell--bottomnav",
|
|
66
|
+
/* 5.14: no top bar at all, or one that only holds the menu button (gone from lg up): the bar-height token is 0. */
|
|
67
|
+
!props.header && !props.nav && "aura-shell--no-bar",
|
|
68
|
+
!props.header && props.nav && "aura-shell--menu-bar",
|
|
69
|
+
props.className
|
|
70
|
+
)
|
|
49
71
|
},
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
72
|
+
props.nav ? /* @__PURE__ */ React.createElement("div", { className: "aura-shell__nav" }, deskNav) : null,
|
|
73
|
+
props.nav ? /* @__PURE__ */ React.createElement(
|
|
74
|
+
Drawer,
|
|
75
|
+
{
|
|
76
|
+
open,
|
|
77
|
+
onClose: function() {
|
|
78
|
+
setOpen(false);
|
|
79
|
+
},
|
|
80
|
+
side: "left",
|
|
81
|
+
size: "nav",
|
|
82
|
+
"aria-label": props.navLabel || t.navigation,
|
|
83
|
+
dismissible: true
|
|
84
|
+
},
|
|
85
|
+
drawerNav
|
|
86
|
+
) : null,
|
|
87
|
+
/* @__PURE__ */ React.createElement("div", { className: "aura-shell__main" }, props.header || props.nav ? /* @__PURE__ */ React.createElement("header", { ref: barRef, className: cx("aura-shell__bar", !props.header && "aura-shell__bar--menu-only") }, props.nav ? /* @__PURE__ */ React.createElement(
|
|
88
|
+
IconButton,
|
|
89
|
+
{
|
|
90
|
+
className: "aura-shell__menu",
|
|
91
|
+
icon: /* @__PURE__ */ React.createElement(IconMenu, null),
|
|
92
|
+
label: props.menuLabel || t.openNav,
|
|
93
|
+
size: "md",
|
|
94
|
+
onClick: function() {
|
|
95
|
+
setOpen(true);
|
|
96
|
+
},
|
|
97
|
+
"aria-expanded": open
|
|
98
|
+
}
|
|
99
|
+
) : null, /* @__PURE__ */ React.createElement("div", { className: "aura-shell__bar-content" }, props.header)) : null, /* @__PURE__ */ React.createElement(
|
|
100
|
+
"main",
|
|
101
|
+
{
|
|
102
|
+
className: cx("aura-shell__content", props.contentPadding === false && "is-flush"),
|
|
103
|
+
id: props.mainId || "main",
|
|
104
|
+
tabIndex: -1
|
|
60
105
|
},
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
)
|
|
106
|
+
props.children
|
|
107
|
+
), props.bottomNav || null)
|
|
108
|
+
);
|
|
64
109
|
});
|
|
65
110
|
export {
|
|
66
111
|
AppShell
|
package/dist/esm/Avatar.js
CHANGED
|
@@ -1,39 +1,11 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import * as React from "react";
|
|
3
|
-
import {
|
|
4
|
-
const AVATAR_TONES = ["progress", "ready", "neutral", "warning"];
|
|
5
|
-
function initials(name) {
|
|
6
|
-
const parts = String(name || "?").trim().split(/\s+/);
|
|
7
|
-
return ((parts[0] || "?")[0] + (parts.length > 1 ? parts[parts.length - 1][0] : parts[0][1] || "")).toUpperCase();
|
|
8
|
-
}
|
|
3
|
+
import { avatarElement } from "./display.js";
|
|
9
4
|
const Avatar = React.forwardRef(function Avatar2(props, ref) {
|
|
10
|
-
const
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
hash = hash * 31 + ch.charCodeAt(0) >>> 0;
|
|
5
|
+
const errState = React.useState(null);
|
|
6
|
+
return avatarElement(props, ref, errState[0], function() {
|
|
7
|
+
errState[1](props.src || null);
|
|
14
8
|
});
|
|
15
|
-
const tone = AVATAR_TONES[hash % AVATAR_TONES.length];
|
|
16
|
-
return /* @__PURE__ */ React.createElement(
|
|
17
|
-
"span",
|
|
18
|
-
{
|
|
19
|
-
ref,
|
|
20
|
-
className: cx("aura-avatar", "aura-avatar--" + size, "aura-avatar--" + tone, props.className),
|
|
21
|
-
role: "img",
|
|
22
|
-
"aria-label": props.name + (props.status ? ", " + props.status : "")
|
|
23
|
-
},
|
|
24
|
-
props.src && errState[0] !== props.src ? /* @__PURE__ */ React.createElement(
|
|
25
|
-
"img",
|
|
26
|
-
{
|
|
27
|
-
key: props.src,
|
|
28
|
-
src: props.src,
|
|
29
|
-
alt: "",
|
|
30
|
-
onError: function() {
|
|
31
|
-
errState[1](props.src || null);
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
) : /* @__PURE__ */ React.createElement("span", { "aria-hidden": true }, initials(props.name)),
|
|
35
|
-
props.status === "online" ? /* @__PURE__ */ React.createElement("span", { className: "aura-avatar__status", "aria-hidden": true }) : null
|
|
36
|
-
);
|
|
37
9
|
});
|
|
38
10
|
export {
|
|
39
11
|
Avatar
|
package/dist/esm/Button.js
CHANGED
|
@@ -52,6 +52,8 @@ const Button = React.forwardRef(
|
|
|
52
52
|
const props = all;
|
|
53
53
|
const variant = props.variant || "primary";
|
|
54
54
|
const loading = !!props.loading;
|
|
55
|
+
const ad = props["aria-disabled"];
|
|
56
|
+
const blocked = loading || ad === true || ad === "true";
|
|
55
57
|
const rest = omit(props, [
|
|
56
58
|
"variant",
|
|
57
59
|
"className",
|
|
@@ -78,8 +80,8 @@ const Button = React.forwardRef(
|
|
|
78
80
|
className: props.className
|
|
79
81
|
}),
|
|
80
82
|
"aria-busy": loading || void 0,
|
|
81
|
-
"aria-disabled":
|
|
82
|
-
onClick:
|
|
83
|
+
"aria-disabled": blocked || void 0,
|
|
84
|
+
onClick: blocked ? function(e) {
|
|
83
85
|
e.preventDefault();
|
|
84
86
|
} : props.onClick
|
|
85
87
|
},
|
package/dist/esm/Stat.js
CHANGED
|
@@ -1,38 +1,10 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import * as React from "react";
|
|
3
|
-
import { cx } from "./internal.js";
|
|
4
|
-
import { Icon } from "./Icon.js";
|
|
5
3
|
import { useLinkComponent } from "./locale.js";
|
|
6
|
-
import {
|
|
4
|
+
import { statElement } from "./display.js";
|
|
7
5
|
const Stat = React.forwardRef(function Stat2(props, ref) {
|
|
8
|
-
const ch = props.change;
|
|
9
|
-
const dir = ch && (ch.direction || "flat");
|
|
10
|
-
const tone = ch && (ch.tone || (dir === "up" ? "positive" : dir === "down" ? "negative" : "neutral"));
|
|
11
6
|
const Link = useLinkComponent(props.linkComponent);
|
|
12
|
-
|
|
13
|
-
const numeric = typeof v === "number" || typeof v === "string" && /\d/.test(v) && /^[\s\d.,:+\-\u2212%()\u0E3F$\u20AC\u00A3\u00A5kKmMbB]+$/.test(v.replace(/\b[A-Z]{3}\b/g, ""));
|
|
14
|
-
const Tag = props.href ? Link : props.onClick ? "button" : "div";
|
|
15
|
-
const interactive = !!(props.href || props.onClick);
|
|
16
|
-
return /* @__PURE__ */ React.createElement(
|
|
17
|
-
Tag,
|
|
18
|
-
{
|
|
19
|
-
ref,
|
|
20
|
-
className: cx("aura-stat", interactive && "is-interactive", props.loading && "is-loading", props.className),
|
|
21
|
-
href: props.href,
|
|
22
|
-
onClick: props.onClick,
|
|
23
|
-
type: Tag === "button" ? "button" : void 0,
|
|
24
|
-
"aria-busy": props.loading || void 0
|
|
25
|
-
},
|
|
26
|
-
/* @__PURE__ */ React.createElement("span", { className: "aura-stat__head" }, /* @__PURE__ */ React.createElement("span", { className: "aura-stat__label" }, props.label), props.icon ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__icon" }, /* @__PURE__ */ React.createElement(Icon, { name: props.icon })) : null),
|
|
27
|
-
props.loading ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__value" }, /* @__PURE__ */ React.createElement("span", { className: "aura-skel aura-stat__skel" })) : /* @__PURE__ */ React.createElement("span", { className: cx("aura-stat__value", numeric && "is-numeric") }, props.value, props.unit ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__unit" }, props.unit) : null),
|
|
28
|
-
ch && !props.loading || props.caption ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__foot" }, ch && !props.loading ? /* @__PURE__ */ React.createElement("span", { className: cx("aura-stat__change", "is-" + tone) }, /* @__PURE__ */ React.createElement(
|
|
29
|
-
Icon,
|
|
30
|
-
{
|
|
31
|
-
name: dir === "up" ? /* @__PURE__ */ React.createElement(IconTrendingUp, null) : dir === "down" ? /* @__PURE__ */ React.createElement(IconTrendingDown, null) : /* @__PURE__ */ React.createElement(IconMinus, null),
|
|
32
|
-
size: 14
|
|
33
|
-
}
|
|
34
|
-
), /* @__PURE__ */ React.createElement("span", null, ch.value)) : null, ch && ch.label && !props.loading ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__caption" }, ch.label) : null, props.caption ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__caption" }, props.caption) : null) : null
|
|
35
|
-
);
|
|
7
|
+
return statElement(props, ref, Link);
|
|
36
8
|
});
|
|
37
9
|
export {
|
|
38
10
|
Stat
|
package/dist/esm/Tabs.js
CHANGED
|
@@ -81,7 +81,7 @@ const Tabs = React.forwardRef(function Tabs2(props, ref) {
|
|
|
81
81
|
key: t.id,
|
|
82
82
|
href: t.href,
|
|
83
83
|
className: tabCls(on, own.className),
|
|
84
|
-
"aria-current": on ? "page" : void 0,
|
|
84
|
+
"aria-current": on ? props.current || "page" : void 0,
|
|
85
85
|
onClick: function(e) {
|
|
86
86
|
if (own.onClick) own.onClick(e);
|
|
87
87
|
if (e.defaultPrevented || e.button !== 0 || e.metaKey || e.ctrlKey || e.shiftKey || e.altKey) return;
|
package/dist/esm/display.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import * as React from "react";
|
|
3
3
|
import { Icon } from "./Icon.js";
|
|
4
|
-
import { cx, omit, tone as badgeTone } from "./classes.js";
|
|
4
|
+
import { cx, devWarnOnce, omit, tone as badgeTone } from "./classes.js";
|
|
5
5
|
import { toneFor } from "./status.js";
|
|
6
6
|
import {
|
|
7
7
|
IconBan,
|
|
@@ -11,6 +11,9 @@ import {
|
|
|
11
11
|
IconCircleDotDashed,
|
|
12
12
|
IconInbox,
|
|
13
13
|
IconInfo,
|
|
14
|
+
IconMinus,
|
|
15
|
+
IconTrendingDown,
|
|
16
|
+
IconTrendingUp,
|
|
14
17
|
IconTriangleAlert
|
|
15
18
|
} from "./icons.js";
|
|
16
19
|
const h = React.createElement;
|
|
@@ -101,7 +104,7 @@ function badgeElement(props, ref) {
|
|
|
101
104
|
);
|
|
102
105
|
}
|
|
103
106
|
function emptyStateElement(props, ref) {
|
|
104
|
-
const HT = "h" + (props.headingLevel || 3);
|
|
107
|
+
const HT = props.headingLevel === false ? "p" : "h" + (props.headingLevel || 3);
|
|
105
108
|
const rest = omit(props, [
|
|
106
109
|
"title",
|
|
107
110
|
"description",
|
|
@@ -133,6 +136,66 @@ function emptyStateElement(props, ref) {
|
|
|
133
136
|
props.action ? /* @__PURE__ */ React.createElement("div", { className: "aura-empty__action" }, props.action) : null
|
|
134
137
|
);
|
|
135
138
|
}
|
|
139
|
+
function statElement(props, ref, Link) {
|
|
140
|
+
const ch = props.change;
|
|
141
|
+
const dir = ch && (ch.direction || "flat");
|
|
142
|
+
const tone = ch && (ch.tone || (dir === "up" ? "positive" : dir === "down" ? "negative" : "neutral"));
|
|
143
|
+
const v = props.value;
|
|
144
|
+
const numeric = typeof v === "number" || typeof v === "string" && /\d/.test(v) && /^[\s\d.,:+\-\u2212%()\u0E3F$\u20AC\u00A3\u00A5kKmMbB]+$/.test(v.replace(/\b[A-Z]{3}\b/g, ""));
|
|
145
|
+
const Tag = props.href ? Link : props.onClick ? "button" : "div";
|
|
146
|
+
const interactive = !!(props.href || props.onClick);
|
|
147
|
+
if (props.headingLevel && Tag === "button")
|
|
148
|
+
devWarnOnce(
|
|
149
|
+
"stat-heading-button",
|
|
150
|
+
"Stat `headingLevel` is ignored with `onClick`: a heading can\u2019t sit in a button. Use `href`, or put the heading outside."
|
|
151
|
+
);
|
|
152
|
+
const LabelTag = props.headingLevel && Tag !== "button" ? "h" + props.headingLevel : "span";
|
|
153
|
+
const HeadTag = LabelTag === "span" ? "span" : "div";
|
|
154
|
+
return /* @__PURE__ */ React.createElement(
|
|
155
|
+
Tag,
|
|
156
|
+
{
|
|
157
|
+
ref,
|
|
158
|
+
className: cx("aura-stat", interactive && "is-interactive", props.loading && "is-loading", props.className),
|
|
159
|
+
href: props.href,
|
|
160
|
+
onClick: props.onClick,
|
|
161
|
+
type: Tag === "button" ? "button" : void 0,
|
|
162
|
+
"aria-busy": props.loading || void 0
|
|
163
|
+
},
|
|
164
|
+
/* @__PURE__ */ React.createElement(HeadTag, { className: "aura-stat__head" }, /* @__PURE__ */ React.createElement(LabelTag, { className: "aura-stat__label" }, props.label), props.icon ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__icon" }, /* @__PURE__ */ React.createElement(Icon, { name: props.icon })) : null),
|
|
165
|
+
props.loading ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__value" }, /* @__PURE__ */ React.createElement("span", { className: "aura-skel aura-stat__skel" })) : /* @__PURE__ */ React.createElement("span", { className: cx("aura-stat__value", numeric && "is-numeric") }, props.value, props.unit ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__unit" }, props.unit) : null),
|
|
166
|
+
ch && !props.loading || props.caption ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__foot" }, ch && !props.loading ? /* @__PURE__ */ React.createElement("span", { className: cx("aura-stat__change", "is-" + tone) }, /* @__PURE__ */ React.createElement(
|
|
167
|
+
Icon,
|
|
168
|
+
{
|
|
169
|
+
name: dir === "up" ? /* @__PURE__ */ React.createElement(IconTrendingUp, null) : dir === "down" ? /* @__PURE__ */ React.createElement(IconTrendingDown, null) : /* @__PURE__ */ React.createElement(IconMinus, null),
|
|
170
|
+
size: 14
|
|
171
|
+
}
|
|
172
|
+
), /* @__PURE__ */ React.createElement("span", null, ch.value)) : null, ch && ch.label && !props.loading ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__caption" }, ch.label) : null, props.caption ? /* @__PURE__ */ React.createElement("span", { className: "aura-stat__caption" }, props.caption) : null) : null
|
|
173
|
+
);
|
|
174
|
+
}
|
|
175
|
+
const AVATAR_TONES = ["progress", "ready", "neutral", "warning"];
|
|
176
|
+
function initials(name) {
|
|
177
|
+
const parts = String(name || "?").trim().split(/\s+/);
|
|
178
|
+
return ((parts[0] || "?")[0] + (parts.length > 1 ? parts[parts.length - 1][0] : parts[0][1] || "")).toUpperCase();
|
|
179
|
+
}
|
|
180
|
+
function avatarElement(props, ref, broken, onError) {
|
|
181
|
+
const size = props.size || "md";
|
|
182
|
+
let hash = 0;
|
|
183
|
+
String(props.name || "").split("").forEach(function(ch) {
|
|
184
|
+
hash = hash * 31 + ch.charCodeAt(0) >>> 0;
|
|
185
|
+
});
|
|
186
|
+
const tone = AVATAR_TONES[hash % AVATAR_TONES.length];
|
|
187
|
+
return /* @__PURE__ */ React.createElement(
|
|
188
|
+
"span",
|
|
189
|
+
{
|
|
190
|
+
ref,
|
|
191
|
+
className: cx("aura-avatar", "aura-avatar--" + size, "aura-avatar--" + tone, props.className),
|
|
192
|
+
role: "img",
|
|
193
|
+
"aria-label": props.name + (props.status ? ", " + props.status : "")
|
|
194
|
+
},
|
|
195
|
+
props.src && broken !== props.src ? /* @__PURE__ */ React.createElement("img", { key: props.src, src: props.src, alt: "", onError }) : /* @__PURE__ */ React.createElement("span", { "aria-hidden": true }, initials(props.name)),
|
|
196
|
+
props.status === "online" ? /* @__PURE__ */ React.createElement("span", { className: "aura-avatar__status", "aria-hidden": true }) : null
|
|
197
|
+
);
|
|
198
|
+
}
|
|
136
199
|
function buttonClass(opts = {}) {
|
|
137
200
|
return cx(
|
|
138
201
|
"aura-btn",
|
|
@@ -158,17 +221,27 @@ function ServerBadge(props) {
|
|
|
158
221
|
function ServerEmptyState(props) {
|
|
159
222
|
return emptyStateElement(props, void 0);
|
|
160
223
|
}
|
|
224
|
+
function ServerStat(props) {
|
|
225
|
+
return statElement(omit(props, ["onClick"]), void 0, props.linkComponent || "a");
|
|
226
|
+
}
|
|
227
|
+
function ServerAvatar(props) {
|
|
228
|
+
return avatarElement(props, void 0, null, void 0);
|
|
229
|
+
}
|
|
161
230
|
export {
|
|
162
231
|
ALERT_ICON,
|
|
163
232
|
ServerAlert,
|
|
233
|
+
ServerAvatar,
|
|
164
234
|
ServerBadge,
|
|
165
235
|
ServerCard,
|
|
166
236
|
ServerEmptyState,
|
|
237
|
+
ServerStat,
|
|
167
238
|
ServerStatusPill,
|
|
168
239
|
alertElement,
|
|
240
|
+
avatarElement,
|
|
169
241
|
badgeElement,
|
|
170
242
|
buttonClass,
|
|
171
243
|
cardElement,
|
|
172
244
|
emptyStateElement,
|
|
245
|
+
statElement,
|
|
173
246
|
statusPillElement
|
|
174
247
|
};
|
package/dist/index.d.cts
CHANGED
|
@@ -660,6 +660,9 @@ export interface TabsProps {
|
|
|
660
660
|
variant?: "underline" | "segmented" | undefined;
|
|
661
661
|
/** With `variant="segmented"`: stretch the track to the full width, tabs sharing it equally. (5.10) */
|
|
662
662
|
fullWidth?: boolean | undefined;
|
|
663
|
+
/** Link tabs: what the current link is (5.14). `page` (default) for routes; `location` for links to sections of
|
|
664
|
+
* this page (`#contacts`). */
|
|
665
|
+
current?: "page" | "location" | undefined;
|
|
663
666
|
}
|
|
664
667
|
export interface NavItem {
|
|
665
668
|
id: string;
|
|
@@ -996,6 +999,8 @@ export interface AppShellProps {
|
|
|
996
999
|
/** A BottomNav for phones (4.19). Shown below its `hideFrom` breakpoint; the content keeps room for it, and a
|
|
997
1000
|
* viewport ActionBar sits on top of it. With a `bottomNav` and no `nav`, there is no menu button. */
|
|
998
1001
|
bottomNav?: React$1.ReactElement | undefined;
|
|
1002
|
+
/** `false` (5.14): `<main>` has no padding, for pages whose containers own the page padding and column. */
|
|
1003
|
+
contentPadding?: boolean | undefined;
|
|
999
1004
|
className?: string | undefined;
|
|
1000
1005
|
}
|
|
1001
1006
|
export interface SeparatorProps {
|
|
@@ -1122,6 +1127,9 @@ export interface StatProps {
|
|
|
1122
1127
|
/** Makes the whole card a link or a button (drill-down). */
|
|
1123
1128
|
href?: string | undefined;
|
|
1124
1129
|
onClick?: (() => void) | undefined;
|
|
1130
|
+
/** The label as a heading of this level (5.14), when the tile titles its section. Not with `onClick` (a heading
|
|
1131
|
+
* can't sit in a button); a link is fine. Default: a plain label. */
|
|
1132
|
+
headingLevel?: 2 | 3 | 4 | 5 | 6 | undefined;
|
|
1125
1133
|
className?: string | undefined;
|
|
1126
1134
|
}
|
|
1127
1135
|
export interface TimePickerProps extends FieldProps {
|
|
@@ -1232,7 +1240,9 @@ export interface EmptyStateProps extends Omit<React$1.HTMLAttributes<HTMLDivElem
|
|
|
1232
1240
|
/** `danger` (5.13) for a failure — the data couldn't load: the danger tint, a danger-coloured icon, and a solid
|
|
1233
1241
|
* danger frame with `bordered`. It stays quiet; pass `role="alert"` if it must interrupt. Default `neutral`. */
|
|
1234
1242
|
tone?: "neutral" | "danger" | undefined;
|
|
1235
|
-
|
|
1243
|
+
/** The title's heading level (default 3); `false` (5.14) makes it a paragraph, for a card or list whose outline
|
|
1244
|
+
* mustn't change. EmptyState has no live-region role unless you pass `role`. */
|
|
1245
|
+
headingLevel?: 2 | 3 | 4 | 5 | 6 | false | undefined;
|
|
1236
1246
|
className?: string | undefined;
|
|
1237
1247
|
}
|
|
1238
1248
|
export interface PaginationProps {
|
package/dist/index.d.ts
CHANGED
|
@@ -660,6 +660,9 @@ export interface TabsProps {
|
|
|
660
660
|
variant?: "underline" | "segmented" | undefined;
|
|
661
661
|
/** With `variant="segmented"`: stretch the track to the full width, tabs sharing it equally. (5.10) */
|
|
662
662
|
fullWidth?: boolean | undefined;
|
|
663
|
+
/** Link tabs: what the current link is (5.14). `page` (default) for routes; `location` for links to sections of
|
|
664
|
+
* this page (`#contacts`). */
|
|
665
|
+
current?: "page" | "location" | undefined;
|
|
663
666
|
}
|
|
664
667
|
export interface NavItem {
|
|
665
668
|
id: string;
|
|
@@ -996,6 +999,8 @@ export interface AppShellProps {
|
|
|
996
999
|
/** A BottomNav for phones (4.19). Shown below its `hideFrom` breakpoint; the content keeps room for it, and a
|
|
997
1000
|
* viewport ActionBar sits on top of it. With a `bottomNav` and no `nav`, there is no menu button. */
|
|
998
1001
|
bottomNav?: React$1.ReactElement | undefined;
|
|
1002
|
+
/** `false` (5.14): `<main>` has no padding, for pages whose containers own the page padding and column. */
|
|
1003
|
+
contentPadding?: boolean | undefined;
|
|
999
1004
|
className?: string | undefined;
|
|
1000
1005
|
}
|
|
1001
1006
|
export interface SeparatorProps {
|
|
@@ -1122,6 +1127,9 @@ export interface StatProps {
|
|
|
1122
1127
|
/** Makes the whole card a link or a button (drill-down). */
|
|
1123
1128
|
href?: string | undefined;
|
|
1124
1129
|
onClick?: (() => void) | undefined;
|
|
1130
|
+
/** The label as a heading of this level (5.14), when the tile titles its section. Not with `onClick` (a heading
|
|
1131
|
+
* can't sit in a button); a link is fine. Default: a plain label. */
|
|
1132
|
+
headingLevel?: 2 | 3 | 4 | 5 | 6 | undefined;
|
|
1125
1133
|
className?: string | undefined;
|
|
1126
1134
|
}
|
|
1127
1135
|
export interface TimePickerProps extends FieldProps {
|
|
@@ -1232,7 +1240,9 @@ export interface EmptyStateProps extends Omit<React$1.HTMLAttributes<HTMLDivElem
|
|
|
1232
1240
|
/** `danger` (5.13) for a failure — the data couldn't load: the danger tint, a danger-coloured icon, and a solid
|
|
1233
1241
|
* danger frame with `bordered`. It stays quiet; pass `role="alert"` if it must interrupt. Default `neutral`. */
|
|
1234
1242
|
tone?: "neutral" | "danger" | undefined;
|
|
1235
|
-
|
|
1243
|
+
/** The title's heading level (default 3); `false` (5.14) makes it a paragraph, for a card or list whose outline
|
|
1244
|
+
* mustn't change. EmptyState has no live-region role unless you pass `role`. */
|
|
1245
|
+
headingLevel?: 2 | 3 | 4 | 5 | 6 | false | undefined;
|
|
1236
1246
|
className?: string | undefined;
|
|
1237
1247
|
}
|
|
1238
1248
|
export interface PaginationProps {
|
package/dist/server/index.cjs
CHANGED
|
@@ -31,11 +31,13 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
|
|
|
31
31
|
var server_exports = {};
|
|
32
32
|
__export(server_exports, {
|
|
33
33
|
Alert: () => ServerAlert,
|
|
34
|
+
Avatar: () => ServerAvatar,
|
|
34
35
|
Badge: () => ServerBadge,
|
|
35
36
|
Card: () => ServerCard,
|
|
36
37
|
EmptyState: () => ServerEmptyState,
|
|
37
38
|
Icon: () => Icon,
|
|
38
39
|
STRINGS: () => STRINGS,
|
|
40
|
+
Stat: () => ServerStat,
|
|
39
41
|
StatusPill: () => ServerStatusPill,
|
|
40
42
|
brandScale: () => scale,
|
|
41
43
|
breakpoints: () => breakpoints,
|
|
@@ -1015,6 +1017,7 @@ var Icon = React2.forwardRef(function Icon2(props, ref) {
|
|
|
1015
1017
|
var iconNames = Object.keys(map);
|
|
1016
1018
|
|
|
1017
1019
|
// src/icons.ts
|
|
1020
|
+
var IconMinus = /* @__PURE__ */ defineIcon("minus", [["path", { d: "M5 12h14" }]]);
|
|
1018
1021
|
var IconCircleAlert = /* @__PURE__ */ defineIcon("circle-alert", [
|
|
1019
1022
|
["circle", { cx: "12", cy: "12", r: "10" }],
|
|
1020
1023
|
["line", { x1: "12", x2: "12", y1: "8", y2: "12" }],
|
|
@@ -1057,6 +1060,14 @@ var IconInbox = /* @__PURE__ */ defineIcon("inbox", [
|
|
|
1057
1060
|
{ d: "M5.45 5.11 2 12v6a2 2 0 0 0 2 2h16a2 2 0 0 0 2-2v-6l-3.45-6.89A2 2 0 0 0 16.76 4H7.24a2 2 0 0 0-1.79 1.11z" }
|
|
1058
1061
|
]
|
|
1059
1062
|
]);
|
|
1063
|
+
var IconTrendingUp = /* @__PURE__ */ defineIcon("trending-up", [
|
|
1064
|
+
["path", { d: "M16 7h6v6" }],
|
|
1065
|
+
["path", { d: "m22 7-8.5 8.5-5-5L2 17" }]
|
|
1066
|
+
]);
|
|
1067
|
+
var IconTrendingDown = /* @__PURE__ */ defineIcon("trending-down", [
|
|
1068
|
+
["path", { d: "M16 17h6v-6" }],
|
|
1069
|
+
["path", { d: "m22 17-8.5-8.5-5 5L2 7" }]
|
|
1070
|
+
]);
|
|
1060
1071
|
|
|
1061
1072
|
// src/display.tsx
|
|
1062
1073
|
var h2 = React3.createElement;
|
|
@@ -1147,7 +1158,7 @@ function badgeElement(props, ref) {
|
|
|
1147
1158
|
);
|
|
1148
1159
|
}
|
|
1149
1160
|
function emptyStateElement(props, ref) {
|
|
1150
|
-
const HT = "h" + (props.headingLevel || 3);
|
|
1161
|
+
const HT = props.headingLevel === false ? "p" : "h" + (props.headingLevel || 3);
|
|
1151
1162
|
const rest = omit(props, [
|
|
1152
1163
|
"title",
|
|
1153
1164
|
"description",
|
|
@@ -1179,6 +1190,66 @@ function emptyStateElement(props, ref) {
|
|
|
1179
1190
|
props.action ? /* @__PURE__ */ React3.createElement("div", { className: "aura-empty__action" }, props.action) : null
|
|
1180
1191
|
);
|
|
1181
1192
|
}
|
|
1193
|
+
function statElement(props, ref, Link) {
|
|
1194
|
+
const ch = props.change;
|
|
1195
|
+
const dir = ch && (ch.direction || "flat");
|
|
1196
|
+
const tone2 = ch && (ch.tone || (dir === "up" ? "positive" : dir === "down" ? "negative" : "neutral"));
|
|
1197
|
+
const v = props.value;
|
|
1198
|
+
const numeric = typeof v === "number" || typeof v === "string" && /\d/.test(v) && /^[\s\d.,:+\-\u2212%()\u0E3F$\u20AC\u00A3\u00A5kKmMbB]+$/.test(v.replace(/\b[A-Z]{3}\b/g, ""));
|
|
1199
|
+
const Tag = props.href ? Link : props.onClick ? "button" : "div";
|
|
1200
|
+
const interactive = !!(props.href || props.onClick);
|
|
1201
|
+
if (props.headingLevel && Tag === "button")
|
|
1202
|
+
devWarnOnce(
|
|
1203
|
+
"stat-heading-button",
|
|
1204
|
+
"Stat `headingLevel` is ignored with `onClick`: a heading can\u2019t sit in a button. Use `href`, or put the heading outside."
|
|
1205
|
+
);
|
|
1206
|
+
const LabelTag = props.headingLevel && Tag !== "button" ? "h" + props.headingLevel : "span";
|
|
1207
|
+
const HeadTag = LabelTag === "span" ? "span" : "div";
|
|
1208
|
+
return /* @__PURE__ */ React3.createElement(
|
|
1209
|
+
Tag,
|
|
1210
|
+
{
|
|
1211
|
+
ref,
|
|
1212
|
+
className: cx("aura-stat", interactive && "is-interactive", props.loading && "is-loading", props.className),
|
|
1213
|
+
href: props.href,
|
|
1214
|
+
onClick: props.onClick,
|
|
1215
|
+
type: Tag === "button" ? "button" : void 0,
|
|
1216
|
+
"aria-busy": props.loading || void 0
|
|
1217
|
+
},
|
|
1218
|
+
/* @__PURE__ */ React3.createElement(HeadTag, { className: "aura-stat__head" }, /* @__PURE__ */ React3.createElement(LabelTag, { className: "aura-stat__label" }, props.label), props.icon ? /* @__PURE__ */ React3.createElement("span", { className: "aura-stat__icon" }, /* @__PURE__ */ React3.createElement(Icon, { name: props.icon })) : null),
|
|
1219
|
+
props.loading ? /* @__PURE__ */ React3.createElement("span", { className: "aura-stat__value" }, /* @__PURE__ */ React3.createElement("span", { className: "aura-skel aura-stat__skel" })) : /* @__PURE__ */ React3.createElement("span", { className: cx("aura-stat__value", numeric && "is-numeric") }, props.value, props.unit ? /* @__PURE__ */ React3.createElement("span", { className: "aura-stat__unit" }, props.unit) : null),
|
|
1220
|
+
ch && !props.loading || props.caption ? /* @__PURE__ */ React3.createElement("span", { className: "aura-stat__foot" }, ch && !props.loading ? /* @__PURE__ */ React3.createElement("span", { className: cx("aura-stat__change", "is-" + tone2) }, /* @__PURE__ */ React3.createElement(
|
|
1221
|
+
Icon,
|
|
1222
|
+
{
|
|
1223
|
+
name: dir === "up" ? /* @__PURE__ */ React3.createElement(IconTrendingUp, null) : dir === "down" ? /* @__PURE__ */ React3.createElement(IconTrendingDown, null) : /* @__PURE__ */ React3.createElement(IconMinus, null),
|
|
1224
|
+
size: 14
|
|
1225
|
+
}
|
|
1226
|
+
), /* @__PURE__ */ React3.createElement("span", null, ch.value)) : null, ch && ch.label && !props.loading ? /* @__PURE__ */ React3.createElement("span", { className: "aura-stat__caption" }, ch.label) : null, props.caption ? /* @__PURE__ */ React3.createElement("span", { className: "aura-stat__caption" }, props.caption) : null) : null
|
|
1227
|
+
);
|
|
1228
|
+
}
|
|
1229
|
+
var AVATAR_TONES = ["progress", "ready", "neutral", "warning"];
|
|
1230
|
+
function initials(name) {
|
|
1231
|
+
const parts = String(name || "?").trim().split(/\s+/);
|
|
1232
|
+
return ((parts[0] || "?")[0] + (parts.length > 1 ? parts[parts.length - 1][0] : parts[0][1] || "")).toUpperCase();
|
|
1233
|
+
}
|
|
1234
|
+
function avatarElement(props, ref, broken, onError) {
|
|
1235
|
+
const size = props.size || "md";
|
|
1236
|
+
let hash = 0;
|
|
1237
|
+
String(props.name || "").split("").forEach(function(ch) {
|
|
1238
|
+
hash = hash * 31 + ch.charCodeAt(0) >>> 0;
|
|
1239
|
+
});
|
|
1240
|
+
const tone2 = AVATAR_TONES[hash % AVATAR_TONES.length];
|
|
1241
|
+
return /* @__PURE__ */ React3.createElement(
|
|
1242
|
+
"span",
|
|
1243
|
+
{
|
|
1244
|
+
ref,
|
|
1245
|
+
className: cx("aura-avatar", "aura-avatar--" + size, "aura-avatar--" + tone2, props.className),
|
|
1246
|
+
role: "img",
|
|
1247
|
+
"aria-label": props.name + (props.status ? ", " + props.status : "")
|
|
1248
|
+
},
|
|
1249
|
+
props.src && broken !== props.src ? /* @__PURE__ */ React3.createElement("img", { key: props.src, src: props.src, alt: "", onError }) : /* @__PURE__ */ React3.createElement("span", { "aria-hidden": true }, initials(props.name)),
|
|
1250
|
+
props.status === "online" ? /* @__PURE__ */ React3.createElement("span", { className: "aura-avatar__status", "aria-hidden": true }) : null
|
|
1251
|
+
);
|
|
1252
|
+
}
|
|
1182
1253
|
function buttonClass(opts = {}) {
|
|
1183
1254
|
return cx(
|
|
1184
1255
|
"aura-btn",
|
|
@@ -1204,3 +1275,9 @@ function ServerBadge(props) {
|
|
|
1204
1275
|
function ServerEmptyState(props) {
|
|
1205
1276
|
return emptyStateElement(props, void 0);
|
|
1206
1277
|
}
|
|
1278
|
+
function ServerStat(props) {
|
|
1279
|
+
return statElement(omit(props, ["onClick"]), void 0, props.linkComponent || "a");
|
|
1280
|
+
}
|
|
1281
|
+
function ServerAvatar(props) {
|
|
1282
|
+
return avatarElement(props, void 0, null, void 0);
|
|
1283
|
+
}
|
package/dist/server/index.d.cts
CHANGED
|
@@ -81,6 +81,15 @@ export interface CardProps extends Omit<React$1.HTMLAttributes<HTMLElement>, "ti
|
|
|
81
81
|
/** id for the title element; the card is then labelled by it (aria-labelledby). */
|
|
82
82
|
titleId?: string | undefined;
|
|
83
83
|
}
|
|
84
|
+
export interface AvatarProps {
|
|
85
|
+
/** Accessible name; also gives the initials and a stable colour. */
|
|
86
|
+
name: string;
|
|
87
|
+
src?: string | undefined;
|
|
88
|
+
/** `sm` 24 · `md` 32 (default) · `lg` 40. */
|
|
89
|
+
size?: "sm" | "md" | "lg" | undefined;
|
|
90
|
+
status?: "online" | undefined;
|
|
91
|
+
className?: string | undefined;
|
|
92
|
+
}
|
|
84
93
|
/** ISO date string, `YYYY-MM-DD` (Gregorian — the era is display only). */
|
|
85
94
|
export type ISODate = string;
|
|
86
95
|
export interface DateDisplayOptions {
|
|
@@ -89,6 +98,35 @@ export interface DateDisplayOptions {
|
|
|
89
98
|
/** `buddhist` (พ.ศ.; default for th) or `gregory` (ค.ศ.; default for en and sv). */
|
|
90
99
|
calendar?: "buddhist" | "gregory" | undefined;
|
|
91
100
|
}
|
|
101
|
+
export interface StatChange {
|
|
102
|
+
/** Shown as written, e.g. "+12%" or "−3". */
|
|
103
|
+
value: React$1.ReactNode;
|
|
104
|
+
direction?: "up" | "down" | "flat" | undefined;
|
|
105
|
+
/** Default: up = positive, down = negative. Set it when a rise is bad (cancellations, wait time). */
|
|
106
|
+
tone?: "positive" | "negative" | "neutral" | undefined;
|
|
107
|
+
/** e.g. "vs last month". */
|
|
108
|
+
label?: React$1.ReactNode | undefined;
|
|
109
|
+
}
|
|
110
|
+
export interface StatProps {
|
|
111
|
+
/** Your router's link (e.g. `Link` from `next/link`) for this component; defaults to AuraProvider's `linkComponent`, then `<a>`. */
|
|
112
|
+
linkComponent?: React$1.ElementType | undefined;
|
|
113
|
+
label: React$1.ReactNode;
|
|
114
|
+
value?: React$1.ReactNode | undefined;
|
|
115
|
+
/** Small unit after the value ("งาน", "คน", "%"). */
|
|
116
|
+
unit?: React$1.ReactNode | undefined;
|
|
117
|
+
change?: StatChange | undefined;
|
|
118
|
+
caption?: React$1.ReactNode | undefined;
|
|
119
|
+
icon?: IconInput | undefined;
|
|
120
|
+
/** Skeleton in place of the value. */
|
|
121
|
+
loading?: boolean | undefined;
|
|
122
|
+
/** Makes the whole card a link or a button (drill-down). */
|
|
123
|
+
href?: string | undefined;
|
|
124
|
+
onClick?: (() => void) | undefined;
|
|
125
|
+
/** The label as a heading of this level (5.14), when the tile titles its section. Not with `onClick` (a heading
|
|
126
|
+
* can't sit in a button); a link is fine. Default: a plain label. */
|
|
127
|
+
headingLevel?: 2 | 3 | 4 | 5 | 6 | undefined;
|
|
128
|
+
className?: string | undefined;
|
|
129
|
+
}
|
|
92
130
|
export type Tone = "neutral" | "accent" | "success" | "warning" | "danger";
|
|
93
131
|
export interface BadgeProps extends React$1.HTMLAttributes<HTMLSpanElement> {
|
|
94
132
|
tone?: Tone | undefined;
|
|
@@ -107,7 +145,9 @@ export interface EmptyStateProps extends Omit<React$1.HTMLAttributes<HTMLDivElem
|
|
|
107
145
|
/** `danger` (5.13) for a failure — the data couldn't load: the danger tint, a danger-coloured icon, and a solid
|
|
108
146
|
* danger frame with `bordered`. It stays quiet; pass `role="alert"` if it must interrupt. Default `neutral`. */
|
|
109
147
|
tone?: "neutral" | "danger" | undefined;
|
|
110
|
-
|
|
148
|
+
/** The title's heading level (default 3); `false` (5.14) makes it a paragraph, for a card or list whose outline
|
|
149
|
+
* mustn't change. EmptyState has no live-region role unless you pass `role`. */
|
|
150
|
+
headingLevel?: 2 | 3 | 4 | 5 | 6 | false | undefined;
|
|
111
151
|
className?: string | undefined;
|
|
112
152
|
}
|
|
113
153
|
export interface ThemeOptions {
|
|
@@ -305,6 +345,11 @@ declare function ServerCard(props: CardProps): React$1.ReactElement;
|
|
|
305
345
|
declare function ServerStatusPill(props: StatusPillProps): React$1.ReactElement;
|
|
306
346
|
declare function ServerBadge(props: BadgeProps): React$1.ReactElement;
|
|
307
347
|
declare function ServerEmptyState(props: EmptyStateProps): React$1.ReactElement;
|
|
348
|
+
/** Stat for Server Components (5.14): no `onClick` (a button needs the client); `href` renders `linkComponent`, else `<a>`. */
|
|
349
|
+
declare function ServerStat(props: Omit<StatProps, "onClick">): React$1.ReactElement;
|
|
350
|
+
/** Avatar for Server Components (5.14): initials and colour. Falling back to the initials when an image fails needs the
|
|
351
|
+
* client, so give a server avatar a `src` you know loads, or none. */
|
|
352
|
+
declare function ServerAvatar(props: AvatarProps): React$1.ReactElement;
|
|
308
353
|
/** Makes icon names as strings work: `registerIcons(allIcons)` once at startup, with `allIcons` from
|
|
309
354
|
* `@jirawatpyk/aura-react/icons`, or only the icons you use (`registerIcons([IconUsers, IconPlus])`). In 5.x every
|
|
310
355
|
* name already works and this only says you are ready for 6.0 (it silences the notice); in 6.0 it is required. Call it in the module
|
|
@@ -315,9 +360,11 @@ export declare const Icon: React$1.ForwardRefExoticComponent<IconProps & React$1
|
|
|
315
360
|
|
|
316
361
|
export {
|
|
317
362
|
ServerAlert as Alert,
|
|
363
|
+
ServerAvatar as Avatar,
|
|
318
364
|
ServerBadge as Badge,
|
|
319
365
|
ServerCard as Card,
|
|
320
366
|
ServerEmptyState as EmptyState,
|
|
367
|
+
ServerStat as Stat,
|
|
321
368
|
ServerStatusPill as StatusPill,
|
|
322
369
|
scale as brandScale,
|
|
323
370
|
toneFor as statusTone,
|