@react-fabric/core 1.0.0-beta.55 → 1.0.0-beta.58
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/css/components/_card.css +8 -4
- package/css/components/_icon.css +3 -3
- package/css/components/_tabPanel.css +40 -0
- package/css/core/_aside.css +4 -6
- package/css/reset/_reset.css +14 -0
- package/dist/cjs/components/avatar/Avatar.js +9 -4
- package/dist/cjs/components/badge/Badge.js +2 -10
- package/dist/cjs/components/button/Button.js +7 -12
- package/dist/cjs/components/card/Card.js +18 -12
- package/dist/cjs/components/chip/Chip.js +9 -14
- package/dist/cjs/components/dropdown/Dropdown.js +1 -0
- package/dist/cjs/components/icon/Icon.js +37 -8
- package/dist/cjs/components/menu/MenuItem.js +5 -12
- package/dist/cjs/components/panel/Panel.js +4 -13
- package/dist/cjs/components/tabpanel/Tab.js +4 -13
- package/dist/cjs/components/tabpanel/TabPanel.js +2 -1
- package/dist/cjs/core/aside/Aside.js +2 -11
- package/dist/cjs/core/headfoot/HeadFoot.js +4 -2
- package/dist/cjs/core/page/Page.js +4 -13
- package/dist/cjs/index.js +1 -0
- package/dist/cjs/overlays/alert/Alert.js +3 -1
- package/dist/cjs/overlays/flyout/Flyout.js +6 -11
- package/dist/cjs/overlays/message/Message.js +2 -0
- package/dist/cjs/overlays/modal/Modal.js +6 -13
- package/dist/cjs/overlays/toast/Toast.js +3 -1
- package/dist/cjs/types/icons.js +2 -1
- package/dist/esm/components/avatar/Avatar.js +9 -4
- package/dist/esm/components/badge/Badge.js +3 -11
- package/dist/esm/components/button/Button.js +9 -14
- package/dist/esm/components/card/Card.js +18 -12
- package/dist/esm/components/chip/Chip.js +10 -15
- package/dist/esm/components/dropdown/Dropdown.js +1 -0
- package/dist/esm/components/icon/Icon.js +39 -11
- package/dist/esm/components/menu/MenuItem.js +6 -13
- package/dist/esm/components/panel/Panel.js +5 -14
- package/dist/esm/components/tabpanel/Tab.js +5 -14
- package/dist/esm/components/tabpanel/TabPanel.js +2 -1
- package/dist/esm/core/aside/Aside.js +3 -12
- package/dist/esm/core/headfoot/HeadFoot.js +4 -2
- package/dist/esm/core/page/Page.js +5 -14
- package/dist/esm/index.js +1 -1
- package/dist/esm/overlays/alert/Alert.js +3 -1
- package/dist/esm/overlays/flyout/Flyout.js +7 -12
- package/dist/esm/overlays/message/Message.js +2 -0
- package/dist/esm/overlays/modal/Modal.js +7 -14
- package/dist/esm/overlays/toast/Toast.js +3 -1
- package/dist/esm/types/icons.js +2 -1
- package/dist/types/components/avatar/Avatar.d.ts +5 -1
- package/dist/types/components/badge/Badge.d.ts +8 -3
- package/dist/types/components/button/Button.d.ts +12 -3
- package/dist/types/components/card/Card.d.ts +5 -3
- package/dist/types/components/chip/Chip.d.ts +12 -3
- package/dist/types/components/icon/Icon.d.ts +10 -4
- package/dist/types/components/index.d.ts +1 -1
- package/dist/types/components/menu/MenuItem.d.ts +1 -1
- package/dist/types/components/menu/types.d.ts +7 -2
- package/dist/types/components/panel/Panel.d.ts +8 -5
- package/dist/types/components/tabpanel/Tab.d.ts +8 -5
- package/dist/types/components/tabpanel/TabPanel.d.ts +5 -1
- package/dist/types/core/aside/Aside.d.ts +8 -5
- package/dist/types/core/page/Page.d.ts +8 -5
- package/dist/types/overlays/alert/Alert.d.ts +15 -3
- package/dist/types/overlays/flyout/Flyout.d.ts +9 -5
- package/dist/types/overlays/message/Message.d.ts +15 -3
- package/dist/types/overlays/modal/Modal.d.ts +6 -6
- package/dist/types/overlays/toast/Toast.d.ts +15 -3
- package/dist/types/types/icons.d.ts +2 -1
- package/dist/types/types/index.d.ts +0 -18
- package/package.json +14 -14
- package/src/components/avatar/Avatar.tsx +10 -2
- package/src/components/badge/Badge.tsx +7 -13
- package/src/components/button/Button.tsx +24 -19
- package/src/components/card/Card.tsx +29 -15
- package/src/components/chip/Chip.tsx +15 -13
- package/src/components/dropdown/Dropdown.tsx +1 -0
- package/src/components/icon/Icon.tsx +48 -7
- package/src/components/index.ts +1 -1
- package/src/components/menu/MenuItem.tsx +4 -9
- package/src/components/menu/types.ts +6 -6
- package/src/components/panel/Panel.tsx +7 -13
- package/src/components/tabpanel/Tab.tsx +8 -19
- package/src/components/tabpanel/TabPanel.tsx +6 -0
- package/src/core/aside/Aside.tsx +7 -13
- package/src/core/headfoot/HeadFoot.tsx +2 -2
- package/src/core/page/Page.tsx +8 -23
- package/src/overlays/alert/Alert.tsx +24 -5
- package/src/overlays/flyout/Flyout.tsx +11 -22
- package/src/overlays/message/Message.tsx +18 -3
- package/src/overlays/modal/Modal.tsx +8 -24
- package/src/overlays/toast/Toast.tsx +23 -4
- package/src/types/global.d.ts +8 -0
- package/src/types/icons.ts +3 -1
- package/src/types/index.ts +0 -19
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@react-fabric/core",
|
|
3
|
-
"version": "1.0.0-beta.
|
|
3
|
+
"version": "1.0.0-beta.58",
|
|
4
4
|
"description": "RUF: Core package",
|
|
5
5
|
"author": "Adarsh Pastakia <adarshpastakia@outlook.com>",
|
|
6
6
|
"license": "MIT",
|
|
@@ -35,24 +35,24 @@
|
|
|
35
35
|
"watch": "npm-run-all -p watch:rollup watch:dts"
|
|
36
36
|
},
|
|
37
37
|
"dependencies": {
|
|
38
|
-
"@floating-ui/react": "
|
|
39
|
-
"@react-fabric/utilities": "^1.0.0-beta.
|
|
40
|
-
"@tailwindcss/postcss": "~4.1.
|
|
41
|
-
"boring-avatars": "
|
|
42
|
-
"classnames": "
|
|
43
|
-
"color": "
|
|
44
|
-
"resize-observer-polyfill": "
|
|
45
|
-
"tailwindcss": "
|
|
38
|
+
"@floating-ui/react": "~0.27.16",
|
|
39
|
+
"@react-fabric/utilities": "^1.0.0-beta.58",
|
|
40
|
+
"@tailwindcss/postcss": "~4.1.16",
|
|
41
|
+
"boring-avatars": "~1.11.2",
|
|
42
|
+
"classnames": "~2.5.1",
|
|
43
|
+
"color": "~5.0.2",
|
|
44
|
+
"resize-observer-polyfill": "~1.5.1",
|
|
45
|
+
"tailwindcss": "~4.1.16"
|
|
46
46
|
},
|
|
47
47
|
"peerDependencies": {
|
|
48
|
-
"i18next": "
|
|
49
|
-
"react": "
|
|
50
|
-
"react-dom": "
|
|
51
|
-
"react-i18next": "
|
|
48
|
+
"i18next": "~25.6.0",
|
|
49
|
+
"react": "~19.2.0",
|
|
50
|
+
"react-dom": "~19.2.0",
|
|
51
|
+
"react-i18next": "~16.2.1"
|
|
52
52
|
},
|
|
53
53
|
"engines": {
|
|
54
54
|
"node": ">=18.12.0",
|
|
55
55
|
"npm": ">=8.19.0"
|
|
56
56
|
},
|
|
57
|
-
"gitHead": "
|
|
57
|
+
"gitHead": "7e66f8c498e37a40e410ecafff2ea6b31505dc1a"
|
|
58
58
|
}
|
|
@@ -73,6 +73,10 @@ export interface AvatarProps extends CssProp, AriaProps, TestProps, RefProp {
|
|
|
73
73
|
* rounded icon
|
|
74
74
|
*/
|
|
75
75
|
rounded?: boolean;
|
|
76
|
+
/**
|
|
77
|
+
* prevent click default, useful when component is within a `a` link
|
|
78
|
+
*/
|
|
79
|
+
preventDefault?: boolean;
|
|
76
80
|
/**
|
|
77
81
|
* click handler
|
|
78
82
|
*/
|
|
@@ -127,6 +131,7 @@ export const Avatar = ({
|
|
|
127
131
|
variant = "beam",
|
|
128
132
|
className,
|
|
129
133
|
viewBox = "0 0 24 24",
|
|
134
|
+
preventDefault,
|
|
130
135
|
onClick,
|
|
131
136
|
...aria
|
|
132
137
|
}: AvatarProps) => {
|
|
@@ -180,7 +185,7 @@ export const Avatar = ({
|
|
|
180
185
|
const fallbackAvatar = useMemo(() => {
|
|
181
186
|
if (fallbackIcon) {
|
|
182
187
|
return isSvgPath(fallbackIcon) ? (
|
|
183
|
-
<svg viewBox={viewBox}>
|
|
188
|
+
<svg viewBox={viewBox} className="p-[0.125em]">
|
|
184
189
|
<path fill="currentColor" d={fallbackIcon.toString()} />
|
|
185
190
|
</svg>
|
|
186
191
|
) : (
|
|
@@ -220,7 +225,10 @@ export const Avatar = ({
|
|
|
220
225
|
!rounded && "rounded",
|
|
221
226
|
rounded && "rounded-full",
|
|
222
227
|
)}
|
|
223
|
-
onClick={
|
|
228
|
+
onClick={(e) => {
|
|
229
|
+
preventDefault && e.preventDefault();
|
|
230
|
+
onClick?.(e);
|
|
231
|
+
}}
|
|
224
232
|
style={styles}
|
|
225
233
|
data-clickable={!!onClick}
|
|
226
234
|
ref={ref}
|
|
@@ -28,16 +28,11 @@ import {
|
|
|
28
28
|
type BadgeType,
|
|
29
29
|
type ChildProp,
|
|
30
30
|
type CssProp,
|
|
31
|
-
type IconProps,
|
|
32
31
|
type RefProp,
|
|
33
32
|
} from "../../types";
|
|
34
|
-
import { Icon } from "../icon/Icon";
|
|
33
|
+
import { getIconProps, Icon, IconProps } from "../icon/Icon";
|
|
35
34
|
|
|
36
|
-
export interface BadgeProps
|
|
37
|
-
extends CssProp,
|
|
38
|
-
RefProp,
|
|
39
|
-
IconProps,
|
|
40
|
-
Partial<ChildProp> {
|
|
35
|
+
export interface BadgeProps extends CssProp, RefProp, Partial<ChildProp> {
|
|
41
36
|
/**
|
|
42
37
|
* make wrapper a block element
|
|
43
38
|
*/
|
|
@@ -50,6 +45,10 @@ export interface BadgeProps
|
|
|
50
45
|
* badge value
|
|
51
46
|
*/
|
|
52
47
|
value?: number | string;
|
|
48
|
+
/**
|
|
49
|
+
* icon path or props
|
|
50
|
+
*/
|
|
51
|
+
icon?: IconProps;
|
|
53
52
|
/**
|
|
54
53
|
* max value for number display
|
|
55
54
|
*/
|
|
@@ -124,9 +123,6 @@ export const Badge = ({
|
|
|
124
123
|
// @ts-expect-error ignore
|
|
125
124
|
forButton = false,
|
|
126
125
|
icon,
|
|
127
|
-
iconBg,
|
|
128
|
-
iconColor,
|
|
129
|
-
rtlFlip,
|
|
130
126
|
...rest
|
|
131
127
|
}: BadgeProps) => {
|
|
132
128
|
const label = useMemo(() => {
|
|
@@ -176,9 +172,7 @@ export const Badge = ({
|
|
|
176
172
|
)}
|
|
177
173
|
>
|
|
178
174
|
{label && <span className="p-1">{label}</span>}
|
|
179
|
-
{icon && (
|
|
180
|
-
<Icon icon={icon} bg={iconBg} color={iconColor} rtlFlip={rtlFlip} />
|
|
181
|
-
)}
|
|
175
|
+
{icon && <Icon {...getIconProps(icon)} />}
|
|
182
176
|
</div>
|
|
183
177
|
)}
|
|
184
178
|
</div>
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
22
22
|
*/
|
|
23
23
|
|
|
24
|
-
import { isNil, isString, mergeRefs } from "@react-fabric/utilities";
|
|
24
|
+
import { isNil, isObject, isString, mergeRefs } from "@react-fabric/utilities";
|
|
25
25
|
import classNames from "classnames";
|
|
26
26
|
import {
|
|
27
27
|
Fragment,
|
|
@@ -39,12 +39,11 @@ import { HotKey } from "../../hotkeys/HotKey";
|
|
|
39
39
|
import { HotKeyLabel } from "../../hotkeys/HotKeyLabel";
|
|
40
40
|
import { Tooltip } from "../../overlays/tooltip/Tooltip";
|
|
41
41
|
import {
|
|
42
|
-
type ColorState,
|
|
43
42
|
type AriaProps,
|
|
44
43
|
type BadgeType,
|
|
45
44
|
type CallbackReturn,
|
|
45
|
+
type ColorState,
|
|
46
46
|
type CssProp,
|
|
47
|
-
type IconProps,
|
|
48
47
|
type PolymorphicProps,
|
|
49
48
|
type RefProp,
|
|
50
49
|
type SizeType,
|
|
@@ -54,14 +53,9 @@ import {
|
|
|
54
53
|
import { getColor } from "../../utils";
|
|
55
54
|
import { AnimationIndicator } from "../animations/Animations";
|
|
56
55
|
import { Badge, getBadgeProps } from "../badge/Badge";
|
|
57
|
-
import { Icon } from "../icon/Icon";
|
|
56
|
+
import { getIconProps, Icon, IconProps } from "../icon/Icon";
|
|
58
57
|
|
|
59
|
-
export interface BaseProps
|
|
60
|
-
extends CssProp,
|
|
61
|
-
AriaProps,
|
|
62
|
-
IconProps,
|
|
63
|
-
RefProp,
|
|
64
|
-
TestProps {
|
|
58
|
+
export interface BaseProps extends CssProp, AriaProps, RefProp, TestProps {
|
|
65
59
|
/**
|
|
66
60
|
* primary icon alignment
|
|
67
61
|
*/
|
|
@@ -78,6 +72,10 @@ export interface BaseProps
|
|
|
78
72
|
* button color
|
|
79
73
|
*/
|
|
80
74
|
color?: ColorState;
|
|
75
|
+
/**
|
|
76
|
+
* icon path or props
|
|
77
|
+
*/
|
|
78
|
+
icon?: IconProps;
|
|
81
79
|
/**
|
|
82
80
|
* button type
|
|
83
81
|
*/
|
|
@@ -136,6 +134,10 @@ export interface BaseProps
|
|
|
136
134
|
*/
|
|
137
135
|
hotKey?: string;
|
|
138
136
|
|
|
137
|
+
/**
|
|
138
|
+
* prevent click default, useful when button is within a `a` link
|
|
139
|
+
*/
|
|
140
|
+
preventDefault?: boolean;
|
|
139
141
|
stopPropagation?: boolean;
|
|
140
142
|
|
|
141
143
|
onMouseOut?: MouseEventHandler;
|
|
@@ -187,11 +189,8 @@ export const Button = <Tag extends React.ElementType = "button">({
|
|
|
187
189
|
active,
|
|
188
190
|
color = "primary",
|
|
189
191
|
icon,
|
|
190
|
-
iconBg,
|
|
191
|
-
iconColor,
|
|
192
192
|
iconAlign = "start",
|
|
193
193
|
altIcon,
|
|
194
|
-
rtlFlip,
|
|
195
194
|
rounded,
|
|
196
195
|
size,
|
|
197
196
|
disabled,
|
|
@@ -202,6 +201,7 @@ export const Button = <Tag extends React.ElementType = "button">({
|
|
|
202
201
|
spinOnHover,
|
|
203
202
|
onClick,
|
|
204
203
|
actionMessage,
|
|
204
|
+
preventDefault,
|
|
205
205
|
stopPropagation,
|
|
206
206
|
type = "button",
|
|
207
207
|
hotKey,
|
|
@@ -220,6 +220,7 @@ export const Button = <Tag extends React.ElementType = "button">({
|
|
|
220
220
|
const clickHandler = useCallback(
|
|
221
221
|
(e: React.MouseEvent) => {
|
|
222
222
|
setBusy(true);
|
|
223
|
+
preventDefault && e.preventDefault();
|
|
223
224
|
stopPropagation && e.stopPropagation();
|
|
224
225
|
const ret = onClick?.(e);
|
|
225
226
|
void Promise.resolve(ret).then((b) => {
|
|
@@ -229,7 +230,14 @@ export const Button = <Tag extends React.ElementType = "button">({
|
|
|
229
230
|
}
|
|
230
231
|
});
|
|
231
232
|
},
|
|
232
|
-
[
|
|
233
|
+
[
|
|
234
|
+
onClick,
|
|
235
|
+
disabled,
|
|
236
|
+
preventDefault,
|
|
237
|
+
actionMessage,
|
|
238
|
+
showActionDoneEvent,
|
|
239
|
+
stopPropagation,
|
|
240
|
+
],
|
|
233
241
|
);
|
|
234
242
|
|
|
235
243
|
/** ***************** reset done state on timeout *******************/
|
|
@@ -310,11 +318,8 @@ export const Button = <Tag extends React.ElementType = "button">({
|
|
|
310
318
|
{icon && (
|
|
311
319
|
<Icon
|
|
312
320
|
className={"fabric-buttonIcon"}
|
|
313
|
-
icon={icon}
|
|
314
|
-
bg={iconBg}
|
|
315
|
-
color={iconColor}
|
|
316
|
-
rtlFlip={rtlFlip}
|
|
317
321
|
data-align={iconAlign}
|
|
322
|
+
{...getIconProps(icon)}
|
|
318
323
|
/>
|
|
319
324
|
)}
|
|
320
325
|
{isValidElement(children) && (
|
|
@@ -323,7 +328,7 @@ export const Button = <Tag extends React.ElementType = "button">({
|
|
|
323
328
|
{isString(children) && (
|
|
324
329
|
<label
|
|
325
330
|
className={classNames("fabric-buttonLabel", "truncate")}
|
|
326
|
-
data-colored-icon={
|
|
331
|
+
data-colored-icon={isObject(icon) && "bg" in icon}
|
|
327
332
|
>
|
|
328
333
|
{children}
|
|
329
334
|
</label>
|
|
@@ -24,10 +24,10 @@
|
|
|
24
24
|
import classNames from "classnames";
|
|
25
25
|
import {
|
|
26
26
|
Children,
|
|
27
|
-
type DragEvent,
|
|
28
|
-
type MouseEventHandler,
|
|
29
27
|
useCallback,
|
|
30
28
|
useMemo,
|
|
29
|
+
type DragEvent,
|
|
30
|
+
type MouseEventHandler,
|
|
31
31
|
} from "react";
|
|
32
32
|
import { ErrorBoundary } from "../../core/boundary/ErrorBoundary";
|
|
33
33
|
import { type ContentProps } from "../../core/content/Content";
|
|
@@ -37,6 +37,7 @@ import {
|
|
|
37
37
|
type HeadFootProps,
|
|
38
38
|
} from "../../core/headfoot/HeadFoot";
|
|
39
39
|
import {
|
|
40
|
+
PolymorphicProps,
|
|
40
41
|
type AriaProps,
|
|
41
42
|
type ChildrenProp,
|
|
42
43
|
type CssProp,
|
|
@@ -45,7 +46,7 @@ import {
|
|
|
45
46
|
} from "../../types";
|
|
46
47
|
import { nodeCheck } from "../../utils";
|
|
47
48
|
|
|
48
|
-
|
|
49
|
+
interface BaseProps
|
|
49
50
|
extends CssProp,
|
|
50
51
|
AriaProps,
|
|
51
52
|
TestProps,
|
|
@@ -93,6 +94,9 @@ export interface CardProps
|
|
|
93
94
|
dragData?: KeyValue;
|
|
94
95
|
}
|
|
95
96
|
|
|
97
|
+
export type CardProps<Tag extends React.ElementType = "div"> = BaseProps &
|
|
98
|
+
PolymorphicProps<Tag>;
|
|
99
|
+
|
|
96
100
|
/**
|
|
97
101
|
* A component that displays a card with a header, body, and footer. It can be used to display content in a structured format.
|
|
98
102
|
* It supports various features such as click handling, drag-and-drop functionality, and customizable styles.
|
|
@@ -127,7 +131,7 @@ export interface CardProps
|
|
|
127
131
|
*
|
|
128
132
|
* @see {@link https://adarshpastakia.github.io/react-fabric/?path=/docs/core-components-card--docs} for more details.
|
|
129
133
|
*/
|
|
130
|
-
export const Card = ({
|
|
134
|
+
export const Card = <Tag extends React.ElementType = "div">({
|
|
131
135
|
children,
|
|
132
136
|
className,
|
|
133
137
|
bodyClassName,
|
|
@@ -140,8 +144,9 @@ export const Card = ({
|
|
|
140
144
|
dragKey,
|
|
141
145
|
dragData,
|
|
142
146
|
ref,
|
|
147
|
+
as,
|
|
143
148
|
...aria
|
|
144
|
-
}: CardProps) => {
|
|
149
|
+
}: CardProps<Tag>) => {
|
|
145
150
|
const [header, body, footer] = useMemo(() => {
|
|
146
151
|
return Children.toArray(children as AnyObject).reduce<AnyObject[]>(
|
|
147
152
|
(ret, node) => {
|
|
@@ -164,6 +169,7 @@ export const Card = ({
|
|
|
164
169
|
[onDragStart, dragKey, dragData],
|
|
165
170
|
);
|
|
166
171
|
|
|
172
|
+
const E = as ?? "div";
|
|
167
173
|
return (
|
|
168
174
|
<div
|
|
169
175
|
className={classNames(
|
|
@@ -171,7 +177,7 @@ export const Card = ({
|
|
|
171
177
|
"rounded-capped relative grid",
|
|
172
178
|
flex && "flex-1",
|
|
173
179
|
selected && selectedRibbon && "selected",
|
|
174
|
-
selected && "outline-
|
|
180
|
+
selected && "outline-1 outline-accent-500 outline-offset-2",
|
|
175
181
|
)}
|
|
176
182
|
>
|
|
177
183
|
<ErrorBoundary>
|
|
@@ -179,22 +185,30 @@ export const Card = ({
|
|
|
179
185
|
className={classNames(
|
|
180
186
|
"fabric-card",
|
|
181
187
|
className,
|
|
182
|
-
"rounded-capped flex flex-col flex-nowrap overflow-hidden",
|
|
188
|
+
"rounded-capped relative flex flex-col flex-nowrap overflow-hidden",
|
|
189
|
+
"href" in aria && "clickable",
|
|
190
|
+
"to" in aria && "clickable",
|
|
183
191
|
onClick && "clickable",
|
|
184
192
|
)}
|
|
185
193
|
draggable={draggable}
|
|
186
194
|
onDragStart={!draggable ? undefined : handleDragStart}
|
|
187
195
|
ref={ref}
|
|
188
|
-
{...aria}
|
|
189
196
|
>
|
|
190
197
|
{header}
|
|
191
|
-
<
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
+
<E role="none" onClick={onClick} {...aria} className="contents">
|
|
199
|
+
{body && (
|
|
200
|
+
<object
|
|
201
|
+
type="none"
|
|
202
|
+
className={classNames(
|
|
203
|
+
"fabric-cardBody",
|
|
204
|
+
bodyClassName,
|
|
205
|
+
"flex-1",
|
|
206
|
+
)}
|
|
207
|
+
>
|
|
208
|
+
{body}
|
|
209
|
+
</object>
|
|
210
|
+
)}
|
|
211
|
+
</E>
|
|
198
212
|
{footer}
|
|
199
213
|
</div>
|
|
200
214
|
</ErrorBoundary>
|
|
@@ -29,7 +29,6 @@ import {
|
|
|
29
29
|
type ChildProp,
|
|
30
30
|
type ColorType,
|
|
31
31
|
type CssProp,
|
|
32
|
-
type IconProps,
|
|
33
32
|
type PaletteType,
|
|
34
33
|
type PolymorphicProps,
|
|
35
34
|
type RefProp,
|
|
@@ -37,12 +36,11 @@ import {
|
|
|
37
36
|
type TestProps,
|
|
38
37
|
} from "../../types";
|
|
39
38
|
import { getColor } from "../../utils";
|
|
40
|
-
import { Icon } from "../icon/Icon";
|
|
39
|
+
import { getIconProps, Icon, IconProps } from "../icon/Icon";
|
|
41
40
|
|
|
42
41
|
export interface ChipProps
|
|
43
42
|
extends CssProp,
|
|
44
43
|
AriaProps,
|
|
45
|
-
IconProps,
|
|
46
44
|
TestProps,
|
|
47
45
|
ChildProp<string | ReactElement>,
|
|
48
46
|
RefProp<HTMLDivElement> {
|
|
@@ -62,10 +60,18 @@ export interface ChipProps
|
|
|
62
60
|
* full rounded edges
|
|
63
61
|
*/
|
|
64
62
|
rounded?: boolean;
|
|
63
|
+
/**
|
|
64
|
+
* icon path or props
|
|
65
|
+
*/
|
|
66
|
+
icon?: IconProps;
|
|
65
67
|
/**
|
|
66
68
|
* disabled state
|
|
67
69
|
*/
|
|
68
70
|
disabled?: boolean;
|
|
71
|
+
/**
|
|
72
|
+
* prevent click default, useful when component is within a `a` link
|
|
73
|
+
*/
|
|
74
|
+
preventDefault?: boolean;
|
|
69
75
|
/**
|
|
70
76
|
* prevent click propagation
|
|
71
77
|
*/
|
|
@@ -120,14 +126,12 @@ export const Chip = <Tag extends React.ElementType = "div">({
|
|
|
120
126
|
color,
|
|
121
127
|
variant,
|
|
122
128
|
icon,
|
|
123
|
-
iconBg,
|
|
124
|
-
iconColor,
|
|
125
|
-
rtlFlip,
|
|
126
129
|
disabled,
|
|
127
130
|
onClick,
|
|
128
131
|
onIconClick,
|
|
129
132
|
onRemove,
|
|
130
133
|
rounded,
|
|
134
|
+
preventDefault,
|
|
131
135
|
stopPropagation,
|
|
132
136
|
as,
|
|
133
137
|
...aria
|
|
@@ -153,10 +157,11 @@ export const Chip = <Tag extends React.ElementType = "div">({
|
|
|
153
157
|
|
|
154
158
|
const clickHandler = useCallback(
|
|
155
159
|
(e: React.MouseEvent) => {
|
|
156
|
-
|
|
160
|
+
preventDefault && e.preventDefault();
|
|
161
|
+
stopPropagation && e.stopPropagation();
|
|
157
162
|
onClick?.(e);
|
|
158
163
|
},
|
|
159
|
-
[onClick, stopPropagation],
|
|
164
|
+
[onClick, preventDefault, stopPropagation],
|
|
160
165
|
);
|
|
161
166
|
|
|
162
167
|
const removeHandler = useCallback(
|
|
@@ -191,17 +196,14 @@ export const Chip = <Tag extends React.ElementType = "div">({
|
|
|
191
196
|
<Icon
|
|
192
197
|
data-ref="chipIcon"
|
|
193
198
|
className={classNames("fabric-chipIcon", "m-1 flex-content")}
|
|
194
|
-
icon={icon}
|
|
195
|
-
bg={iconBg}
|
|
196
199
|
onClick={onIconClick}
|
|
197
|
-
|
|
198
|
-
rtlFlip={rtlFlip}
|
|
200
|
+
{...getIconProps(icon)}
|
|
199
201
|
/>
|
|
200
202
|
)}
|
|
201
203
|
{children && (
|
|
202
204
|
<label
|
|
203
205
|
data-ref="chipLabel"
|
|
204
|
-
className={classNames("fabric-chipLabel", "truncate")}
|
|
206
|
+
className={classNames("fabric-chipLabel", "truncate flex-1")}
|
|
205
207
|
>
|
|
206
208
|
{children}
|
|
207
209
|
</label>
|
|
@@ -23,23 +23,27 @@
|
|
|
23
23
|
|
|
24
24
|
import { isString, isSvgPath } from "@react-fabric/utilities";
|
|
25
25
|
import classNames from "classnames";
|
|
26
|
-
import { useMemo } from "react";
|
|
26
|
+
import { isValidElement, useEffect, useMemo, useState } from "react";
|
|
27
27
|
import {
|
|
28
|
-
type PaletteType,
|
|
29
28
|
type AriaProps,
|
|
30
29
|
type ColorType,
|
|
31
30
|
type CssProp,
|
|
31
|
+
type PaletteType,
|
|
32
32
|
type RefProp,
|
|
33
33
|
type SizeType,
|
|
34
34
|
type TestProps,
|
|
35
35
|
} from "../../types";
|
|
36
36
|
import { getColor } from "../../utils";
|
|
37
37
|
|
|
38
|
-
export interface
|
|
38
|
+
export interface Props extends CssProp, AriaProps, RefProp, TestProps {
|
|
39
39
|
/**
|
|
40
40
|
* svg path / webfont className / 1-4 letter text
|
|
41
41
|
*/
|
|
42
|
-
icon: string;
|
|
42
|
+
icon: string | JSX.Element;
|
|
43
|
+
/**
|
|
44
|
+
* icon image source URL, if failed to load then shows icon
|
|
45
|
+
*/
|
|
46
|
+
iconSrc?: string;
|
|
43
47
|
/**
|
|
44
48
|
* background color (CSS color / tailwind color)
|
|
45
49
|
*/
|
|
@@ -75,6 +79,28 @@ export interface IconProps extends CssProp, AriaProps, RefProp, TestProps {
|
|
|
75
79
|
onClick?: React.MouseEventHandler;
|
|
76
80
|
}
|
|
77
81
|
|
|
82
|
+
export type IconProps =
|
|
83
|
+
| string
|
|
84
|
+
| Pick<
|
|
85
|
+
Props,
|
|
86
|
+
| "icon"
|
|
87
|
+
| "iconSrc"
|
|
88
|
+
| "bg"
|
|
89
|
+
| "color"
|
|
90
|
+
| "size"
|
|
91
|
+
| "rtlFlip"
|
|
92
|
+
| "viewBox"
|
|
93
|
+
| "rounded"
|
|
94
|
+
| "animate"
|
|
95
|
+
>;
|
|
96
|
+
|
|
97
|
+
export const getIconProps = (props: IconProps): Props => {
|
|
98
|
+
if (typeof props === "string") {
|
|
99
|
+
return { icon: props };
|
|
100
|
+
}
|
|
101
|
+
return props;
|
|
102
|
+
};
|
|
103
|
+
|
|
78
104
|
const SvgTextSize = ["", ".875em", ".525em", ".35em", ".25em"];
|
|
79
105
|
const SizeMap: KeyValue<string> = {
|
|
80
106
|
xs: "0.625rem",
|
|
@@ -116,6 +142,7 @@ const SizeMap: KeyValue<string> = {
|
|
|
116
142
|
export const Icon = ({
|
|
117
143
|
ref,
|
|
118
144
|
icon,
|
|
145
|
+
iconSrc,
|
|
119
146
|
bg,
|
|
120
147
|
color,
|
|
121
148
|
size = "",
|
|
@@ -127,7 +154,13 @@ export const Icon = ({
|
|
|
127
154
|
className,
|
|
128
155
|
onClick,
|
|
129
156
|
...rest
|
|
130
|
-
}:
|
|
157
|
+
}: Props) => {
|
|
158
|
+
const [imageFailed, setImageFailed] = useState(false);
|
|
159
|
+
|
|
160
|
+
useEffect(() => {
|
|
161
|
+
setImageFailed(false);
|
|
162
|
+
}, [iconSrc]);
|
|
163
|
+
|
|
131
164
|
/** ***************** style map *******************/
|
|
132
165
|
const styles = useMemo(() => {
|
|
133
166
|
const s: KeyValue = {};
|
|
@@ -153,6 +186,7 @@ export const Icon = ({
|
|
|
153
186
|
|
|
154
187
|
/** ***************** render icon *******************/
|
|
155
188
|
const iconEl = useMemo(() => {
|
|
189
|
+
if (isValidElement(icon)) return icon;
|
|
156
190
|
if (!isString(icon)) {
|
|
157
191
|
throw Error("Invalid icon expected string");
|
|
158
192
|
}
|
|
@@ -193,13 +227,20 @@ export const Icon = ({
|
|
|
193
227
|
!!onClick && disabled && "opacity-30 pointer-events-none",
|
|
194
228
|
className,
|
|
195
229
|
)}
|
|
196
|
-
onClick={
|
|
230
|
+
onClick={(e) => {
|
|
231
|
+
onClick && e.stopPropagation();
|
|
232
|
+
onClick && e.preventDefault();
|
|
233
|
+
onClick?.(e);
|
|
234
|
+
}}
|
|
197
235
|
data-flip={rtlFlip}
|
|
198
236
|
style={styles}
|
|
199
237
|
data-clickable={!!onClick}
|
|
200
238
|
data-inner-clickable={!!onClick}
|
|
201
239
|
>
|
|
202
|
-
{
|
|
240
|
+
{iconSrc && !imageFailed && (
|
|
241
|
+
<img src={iconSrc} onError={() => setImageFailed(true)} />
|
|
242
|
+
)}
|
|
243
|
+
{(!iconSrc || imageFailed) && iconEl}
|
|
203
244
|
</dfn>
|
|
204
245
|
);
|
|
205
246
|
};
|
package/src/components/index.ts
CHANGED
|
@@ -47,7 +47,7 @@ export { Divider } from "./divider/Divider";
|
|
|
47
47
|
export { Dropdown, DropdownDismiss } from "./dropdown/Dropdown";
|
|
48
48
|
export { DropdownTool } from "./dropdown/DropdownTool";
|
|
49
49
|
export { EmptyContent } from "./empty/EmptyContent";
|
|
50
|
-
export { Icon } from "./icon/Icon";
|
|
50
|
+
export { Icon, getIconProps } from "./icon/Icon";
|
|
51
51
|
export { Image, Video } from "./media/Media";
|
|
52
52
|
export { ContextMenu } from "./menu/ContextMenu";
|
|
53
53
|
export { Menu } from "./menu/Menu";
|
|
@@ -30,8 +30,9 @@ import { HotKeyLabel } from "../../hotkeys/HotKeyLabel";
|
|
|
30
30
|
import { Tooltip } from "../../overlays";
|
|
31
31
|
import { type PolymorphicProps } from "../../types";
|
|
32
32
|
import { Badge, getBadgeProps } from "../badge/Badge";
|
|
33
|
-
import { Icon } from "../icon/Icon";
|
|
33
|
+
import { getIconProps, Icon } from "../icon/Icon";
|
|
34
34
|
import { type MenuItemProps } from "./types";
|
|
35
|
+
import { get } from "http";
|
|
35
36
|
|
|
36
37
|
/**
|
|
37
38
|
* A menu item component that can be used in a dropdown or menu.
|
|
@@ -60,10 +61,7 @@ export const MenuItem = <Tag extends React.ElementType = "button">({
|
|
|
60
61
|
color = "primary",
|
|
61
62
|
className,
|
|
62
63
|
icon,
|
|
63
|
-
iconBg,
|
|
64
|
-
iconColor,
|
|
65
64
|
appendLabel,
|
|
66
|
-
rtlFlip,
|
|
67
65
|
altIcon,
|
|
68
66
|
id,
|
|
69
67
|
active,
|
|
@@ -98,13 +96,10 @@ export const MenuItem = <Tag extends React.ElementType = "button">({
|
|
|
98
96
|
return (
|
|
99
97
|
<Icon
|
|
100
98
|
className={classNames("fabric-menuIcon", minimal && "minimal")}
|
|
101
|
-
|
|
102
|
-
bg={iconBg}
|
|
103
|
-
color={iconColor}
|
|
104
|
-
rtlFlip={rtlFlip}
|
|
99
|
+
{...getIconProps(path ?? "")}
|
|
105
100
|
/>
|
|
106
101
|
);
|
|
107
|
-
}, [icon,
|
|
102
|
+
}, [icon, minimal, label]);
|
|
108
103
|
|
|
109
104
|
const Wrapper = useCallback(
|
|
110
105
|
({ children, ...rest }: AnyObject) => {
|
|
@@ -29,15 +29,11 @@ import {
|
|
|
29
29
|
type ChildrenProp,
|
|
30
30
|
type ColorState,
|
|
31
31
|
type CssProp,
|
|
32
|
-
type IconProps,
|
|
33
32
|
type TestProps,
|
|
34
33
|
} from "../../types";
|
|
34
|
+
import { IconProps } from "../icon/Icon";
|
|
35
35
|
|
|
36
|
-
export interface MenuItemProps
|
|
37
|
-
extends CssProp,
|
|
38
|
-
AriaProps,
|
|
39
|
-
TestProps,
|
|
40
|
-
IconProps {
|
|
36
|
+
export interface MenuItemProps extends CssProp, AriaProps, TestProps {
|
|
41
37
|
/**
|
|
42
38
|
* menu id passed via menu.onClick
|
|
43
39
|
*/
|
|
@@ -54,6 +50,10 @@ export interface MenuItemProps
|
|
|
54
50
|
* menu color
|
|
55
51
|
*/
|
|
56
52
|
color?: ColorState;
|
|
53
|
+
/**
|
|
54
|
+
* icon path or props
|
|
55
|
+
*/
|
|
56
|
+
icon?: IconProps;
|
|
57
57
|
/**
|
|
58
58
|
* item active
|
|
59
59
|
*/
|