@itwin/itwinui-react 5.0.0-alpha.1 → 5.0.0-alpha.11
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/CHANGELOG.md +102 -0
- package/LICENSE.md +1 -1
- package/README.md +6 -6
- package/dist/DEV/bricks/Anchor.js +5 -10
- package/dist/DEV/bricks/Avatar.js +24 -0
- package/dist/DEV/bricks/Badge.js +22 -0
- package/dist/DEV/bricks/Button.js +11 -4
- package/dist/DEV/bricks/Checkbox.js +17 -9
- package/dist/DEV/bricks/Chip.js +42 -0
- package/dist/DEV/bricks/Description.js +29 -0
- package/dist/DEV/bricks/Divider.js +3 -2
- package/dist/DEV/bricks/DropdownMenu.js +109 -30
- package/dist/DEV/bricks/Field.js +115 -14
- package/dist/DEV/bricks/Icon.js +177 -10
- package/dist/DEV/bricks/IconButton.js +14 -3
- package/dist/DEV/bricks/Kbd.internal.js +19 -0
- package/dist/DEV/bricks/Kbd.js +23 -6
- package/dist/DEV/bricks/Label.js +11 -8
- package/dist/DEV/bricks/ProgressBar.js +25 -0
- package/dist/DEV/bricks/Radio.js +17 -9
- package/dist/DEV/bricks/Root.internal.js +17 -0
- package/dist/DEV/bricks/Root.js +103 -26
- package/dist/DEV/bricks/Select.js +17 -11
- package/dist/DEV/bricks/Skeleton.js +24 -0
- package/dist/DEV/bricks/Spinner.js +55 -0
- package/dist/DEV/bricks/Switch.js +18 -10
- package/dist/DEV/bricks/Table.js +114 -0
- package/dist/DEV/bricks/Tabs.js +6 -6
- package/dist/DEV/bricks/Text.js +2 -2
- package/dist/DEV/bricks/TextBox.js +54 -16
- package/dist/DEV/bricks/Tooltip.js +17 -25
- package/dist/DEV/bricks/Tree.js +15 -107
- package/dist/DEV/bricks/TreeItem.js +227 -0
- package/dist/DEV/bricks/VisuallyHidden.js +2 -2
- package/dist/DEV/bricks/index.js +16 -0
- package/dist/DEV/bricks/styles.css.js +2 -2
- package/dist/DEV/bricks/~hooks.js +57 -3
- package/dist/DEV/bricks/~utils.GhostAligner.js +13 -0
- package/dist/DEV/bricks/{ListItem.js → ~utils.ListItem.js} +19 -3
- package/dist/DEV/bricks/~utils.js +17 -0
- package/dist/DEV/foundations/styles.css.js +2 -2
- package/dist/bricks/Anchor.js +5 -10
- package/dist/bricks/Avatar.d.ts +47 -0
- package/dist/bricks/Avatar.js +23 -0
- package/dist/bricks/Badge.d.ts +28 -0
- package/dist/bricks/Badge.js +21 -0
- package/dist/bricks/Button.js +11 -4
- package/dist/bricks/Checkbox.d.ts +2 -2
- package/dist/bricks/Checkbox.js +17 -9
- package/dist/bricks/Chip.d.ts +31 -0
- package/dist/bricks/Chip.js +41 -0
- package/dist/bricks/Description.d.ts +19 -0
- package/dist/bricks/Description.js +29 -0
- package/dist/bricks/Divider.d.ts +2 -2
- package/dist/bricks/Divider.js +3 -2
- package/dist/bricks/DropdownMenu.d.ts +41 -14
- package/dist/bricks/DropdownMenu.js +106 -30
- package/dist/bricks/Field.d.ts +23 -1
- package/dist/bricks/Field.js +115 -14
- package/dist/bricks/Icon.d.ts +43 -4
- package/dist/bricks/Icon.js +174 -10
- package/dist/bricks/IconButton.d.ts +20 -4
- package/dist/bricks/IconButton.js +14 -3
- package/dist/bricks/Kbd.d.ts +15 -0
- package/dist/bricks/Kbd.internal.d.ts +17 -0
- package/dist/bricks/Kbd.internal.js +19 -0
- package/dist/bricks/Kbd.js +16 -6
- package/dist/bricks/Label.js +11 -8
- package/dist/bricks/ProgressBar.d.ts +31 -0
- package/dist/bricks/ProgressBar.js +24 -0
- package/dist/bricks/Radio.d.ts +2 -2
- package/dist/bricks/Radio.js +17 -9
- package/dist/bricks/Root.d.ts +12 -0
- package/dist/bricks/Root.internal.d.ts +6 -0
- package/dist/bricks/Root.internal.js +17 -0
- package/dist/bricks/Root.js +103 -26
- package/dist/bricks/Select.d.ts +9 -3
- package/dist/bricks/Select.js +17 -11
- package/dist/bricks/Skeleton.d.ts +25 -0
- package/dist/bricks/Skeleton.js +23 -0
- package/dist/bricks/Spinner.d.ts +31 -0
- package/dist/bricks/Spinner.js +54 -0
- package/dist/bricks/Switch.d.ts +2 -2
- package/dist/bricks/Switch.js +18 -10
- package/dist/bricks/Table.d.ts +115 -0
- package/dist/bricks/Table.js +108 -0
- package/dist/bricks/Tabs.d.ts +4 -4
- package/dist/bricks/Tabs.js +6 -6
- package/dist/bricks/Text.d.ts +1 -1
- package/dist/bricks/Text.js +2 -2
- package/dist/bricks/TextBox.d.ts +23 -2
- package/dist/bricks/TextBox.js +53 -16
- package/dist/bricks/Tooltip.d.ts +2 -2
- package/dist/bricks/Tooltip.js +17 -25
- package/dist/bricks/Tree.d.ts +19 -20
- package/dist/bricks/Tree.js +14 -102
- package/dist/bricks/TreeItem.d.ts +129 -0
- package/dist/bricks/TreeItem.js +222 -0
- package/dist/bricks/VisuallyHidden.js +2 -2
- package/dist/bricks/index.d.ts +8 -0
- package/dist/bricks/index.js +16 -0
- package/dist/bricks/styles.css.js +2 -2
- package/dist/bricks/~hooks.d.ts +63 -0
- package/dist/bricks/~hooks.js +57 -3
- package/dist/bricks/~utils.GhostAligner.d.ts +22 -0
- package/dist/bricks/~utils.GhostAligner.js +13 -0
- package/dist/bricks/~utils.ListItem.d.ts +14 -0
- package/dist/bricks/{ListItem.js → ~utils.ListItem.js} +18 -3
- package/dist/bricks/~utils.d.ts +14 -3
- package/dist/bricks/~utils.js +17 -0
- package/dist/foundations/styles.css.js +2 -2
- package/package.json +14 -13
- package/dist/DEV/bricks/Textarea.js +0 -30
- package/dist/bricks/ListItem.d.ts +0 -10
- package/dist/bricks/Textarea.d.ts +0 -24
- package/dist/bricks/Textarea.js +0 -29
package/dist/bricks/Field.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import * as React from "react";
|
|
2
|
+
import { useCollectionStore, type CollectionItemProps } from "@ariakit/react/collection";
|
|
2
3
|
import { type BaseProps } from "./~utils.js";
|
|
3
4
|
interface FieldProps extends BaseProps {
|
|
4
5
|
/**
|
|
@@ -27,5 +28,26 @@ interface FieldProps extends BaseProps {
|
|
|
27
28
|
* - `Switch`
|
|
28
29
|
*/
|
|
29
30
|
export declare const Field: React.ForwardRefExoticComponent<FieldProps & React.RefAttributes<HTMLElement | HTMLDivElement>>;
|
|
30
|
-
|
|
31
|
+
type CollectionStoreItem = NonNullable<ReturnType<ReturnType<typeof useCollectionStore>["item"]>>;
|
|
32
|
+
interface FieldCollectionStoreItem extends CollectionStoreItem {
|
|
33
|
+
/** The type of field element being tracked */
|
|
34
|
+
elementType: "label" | "control" | "description";
|
|
35
|
+
/** If a control, the type of control. */
|
|
36
|
+
controlType?: "textlike" | "checkable";
|
|
37
|
+
}
|
|
38
|
+
interface FieldCollectionItemControlProps extends Pick<CollectionItemProps, "render" | "id"> {
|
|
39
|
+
type: FieldCollectionStoreItem["controlType"];
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* An element tracked as a control in the `Field`’s collection.
|
|
43
|
+
*/
|
|
44
|
+
export declare function FieldControl(props: FieldCollectionItemControlProps): import("react/jsx-runtime").JSX.Element;
|
|
45
|
+
/**
|
|
46
|
+
* An element tracked as a label in the `Field`’s collection.
|
|
47
|
+
*/
|
|
48
|
+
export declare function FieldLabel(props: Pick<CollectionItemProps, "render">): import("react/jsx-runtime").JSX.Element;
|
|
49
|
+
/**
|
|
50
|
+
* An element tracked as a description in the `Field`’s collection.
|
|
51
|
+
*/
|
|
52
|
+
export declare function FieldDescription(props: Pick<CollectionItemProps, "render" | "id">): import("react/jsx-runtime").JSX.Element;
|
|
31
53
|
export {};
|
package/dist/bricks/Field.js
CHANGED
|
@@ -1,26 +1,127 @@
|
|
|
1
1
|
import { jsx } from "react/jsx-runtime";
|
|
2
2
|
import * as React from "react";
|
|
3
|
-
import * as Ariakit from "@ariakit/react";
|
|
4
3
|
import cx from "classnames";
|
|
4
|
+
import { Role } from "@ariakit/react/role";
|
|
5
|
+
import {
|
|
6
|
+
useCollectionStore,
|
|
7
|
+
Collection,
|
|
8
|
+
useCollectionContext,
|
|
9
|
+
CollectionItem
|
|
10
|
+
} from "@ariakit/react/collection";
|
|
11
|
+
import { useStoreState } from "@ariakit/react/store";
|
|
5
12
|
import { forwardRef } from "./~utils.js";
|
|
6
13
|
const Field = forwardRef((props, forwardedRef) => {
|
|
7
|
-
const
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
Ariakit.Role,
|
|
14
|
+
const { layout, ...rest } = props;
|
|
15
|
+
return /* @__PURE__ */ jsx(
|
|
16
|
+
FieldCollection,
|
|
11
17
|
{
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
18
|
+
render: /* @__PURE__ */ jsx(
|
|
19
|
+
Role.div,
|
|
20
|
+
{
|
|
21
|
+
...rest,
|
|
22
|
+
className: cx("\u{1F95D}-field", props.className),
|
|
23
|
+
"data-kiwi-layout": layout,
|
|
24
|
+
ref: forwardedRef
|
|
25
|
+
}
|
|
26
|
+
)
|
|
16
27
|
}
|
|
17
|
-
)
|
|
28
|
+
);
|
|
18
29
|
});
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
30
|
+
function FieldCollection(props) {
|
|
31
|
+
const fieldElementCollection = useCollectionStore({
|
|
32
|
+
defaultItems: []
|
|
33
|
+
});
|
|
34
|
+
const renderedItems = useStoreState(fieldElementCollection, "renderedItems");
|
|
35
|
+
const [controlType, controlIndex] = React.useMemo(() => {
|
|
36
|
+
const controlIndex2 = renderedItems.findIndex(
|
|
37
|
+
(item) => item.elementType === "control"
|
|
38
|
+
);
|
|
39
|
+
return [renderedItems[controlIndex2]?.controlType, controlIndex2];
|
|
40
|
+
}, [renderedItems]);
|
|
41
|
+
const labelPlacement = React.useMemo(() => {
|
|
42
|
+
const labelIndex = renderedItems.findIndex(
|
|
43
|
+
(item) => item.elementType === "label"
|
|
44
|
+
);
|
|
45
|
+
if (controlIndex === -1 || labelIndex === -1) return;
|
|
46
|
+
return labelIndex < controlIndex ? "before" : "after";
|
|
47
|
+
}, [renderedItems, controlIndex]);
|
|
48
|
+
return /* @__PURE__ */ jsx(
|
|
49
|
+
Collection,
|
|
50
|
+
{
|
|
51
|
+
...props,
|
|
52
|
+
store: fieldElementCollection,
|
|
53
|
+
"data-kiwi-label-placement": labelPlacement,
|
|
54
|
+
"data-kiwi-control-type": controlType
|
|
55
|
+
}
|
|
56
|
+
);
|
|
57
|
+
}
|
|
58
|
+
function FieldControl(props) {
|
|
59
|
+
const store = useCollectionContext();
|
|
60
|
+
const generatedId = React.useId();
|
|
61
|
+
const { id = store ? generatedId : void 0, type, ...rest } = props;
|
|
62
|
+
const renderedItems = useStoreState(store, "renderedItems");
|
|
63
|
+
const describedBy = React.useMemo(() => {
|
|
64
|
+
const idRefList = renderedItems?.filter(
|
|
65
|
+
(item) => item.elementType === "description"
|
|
66
|
+
)?.map((item) => item.id).join(" ");
|
|
67
|
+
return idRefList || void 0;
|
|
68
|
+
}, [renderedItems]);
|
|
69
|
+
const getData = React.useCallback(
|
|
70
|
+
(data) => ({
|
|
71
|
+
...data,
|
|
72
|
+
elementType: "control",
|
|
73
|
+
controlType: type
|
|
74
|
+
}),
|
|
75
|
+
[type]
|
|
76
|
+
);
|
|
77
|
+
return /* @__PURE__ */ jsx(
|
|
78
|
+
CollectionItem,
|
|
79
|
+
{
|
|
80
|
+
id,
|
|
81
|
+
getItem: getData,
|
|
82
|
+
render: /* @__PURE__ */ jsx(Role, { ...rest, "aria-describedby": describedBy })
|
|
83
|
+
}
|
|
84
|
+
);
|
|
85
|
+
}
|
|
86
|
+
function FieldLabel(props) {
|
|
87
|
+
const store = useCollectionContext();
|
|
88
|
+
const renderedItems = useStoreState(store, "renderedItems");
|
|
89
|
+
const fieldId = React.useMemo(
|
|
90
|
+
() => renderedItems?.find(
|
|
91
|
+
(item) => item.elementType === "control"
|
|
92
|
+
)?.id,
|
|
93
|
+
[renderedItems]
|
|
94
|
+
);
|
|
95
|
+
const getData = React.useCallback(
|
|
96
|
+
(data) => ({
|
|
97
|
+
...data,
|
|
98
|
+
elementType: "label"
|
|
99
|
+
}),
|
|
100
|
+
[]
|
|
101
|
+
);
|
|
102
|
+
return /* @__PURE__ */ jsx(
|
|
103
|
+
CollectionItem,
|
|
104
|
+
{
|
|
105
|
+
getItem: getData,
|
|
106
|
+
render: /* @__PURE__ */ jsx(Role.label, { ...props, htmlFor: fieldId })
|
|
107
|
+
}
|
|
108
|
+
);
|
|
109
|
+
}
|
|
110
|
+
function FieldDescription(props) {
|
|
111
|
+
const generatedId = React.useId();
|
|
112
|
+
const { id = generatedId, ...rest } = props;
|
|
113
|
+
const getData = React.useCallback(
|
|
114
|
+
(data) => ({
|
|
115
|
+
...data,
|
|
116
|
+
elementType: "description"
|
|
117
|
+
}),
|
|
118
|
+
[]
|
|
119
|
+
);
|
|
120
|
+
return /* @__PURE__ */ jsx(CollectionItem, { ...rest, id, getItem: getData });
|
|
22
121
|
}
|
|
23
122
|
export {
|
|
24
123
|
Field,
|
|
25
|
-
|
|
124
|
+
FieldControl,
|
|
125
|
+
FieldDescription,
|
|
126
|
+
FieldLabel
|
|
26
127
|
};
|
package/dist/bricks/Icon.d.ts
CHANGED
|
@@ -1,14 +1,38 @@
|
|
|
1
1
|
import * as React from "react";
|
|
2
2
|
import { type BaseProps } from "./~utils.js";
|
|
3
3
|
interface IconProps extends Omit<BaseProps<"svg">, "children"> {
|
|
4
|
-
/**
|
|
4
|
+
/**
|
|
5
|
+
* URL of the symbol sprite.
|
|
6
|
+
*
|
|
7
|
+
* Should be a URL to an `.svg` file from `@itwin/itwinui-icons`.
|
|
8
|
+
*
|
|
9
|
+
* Note: The `.svg` must be an external HTTP resource for it to be processed by
|
|
10
|
+
* the `<use>` element. As a fallback, JS will be used to `fetch` the SVG from
|
|
11
|
+
* non-supported URLs; the fetched SVG content will be sanitized using the
|
|
12
|
+
* `unstable_htmlSanitizer` function passed to `<Root>`.
|
|
13
|
+
*/
|
|
5
14
|
href?: string;
|
|
6
|
-
/**
|
|
15
|
+
/**
|
|
16
|
+
* Size of the icon. This affects the icon's physical dimensions, as well as the
|
|
17
|
+
* actual SVG contents (different sizes might have different fidelity).
|
|
18
|
+
*
|
|
19
|
+
* Defaults to `"regular"` (16px) and can be optionally set to `"large"` (24px).
|
|
20
|
+
*/
|
|
7
21
|
size?: "regular" | "large";
|
|
22
|
+
/**
|
|
23
|
+
* Alternative text describing the icon.
|
|
24
|
+
*
|
|
25
|
+
* When this prop is passed, the SVG gets rendered as `role="img"` and labelled
|
|
26
|
+
* using the provided text.
|
|
27
|
+
*
|
|
28
|
+
* This prop is not required if the icon is purely decorative. By default, the icon
|
|
29
|
+
* will be hidden from the accessibility tree.
|
|
30
|
+
*/
|
|
31
|
+
alt?: string;
|
|
8
32
|
}
|
|
9
33
|
/**
|
|
10
34
|
* Icon component that provides fill and sizing to the SVGs from `@itwin/itwinui-icons`.
|
|
11
|
-
* It
|
|
35
|
+
* It renders the correct symbol sprite based on the specified `size`.
|
|
12
36
|
*
|
|
13
37
|
* ```tsx
|
|
14
38
|
* const arrowIcon = new URL("@itwin/itwinui-icons/arrow.svg", import.meta.url).href;
|
|
@@ -21,7 +45,13 @@ interface IconProps extends Omit<BaseProps<"svg">, "children"> {
|
|
|
21
45
|
* <Icon render={<svg><path d="…" fill="currentColor" /></svg>} />
|
|
22
46
|
* ```
|
|
23
47
|
*
|
|
24
|
-
*
|
|
48
|
+
* By default, this component assumes that the icon is decorative, so it adds `aria-hidden` by default.
|
|
49
|
+
*
|
|
50
|
+
* If the icon is semantically meaningful, the `alt` prop can be used to provide alternative text.
|
|
51
|
+
*
|
|
52
|
+
* ```tsx
|
|
53
|
+
* <Icon href={…} alt="Help" />
|
|
54
|
+
* ```
|
|
25
55
|
*/
|
|
26
56
|
export declare const Icon: React.ForwardRefExoticComponent<IconProps & React.RefAttributes<HTMLElement | SVGSVGElement>>;
|
|
27
57
|
interface DisclosureArrowProps extends Omit<BaseProps<"svg">, "children"> {
|
|
@@ -32,4 +62,13 @@ interface DisclosureArrowProps extends Omit<BaseProps<"svg">, "children"> {
|
|
|
32
62
|
direction?: "down" | "right";
|
|
33
63
|
}
|
|
34
64
|
export declare const DisclosureArrow: React.ForwardRefExoticComponent<DisclosureArrowProps & React.RefAttributes<HTMLElement | SVGSVGElement>>;
|
|
65
|
+
interface CheckmarkProps extends Omit<BaseProps<"svg">, "children"> {
|
|
66
|
+
}
|
|
67
|
+
export declare const Checkmark: React.ForwardRefExoticComponent<CheckmarkProps & React.RefAttributes<HTMLElement | SVGSVGElement>>;
|
|
68
|
+
interface DismissProps extends Omit<BaseProps<"svg">, "children"> {
|
|
69
|
+
}
|
|
70
|
+
export declare const Dismiss: React.ForwardRefExoticComponent<DismissProps & React.RefAttributes<HTMLElement | SVGSVGElement>>;
|
|
71
|
+
interface StatusWarningProps extends Omit<BaseProps<"svg">, "children"> {
|
|
72
|
+
}
|
|
73
|
+
export declare const StatusWarning: React.ForwardRefExoticComponent<StatusWarningProps & React.RefAttributes<HTMLElement | SVGSVGElement>>;
|
|
35
74
|
export {};
|
package/dist/bricks/Icon.js
CHANGED
|
@@ -1,27 +1,107 @@
|
|
|
1
1
|
import { jsx } from "react/jsx-runtime";
|
|
2
2
|
import * as React from "react";
|
|
3
3
|
import cx from "classnames";
|
|
4
|
-
import
|
|
5
|
-
import {
|
|
4
|
+
import { Role } from "@ariakit/react/role";
|
|
5
|
+
import {
|
|
6
|
+
forwardRef,
|
|
7
|
+
getOwnerDocument,
|
|
8
|
+
parseDOM
|
|
9
|
+
} from "./~utils.js";
|
|
10
|
+
import {
|
|
11
|
+
HtmlSanitizerContext,
|
|
12
|
+
spriteSheetId,
|
|
13
|
+
useRootNode
|
|
14
|
+
} from "./Root.internal.js";
|
|
15
|
+
import { useLatestRef, useSafeContext } from "./~hooks.js";
|
|
6
16
|
const Icon = forwardRef((props, forwardedRef) => {
|
|
7
|
-
const { href, size
|
|
8
|
-
const
|
|
17
|
+
const { href: hrefProp, size, alt, ...rest } = props;
|
|
18
|
+
const isDecorative = !alt;
|
|
19
|
+
const hrefBase = useNormalizedHrefBase(hrefProp);
|
|
9
20
|
return /* @__PURE__ */ jsx(
|
|
10
|
-
|
|
21
|
+
Role.svg,
|
|
11
22
|
{
|
|
12
|
-
"
|
|
13
|
-
"
|
|
23
|
+
"aria-hidden": isDecorative ? "true" : void 0,
|
|
24
|
+
role: isDecorative ? void 0 : "img",
|
|
25
|
+
"aria-label": isDecorative ? void 0 : alt,
|
|
14
26
|
...rest,
|
|
27
|
+
"data-kiwi-size": size,
|
|
15
28
|
className: cx("\u{1F95D}-icon", props.className),
|
|
16
29
|
ref: forwardedRef,
|
|
17
|
-
children: /* @__PURE__ */ jsx("use", { href:
|
|
30
|
+
children: hrefBase ? /* @__PURE__ */ jsx("use", { href: toIconHref(hrefBase, size) }) : null
|
|
18
31
|
}
|
|
19
32
|
);
|
|
20
33
|
});
|
|
34
|
+
function toIconHref(hrefBase, size) {
|
|
35
|
+
const separator = hrefBase.includes("#") ? "--" : "#";
|
|
36
|
+
const suffix = toIconId(size);
|
|
37
|
+
return `${hrefBase}${separator}${suffix}`;
|
|
38
|
+
}
|
|
21
39
|
function toIconId(size) {
|
|
22
40
|
if (size === "large") return "icon-large";
|
|
23
41
|
return "icon";
|
|
24
42
|
}
|
|
43
|
+
function useNormalizedHrefBase(rawHref) {
|
|
44
|
+
const generatedId = React.useId();
|
|
45
|
+
const sanitizeHtml = useLatestRef(useSafeContext(HtmlSanitizerContext));
|
|
46
|
+
const rootNode = useRootNode();
|
|
47
|
+
const inlineHref = React.useRef(void 0);
|
|
48
|
+
const getClientSnapshot = () => {
|
|
49
|
+
const ownerDocument = getOwnerDocument(rootNode);
|
|
50
|
+
if (!rawHref || !ownerDocument) return void 0;
|
|
51
|
+
if (isHttpProtocol(rawHref, ownerDocument)) return rawHref;
|
|
52
|
+
return inlineHref.current;
|
|
53
|
+
};
|
|
54
|
+
const subscribe = React.useCallback(
|
|
55
|
+
(notify) => {
|
|
56
|
+
const ownerDocument = getOwnerDocument(rootNode);
|
|
57
|
+
const spriteSheet = ownerDocument?.getElementById(spriteSheetId);
|
|
58
|
+
if (!rawHref || !ownerDocument || !spriteSheet) return () => {
|
|
59
|
+
};
|
|
60
|
+
if (isHttpProtocol(rawHref, ownerDocument)) return () => {
|
|
61
|
+
};
|
|
62
|
+
const cache = spriteSheet[Symbol.for("\u{1F95D}")]?.icons;
|
|
63
|
+
if (!cache) return () => {
|
|
64
|
+
};
|
|
65
|
+
const prefix = `\u{1F95D}${generatedId}`;
|
|
66
|
+
if (cache.has(rawHref)) {
|
|
67
|
+
inlineHref.current = cache.get(rawHref);
|
|
68
|
+
notify();
|
|
69
|
+
return () => {
|
|
70
|
+
};
|
|
71
|
+
}
|
|
72
|
+
const abortController = new AbortController();
|
|
73
|
+
const { signal } = abortController;
|
|
74
|
+
(async () => {
|
|
75
|
+
const response = await fetch(rawHref, { signal });
|
|
76
|
+
if (!response.ok) throw new Error(`Failed to fetch ${rawHref}`);
|
|
77
|
+
const fetchedSvgString = sanitizeHtml.current(await response.text());
|
|
78
|
+
const parsedSvgContent = parseDOM(fetchedSvgString, {
|
|
79
|
+
ownerDocument
|
|
80
|
+
});
|
|
81
|
+
const symbols = parsedSvgContent.querySelectorAll("symbol");
|
|
82
|
+
for (const symbol of symbols) {
|
|
83
|
+
symbol.id = `${prefix}--${symbol.id}`;
|
|
84
|
+
if (ownerDocument.getElementById(symbol.id)) continue;
|
|
85
|
+
spriteSheet.appendChild(symbol.cloneNode(true));
|
|
86
|
+
}
|
|
87
|
+
inlineHref.current = `#${prefix}`;
|
|
88
|
+
cache.set(rawHref, inlineHref.current);
|
|
89
|
+
if (!signal.aborted) notify();
|
|
90
|
+
})();
|
|
91
|
+
return () => abortController.abort();
|
|
92
|
+
},
|
|
93
|
+
[rawHref, rootNode, sanitizeHtml, generatedId]
|
|
94
|
+
);
|
|
95
|
+
return React.useSyncExternalStore(
|
|
96
|
+
subscribe,
|
|
97
|
+
getClientSnapshot,
|
|
98
|
+
() => rawHref
|
|
99
|
+
);
|
|
100
|
+
}
|
|
101
|
+
function isHttpProtocol(url, ownerDocument) {
|
|
102
|
+
const { protocol } = new URL(url, ownerDocument.baseURI);
|
|
103
|
+
return ["http:", "https:"].includes(protocol);
|
|
104
|
+
}
|
|
25
105
|
const DisclosureArrow = forwardRef(
|
|
26
106
|
(props, forwardedRef) => {
|
|
27
107
|
const { direction = "down", ...rest } = props;
|
|
@@ -38,7 +118,7 @@ const DisclosureArrow = forwardRef(
|
|
|
38
118
|
{
|
|
39
119
|
...rest,
|
|
40
120
|
render: /* @__PURE__ */ jsx(
|
|
41
|
-
|
|
121
|
+
Role.svg,
|
|
42
122
|
{
|
|
43
123
|
width: "16",
|
|
44
124
|
height: "16",
|
|
@@ -54,7 +134,91 @@ const DisclosureArrow = forwardRef(
|
|
|
54
134
|
);
|
|
55
135
|
}
|
|
56
136
|
);
|
|
137
|
+
const Checkmark = forwardRef(
|
|
138
|
+
(props, forwardedRef) => {
|
|
139
|
+
return /* @__PURE__ */ jsx(
|
|
140
|
+
Icon,
|
|
141
|
+
{
|
|
142
|
+
...props,
|
|
143
|
+
render: /* @__PURE__ */ jsx(
|
|
144
|
+
Role.svg,
|
|
145
|
+
{
|
|
146
|
+
width: "16",
|
|
147
|
+
height: "16",
|
|
148
|
+
fill: "currentColor",
|
|
149
|
+
viewBox: "0 0 16 16",
|
|
150
|
+
render: props.render,
|
|
151
|
+
children: /* @__PURE__ */ jsx(
|
|
152
|
+
"path",
|
|
153
|
+
{
|
|
154
|
+
fillRule: "evenodd",
|
|
155
|
+
d: "M13.854 4.146a.5.5 0 0 1 0 .708l-7 7a.5.5 0 0 1-.708 0l-3-3a.5.5 0 1 1 .708-.708L6.5 10.793l6.646-6.647a.5.5 0 0 1 .708 0Z",
|
|
156
|
+
clipRule: "evenodd"
|
|
157
|
+
}
|
|
158
|
+
)
|
|
159
|
+
}
|
|
160
|
+
),
|
|
161
|
+
ref: forwardedRef
|
|
162
|
+
}
|
|
163
|
+
);
|
|
164
|
+
}
|
|
165
|
+
);
|
|
166
|
+
const Dismiss = forwardRef(
|
|
167
|
+
(props, forwardedRef) => {
|
|
168
|
+
return /* @__PURE__ */ jsx(
|
|
169
|
+
Icon,
|
|
170
|
+
{
|
|
171
|
+
...props,
|
|
172
|
+
render: /* @__PURE__ */ jsx(
|
|
173
|
+
Role.svg,
|
|
174
|
+
{
|
|
175
|
+
width: "16",
|
|
176
|
+
height: "16",
|
|
177
|
+
viewBox: "0 0 16 16",
|
|
178
|
+
fill: "currentColor",
|
|
179
|
+
render: props.render,
|
|
180
|
+
children: /* @__PURE__ */ jsx("path", { d: "M4.853 4.146a.5.5 0 1 0-.707.708L7.293 8l-3.147 3.146a.5.5 0 0 0 .707.708L8 8.707l3.146 3.147a.5.5 0 0 0 .707-.708L8.707 8l3.146-3.146a.5.5 0 1 0-.707-.708L8 7.293 4.853 4.146Z" })
|
|
181
|
+
}
|
|
182
|
+
),
|
|
183
|
+
ref: forwardedRef
|
|
184
|
+
}
|
|
185
|
+
);
|
|
186
|
+
}
|
|
187
|
+
);
|
|
188
|
+
const StatusWarning = forwardRef(
|
|
189
|
+
(props, forwardedRef) => {
|
|
190
|
+
return /* @__PURE__ */ jsx(
|
|
191
|
+
Icon,
|
|
192
|
+
{
|
|
193
|
+
...props,
|
|
194
|
+
render: /* @__PURE__ */ jsx(
|
|
195
|
+
Role.svg,
|
|
196
|
+
{
|
|
197
|
+
width: "16",
|
|
198
|
+
height: "16",
|
|
199
|
+
fill: "currentColor",
|
|
200
|
+
viewBox: "0 0 16 16",
|
|
201
|
+
render: props.render,
|
|
202
|
+
children: /* @__PURE__ */ jsx(
|
|
203
|
+
"path",
|
|
204
|
+
{
|
|
205
|
+
fill: "currentColor",
|
|
206
|
+
fillRule: "evenodd",
|
|
207
|
+
d: "M8.354 2.06a.5.5 0 0 0-.708 0L2.061 7.647a.5.5 0 0 0 0 .707l5.585 5.586a.5.5 0 0 0 .708 0l5.585-5.586a.5.5 0 0 0 0-.707L8.354 2.061Zm-1.415-.707a1.5 1.5 0 0 1 2.122 0l5.585 5.586a1.5 1.5 0 0 1 0 2.122l-5.585 5.585a1.5 1.5 0 0 1-2.122 0L1.354 9.061a1.5 1.5 0 0 1 0-2.122l5.585-5.586ZM8.75 10.75a.75.75 0 1 1-1.5 0 .75.75 0 0 1 1.5 0ZM8.5 8.5v-3a.5.5 0 0 0-1 0v3a.5.5 0 0 0 1 0Z",
|
|
208
|
+
clipRule: "evenodd"
|
|
209
|
+
}
|
|
210
|
+
)
|
|
211
|
+
}
|
|
212
|
+
),
|
|
213
|
+
ref: forwardedRef
|
|
214
|
+
}
|
|
215
|
+
);
|
|
216
|
+
}
|
|
217
|
+
);
|
|
57
218
|
export {
|
|
219
|
+
Checkmark,
|
|
58
220
|
DisclosureArrow,
|
|
59
|
-
|
|
221
|
+
Dismiss,
|
|
222
|
+
Icon,
|
|
223
|
+
StatusWarning
|
|
60
224
|
};
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import * as React from "react";
|
|
1
2
|
import { Button } from "./Button.js";
|
|
2
3
|
interface IconButtonBaseProps extends Omit<React.ComponentProps<typeof Button>, "children" | "tone"> {
|
|
3
4
|
/**
|
|
@@ -10,7 +11,7 @@ interface IconButtonBaseProps extends Omit<React.ComponentProps<typeof Button>,
|
|
|
10
11
|
/**
|
|
11
12
|
* Icon to be displayed inside the button.
|
|
12
13
|
*
|
|
13
|
-
* Can be a URL of an SVG from the
|
|
14
|
+
* Can be a URL of an SVG from the `@itwin/itwinui-icons` package,
|
|
14
15
|
* or a custom JSX icon.
|
|
15
16
|
*/
|
|
16
17
|
icon: string | React.JSX.Element;
|
|
@@ -23,11 +24,26 @@ interface IconButtonBaseProps extends Omit<React.ComponentProps<typeof Button>,
|
|
|
23
24
|
* @default "tooltip"
|
|
24
25
|
*/
|
|
25
26
|
labelVariant?: "tooltip" | "visually-hidden";
|
|
27
|
+
/**
|
|
28
|
+
* A small dot displayed in the corner of the icon.
|
|
29
|
+
*
|
|
30
|
+
* The value of this prop gets used as the button's "accessible description".
|
|
31
|
+
*
|
|
32
|
+
* Example:
|
|
33
|
+
* ```tsx
|
|
34
|
+
* <IconButton
|
|
35
|
+
* label="Messages"
|
|
36
|
+
* dot="You have unread messages"
|
|
37
|
+
* icon={…}
|
|
38
|
+
* />
|
|
39
|
+
* ```
|
|
40
|
+
*/
|
|
41
|
+
dot?: string;
|
|
26
42
|
}
|
|
27
43
|
/**
|
|
28
44
|
* An icon-only button, with a required accessible name.
|
|
29
45
|
*
|
|
30
|
-
* The icon can be a URL from the
|
|
46
|
+
* The icon can be a URL from the `@itwin/itwinui-icons` package:
|
|
31
47
|
* ```tsx
|
|
32
48
|
* <IconButton
|
|
33
49
|
* label="Reveal full content"
|
|
@@ -56,7 +72,7 @@ interface IconButtonBaseProps extends Omit<React.ComponentProps<typeof Button>,
|
|
|
56
72
|
* />
|
|
57
73
|
* ```
|
|
58
74
|
*/
|
|
59
|
-
export declare const IconButton:
|
|
75
|
+
export declare const IconButton: React.ForwardRefExoticComponent<(Omit<IconButtonBaseProps & {
|
|
60
76
|
variant: "ghost";
|
|
61
77
|
/**
|
|
62
78
|
* Whether the button is in a toggled state and currently "active" (toggled on).
|
|
@@ -75,5 +91,5 @@ export declare const IconButton: import("react").ForwardRefExoticComponent<(Omit
|
|
|
75
91
|
}, "ref"> | Omit<IconButtonBaseProps & {
|
|
76
92
|
variant?: Omit<React.ComponentProps<typeof Button>["variant"], "ghost">;
|
|
77
93
|
isActive?: never;
|
|
78
|
-
}, "ref">) &
|
|
94
|
+
}, "ref">) & React.RefAttributes<HTMLElement | HTMLButtonElement>>;
|
|
79
95
|
export {};
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
import * as React from "react";
|
|
2
3
|
import cx from "classnames";
|
|
4
|
+
import { useToolbarContext, ToolbarItem } from "@ariakit/react/toolbar";
|
|
3
5
|
import { Button } from "./Button.js";
|
|
4
6
|
import { VisuallyHidden } from "./VisuallyHidden.js";
|
|
5
7
|
import { Icon } from "./Icon.js";
|
|
@@ -7,17 +9,26 @@ import { Tooltip } from "./Tooltip.js";
|
|
|
7
9
|
import { forwardRef } from "./~utils.js";
|
|
8
10
|
const IconButton = forwardRef(
|
|
9
11
|
(props, forwardedRef) => {
|
|
10
|
-
const { label, icon, isActive, labelVariant, ...rest } = props;
|
|
12
|
+
const { label, icon, isActive, labelVariant, dot, ...rest } = props;
|
|
13
|
+
const baseId = React.useId();
|
|
14
|
+
const labelId = `${baseId}-label`;
|
|
15
|
+
const dotId = `${baseId}-dot`;
|
|
16
|
+
const toolbar = useToolbarContext();
|
|
11
17
|
const button = /* @__PURE__ */ jsxs(
|
|
12
18
|
Button,
|
|
13
19
|
{
|
|
14
20
|
"aria-pressed": isActive,
|
|
21
|
+
"aria-labelledby": labelId,
|
|
22
|
+
"aria-describedby": dot ? dotId : void 0,
|
|
15
23
|
...rest,
|
|
24
|
+
"data-kiwi-dot": dot ? "true" : void 0,
|
|
25
|
+
render: toolbar ? /* @__PURE__ */ jsx(ToolbarItem, { render: props.render }) : props.render,
|
|
16
26
|
className: cx("\u{1F95D}-icon-button", props.className),
|
|
17
27
|
ref: forwardedRef,
|
|
18
28
|
children: [
|
|
19
|
-
/* @__PURE__ */ jsx(VisuallyHidden, { children: label }),
|
|
20
|
-
typeof icon === "string" ? /* @__PURE__ */ jsx(Icon, { href: icon }) : icon
|
|
29
|
+
/* @__PURE__ */ jsx(VisuallyHidden, { id: labelId, children: label }),
|
|
30
|
+
typeof icon === "string" ? /* @__PURE__ */ jsx(Icon, { href: icon }) : icon,
|
|
31
|
+
dot ? /* @__PURE__ */ jsx(VisuallyHidden, { id: dotId, "aria-hidden": "true", children: dot }) : null
|
|
21
32
|
]
|
|
22
33
|
}
|
|
23
34
|
);
|
package/dist/bricks/Kbd.d.ts
CHANGED
|
@@ -1,7 +1,18 @@
|
|
|
1
1
|
import { type BaseProps } from "./~utils.js";
|
|
2
|
+
import { type PredefinedSymbol } from "./Kbd.internal.js";
|
|
2
3
|
interface KbdProps extends BaseProps<"kbd"> {
|
|
3
4
|
/** @default "solid" */
|
|
4
5
|
variant?: "solid" | "muted" | "ghost";
|
|
6
|
+
/**
|
|
7
|
+
* Display a specific key symbol from a predefined list. This is useful for
|
|
8
|
+
* displaying modifier keys or special keys, such as `Control`, `Shift`, `Enter`, etc.
|
|
9
|
+
*
|
|
10
|
+
* Example:
|
|
11
|
+
* ```tsx
|
|
12
|
+
* <Kbd symbol="Control" />
|
|
13
|
+
* ```
|
|
14
|
+
*/
|
|
15
|
+
symbol?: PredefinedSymbol;
|
|
5
16
|
}
|
|
6
17
|
/**
|
|
7
18
|
* A styled wrapper over the HTML `<kbd>` element. This is typically
|
|
@@ -10,6 +21,10 @@ interface KbdProps extends BaseProps<"kbd"> {
|
|
|
10
21
|
* ```tsx
|
|
11
22
|
* <Kbd>Ctrl</Kbd> <Kbd>S</Kbd>
|
|
12
23
|
* ```
|
|
24
|
+
*
|
|
25
|
+
* ```tsx
|
|
26
|
+
* <Kbd symbol="Control" />
|
|
27
|
+
* ```
|
|
13
28
|
*/
|
|
14
29
|
export declare const Kbd: import("react").ForwardRefExoticComponent<KbdProps & import("react").RefAttributes<HTMLElement>>;
|
|
15
30
|
export {};
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export type PredefinedSymbol = keyof typeof predefinedSymbols;
|
|
2
|
+
export declare const predefinedSymbols: {
|
|
3
|
+
readonly Backspace: "⌫";
|
|
4
|
+
readonly Command: "⌘";
|
|
5
|
+
readonly Control: "Ctrl";
|
|
6
|
+
readonly Down: "↓";
|
|
7
|
+
readonly Eject: "⏏";
|
|
8
|
+
readonly Enter: "↵";
|
|
9
|
+
readonly Escape: "Esc";
|
|
10
|
+
readonly Left: "←";
|
|
11
|
+
readonly Option: "⌥";
|
|
12
|
+
readonly Right: "→";
|
|
13
|
+
readonly Shift: "⇧";
|
|
14
|
+
readonly Space: "␣";
|
|
15
|
+
readonly Tab: "Tab";
|
|
16
|
+
readonly Up: "↑";
|
|
17
|
+
};
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
const predefinedSymbols = {
|
|
2
|
+
Backspace: "\u232B",
|
|
3
|
+
Command: "\u2318",
|
|
4
|
+
Control: "Ctrl",
|
|
5
|
+
Down: "\u2193",
|
|
6
|
+
Eject: "\u23CF",
|
|
7
|
+
Enter: "\u21B5",
|
|
8
|
+
Escape: "Esc",
|
|
9
|
+
Left: "\u2190",
|
|
10
|
+
Option: "\u2325",
|
|
11
|
+
Right: "\u2192",
|
|
12
|
+
Shift: "\u21E7",
|
|
13
|
+
Space: "\u2423",
|
|
14
|
+
Tab: "Tab",
|
|
15
|
+
Up: "\u2191"
|
|
16
|
+
};
|
|
17
|
+
export {
|
|
18
|
+
predefinedSymbols
|
|
19
|
+
};
|
package/dist/bricks/Kbd.js
CHANGED
|
@@ -1,17 +1,27 @@
|
|
|
1
|
-
import { jsx } from "react/jsx-runtime";
|
|
1
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
2
2
|
import cx from "classnames";
|
|
3
|
-
import
|
|
3
|
+
import { Role } from "@ariakit/react/role";
|
|
4
4
|
import { forwardRef } from "./~utils.js";
|
|
5
|
+
import { VisuallyHidden } from "./VisuallyHidden.js";
|
|
6
|
+
import { predefinedSymbols } from "./Kbd.internal.js";
|
|
5
7
|
const Kbd = forwardRef((props, forwardedRef) => {
|
|
6
|
-
const { variant = "solid", ...rest } = props;
|
|
8
|
+
const { variant = "solid", symbol, children, ...rest } = props;
|
|
9
|
+
let content = children;
|
|
10
|
+
if (symbol) {
|
|
11
|
+
content = /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
12
|
+
/* @__PURE__ */ jsx("span", { "aria-hidden": "true", children: predefinedSymbols[symbol] }),
|
|
13
|
+
children || /* @__PURE__ */ jsx(VisuallyHidden, { children: symbol })
|
|
14
|
+
] });
|
|
15
|
+
}
|
|
7
16
|
return /* @__PURE__ */ jsx(
|
|
8
|
-
|
|
17
|
+
Role,
|
|
9
18
|
{
|
|
10
|
-
"data-kiwi-variant": variant,
|
|
11
19
|
...rest,
|
|
20
|
+
"data-kiwi-variant": variant,
|
|
12
21
|
className: cx("\u{1F95D}-kbd", props.className),
|
|
13
22
|
render: props.render || /* @__PURE__ */ jsx("kbd", {}),
|
|
14
|
-
ref: forwardedRef
|
|
23
|
+
ref: forwardedRef,
|
|
24
|
+
children: content
|
|
15
25
|
}
|
|
16
26
|
);
|
|
17
27
|
});
|