@chayns-ui/core 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +51 -1
- package/dist/avatar.css +104 -0
- package/dist/components/accordion/Accordion.d.ts +1 -1
- package/dist/components/accordion/Accordion.d.ts.map +1 -1
- package/dist/components/accordion/Accordion.js +2 -2
- package/dist/components/accordion/Accordion.js.map +1 -1
- package/dist/components/accordion/Accordion.types.d.ts +61 -16
- package/dist/components/accordion/Accordion.types.d.ts.map +1 -1
- package/dist/components/accordion-group/AccordionGroup.d.ts +4 -0
- package/dist/components/accordion-group/AccordionGroup.d.ts.map +1 -0
- package/dist/components/{accordion → accordion-group}/AccordionGroup.js +4 -4
- package/dist/components/accordion-group/AccordionGroup.js.map +1 -0
- package/dist/components/avatar/Avatar.d.ts +4 -0
- package/dist/components/avatar/Avatar.d.ts.map +1 -0
- package/dist/components/avatar/Avatar.js +48 -0
- package/dist/components/avatar/Avatar.js.map +1 -0
- package/dist/components/avatar/Avatar.types.d.ts +46 -0
- package/dist/components/avatar/Avatar.types.d.ts.map +1 -0
- package/dist/components/avatar-group/AvatarGroup.d.ts +4 -0
- package/dist/components/avatar-group/AvatarGroup.d.ts.map +1 -0
- package/dist/components/avatar-group/AvatarGroup.js +26 -0
- package/dist/components/avatar-group/AvatarGroup.js.map +1 -0
- package/dist/components/avatar-group/AvatarGroup.types.d.ts +33 -0
- package/dist/components/avatar-group/AvatarGroup.types.d.ts.map +1 -0
- package/dist/components/button/Button.d.ts.map +1 -1
- package/dist/components/button/Button.js +6 -3
- package/dist/components/button/Button.js.map +1 -1
- package/dist/components/button/Button.types.d.ts +39 -25
- package/dist/components/button/Button.types.d.ts.map +1 -1
- package/dist/components/button/button-icon/ButtonIcon.d.ts +7 -0
- package/dist/components/button/button-icon/ButtonIcon.d.ts.map +1 -0
- package/dist/components/button/button-icon/ButtonIcon.js +17 -0
- package/dist/components/button/button-icon/ButtonIcon.js.map +1 -0
- package/dist/components/card/Card.d.ts +1 -1
- package/dist/components/card/Card.d.ts.map +1 -1
- package/dist/components/card/Card.js +2 -2
- package/dist/components/card/Card.js.map +1 -1
- package/dist/components/card/Card.types.d.ts +16 -3
- package/dist/components/card/Card.types.d.ts.map +1 -1
- package/dist/components/{button → icon-button}/IconButton.d.ts +1 -1
- package/dist/components/icon-button/IconButton.d.ts.map +1 -0
- package/dist/components/{button → icon-button}/IconButton.js +7 -4
- package/dist/components/icon-button/IconButton.js.map +1 -0
- package/dist/components/icon-button/IconButton.types.d.ts +43 -0
- package/dist/components/icon-button/IconButton.types.d.ts.map +1 -0
- package/dist/components/list/List.d.ts +1 -1
- package/dist/components/list/List.d.ts.map +1 -1
- package/dist/components/list/List.js +2 -2
- package/dist/components/list/List.js.map +1 -1
- package/dist/components/list/List.types.d.ts +62 -14
- package/dist/components/list/List.types.d.ts.map +1 -1
- package/dist/components/list-item/ListItem.d.ts +4 -0
- package/dist/components/list-item/ListItem.d.ts.map +1 -0
- package/dist/components/list-item/ListItem.js +42 -0
- package/dist/components/list-item/ListItem.js.map +1 -0
- package/dist/components/list-item/list-item-body/ListItemBody.d.ts +10 -0
- package/dist/components/list-item/list-item-body/ListItemBody.d.ts.map +1 -0
- package/dist/components/list-item/list-item-body/ListItemBody.js +30 -0
- package/dist/components/list-item/list-item-body/ListItemBody.js.map +1 -0
- package/dist/components/popup/Popup.d.ts +4 -0
- package/dist/components/popup/Popup.d.ts.map +1 -0
- package/dist/components/popup/Popup.js +107 -0
- package/dist/components/popup/Popup.js.map +1 -0
- package/dist/components/popup/Popup.types.d.ts +18 -0
- package/dist/components/popup/Popup.types.d.ts.map +1 -0
- package/dist/components/popup/PopupList.d.ts +4 -0
- package/dist/components/popup/PopupList.d.ts.map +1 -0
- package/dist/components/popup/PopupList.js +44 -0
- package/dist/components/popup/PopupList.js.map +1 -0
- package/dist/components/split-button/SplitButton.d.ts +4 -0
- package/dist/components/split-button/SplitButton.d.ts.map +1 -0
- package/dist/components/split-button/SplitButton.js +52 -0
- package/dist/components/split-button/SplitButton.js.map +1 -0
- package/dist/components/split-button/SplitButton.types.d.ts +12 -0
- package/dist/components/split-button/SplitButton.types.d.ts.map +1 -0
- package/dist/index.d.ts +21 -8
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +9 -4
- package/dist/list.css +8 -1
- package/dist/popup.css +34 -0
- package/dist/split-button.css +128 -0
- package/dist/styles.css +3 -0
- package/package.json +11 -19
- package/dist/components/accordion/AccordionGroup.d.ts +0 -4
- package/dist/components/accordion/AccordionGroup.d.ts.map +0 -1
- package/dist/components/accordion/AccordionGroup.js.map +0 -1
- package/dist/components/accordion/index.d.ts +0 -4
- package/dist/components/accordion/index.d.ts.map +0 -1
- package/dist/components/accordion/index.js +0 -3
- package/dist/components/button/ButtonIcon.d.ts +0 -7
- package/dist/components/button/ButtonIcon.d.ts.map +0 -1
- package/dist/components/button/ButtonIcon.js +0 -19
- package/dist/components/button/ButtonIcon.js.map +0 -1
- package/dist/components/button/IconButton.d.ts.map +0 -1
- package/dist/components/button/IconButton.js.map +0 -1
- package/dist/components/button/buttonClassName.d.ts +0 -3
- package/dist/components/button/buttonClassName.d.ts.map +0 -1
- package/dist/components/button/buttonClassName.js +0 -9
- package/dist/components/button/buttonClassName.js.map +0 -1
- package/dist/components/button/index.d.ts +0 -4
- package/dist/components/button/index.d.ts.map +0 -1
- package/dist/components/button/index.js +0 -3
- package/dist/components/card/index.d.ts +0 -3
- package/dist/components/card/index.d.ts.map +0 -1
- package/dist/components/card/index.js +0 -2
- package/dist/components/list/ListItem.d.ts +0 -4
- package/dist/components/list/ListItem.d.ts.map +0 -1
- package/dist/components/list/ListItem.js +0 -67
- package/dist/components/list/ListItem.js.map +0 -1
- package/dist/components/list/index.d.ts +0 -4
- package/dist/components/list/index.d.ts.map +0 -1
- package/dist/components/list/index.js +0 -3
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { cloneElement, useCallback, useEffect, useId, useLayoutEffect, useRef, useState } from "react";
|
|
3
|
+
import { createPortal } from "react-dom";
|
|
4
|
+
//#region src/components/popup/Popup.tsx
|
|
5
|
+
var Popup = ({ children, className, trigger }) => {
|
|
6
|
+
const [open, setOpen] = useState(false);
|
|
7
|
+
const [position, setPosition] = useState({
|
|
8
|
+
left: 0,
|
|
9
|
+
top: 0
|
|
10
|
+
});
|
|
11
|
+
const triggerRef = useRef(null);
|
|
12
|
+
const popupRef = useRef(null);
|
|
13
|
+
const popupId = useId();
|
|
14
|
+
const updatePosition = () => {
|
|
15
|
+
const anchor = triggerRef.current;
|
|
16
|
+
if (!anchor) return;
|
|
17
|
+
const rect = anchor.getBoundingClientRect();
|
|
18
|
+
const popup = popupRef.current;
|
|
19
|
+
const popupWidth = popup?.offsetWidth ?? 0;
|
|
20
|
+
const popupHeight = popup?.offsetHeight ?? 0;
|
|
21
|
+
const gap = 8;
|
|
22
|
+
const margin = 8;
|
|
23
|
+
const left = Math.min(Math.max(margin, rect.left), Math.max(margin, window.innerWidth - popupWidth - margin));
|
|
24
|
+
const below = rect.bottom + gap;
|
|
25
|
+
const top = below + popupHeight <= window.innerHeight - margin ? below : Math.max(margin, rect.top - popupHeight - gap);
|
|
26
|
+
setPosition({
|
|
27
|
+
left,
|
|
28
|
+
top
|
|
29
|
+
});
|
|
30
|
+
};
|
|
31
|
+
const close = (restoreFocus) => {
|
|
32
|
+
setOpen(false);
|
|
33
|
+
if (restoreFocus) queueMicrotask(() => triggerRef.current?.focus());
|
|
34
|
+
};
|
|
35
|
+
const setTriggerRef = useCallback((node) => {
|
|
36
|
+
triggerRef.current = node;
|
|
37
|
+
}, []);
|
|
38
|
+
useLayoutEffect(() => {
|
|
39
|
+
if (!open) return;
|
|
40
|
+
updatePosition();
|
|
41
|
+
(popupRef.current?.querySelector("[role=\"menuitem\"]"))?.focus();
|
|
42
|
+
}, [open]);
|
|
43
|
+
useEffect(() => {
|
|
44
|
+
if (!open) return;
|
|
45
|
+
const handlePointerDown = (event) => {
|
|
46
|
+
const target = event.target;
|
|
47
|
+
if (target instanceof Node && !triggerRef.current?.contains(target) && !popupRef.current?.contains(target)) close(false);
|
|
48
|
+
};
|
|
49
|
+
const handleKeyDown = (event) => {
|
|
50
|
+
if (event.key === "Escape") {
|
|
51
|
+
event.preventDefault();
|
|
52
|
+
close(true);
|
|
53
|
+
}
|
|
54
|
+
if (event.key === "Tab") close(false);
|
|
55
|
+
};
|
|
56
|
+
const handleViewportChange = () => updatePosition();
|
|
57
|
+
const handlePopupClick = (event) => {
|
|
58
|
+
if (event.target.closest("[role=\"menuitem\"]")) close(true);
|
|
59
|
+
};
|
|
60
|
+
const popupElement = popupRef.current;
|
|
61
|
+
document.addEventListener("pointerdown", handlePointerDown);
|
|
62
|
+
document.addEventListener("keydown", handleKeyDown);
|
|
63
|
+
window.addEventListener("resize", handleViewportChange);
|
|
64
|
+
window.addEventListener("scroll", handleViewportChange, true);
|
|
65
|
+
popupElement?.addEventListener("click", handlePopupClick);
|
|
66
|
+
return () => {
|
|
67
|
+
document.removeEventListener("pointerdown", handlePointerDown);
|
|
68
|
+
document.removeEventListener("keydown", handleKeyDown);
|
|
69
|
+
window.removeEventListener("resize", handleViewportChange);
|
|
70
|
+
window.removeEventListener("scroll", handleViewportChange, true);
|
|
71
|
+
popupElement?.removeEventListener("click", handlePopupClick);
|
|
72
|
+
};
|
|
73
|
+
}, [open]);
|
|
74
|
+
const triggerElement = trigger;
|
|
75
|
+
const enhancedTrigger = cloneElement(triggerElement, {
|
|
76
|
+
"aria-controls": popupId,
|
|
77
|
+
"aria-expanded": open,
|
|
78
|
+
"aria-haspopup": "menu",
|
|
79
|
+
onClick: (event) => {
|
|
80
|
+
triggerElement.props.onClick?.(event);
|
|
81
|
+
if (!event.defaultPrevented) setOpen((value) => !value);
|
|
82
|
+
},
|
|
83
|
+
onKeyDown: (event) => {
|
|
84
|
+
triggerElement.props.onKeyDown?.(event);
|
|
85
|
+
if (event.defaultPrevented) return;
|
|
86
|
+
if (event.key === "ArrowDown" || event.key === "ArrowUp") {
|
|
87
|
+
event.preventDefault();
|
|
88
|
+
setOpen(true);
|
|
89
|
+
}
|
|
90
|
+
},
|
|
91
|
+
ref: setTriggerRef
|
|
92
|
+
});
|
|
93
|
+
return /* @__PURE__ */ jsxs(Fragment, { children: [enhancedTrigger, open ? createPortal(/* @__PURE__ */ jsx("div", {
|
|
94
|
+
className: ["chayns-popup", className].filter(Boolean).join(" "),
|
|
95
|
+
id: popupId,
|
|
96
|
+
ref: popupRef,
|
|
97
|
+
style: {
|
|
98
|
+
left: position.left,
|
|
99
|
+
top: position.top
|
|
100
|
+
},
|
|
101
|
+
children
|
|
102
|
+
}), document.body) : null] });
|
|
103
|
+
};
|
|
104
|
+
//#endregion
|
|
105
|
+
export { Popup as default };
|
|
106
|
+
|
|
107
|
+
//# sourceMappingURL=Popup.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Popup.js","names":[],"sources":["../../../src/components/popup/Popup.tsx"],"sourcesContent":["import {\n cloneElement,\n useCallback,\n useEffect,\n useId,\n useLayoutEffect,\n useRef,\n useState,\n type KeyboardEvent,\n type MouseEvent,\n type Ref,\n type ReactElement,\n} from 'react';\nimport { createPortal } from 'react-dom';\n\nimport type { PopupProps } from './Popup.types.js';\n\ninterface PopupTriggerProps {\n 'aria-controls'?: string;\n 'aria-expanded'?: boolean;\n 'aria-haspopup'?: string;\n onClick?: (event: MouseEvent) => void;\n onKeyDown?: (event: KeyboardEvent) => void;\n}\n\ntype PopupTriggerElement = ReactElement<PopupTriggerProps & { ref?: Ref<HTMLElement> }>;\nconst Popup = ({ children, className, trigger }: PopupProps) => {\n const [open, setOpen] = useState(false);\n const [position, setPosition] = useState({ left: 0, top: 0 });\n const triggerRef = useRef<HTMLElement>(null);\n const popupRef = useRef<HTMLDivElement>(null);\n const popupId = useId();\n\n const updatePosition = () => {\n const anchor = triggerRef.current;\n if (!anchor) return;\n\n const rect = anchor.getBoundingClientRect();\n const popup = popupRef.current;\n const popupWidth = popup?.offsetWidth ?? 0;\n const popupHeight = popup?.offsetHeight ?? 0;\n const gap = 8;\n const margin = 8;\n const left = Math.min(\n Math.max(margin, rect.left),\n Math.max(margin, window.innerWidth - popupWidth - margin),\n );\n const below = rect.bottom + gap;\n const top =\n below + popupHeight <= window.innerHeight - margin\n ? below\n : Math.max(margin, rect.top - popupHeight - gap);\n\n setPosition({ left, top });\n };\n\n const close = (restoreFocus: boolean) => {\n setOpen(false);\n if (restoreFocus) {\n queueMicrotask(() => triggerRef.current?.focus());\n }\n };\n\n const setTriggerRef = useCallback((node: HTMLElement | null) => {\n triggerRef.current = node;\n }, []);\n\n useLayoutEffect(() => {\n if (!open) return;\n updatePosition();\n const firstItem = popupRef.current?.querySelector<HTMLElement>('[role=\"menuitem\"]');\n firstItem?.focus();\n }, [open]);\n\n useEffect(() => {\n if (!open) return;\n\n const handlePointerDown = (event: PointerEvent) => {\n const target = event.target;\n if (\n target instanceof Node &&\n !triggerRef.current?.contains(target) &&\n !popupRef.current?.contains(target)\n ) {\n close(false);\n }\n };\n const handleKeyDown = (event: globalThis.KeyboardEvent) => {\n if (event.key === 'Escape') {\n event.preventDefault();\n close(true);\n }\n if (event.key === 'Tab') close(false);\n };\n const handleViewportChange = () => updatePosition();\n const handlePopupClick = (event: globalThis.MouseEvent) => {\n if ((event.target as HTMLElement).closest('[role=\"menuitem\"]')) {\n close(true);\n }\n };\n\n const popupElement = popupRef.current;\n\n document.addEventListener('pointerdown', handlePointerDown);\n document.addEventListener('keydown', handleKeyDown);\n window.addEventListener('resize', handleViewportChange);\n window.addEventListener('scroll', handleViewportChange, true);\n popupElement?.addEventListener('click', handlePopupClick);\n\n return () => {\n document.removeEventListener('pointerdown', handlePointerDown);\n document.removeEventListener('keydown', handleKeyDown);\n window.removeEventListener('resize', handleViewportChange);\n window.removeEventListener('scroll', handleViewportChange, true);\n popupElement?.removeEventListener('click', handlePopupClick);\n };\n }, [open]);\n\n const triggerElement = trigger as PopupTriggerElement;\n // cloneElement forwards `ref` as a plain prop to merge it with the trigger's own ref; the ref\n // is never read during this render, only later by React when attaching the trigger DOM node.\n // eslint-disable-next-line react-hooks/refs\n const enhancedTrigger = cloneElement(triggerElement, {\n 'aria-controls': popupId,\n 'aria-expanded': open,\n 'aria-haspopup': 'menu',\n onClick: (event: React.MouseEvent) => {\n triggerElement.props.onClick?.(event);\n if (!event.defaultPrevented) setOpen((value) => !value);\n },\n onKeyDown: (event: KeyboardEvent) => {\n triggerElement.props.onKeyDown?.(event);\n if (event.defaultPrevented) return;\n if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {\n event.preventDefault();\n setOpen(true);\n }\n },\n ref: setTriggerRef,\n });\n\n return (\n <>\n {enhancedTrigger}\n {open\n ? createPortal(\n <div\n className={['chayns-popup', className].filter(Boolean).join(' ')}\n id={popupId}\n ref={popupRef}\n style={{ left: position.left, top: position.top }}\n >\n {children}\n </div>,\n document.body,\n )\n : null}\n </>\n );\n};\n\nexport default Popup;\n"],"mappings":"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"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import type { ReactElement, ReactNode } from 'react';
|
|
2
|
+
import type { ButtonIcon } from '../button/Button.types.js';
|
|
3
|
+
export interface PopupListItem {
|
|
4
|
+
icon: ButtonIcon;
|
|
5
|
+
text: string;
|
|
6
|
+
onClick: () => void;
|
|
7
|
+
}
|
|
8
|
+
export interface PopupProps {
|
|
9
|
+
trigger: ReactElement;
|
|
10
|
+
children: ReactNode;
|
|
11
|
+
className?: string;
|
|
12
|
+
}
|
|
13
|
+
export interface PopupListProps {
|
|
14
|
+
trigger: ReactElement;
|
|
15
|
+
items: PopupListItem[];
|
|
16
|
+
className?: string;
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=Popup.types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Popup.types.d.ts","sourceRoot":"","sources":["../../../src/components/popup/Popup.types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,SAAS,EAAE,MAAM,OAAO,CAAC;AAErD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAE5D,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,UAAU,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED,MAAM,WAAW,UAAU;IACzB,OAAO,EAAE,YAAY,CAAC;IACtB,QAAQ,EAAE,SAAS,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,cAAc;IAC7B,OAAO,EAAE,YAAY,CAAC;IACtB,KAAK,EAAE,aAAa,EAAE,CAAC;IACvB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PopupList.d.ts","sourceRoot":"","sources":["../../../src/components/popup/PopupList.tsx"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAEvD,QAAA,MAAM,SAAS,GAAI,+BAA+B,cAAc,gCAwC/D,CAAC;AAEF,eAAe,SAAS,CAAC"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import ButtonIcon from "../button/button-icon/ButtonIcon.js";
|
|
2
|
+
import Popup from "./Popup.js";
|
|
3
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
4
|
+
import { useRef } from "react";
|
|
5
|
+
//#region src/components/popup/PopupList.tsx
|
|
6
|
+
var PopupList = ({ className, items, trigger }) => {
|
|
7
|
+
const itemRefs = useRef([]);
|
|
8
|
+
const handleKeyDown = (event) => {
|
|
9
|
+
const index = itemRefs.current.indexOf(document.activeElement);
|
|
10
|
+
if (index < 0 || items.length === 0) return;
|
|
11
|
+
if (event.key === "ArrowDown" || event.key === "ArrowUp") {
|
|
12
|
+
event.preventDefault();
|
|
13
|
+
const nextIndex = (index + (event.key === "ArrowDown" ? 1 : -1) + items.length) % items.length;
|
|
14
|
+
itemRefs.current[nextIndex]?.focus();
|
|
15
|
+
}
|
|
16
|
+
if (event.key === "Home" || event.key === "End") {
|
|
17
|
+
event.preventDefault();
|
|
18
|
+
itemRefs.current[event.key === "Home" ? 0 : items.length - 1]?.focus();
|
|
19
|
+
}
|
|
20
|
+
};
|
|
21
|
+
return /* @__PURE__ */ jsx(Popup, {
|
|
22
|
+
...className ? { className } : {},
|
|
23
|
+
trigger,
|
|
24
|
+
children: /* @__PURE__ */ jsx("div", {
|
|
25
|
+
onKeyDown: handleKeyDown,
|
|
26
|
+
role: "menu",
|
|
27
|
+
tabIndex: -1,
|
|
28
|
+
children: items.map((item, index) => /* @__PURE__ */ jsxs("button", {
|
|
29
|
+
className: "chayns-popup-list__item",
|
|
30
|
+
onClick: item.onClick,
|
|
31
|
+
ref: (element) => {
|
|
32
|
+
itemRefs.current[index] = element;
|
|
33
|
+
},
|
|
34
|
+
role: "menuitem",
|
|
35
|
+
type: "button",
|
|
36
|
+
children: [/* @__PURE__ */ jsx(ButtonIcon, { icon: item.icon }), /* @__PURE__ */ jsx("span", { children: item.text })]
|
|
37
|
+
}, `${item.text}-${index}`))
|
|
38
|
+
})
|
|
39
|
+
});
|
|
40
|
+
};
|
|
41
|
+
//#endregion
|
|
42
|
+
export { PopupList as default };
|
|
43
|
+
|
|
44
|
+
//# sourceMappingURL=PopupList.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PopupList.js","names":[],"sources":["../../../src/components/popup/PopupList.tsx"],"sourcesContent":["import { useRef, type KeyboardEvent } from 'react';\n\nimport ButtonIcon from '../button/button-icon/ButtonIcon.js';\nimport Popup from './Popup.js';\nimport type { PopupListProps } from './Popup.types.js';\n\nconst PopupList = ({ className, items, trigger }: PopupListProps) => {\n const itemRefs = useRef<(HTMLButtonElement | null)[]>([]);\n\n const handleKeyDown = (event: KeyboardEvent<HTMLDivElement>) => {\n const index = itemRefs.current.indexOf(document.activeElement as HTMLButtonElement);\n if (index < 0 || items.length === 0) return;\n\n if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {\n event.preventDefault();\n const direction = event.key === 'ArrowDown' ? 1 : -1;\n const nextIndex = (index + direction + items.length) % items.length;\n itemRefs.current[nextIndex]?.focus();\n }\n if (event.key === 'Home' || event.key === 'End') {\n event.preventDefault();\n itemRefs.current[event.key === 'Home' ? 0 : items.length - 1]?.focus();\n }\n };\n\n return (\n <Popup {...(className ? { className } : {})} trigger={trigger}>\n <div onKeyDown={handleKeyDown} role=\"menu\" tabIndex={-1}>\n {items.map((item, index) => (\n <button\n className=\"chayns-popup-list__item\"\n key={`${item.text}-${index}`}\n onClick={item.onClick}\n ref={(element) => {\n itemRefs.current[index] = element;\n }}\n role=\"menuitem\"\n type=\"button\"\n >\n <ButtonIcon icon={item.icon} />\n <span>{item.text}</span>\n </button>\n ))}\n </div>\n </Popup>\n );\n};\n\nexport default PopupList;\n"],"mappings":";;;;;AAMA,IAAM,aAAa,EAAE,WAAW,OAAO,cAA8B;CACnE,MAAM,WAAW,OAAqC,CAAC,CAAC;CAExD,MAAM,iBAAiB,UAAyC;EAC9D,MAAM,QAAQ,SAAS,QAAQ,QAAQ,SAAS,aAAkC;EAClF,IAAI,QAAQ,KAAK,MAAM,WAAW,GAAG;EAErC,IAAI,MAAM,QAAQ,eAAe,MAAM,QAAQ,WAAW;GACxD,MAAM,eAAe;GAErB,MAAM,aAAa,SADD,MAAM,QAAQ,cAAc,IAAI,MACX,MAAM,UAAU,MAAM;GAC7D,SAAS,QAAQ,UAAU,EAAE,MAAM;EACrC;EACA,IAAI,MAAM,QAAQ,UAAU,MAAM,QAAQ,OAAO;GAC/C,MAAM,eAAe;GACrB,SAAS,QAAQ,MAAM,QAAQ,SAAS,IAAI,MAAM,SAAS,EAAE,EAAE,MAAM;EACvE;CACF;CAEA,OACE,oBAAC,OAAD;EAAO,GAAK,YAAY,EAAE,UAAU,IAAI,CAAC;EAAa;EACpD,UAAA,oBAAC,OAAD;GAAK,WAAW;GAAe,MAAK;GAAO,UAAU;GAClD,UAAA,MAAM,KAAK,MAAM,UAChB,qBAAC,UAAD;IACE,WAAU;IAEV,SAAS,KAAK;IACd,MAAM,YAAY;KAChB,SAAS,QAAQ,SAAS;IAC5B;IACA,MAAK;IACL,MAAK;IARP,UAAA,CAUE,oBAAC,YAAD,EAAY,MAAM,KAAK,KAAO,CAAA,GAC9B,oBAAC,QAAD,EAAA,UAAO,KAAK,KAAW,CAAA,CACjB;GAVD,GAAA,GAAG,KAAK,KAAK,GAAG,OAUf,CACT;EACE,CAAA;CACA,CAAA;AAEX"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { SplitButtonProps } from './SplitButton.types.js';
|
|
2
|
+
declare const SplitButton: ({ children, className, disabled, icon, items, onClick, variant, ...containerProps }: SplitButtonProps) => import("react").JSX.Element;
|
|
3
|
+
export default SplitButton;
|
|
4
|
+
//# sourceMappingURL=SplitButton.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SplitButton.d.ts","sourceRoot":"","sources":["../../../src/components/split-button/SplitButton.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,wBAAwB,CAAC;AAE/D,QAAA,MAAM,WAAW,GAAI,qFASlB,gBAAgB,gCA+ClB,CAAC;AAEF,eAAe,WAAW,CAAC"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import ButtonIcon from "../button/button-icon/ButtonIcon.js";
|
|
2
|
+
import Button from "../button/Button.js";
|
|
3
|
+
import PopupList from "../popup/PopupList.js";
|
|
4
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
5
|
+
import { useId } from "react";
|
|
6
|
+
//#region src/components/split-button/SplitButton.tsx
|
|
7
|
+
var SplitButton = ({ children, className, disabled, icon, items, onClick, variant, ...containerProps }) => {
|
|
8
|
+
const labelId = useId();
|
|
9
|
+
return /* @__PURE__ */ jsxs("div", {
|
|
10
|
+
...containerProps,
|
|
11
|
+
className: ["chayns-split-button", className].filter(Boolean).join(" "),
|
|
12
|
+
children: [icon ? /* @__PURE__ */ jsx(Button, {
|
|
13
|
+
"aria-labelledby": labelId,
|
|
14
|
+
className: "chayns-split-button__primary",
|
|
15
|
+
...disabled ? { disabled: true } : {},
|
|
16
|
+
icon,
|
|
17
|
+
...onClick ? { onClick } : {},
|
|
18
|
+
variant,
|
|
19
|
+
children: /* @__PURE__ */ jsx("span", {
|
|
20
|
+
id: labelId,
|
|
21
|
+
children
|
|
22
|
+
})
|
|
23
|
+
}) : /* @__PURE__ */ jsx(Button, {
|
|
24
|
+
"aria-labelledby": labelId,
|
|
25
|
+
className: "chayns-split-button__primary",
|
|
26
|
+
...disabled ? { disabled: true } : {},
|
|
27
|
+
...onClick ? { onClick } : {},
|
|
28
|
+
variant,
|
|
29
|
+
children: /* @__PURE__ */ jsx("span", {
|
|
30
|
+
id: labelId,
|
|
31
|
+
children
|
|
32
|
+
})
|
|
33
|
+
}), /* @__PURE__ */ jsx(PopupList, {
|
|
34
|
+
items,
|
|
35
|
+
trigger: /* @__PURE__ */ jsx("button", {
|
|
36
|
+
"aria-labelledby": labelId,
|
|
37
|
+
className: `chayns-split-button__trigger chayns-button--${variant}`,
|
|
38
|
+
...disabled ? { disabled: true } : {},
|
|
39
|
+
type: "button",
|
|
40
|
+
children: /* @__PURE__ */ jsx("span", {
|
|
41
|
+
"aria-hidden": "true",
|
|
42
|
+
className: "chayns-split-button__chevron",
|
|
43
|
+
children: /* @__PURE__ */ jsx(ButtonIcon, { icon: "fa-chevron-down" })
|
|
44
|
+
})
|
|
45
|
+
})
|
|
46
|
+
})]
|
|
47
|
+
});
|
|
48
|
+
};
|
|
49
|
+
//#endregion
|
|
50
|
+
export { SplitButton as default };
|
|
51
|
+
|
|
52
|
+
//# sourceMappingURL=SplitButton.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SplitButton.js","names":[],"sources":["../../../src/components/split-button/SplitButton.tsx"],"sourcesContent":["import { useId } from 'react';\n\nimport Button from '../button/Button.js';\nimport ButtonIcon from '../button/button-icon/ButtonIcon.js';\nimport PopupList from '../popup/PopupList.js';\nimport type { SplitButtonProps } from './SplitButton.types.js';\n\nconst SplitButton = ({\n children,\n className,\n disabled,\n icon,\n items,\n onClick,\n variant,\n ...containerProps\n}: SplitButtonProps) => {\n const labelId = useId();\n\n return (\n <div\n {...containerProps}\n className={['chayns-split-button', className].filter(Boolean).join(' ')}\n >\n {icon ? (\n <Button\n aria-labelledby={labelId}\n className=\"chayns-split-button__primary\"\n {...(disabled ? { disabled: true } : {})}\n icon={icon}\n {...(onClick ? { onClick } : {})}\n variant={variant}\n >\n <span id={labelId}>{children}</span>\n </Button>\n ) : (\n <Button\n aria-labelledby={labelId}\n className=\"chayns-split-button__primary\"\n {...(disabled ? { disabled: true } : {})}\n {...(onClick ? { onClick } : {})}\n variant={variant}\n >\n <span id={labelId}>{children}</span>\n </Button>\n )}\n <PopupList\n items={items}\n trigger={\n <button\n aria-labelledby={labelId}\n className={`chayns-split-button__trigger chayns-button--${variant}`}\n {...(disabled ? { disabled: true } : {})}\n type=\"button\"\n >\n <span aria-hidden=\"true\" className=\"chayns-split-button__chevron\">\n <ButtonIcon icon=\"fa-chevron-down\" />\n </span>\n </button>\n }\n />\n </div>\n );\n};\n\nexport default SplitButton;\n"],"mappings":";;;;;;AAOA,IAAM,eAAe,EACnB,UACA,WACA,UACA,MACA,OACA,SACA,SACA,GAAG,qBACmB;CACtB,MAAM,UAAU,MAAM;CAEtB,OACE,qBAAC,OAAD;EACE,GAAI;EACJ,WAAW,CAAC,uBAAuB,SAAS,CAAC,CAAC,OAAO,OAAO,CAAC,CAAC,KAAK,GAAG;EAFxE,UAAA,CAIG,OACC,oBAAC,QAAD;GACE,mBAAiB;GACjB,WAAU;GACV,GAAK,WAAW,EAAE,UAAU,KAAK,IAAI,CAAC;GAChC;GACN,GAAK,UAAU,EAAE,QAAQ,IAAI,CAAC;GACrB;GAET,UAAA,oBAAC,QAAD;IAAM,IAAI;IAAU;GAAe,CAAA;EAC7B,CAAA,IAER,oBAAC,QAAD;GACE,mBAAiB;GACjB,WAAU;GACV,GAAK,WAAW,EAAE,UAAU,KAAK,IAAI,CAAC;GACtC,GAAK,UAAU,EAAE,QAAQ,IAAI,CAAC;GACrB;GAET,UAAA,oBAAC,QAAD;IAAM,IAAI;IAAU;GAAe,CAAA;EAC7B,CAAA,GAEV,oBAAC,WAAD;GACS;GACP,SACE,oBAAC,UAAD;IACE,mBAAiB;IACjB,WAAW,+CAA+C;IAC1D,GAAK,WAAW,EAAE,UAAU,KAAK,IAAI,CAAC;IACtC,MAAK;IAEL,UAAA,oBAAC,QAAD;KAAM,eAAY;KAAO,WAAU;KACjC,UAAA,oBAAC,YAAD,EAAY,MAAK,kBAAmB,CAAA;IAChC,CAAA;GACA,CAAA;EAEX,CAAA,CACE;;AAET"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { ComponentPropsWithRef } from 'react';
|
|
2
|
+
import type { ButtonContent, ButtonIcon, ButtonVariant } from '../button/Button.types.js';
|
|
3
|
+
import type { PopupListItem } from '../popup/Popup.types.js';
|
|
4
|
+
export interface SplitButtonProps extends Omit<ComponentPropsWithRef<'div'>, 'children' | 'onClick'> {
|
|
5
|
+
variant: ButtonVariant;
|
|
6
|
+
children: ButtonContent;
|
|
7
|
+
items: PopupListItem[];
|
|
8
|
+
icon?: ButtonIcon;
|
|
9
|
+
onClick?: ComponentPropsWithRef<'button'>['onClick'];
|
|
10
|
+
disabled?: boolean;
|
|
11
|
+
}
|
|
12
|
+
//# sourceMappingURL=SplitButton.types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"SplitButton.types.d.ts","sourceRoot":"","sources":["../../../src/components/split-button/SplitButton.types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,OAAO,CAAC;AAEnD,OAAO,KAAK,EAAE,aAAa,EAAE,UAAU,EAAE,aAAa,EAAE,MAAM,2BAA2B,CAAC;AAC1F,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,yBAAyB,CAAC;AAE7D,MAAM,WAAW,gBAAiB,SAAQ,IAAI,CAC5C,qBAAqB,CAAC,KAAK,CAAC,EAC5B,UAAU,GAAG,SAAS,CACvB;IACC,OAAO,EAAE,aAAa,CAAC;IACvB,QAAQ,EAAE,aAAa,CAAC;IACxB,KAAK,EAAE,aAAa,EAAE,CAAC;IACvB,IAAI,CAAC,EAAE,UAAU,CAAC;IAClB,OAAO,CAAC,EAAE,qBAAqB,CAAC,QAAQ,CAAC,CAAC,SAAS,CAAC,CAAC;IACrD,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB"}
|
package/dist/index.d.ts
CHANGED
|
@@ -1,9 +1,22 @@
|
|
|
1
|
-
export { Button
|
|
2
|
-
export
|
|
3
|
-
export {
|
|
4
|
-
export type {
|
|
5
|
-
export {
|
|
6
|
-
export
|
|
7
|
-
export {
|
|
8
|
-
export
|
|
1
|
+
export { default as Button } from './components/button/Button.js';
|
|
2
|
+
export { default as IconButton } from './components/icon-button/IconButton.js';
|
|
3
|
+
export type { ButtonContent, ButtonIcon, ButtonProps, ButtonVariant, } from './components/button/Button.types.js';
|
|
4
|
+
export type { IconButtonProps } from './components/icon-button/IconButton.types.js';
|
|
5
|
+
export { default as Popup } from './components/popup/Popup.js';
|
|
6
|
+
export { default as PopupList } from './components/popup/PopupList.js';
|
|
7
|
+
export type { PopupListItem, PopupListProps, PopupProps } from './components/popup/Popup.types.js';
|
|
8
|
+
export { default as SplitButton } from './components/split-button/SplitButton.js';
|
|
9
|
+
export type { SplitButtonProps } from './components/split-button/SplitButton.types.js';
|
|
10
|
+
export { default as Card } from './components/card/Card.js';
|
|
11
|
+
export type { CardProps } from './components/card/Card.types.js';
|
|
12
|
+
export { default as Avatar } from './components/avatar/Avatar.js';
|
|
13
|
+
export { default as AvatarGroup } from './components/avatar-group/AvatarGroup.js';
|
|
14
|
+
export type { AvatarProps } from './components/avatar/Avatar.types.js';
|
|
15
|
+
export type { AvatarGroupProps } from './components/avatar-group/AvatarGroup.types.js';
|
|
16
|
+
export { default as List } from './components/list/List.js';
|
|
17
|
+
export { default as ListItem } from './components/list-item/ListItem.js';
|
|
18
|
+
export type { ListProps, ListItemProps } from './components/list/List.types.js';
|
|
19
|
+
export { default as Accordion } from './components/accordion/Accordion.js';
|
|
20
|
+
export { default as AccordionGroup } from './components/accordion-group/AccordionGroup.js';
|
|
21
|
+
export type { AccordionProps, AccordionGroupProps, } from './components/accordion/Accordion.types.js';
|
|
9
22
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,IAAI,MAAM,EAAE,MAAM,+BAA+B,CAAC;AAClE,OAAO,EAAE,OAAO,IAAI,UAAU,EAAE,MAAM,wCAAwC,CAAC;AAC/E,YAAY,EACV,aAAa,EACb,UAAU,EACV,WAAW,EACX,aAAa,GACd,MAAM,qCAAqC,CAAC;AAC7C,YAAY,EAAE,eAAe,EAAE,MAAM,8CAA8C,CAAC;AAEpF,OAAO,EAAE,OAAO,IAAI,KAAK,EAAE,MAAM,6BAA6B,CAAC;AAC/D,OAAO,EAAE,OAAO,IAAI,SAAS,EAAE,MAAM,iCAAiC,CAAC;AACvE,YAAY,EAAE,aAAa,EAAE,cAAc,EAAE,UAAU,EAAE,MAAM,mCAAmC,CAAC;AAEnG,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,0CAA0C,CAAC;AAClF,YAAY,EAAE,gBAAgB,EAAE,MAAM,gDAAgD,CAAC;AAEvF,OAAO,EAAE,OAAO,IAAI,IAAI,EAAE,MAAM,2BAA2B,CAAC;AAC5D,YAAY,EAAE,SAAS,EAAE,MAAM,iCAAiC,CAAC;AAEjE,OAAO,EAAE,OAAO,IAAI,MAAM,EAAE,MAAM,+BAA+B,CAAC;AAClE,OAAO,EAAE,OAAO,IAAI,WAAW,EAAE,MAAM,0CAA0C,CAAC;AAClF,YAAY,EAAE,WAAW,EAAE,MAAM,qCAAqC,CAAC;AACvE,YAAY,EAAE,gBAAgB,EAAE,MAAM,gDAAgD,CAAC;AAEvF,OAAO,EAAE,OAAO,IAAI,IAAI,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,OAAO,IAAI,QAAQ,EAAE,MAAM,oCAAoC,CAAC;AACzE,YAAY,EAAE,SAAS,EAAE,aAAa,EAAE,MAAM,iCAAiC,CAAC;AAEhF,OAAO,EAAE,OAAO,IAAI,SAAS,EAAE,MAAM,qCAAqC,CAAC;AAC3E,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,gDAAgD,CAAC;AAC3F,YAAY,EACV,cAAc,EACd,mBAAmB,GACpB,MAAM,2CAA2C,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -1,8 +1,13 @@
|
|
|
1
1
|
import Button from "./components/button/Button.js";
|
|
2
|
-
import IconButton from "./components/button/IconButton.js";
|
|
2
|
+
import IconButton from "./components/icon-button/IconButton.js";
|
|
3
|
+
import Popup from "./components/popup/Popup.js";
|
|
4
|
+
import PopupList from "./components/popup/PopupList.js";
|
|
5
|
+
import SplitButton from "./components/split-button/SplitButton.js";
|
|
3
6
|
import Card from "./components/card/Card.js";
|
|
7
|
+
import Avatar from "./components/avatar/Avatar.js";
|
|
8
|
+
import AvatarGroup from "./components/avatar-group/AvatarGroup.js";
|
|
4
9
|
import List from "./components/list/List.js";
|
|
5
|
-
import ListItem from "./components/list/ListItem.js";
|
|
10
|
+
import ListItem from "./components/list-item/ListItem.js";
|
|
6
11
|
import Accordion from "./components/accordion/Accordion.js";
|
|
7
|
-
import AccordionGroup from "./components/accordion/AccordionGroup.js";
|
|
8
|
-
export { Accordion, AccordionGroup, Button, Card, IconButton, List, ListItem };
|
|
12
|
+
import AccordionGroup from "./components/accordion-group/AccordionGroup.js";
|
|
13
|
+
export { Accordion, AccordionGroup, Avatar, AvatarGroup, Button, Card, IconButton, List, ListItem, Popup, PopupList, SplitButton };
|
package/dist/list.css
CHANGED
|
@@ -89,10 +89,17 @@
|
|
|
89
89
|
|
|
90
90
|
.chayns-list-item__trailing {
|
|
91
91
|
flex: none;
|
|
92
|
+
align-self: flex-start;
|
|
92
93
|
display: flex;
|
|
93
|
-
align-items:
|
|
94
|
+
align-items: flex-start;
|
|
95
|
+
justify-content: flex-end;
|
|
94
96
|
gap: var(--k8);
|
|
97
|
+
padding-block-start: var(--k10);
|
|
95
98
|
padding-inline-end: var(--k16);
|
|
99
|
+
color: var(--text-3);
|
|
100
|
+
font-size: var(--fs-meta);
|
|
101
|
+
text-align: end;
|
|
102
|
+
white-space: nowrap;
|
|
96
103
|
}
|
|
97
104
|
|
|
98
105
|
.chayns-visually-hidden {
|
package/dist/popup.css
ADDED
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
@layer chayns.components {
|
|
2
|
+
.chayns-popup {
|
|
3
|
+
position: fixed;
|
|
4
|
+
z-index: var(--z-popover);
|
|
5
|
+
min-inline-size: 14rem;
|
|
6
|
+
padding: var(--sp-2);
|
|
7
|
+
border: 1px solid var(--disabled-border);
|
|
8
|
+
border-radius: 12px;
|
|
9
|
+
background: var(--surface);
|
|
10
|
+
box-shadow: var(--shadow-pop);
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
.chayns-popup-list__item {
|
|
14
|
+
display: flex;
|
|
15
|
+
inline-size: 100%;
|
|
16
|
+
align-items: center;
|
|
17
|
+
gap: var(--sp-2);
|
|
18
|
+
min-block-size: var(--ctrl-h);
|
|
19
|
+
padding: var(--sp-2) var(--sp-4);
|
|
20
|
+
border: 0;
|
|
21
|
+
border-radius: 8px;
|
|
22
|
+
background: transparent;
|
|
23
|
+
color: var(--text);
|
|
24
|
+
font: inherit;
|
|
25
|
+
text-align: start;
|
|
26
|
+
cursor: pointer;
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
.chayns-popup-list__item:hover,
|
|
30
|
+
.chayns-popup-list__item:focus-visible {
|
|
31
|
+
background: var(--surface-alt);
|
|
32
|
+
outline: none;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
@layer chayns.components {
|
|
2
|
+
.chayns-split-button {
|
|
3
|
+
display: inline-flex;
|
|
4
|
+
align-items: stretch;
|
|
5
|
+
max-inline-size: 100%;
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
.chayns-split-button__primary {
|
|
9
|
+
border-start-end-radius: 0;
|
|
10
|
+
border-end-end-radius: 0;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
.chayns-split-button__trigger {
|
|
14
|
+
display: inline-flex;
|
|
15
|
+
align-items: center;
|
|
16
|
+
justify-content: center;
|
|
17
|
+
min-inline-size: var(--ctrl-h);
|
|
18
|
+
padding: 0 var(--sp-2);
|
|
19
|
+
border: 0;
|
|
20
|
+
border-inline-start: 1px solid color-mix(in srgb, currentcolor 30%, transparent);
|
|
21
|
+
border-start-end-radius: 999px;
|
|
22
|
+
border-end-end-radius: 999px;
|
|
23
|
+
font: inherit;
|
|
24
|
+
cursor: pointer;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
.chayns-split-button__trigger.chayns-button--primary {
|
|
28
|
+
background: var(--accent);
|
|
29
|
+
color: var(--on-accent);
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
.chayns-split-button__trigger.chayns-button--outline {
|
|
33
|
+
border-block: 1.5px solid var(--accent);
|
|
34
|
+
border-inline-end: 1.5px solid var(--accent);
|
|
35
|
+
background: var(--surface);
|
|
36
|
+
color: var(--accent);
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
.chayns-split-button__trigger.chayns-button--ghost {
|
|
40
|
+
background: transparent;
|
|
41
|
+
color: var(--text-2);
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
.chayns-split-button__trigger.chayns-button--danger {
|
|
45
|
+
background: var(--danger-bg);
|
|
46
|
+
color: var(--danger);
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
.chayns-split-button__trigger:disabled {
|
|
50
|
+
background: var(--disabled-bg);
|
|
51
|
+
border-inline-start-color: var(--disabled-border);
|
|
52
|
+
border-inline-end-color: var(--disabled-border);
|
|
53
|
+
color: var(--disabled-fg);
|
|
54
|
+
cursor: not-allowed;
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
.chayns-split-button__trigger.chayns-button--outline:disabled {
|
|
58
|
+
border-block-color: var(--disabled-border);
|
|
59
|
+
background: var(--surface);
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
.chayns-split-button__trigger:focus-visible {
|
|
63
|
+
outline: none;
|
|
64
|
+
box-shadow: 0 0 0 var(--focus-ring-size)
|
|
65
|
+
rgb(var(--focus-ring-rgb), var(--focus-ring-alpha-strong));
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
.chayns-split-button__trigger:active:not(:disabled) {
|
|
69
|
+
transform: scale(0.97);
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
.chayns-split-button__trigger.chayns-button--primary:active:not(:disabled) {
|
|
73
|
+
background: var(--accent-active);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
.chayns-split-button__trigger.chayns-button--outline:active:not(:disabled) {
|
|
77
|
+
background: var(--accent);
|
|
78
|
+
color: var(--on-accent);
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
.chayns-split-button__trigger.chayns-button--ghost:active:not(:disabled) {
|
|
82
|
+
background: var(--surface-alt);
|
|
83
|
+
color: var(--accent);
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
.chayns-split-button__trigger.chayns-button--danger:active:not(:disabled) {
|
|
87
|
+
background: var(--danger-bg-hover);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
.chayns-split-button__trigger:active:not(:disabled)
|
|
91
|
+
.chayns-button-icon__weight:not(.chayns-button-icon__weight--active),
|
|
92
|
+
.chayns-split-button__trigger:hover:not(:disabled)
|
|
93
|
+
.chayns-button-icon__weight:not(.chayns-button-icon__weight--active) {
|
|
94
|
+
display: none;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
.chayns-split-button__trigger:active:not(:disabled) .chayns-button-icon__weight--active,
|
|
98
|
+
.chayns-split-button__trigger:hover:not(:disabled) .chayns-button-icon__weight--active {
|
|
99
|
+
display: inline-flex;
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
@media (hover: hover) {
|
|
103
|
+
.chayns-split-button__trigger.chayns-button--primary:hover:not(:disabled) {
|
|
104
|
+
background: var(--accent-hover);
|
|
105
|
+
box-shadow: var(--shadow-btn-hover);
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
.chayns-split-button__trigger.chayns-button--outline:hover:not(:disabled) {
|
|
109
|
+
background: var(--accent);
|
|
110
|
+
color: var(--on-accent);
|
|
111
|
+
box-shadow: var(--shadow-btn-hover);
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
.chayns-split-button__trigger.chayns-button--ghost:hover:not(:disabled) {
|
|
115
|
+
background: var(--surface-alt);
|
|
116
|
+
color: var(--accent);
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
.chayns-split-button__trigger.chayns-button--danger:hover:not(:disabled) {
|
|
120
|
+
background: var(--danger-bg-hover);
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
.chayns-split-button__chevron .chayns-button-icon {
|
|
125
|
+
inline-size: 1em;
|
|
126
|
+
block-size: 1em;
|
|
127
|
+
}
|
|
128
|
+
}
|
package/dist/styles.css
CHANGED
package/package.json
CHANGED
|
@@ -1,9 +1,14 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@chayns-ui/core",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.0",
|
|
4
4
|
"description": "Accessible React core components for chayns UI",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
|
7
|
+
"repository": {
|
|
8
|
+
"type": "git",
|
|
9
|
+
"url": "git+https://github.com/TobitSoftware/chayns-ui.git",
|
|
10
|
+
"directory": "packages/core"
|
|
11
|
+
},
|
|
7
12
|
"sideEffects": [
|
|
8
13
|
"**/*.css"
|
|
9
14
|
],
|
|
@@ -17,34 +22,21 @@
|
|
|
17
22
|
"types": "./dist/index.d.ts",
|
|
18
23
|
"import": "./dist/index.js"
|
|
19
24
|
},
|
|
20
|
-
"./button": {
|
|
21
|
-
"types": "./dist/components/button/index.d.ts",
|
|
22
|
-
"import": "./dist/components/button/index.js"
|
|
23
|
-
},
|
|
24
25
|
"./button.css": "./dist/button.css",
|
|
25
|
-
"./card": {
|
|
26
|
-
"types": "./dist/components/card/index.d.ts",
|
|
27
|
-
"import": "./dist/components/card/index.js"
|
|
28
|
-
},
|
|
29
26
|
"./card.css": "./dist/card.css",
|
|
30
|
-
"./
|
|
31
|
-
"types": "./dist/components/list/index.d.ts",
|
|
32
|
-
"import": "./dist/components/list/index.js"
|
|
33
|
-
},
|
|
27
|
+
"./avatar.css": "./dist/avatar.css",
|
|
34
28
|
"./list.css": "./dist/list.css",
|
|
35
|
-
"./accordion": {
|
|
36
|
-
"types": "./dist/components/accordion/index.d.ts",
|
|
37
|
-
"import": "./dist/components/accordion/index.js"
|
|
38
|
-
},
|
|
39
29
|
"./accordion.css": "./dist/accordion.css",
|
|
30
|
+
"./popup.css": "./dist/popup.css",
|
|
31
|
+
"./split-button.css": "./dist/split-button.css",
|
|
40
32
|
"./styles.css": "./dist/styles.css",
|
|
41
33
|
"./package.json": "./package.json"
|
|
42
34
|
},
|
|
43
35
|
"peerDependencies": {
|
|
44
|
-
"react": ">=
|
|
36
|
+
"react": ">=18 <20"
|
|
45
37
|
},
|
|
46
38
|
"engines": {
|
|
47
|
-
"node": ">=
|
|
39
|
+
"node": ">=18"
|
|
48
40
|
},
|
|
49
41
|
"publishConfig": {
|
|
50
42
|
"access": "public"
|
|
@@ -1,4 +0,0 @@
|
|
|
1
|
-
import type { AccordionGroupProps } from './Accordion.types.js';
|
|
2
|
-
declare function AccordionGroup({ children, className, defaultOpenId, onOpenChange, openId, }: AccordionGroupProps): import("react").JSX.Element;
|
|
3
|
-
export default AccordionGroup;
|
|
4
|
-
//# sourceMappingURL=AccordionGroup.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"AccordionGroup.d.ts","sourceRoot":"","sources":["../../../src/components/accordion/AccordionGroup.tsx"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,sBAAsB,CAAC;AAEhE,iBAAS,cAAc,CAAC,EACtB,QAAQ,EACR,SAAS,EACT,aAAoB,EACpB,YAAY,EACZ,MAAM,GACP,EAAE,mBAAmB,+BA6BrB;AAED,eAAe,cAAc,CAAC"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"AccordionGroup.js","names":[],"sources":["../../../src/components/accordion/AccordionGroup.tsx"],"sourcesContent":["import { useCallback, useMemo, useState } from 'react';\n\nimport { AccordionGroupContext } from './AccordionContext.js';\nimport type { AccordionGroupContextValue } from './AccordionContext.js';\nimport type { AccordionGroupProps } from './Accordion.types.js';\n\nfunction AccordionGroup({\n children,\n className,\n defaultOpenId = null,\n onOpenChange,\n openId,\n}: AccordionGroupProps) {\n const [uncontrolledOpenId, setUncontrolledOpenId] = useState<string | null>(defaultOpenId);\n\n const isControlled = openId !== undefined;\n const currentOpenId = isControlled ? openId : uncontrolledOpenId;\n\n const isOpen = useCallback((id: string) => currentOpenId === id, [currentOpenId]);\n\n const toggle = useCallback(\n (id: string) => {\n const nextOpenId = currentOpenId === id ? null : id;\n if (!isControlled) setUncontrolledOpenId(nextOpenId);\n onOpenChange?.(nextOpenId);\n },\n [currentOpenId, isControlled, onOpenChange],\n );\n\n const contextValue = useMemo<AccordionGroupContextValue>(\n () => ({ isOpen, toggle }),\n [isOpen, toggle],\n );\n\n const rootClassName = ['chayns-accordion-group', className].filter(Boolean).join(' ');\n\n return (\n <AccordionGroupContext.Provider value={contextValue}>\n <div className={rootClassName}>{children}</div>\n </AccordionGroupContext.Provider>\n );\n}\n\nexport default AccordionGroup;\n"],"mappings":";;;;AAMA,SAAS,eAAe,EACtB,UACA,WACA,gBAAgB,MAChB,cACA,UACsB;CACtB,MAAM,CAAC,oBAAoB,yBAAyB,SAAwB,aAAa;CAEzF,MAAM,eAAe,WAAW,KAAA;CAChC,MAAM,gBAAgB,eAAe,SAAS;CAE9C,MAAM,SAAS,aAAa,OAAe,kBAAkB,IAAI,CAAC,aAAa,CAAC;CAEhF,MAAM,SAAS,aACZ,OAAe;EACd,MAAM,aAAa,kBAAkB,KAAK,OAAO;EACjD,IAAI,CAAC,cAAc,sBAAsB,UAAU;EACnD,eAAe,UAAU;CAC3B,GACA;EAAC;EAAe;EAAc;CAAY,CAC5C;CAEA,MAAM,eAAe,eACZ;EAAE;EAAQ;CAAO,IACxB,CAAC,QAAQ,MAAM,CACjB;CAEA,MAAM,gBAAgB,CAAC,0BAA0B,SAAS,CAAC,CAAC,OAAO,OAAO,CAAC,CAAC,KAAK,GAAG;CAEpF,OACE,oBAAC,sBAAsB,UAAvB;EAAgC,OAAO;EACrC,UAAA,oBAAC,OAAD;GAAK,WAAW;GAAgB;EAAc,CAAA;CAChB,CAAA;AAEpC"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/accordion/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,IAAI,SAAS,EAAE,MAAM,gBAAgB,CAAC;AACtD,OAAO,EAAE,OAAO,IAAI,cAAc,EAAE,MAAM,qBAAqB,CAAC;AAChE,YAAY,EAAE,mBAAmB,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC"}
|