no-frills-ui 0.0.14-alpha.3 → 0.0.14-alpha.5
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/dist/index.js +1622 -539
- package/dist/index.js.map +1 -1
- package/lib-esm/components/Accordion/AccordionStep.d.ts.map +1 -1
- package/lib-esm/components/Accordion/AccordionStep.js +27 -38
- package/lib-esm/components/Accordion/AccordionStep.js.map +1 -1
- package/lib-esm/components/Badge/Badge.js +7 -7
- package/lib-esm/components/Badge/Badge.js.map +1 -1
- package/lib-esm/components/Button/ActionButton.d.ts.map +1 -1
- package/lib-esm/components/Button/ActionButton.js +12 -11
- package/lib-esm/components/Button/ActionButton.js.map +1 -1
- package/lib-esm/components/Button/Button.d.ts +2 -2
- package/lib-esm/components/Button/Button.d.ts.map +1 -1
- package/lib-esm/components/Button/Button.js +19 -14
- package/lib-esm/components/Button/Button.js.map +1 -1
- package/lib-esm/components/Button/IconButton.d.ts.map +1 -1
- package/lib-esm/components/Button/IconButton.js +15 -14
- package/lib-esm/components/Button/IconButton.js.map +1 -1
- package/lib-esm/components/Button/LinkButton.d.ts.map +1 -1
- package/lib-esm/components/Button/LinkButton.js +7 -6
- package/lib-esm/components/Button/LinkButton.js.map +1 -1
- package/lib-esm/components/Button/RaisedButton.d.ts.map +1 -1
- package/lib-esm/components/Button/RaisedButton.js +15 -14
- package/lib-esm/components/Button/RaisedButton.js.map +1 -1
- package/lib-esm/components/Card/Card.d.ts.map +1 -1
- package/lib-esm/components/Card/Card.js +4 -4
- package/lib-esm/components/Card/Card.js.map +1 -1
- package/lib-esm/components/Chip/Chip.d.ts +5 -2
- package/lib-esm/components/Chip/Chip.d.ts.map +1 -1
- package/lib-esm/components/Chip/Chip.js +20 -14
- package/lib-esm/components/Chip/Chip.js.map +1 -1
- package/lib-esm/components/ChipInput/ChipInput.d.ts +9 -0
- package/lib-esm/components/ChipInput/ChipInput.d.ts.map +1 -1
- package/lib-esm/components/ChipInput/ChipInput.js +63 -24
- package/lib-esm/components/ChipInput/ChipInput.js.map +1 -1
- package/lib-esm/components/Dialog/AlertDialog.d.ts.map +1 -1
- package/lib-esm/components/Dialog/AlertDialog.js +4 -1
- package/lib-esm/components/Dialog/AlertDialog.js.map +1 -1
- package/lib-esm/components/Dialog/Dialog.d.ts +32 -2
- package/lib-esm/components/Dialog/Dialog.d.ts.map +1 -1
- package/lib-esm/components/Dialog/Dialog.js +84 -1
- package/lib-esm/components/Dialog/Dialog.js.map +1 -1
- package/lib-esm/components/DragAndDrop/DragAndDrop.d.ts +24 -0
- package/lib-esm/components/DragAndDrop/DragAndDrop.d.ts.map +1 -1
- package/lib-esm/components/DragAndDrop/DragAndDrop.js +85 -3
- package/lib-esm/components/DragAndDrop/DragAndDrop.js.map +1 -1
- package/lib-esm/components/DragAndDrop/DragItem.d.ts +4 -0
- package/lib-esm/components/DragAndDrop/DragItem.d.ts.map +1 -1
- package/lib-esm/components/DragAndDrop/DragItem.js +92 -12
- package/lib-esm/components/DragAndDrop/DragItem.js.map +1 -1
- package/lib-esm/components/DragAndDrop/types.d.ts +19 -0
- package/lib-esm/components/DragAndDrop/types.d.ts.map +1 -1
- package/lib-esm/components/DragAndDrop/types.js.map +1 -1
- package/lib-esm/components/Drawer/Drawer.d.ts +76 -1
- package/lib-esm/components/Drawer/Drawer.d.ts.map +1 -1
- package/lib-esm/components/Drawer/Drawer.js +158 -24
- package/lib-esm/components/Drawer/Drawer.js.map +1 -1
- package/lib-esm/components/Groups/Group.d.ts.map +1 -1
- package/lib-esm/components/Groups/Group.js +10 -8
- package/lib-esm/components/Groups/Group.js.map +1 -1
- package/lib-esm/components/Groups/GroupLabel.d.ts.map +1 -1
- package/lib-esm/components/Groups/GroupLabel.js +3 -3
- package/lib-esm/components/Groups/GroupLabel.js.map +1 -1
- package/lib-esm/components/Input/Checkbox.d.ts.map +1 -1
- package/lib-esm/components/Input/Checkbox.js +63 -58
- package/lib-esm/components/Input/Checkbox.js.map +1 -1
- package/lib-esm/components/Input/Dropdown.d.ts +8 -0
- package/lib-esm/components/Input/Dropdown.d.ts.map +1 -1
- package/lib-esm/components/Input/Dropdown.js +54 -31
- package/lib-esm/components/Input/Dropdown.js.map +1 -1
- package/lib-esm/components/Input/Input.d.ts.map +1 -1
- package/lib-esm/components/Input/Input.js +27 -22
- package/lib-esm/components/Input/Input.js.map +1 -1
- package/lib-esm/components/Input/Radio.d.ts.map +1 -1
- package/lib-esm/components/Input/Radio.js +58 -42
- package/lib-esm/components/Input/Radio.js.map +1 -1
- package/lib-esm/components/Input/RadioButton.d.ts.map +1 -1
- package/lib-esm/components/Input/RadioButton.js +12 -12
- package/lib-esm/components/Input/RadioButton.js.map +1 -1
- package/lib-esm/components/Input/Select.d.ts.map +1 -1
- package/lib-esm/components/Input/Select.js +27 -22
- package/lib-esm/components/Input/Select.js.map +1 -1
- package/lib-esm/components/Input/TextArea.d.ts.map +1 -1
- package/lib-esm/components/Input/TextArea.js +27 -22
- package/lib-esm/components/Input/TextArea.js.map +1 -1
- package/lib-esm/components/Input/Toggle.d.ts.map +1 -1
- package/lib-esm/components/Input/Toggle.js +17 -14
- package/lib-esm/components/Input/Toggle.js.map +1 -1
- package/lib-esm/components/Menu/Menu.d.ts +13 -1
- package/lib-esm/components/Menu/Menu.d.ts.map +1 -1
- package/lib-esm/components/Menu/Menu.js +98 -3
- package/lib-esm/components/Menu/Menu.js.map +1 -1
- package/lib-esm/components/Menu/MenuItem.d.ts +6 -3
- package/lib-esm/components/Menu/MenuItem.d.ts.map +1 -1
- package/lib-esm/components/Menu/MenuItem.js +10 -10
- package/lib-esm/components/Menu/MenuItem.js.map +1 -1
- package/lib-esm/components/Modal/Modal.d.ts +70 -1
- package/lib-esm/components/Modal/Modal.d.ts.map +1 -1
- package/lib-esm/components/Modal/Modal.js +145 -11
- package/lib-esm/components/Modal/Modal.js.map +1 -1
- package/lib-esm/components/Notification/Notification.d.ts +11 -7
- package/lib-esm/components/Notification/Notification.d.ts.map +1 -1
- package/lib-esm/components/Notification/Notification.js +54 -25
- package/lib-esm/components/Notification/Notification.js.map +1 -1
- package/lib-esm/components/Notification/NotificationManager.d.ts +11 -1
- package/lib-esm/components/Notification/NotificationManager.d.ts.map +1 -1
- package/lib-esm/components/Notification/NotificationManager.js +43 -8
- package/lib-esm/components/Notification/NotificationManager.js.map +1 -1
- package/lib-esm/components/Notification/style.d.ts +4 -0
- package/lib-esm/components/Notification/style.d.ts.map +1 -1
- package/lib-esm/components/Notification/style.js +30 -15
- package/lib-esm/components/Notification/style.js.map +1 -1
- package/lib-esm/components/Notification/types.d.ts +2 -0
- package/lib-esm/components/Notification/types.d.ts.map +1 -1
- package/lib-esm/components/Notification/types.js.map +1 -1
- package/lib-esm/components/Popover/Popover.d.ts.map +1 -1
- package/lib-esm/components/Popover/Popover.js +17 -2
- package/lib-esm/components/Popover/Popover.js.map +1 -1
- package/lib-esm/components/Spinner/Spinner.d.ts +3 -0
- package/lib-esm/components/Spinner/Spinner.d.ts.map +1 -1
- package/lib-esm/components/Spinner/Spinner.js +19 -4
- package/lib-esm/components/Spinner/Spinner.js.map +1 -1
- package/lib-esm/components/Stepper/Stepper.d.ts.map +1 -1
- package/lib-esm/components/Stepper/Stepper.js +29 -10
- package/lib-esm/components/Stepper/Stepper.js.map +1 -1
- package/lib-esm/components/Tabs/Tabs.d.ts.map +1 -1
- package/lib-esm/components/Tabs/Tabs.js +45 -12
- package/lib-esm/components/Tabs/Tabs.js.map +1 -1
- package/lib-esm/components/Toast/Toast.d.ts +25 -4
- package/lib-esm/components/Toast/Toast.d.ts.map +1 -1
- package/lib-esm/components/Toast/Toast.js +114 -18
- package/lib-esm/components/Toast/Toast.js.map +1 -1
- package/lib-esm/components/Tooltip/Tooltip.d.ts.map +1 -1
- package/lib-esm/components/Tooltip/Tooltip.js +16 -5
- package/lib-esm/components/Tooltip/Tooltip.js.map +1 -1
- package/lib-esm/shared/LayerManager.d.ts.map +1 -1
- package/lib-esm/shared/LayerManager.js +63 -1
- package/lib-esm/shared/LayerManager.js.map +1 -1
- package/lib-esm/shared/constants.d.ts +58 -27
- package/lib-esm/shared/constants.d.ts.map +1 -1
- package/lib-esm/shared/constants.js +88 -25
- package/lib-esm/shared/constants.js.map +1 -1
- package/lib-esm/shared/styles.d.ts +1 -1
- package/lib-esm/shared/styles.d.ts.map +1 -1
- package/lib-esm/shared/styles.js +5 -3
- package/lib-esm/shared/styles.js.map +1 -1
- package/package.json +1 -1
|
@@ -6,8 +6,27 @@ export declare const DragContext: import("react").Context<{
|
|
|
6
6
|
startIndex: number;
|
|
7
7
|
setStartIndex: (value: number) => void;
|
|
8
8
|
drop: (index: number) => void;
|
|
9
|
+
onDrop: (start: number, end: number) => void;
|
|
10
|
+
cancel: () => void;
|
|
11
|
+
startGrab: (index: number) => void;
|
|
9
12
|
isDragging: boolean;
|
|
10
13
|
setIsDragging: (value: boolean) => void;
|
|
11
14
|
setDragOver: (value: number) => void;
|
|
15
|
+
i18n: {
|
|
16
|
+
itemAriaLabelTemplate: string;
|
|
17
|
+
dragHandleAriaLabel: string;
|
|
18
|
+
grabbedAnnouncementTemplate: string;
|
|
19
|
+
movedAnnouncementTemplate: string;
|
|
20
|
+
droppedAnnouncementTemplate: string;
|
|
21
|
+
cancelledAnnouncementTemplate: string;
|
|
22
|
+
replacePlaceholders: (template: string, data: {
|
|
23
|
+
position?: number;
|
|
24
|
+
grabKey?: string;
|
|
25
|
+
dropKey?: string;
|
|
26
|
+
altDropKey?: string;
|
|
27
|
+
cancelKey?: string;
|
|
28
|
+
moveKeys?: string;
|
|
29
|
+
}) => string;
|
|
30
|
+
};
|
|
12
31
|
}>;
|
|
13
32
|
//# sourceMappingURL=types.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/components/DragAndDrop/types.ts"],"names":[],"mappings":"AAEA,oBAAY,WAAW;IACnB,UAAU,eAAe;IACzB,QAAQ,aAAa;CACxB;AAED,eAAO,MAAM,WAAW;gBACR,MAAM;mBACH,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI;UAChC,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI;
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/components/DragAndDrop/types.ts"],"names":[],"mappings":"AAEA,oBAAY,WAAW;IACnB,UAAU,eAAe;IACzB,QAAQ,aAAa;CACxB;AAED,eAAO,MAAM,WAAW;gBACR,MAAM;mBACH,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI;UAChC,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI;YACrB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,KAAK,IAAI;YACpC,MAAM,IAAI;eACP,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI;gBACtB,OAAO;mBACJ,CAAC,KAAK,EAAE,OAAO,KAAK,IAAI;iBAC1B,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI;UAC9B;QACF,qBAAqB,EAAE,MAAM,CAAC;QAC9B,mBAAmB,EAAE,MAAM,CAAC;QAC5B,2BAA2B,EAAE,MAAM,CAAC;QACpC,yBAAyB,EAAE,MAAM,CAAC;QAClC,2BAA2B,EAAE,MAAM,CAAC;QACpC,6BAA6B,EAAE,MAAM,CAAC;QACtC,mBAAmB,EAAE,CACjB,QAAQ,EAAE,MAAM,EAChB,IAAI,EAAE;YACF,QAAQ,CAAC,EAAE,MAAM,CAAC;YAClB,OAAO,CAAC,EAAE,MAAM,CAAC;YACjB,OAAO,CAAC,EAAE,MAAM,CAAC;YACjB,UAAU,CAAC,EAAE,MAAM,CAAC;YACpB,SAAS,CAAC,EAAE,MAAM,CAAC;YACnB,QAAQ,CAAC,EAAE,MAAM,CAAC;SACrB,KACA,MAAM,CAAC;KACf;EACG,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../../src/components/DragAndDrop/types.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,OAAO,CAAC;AAEtC,MAAM,CAAN,IAAY,WAGX;AAHD,WAAY,WAAW;IACnB,wCAAyB,CAAA;IACzB,oCAAqB,CAAA;AACzB,CAAC,EAHW,WAAW,KAAX,WAAW,QAGtB;AAED,MAAM,CAAC,MAAM,WAAW,GAAG,aAAa,
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../../src/components/DragAndDrop/types.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,MAAM,OAAO,CAAC;AAEtC,MAAM,CAAN,IAAY,WAGX;AAHD,WAAY,WAAW;IACnB,wCAAyB,CAAA;IACzB,oCAAqB,CAAA;AACzB,CAAC,EAHW,WAAW,KAAX,WAAW,QAGtB;AAED,MAAM,CAAC,MAAM,WAAW,GAAG,aAAa,CA6BrC,IAAI,CAAC,CAAC","sourcesContent":["import { createContext } from 'react';\n\nexport enum ORIENTATION {\n HORIZONTAL = 'horizontal',\n VERTICAL = 'vertical',\n}\n\nexport const DragContext = createContext<{\n startIndex: number;\n setStartIndex: (value: number) => void;\n drop: (index: number) => void;\n onDrop: (start: number, end: number) => void;\n cancel: () => void;\n startGrab: (index: number) => void;\n isDragging: boolean;\n setIsDragging: (value: boolean) => void;\n setDragOver: (value: number) => void;\n i18n: {\n itemAriaLabelTemplate: string;\n dragHandleAriaLabel: string;\n grabbedAnnouncementTemplate: string;\n movedAnnouncementTemplate: string;\n droppedAnnouncementTemplate: string;\n cancelledAnnouncementTemplate: string;\n replacePlaceholders: (\n template: string,\n data: {\n position?: number;\n grabKey?: string;\n dropKey?: string;\n altDropKey?: string;\n cancelKey?: string;\n moveKeys?: string;\n },\n ) => string;\n };\n}>(null);\n"]}
|
|
@@ -6,10 +6,38 @@ export declare enum DRAWER_POSITION {
|
|
|
6
6
|
RIGHT = "RIGHT",
|
|
7
7
|
BOTTOM = "BOTTOM"
|
|
8
8
|
}
|
|
9
|
-
|
|
9
|
+
declare const drawerPropTypes: {
|
|
10
|
+
/** Opens the drawer */
|
|
11
|
+
open: PropTypes.Validator<boolean>;
|
|
12
|
+
/** position of the drawer */
|
|
13
|
+
position: PropTypes.Requireable<DRAWER_POSITION>;
|
|
14
|
+
/** size of the drawer */
|
|
15
|
+
size: PropTypes.Requireable<string>;
|
|
16
|
+
/** Shows an overlay behind the drawer. */
|
|
17
|
+
overlay: PropTypes.Requireable<boolean>;
|
|
18
|
+
/** Closes the drawer on esc */
|
|
19
|
+
closeOnEsc: PropTypes.Requireable<boolean>;
|
|
20
|
+
/** Closes the drawer on overlay click */
|
|
21
|
+
closeOnOverlayClick: PropTypes.Requireable<boolean>;
|
|
22
|
+
/** Call back function called when the drawer closes. */
|
|
23
|
+
onClose: PropTypes.Requireable<(...args: any[]) => any>;
|
|
24
|
+
};
|
|
25
|
+
type DrawerProps = PropTypes.InferProps<typeof drawerPropTypes>;
|
|
10
26
|
interface DrawerState {
|
|
11
27
|
open: boolean;
|
|
12
28
|
}
|
|
29
|
+
/**
|
|
30
|
+
* Drawer component
|
|
31
|
+
*
|
|
32
|
+
* A panel that slides in from the edge of the screen.
|
|
33
|
+
* It sits on top of the application content and is often used for navigation or details.
|
|
34
|
+
*
|
|
35
|
+
* Accessibility:
|
|
36
|
+
* - Implements ARIA `role="dialog"` and `aria-modal="true"`.
|
|
37
|
+
* - Traps focus effectively within the drawer while open.
|
|
38
|
+
* - Restores focus to the triggering element upon closure.
|
|
39
|
+
* - Supports closing via ESC key and overlay click.
|
|
40
|
+
*/
|
|
13
41
|
export default class Drawer extends React.Component<React.PropsWithChildren<DrawerProps>, DrawerState> {
|
|
14
42
|
state: {
|
|
15
43
|
open: boolean;
|
|
@@ -36,13 +64,60 @@ export default class Drawer extends React.Component<React.PropsWithChildren<Draw
|
|
|
36
64
|
closeOnEsc: boolean;
|
|
37
65
|
closeOnOverlayClick: boolean;
|
|
38
66
|
};
|
|
67
|
+
/**
|
|
68
|
+
* Syncs state with props.
|
|
69
|
+
*/
|
|
39
70
|
static getDerivedStateFromProps(props: DrawerProps): {
|
|
40
71
|
open: boolean;
|
|
41
72
|
};
|
|
42
73
|
private layer;
|
|
43
74
|
private closeCallback;
|
|
75
|
+
/**
|
|
76
|
+
* Internal close handler.
|
|
77
|
+
* Restores focus and calls the external onClose callback.
|
|
78
|
+
*/
|
|
44
79
|
private onClose;
|
|
80
|
+
private lastFocusedElement;
|
|
81
|
+
private drawerRef;
|
|
82
|
+
/**
|
|
83
|
+
* Retrieves all focusable elements within the drawer.
|
|
84
|
+
*/
|
|
85
|
+
private getFocusableElements;
|
|
86
|
+
/**
|
|
87
|
+
* Handles keydown events to implement the focus trap.
|
|
88
|
+
* Traps Tab and Shift+Tab within the drawer.
|
|
89
|
+
*/
|
|
90
|
+
private handleKeyDown;
|
|
91
|
+
/**
|
|
92
|
+
* Lifecycle method to save the currently focused element when the drawer mounts while open.
|
|
93
|
+
*/
|
|
94
|
+
componentDidMount(): void;
|
|
95
|
+
/**
|
|
96
|
+
* Lifecycle method to restore focus when the drawer unmounts.
|
|
97
|
+
*/
|
|
98
|
+
componentWillUnmount(): void;
|
|
99
|
+
/**
|
|
100
|
+
* Restores focus to the element that was focused before the drawer opened.
|
|
101
|
+
*/
|
|
102
|
+
private restoreFocus;
|
|
103
|
+
/**
|
|
104
|
+
* Callback ref to capture the Drawer DOM element.
|
|
105
|
+
* Triggers initial focus setting when the element mounts.
|
|
106
|
+
*/
|
|
107
|
+
private setDrawerRef;
|
|
108
|
+
/**
|
|
109
|
+
* Sets initial focus within the drawer.
|
|
110
|
+
* Tries to focus the header first, then the first interactive element, or falls back to the container.
|
|
111
|
+
*/
|
|
112
|
+
private setInitialFocus;
|
|
113
|
+
/**
|
|
114
|
+
* Lifecycle method to handle Drawer updates.
|
|
115
|
+
* Manages opening/closing logic via LayerManager and focus preservation.
|
|
116
|
+
*/
|
|
45
117
|
getSnapshotBeforeUpdate(prevProps: DrawerProps): void;
|
|
118
|
+
/**
|
|
119
|
+
* Renders the Drawer component via the LayerManager portal.
|
|
120
|
+
*/
|
|
46
121
|
render(): import("@emotion/react/jsx-runtime").JSX.Element;
|
|
47
122
|
}
|
|
48
123
|
//# sourceMappingURL=Drawer.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Drawer.d.ts","sourceRoot":"","sources":["../../../src/components/Drawer/Drawer.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,SAAS,MAAM,YAAY,CAAC;AAKnC,OAAO,EACH,MAAM,IAAI,YAAY,EACtB,IAAI,IAAI,UAAU,EAClB,MAAM,IAAI,YAAY,GACzB,MAAM,qBAAqB,CAAC;AAE7B,oBAAY,eAAe;IACvB,IAAI,SAAS;IACb,KAAK,UAAU;IACf,MAAM,WAAW;CACpB;AAsCD,KAAK,WAAW,GAAG,SAAS,CAAC,UAAU,CAAC,OAAO,
|
|
1
|
+
{"version":3,"file":"Drawer.d.ts","sourceRoot":"","sources":["../../../src/components/Drawer/Drawer.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,SAAS,MAAM,YAAY,CAAC;AAKnC,OAAO,EACH,MAAM,IAAI,YAAY,EACtB,IAAI,IAAI,UAAU,EAClB,MAAM,IAAI,YAAY,GACzB,MAAM,qBAAqB,CAAC;AAE7B,oBAAY,eAAe;IACvB,IAAI,SAAS;IACb,KAAK,UAAU;IACf,MAAM,WAAW;CACpB;AAsCD,QAAA,MAAM,eAAe;IACjB,uBAAuB;;IAEvB,6BAA6B;;IAM7B,yBAAyB;;IAEzB,0CAA0C;;IAE1C,+BAA+B;;IAE/B,yCAAyC;;IAEzC,wDAAwD;;CAE3D,CAAC;AAEF,KAAK,WAAW,GAAG,SAAS,CAAC,UAAU,CAAC,OAAO,eAAe,CAAC,CAAC;AAEhE,UAAU,WAAW;IACjB,IAAI,EAAE,OAAO,CAAC;CACjB;AAQD;;;;;;;;;;;GAWG;AACH,MAAM,CAAC,OAAO,OAAO,MAAO,SAAQ,KAAK,CAAC,SAAS,CAC/C,KAAK,CAAC,iBAAiB,CAAC,WAAW,CAAC,EACpC,WAAW,CACd;IACG,KAAK;;MAEH;IAEF,MAAM,CAAC,SAAS;QApDhB,uBAAuB;;QAEvB,6BAA6B;;QAM7B,yBAAyB;;QAEzB,0CAA0C;;QAE1C,+BAA+B;;QAE/B,yCAAyC;;QAEzC,wDAAwD;;MAoCrB;IAEnC,MAAM,CAAC,YAAY;;;;;MAKjB;IAEF;;OAEG;IACH,MAAM,CAAC,wBAAwB,CAAC,KAAK,EAAE,WAAW;;;IASlD,OAAO,CAAC,KAAK,CAA8C;IAE3D,OAAO,CAAC,aAAa,CAA2B;IAEhD;;;OAGG;IACH,OAAO,CAAC,OAAO,CAQb;IAEF,OAAO,CAAC,kBAAkB,CAA4B;IACtD,OAAO,CAAC,SAAS,CAAqC;IAEtD;;OAEG;IACH,OAAO,CAAC,oBAAoB,CAO1B;IAEF;;;OAGG;IACH,OAAO,CAAC,aAAa,CAoBnB;IAEF;;OAEG;IACH,iBAAiB;IAMjB;;OAEG;IACH,oBAAoB;IAMpB;;OAEG;IACH,OAAO,CAAC,YAAY,CAWlB;IAEF;;;OAGG;IACH,OAAO,CAAC,YAAY,CAQlB;IAEF;;;OAGG;IACH,OAAO,CAAC,eAAe,CAoBrB;IAEF;;;OAGG;IACH,uBAAuB,CAAC,SAAS,EAAE,WAAW;IAiD9C;;OAEG;IACH,MAAM;CAQT"}
|
|
@@ -13,7 +13,7 @@ import { jsx as _jsx } from "@emotion/react/jsx-runtime";
|
|
|
13
13
|
import React from 'react';
|
|
14
14
|
import PropTypes from 'prop-types';
|
|
15
15
|
import styled from '@emotion/styled';
|
|
16
|
-
import
|
|
16
|
+
import { getThemeValue, THEME_NAME } from '../../shared/constants';
|
|
17
17
|
import LayerManager, { LAYER_POSITION } from '../../shared/LayerManager';
|
|
18
18
|
export { Header as DrawerHeader, Body as DrawerBody, Footer as DrawerFooter, } from '../../shared/styles';
|
|
19
19
|
export var DRAWER_POSITION;
|
|
@@ -46,9 +46,9 @@ const positionStyle = (size) => ({
|
|
|
46
46
|
const DrawerDiv = styled.div `
|
|
47
47
|
display: flex;
|
|
48
48
|
flex-direction: column;
|
|
49
|
-
background-color:
|
|
49
|
+
background-color: ${getThemeValue(THEME_NAME.BACKGROUND)};
|
|
50
50
|
transition: transform 0.3s ease;
|
|
51
|
-
box-shadow:
|
|
51
|
+
box-shadow: ${getThemeValue(THEME_NAME.MODAL_SHADOW)};
|
|
52
52
|
${(props) => positionStyle(props.size)[props.position].before}
|
|
53
53
|
|
|
54
54
|
.nf-layer-enter & {
|
|
@@ -56,19 +56,56 @@ const DrawerDiv = styled.div `
|
|
|
56
56
|
${(props) => positionStyle(props.size)[props.position].after}
|
|
57
57
|
}
|
|
58
58
|
`;
|
|
59
|
+
const drawerPropTypes = {
|
|
60
|
+
/** Opens the drawer */
|
|
61
|
+
open: PropTypes.bool.isRequired,
|
|
62
|
+
/** position of the drawer */
|
|
63
|
+
position: PropTypes.oneOf([
|
|
64
|
+
DRAWER_POSITION.LEFT,
|
|
65
|
+
DRAWER_POSITION.RIGHT,
|
|
66
|
+
DRAWER_POSITION.BOTTOM,
|
|
67
|
+
]),
|
|
68
|
+
/** size of the drawer */
|
|
69
|
+
size: PropTypes.string,
|
|
70
|
+
/** Shows an overlay behind the drawer. */
|
|
71
|
+
overlay: PropTypes.bool,
|
|
72
|
+
/** Closes the drawer on esc */
|
|
73
|
+
closeOnEsc: PropTypes.bool,
|
|
74
|
+
/** Closes the drawer on overlay click */
|
|
75
|
+
closeOnOverlayClick: PropTypes.bool,
|
|
76
|
+
/** Call back function called when the drawer closes. */
|
|
77
|
+
onClose: PropTypes.func,
|
|
78
|
+
};
|
|
59
79
|
const positionMap = {
|
|
60
80
|
[DRAWER_POSITION.LEFT]: LAYER_POSITION.TOP_LEFT,
|
|
61
81
|
[DRAWER_POSITION.RIGHT]: LAYER_POSITION.TOP_RIGHT,
|
|
62
82
|
[DRAWER_POSITION.BOTTOM]: LAYER_POSITION.BOTTOM_LEFT,
|
|
63
83
|
};
|
|
84
|
+
/**
|
|
85
|
+
* Drawer component
|
|
86
|
+
*
|
|
87
|
+
* A panel that slides in from the edge of the screen.
|
|
88
|
+
* It sits on top of the application content and is often used for navigation or details.
|
|
89
|
+
*
|
|
90
|
+
* Accessibility:
|
|
91
|
+
* - Implements ARIA `role="dialog"` and `aria-modal="true"`.
|
|
92
|
+
* - Traps focus effectively within the drawer while open.
|
|
93
|
+
* - Restores focus to the triggering element upon closure.
|
|
94
|
+
* - Supports closing via ESC key and overlay click.
|
|
95
|
+
*/
|
|
64
96
|
class Drawer extends React.Component {
|
|
65
97
|
constructor() {
|
|
66
98
|
super(...arguments);
|
|
67
99
|
this.state = {
|
|
68
100
|
open: false,
|
|
69
101
|
};
|
|
102
|
+
/**
|
|
103
|
+
* Internal close handler.
|
|
104
|
+
* Restores focus and calls the external onClose callback.
|
|
105
|
+
*/
|
|
70
106
|
this.onClose = () => {
|
|
71
107
|
var _a, _b;
|
|
108
|
+
this.restoreFocus();
|
|
72
109
|
this.setState({
|
|
73
110
|
open: false,
|
|
74
111
|
});
|
|
@@ -76,7 +113,97 @@ class Drawer extends React.Component {
|
|
|
76
113
|
this.closeCallback = null;
|
|
77
114
|
this.layer = null;
|
|
78
115
|
};
|
|
116
|
+
this.lastFocusedElement = null;
|
|
117
|
+
this.drawerRef = React.createRef();
|
|
118
|
+
/**
|
|
119
|
+
* Retrieves all focusable elements within the drawer.
|
|
120
|
+
*/
|
|
121
|
+
this.getFocusableElements = () => {
|
|
122
|
+
if (!this.drawerRef.current)
|
|
123
|
+
return [];
|
|
124
|
+
return Array.from(this.drawerRef.current.querySelectorAll('button, [href], input, select, textarea, [tabindex]:not([tabindex="-1"])'));
|
|
125
|
+
};
|
|
126
|
+
/**
|
|
127
|
+
* Handles keydown events to implement the focus trap.
|
|
128
|
+
* Traps Tab and Shift+Tab within the drawer.
|
|
129
|
+
*/
|
|
130
|
+
this.handleKeyDown = (e) => {
|
|
131
|
+
if (e.key === 'Tab') {
|
|
132
|
+
const focusableElements = this.getFocusableElements();
|
|
133
|
+
if (focusableElements.length === 0)
|
|
134
|
+
return;
|
|
135
|
+
const firstElement = focusableElements[0];
|
|
136
|
+
const lastElement = focusableElements[focusableElements.length - 1];
|
|
137
|
+
if (e.shiftKey) {
|
|
138
|
+
if (document.activeElement === firstElement) {
|
|
139
|
+
lastElement.focus();
|
|
140
|
+
e.preventDefault();
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
else {
|
|
144
|
+
if (document.activeElement === lastElement) {
|
|
145
|
+
firstElement.focus();
|
|
146
|
+
e.preventDefault();
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
};
|
|
151
|
+
/**
|
|
152
|
+
* Restores focus to the element that was focused before the drawer opened.
|
|
153
|
+
*/
|
|
154
|
+
this.restoreFocus = () => {
|
|
155
|
+
if (this.lastFocusedElement) {
|
|
156
|
+
// Check if the element is still in the document
|
|
157
|
+
const elementToBeFocused = this.lastFocusedElement;
|
|
158
|
+
this.lastFocusedElement = null;
|
|
159
|
+
setTimeout(() => {
|
|
160
|
+
if (document.body.contains(elementToBeFocused)) {
|
|
161
|
+
elementToBeFocused.focus();
|
|
162
|
+
}
|
|
163
|
+
}, 100);
|
|
164
|
+
}
|
|
165
|
+
};
|
|
166
|
+
/**
|
|
167
|
+
* Callback ref to capture the Drawer DOM element.
|
|
168
|
+
* Triggers initial focus setting when the element mounts.
|
|
169
|
+
*/
|
|
170
|
+
this.setDrawerRef = (node) => {
|
|
171
|
+
// Update ref
|
|
172
|
+
this.drawerRef.current = node;
|
|
173
|
+
if (node) {
|
|
174
|
+
// Set initial focus when the node is mounted
|
|
175
|
+
this.setInitialFocus(node);
|
|
176
|
+
}
|
|
177
|
+
};
|
|
178
|
+
/**
|
|
179
|
+
* Sets initial focus within the drawer.
|
|
180
|
+
* Tries to focus the header first, then the first interactive element, or falls back to the container.
|
|
181
|
+
*/
|
|
182
|
+
this.setInitialFocus = (root) => {
|
|
183
|
+
// Try to find the header (assumed to be the first child)
|
|
184
|
+
const firstChild = root.firstElementChild;
|
|
185
|
+
if (firstChild) {
|
|
186
|
+
// Ensure it's focusable
|
|
187
|
+
if (firstChild.getAttribute('tabindex') === null) {
|
|
188
|
+
firstChild.setAttribute('tabindex', '-1');
|
|
189
|
+
}
|
|
190
|
+
firstChild.focus();
|
|
191
|
+
return;
|
|
192
|
+
}
|
|
193
|
+
// Fallback to focusable elements
|
|
194
|
+
const focusableElements = this.getFocusableElements();
|
|
195
|
+
if (focusableElements.length > 0) {
|
|
196
|
+
focusableElements[0].focus();
|
|
197
|
+
}
|
|
198
|
+
else {
|
|
199
|
+
// Fallback to container
|
|
200
|
+
root.focus();
|
|
201
|
+
}
|
|
202
|
+
};
|
|
79
203
|
}
|
|
204
|
+
/**
|
|
205
|
+
* Syncs state with props.
|
|
206
|
+
*/
|
|
80
207
|
static getDerivedStateFromProps(props) {
|
|
81
208
|
if (props.open) {
|
|
82
209
|
return {
|
|
@@ -85,13 +212,36 @@ class Drawer extends React.Component {
|
|
|
85
212
|
}
|
|
86
213
|
return null;
|
|
87
214
|
}
|
|
215
|
+
/**
|
|
216
|
+
* Lifecycle method to save the currently focused element when the drawer mounts while open.
|
|
217
|
+
*/
|
|
218
|
+
componentDidMount() {
|
|
219
|
+
if (this.props.open) {
|
|
220
|
+
this.lastFocusedElement = document.activeElement;
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
/**
|
|
224
|
+
* Lifecycle method to restore focus when the drawer unmounts.
|
|
225
|
+
*/
|
|
226
|
+
componentWillUnmount() {
|
|
227
|
+
if (this.props.open) {
|
|
228
|
+
this.restoreFocus();
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
/**
|
|
232
|
+
* Lifecycle method to handle Drawer updates.
|
|
233
|
+
* Manages opening/closing logic via LayerManager and focus preservation.
|
|
234
|
+
*/
|
|
88
235
|
getSnapshotBeforeUpdate(prevProps) {
|
|
89
236
|
var _a;
|
|
90
237
|
const _b = this.props, { open, closeOnEsc, closeOnOverlayClick, overlay, position, children, size } = _b, rest = __rest(_b, ["open", "closeOnEsc", "closeOnOverlayClick", "overlay", "position", "children", "size"]);
|
|
91
238
|
if (prevProps.open && !open) {
|
|
92
239
|
(_a = this.closeCallback) === null || _a === void 0 ? void 0 : _a.call(this);
|
|
240
|
+
this.restoreFocus();
|
|
93
241
|
}
|
|
94
242
|
if (!prevProps.open && open) {
|
|
243
|
+
// Save current focus
|
|
244
|
+
this.lastFocusedElement = document.activeElement;
|
|
95
245
|
this.layer = LayerManager.renderLayer({
|
|
96
246
|
overlay,
|
|
97
247
|
exitDelay: 300,
|
|
@@ -99,12 +249,15 @@ class Drawer extends React.Component {
|
|
|
99
249
|
closeCallback: this.onClose,
|
|
100
250
|
closeOnEsc,
|
|
101
251
|
closeOnOverlayClick,
|
|
102
|
-
component: (_jsx(DrawerDiv, Object.assign({}, rest, { position: position, size: size, onClick: (e) => e.stopPropagation(), children: children }))),
|
|
252
|
+
component: (_jsx(DrawerDiv, Object.assign({}, rest, { ref: this.setDrawerRef, role: "dialog", "aria-modal": "true", tabIndex: -1, onKeyDown: this.handleKeyDown, position: position, size: size, onClick: (e) => e.stopPropagation(), children: children }))),
|
|
103
253
|
});
|
|
104
254
|
this.closeCallback = this.layer[1];
|
|
105
255
|
this.forceUpdate();
|
|
106
256
|
}
|
|
107
257
|
}
|
|
258
|
+
/**
|
|
259
|
+
* Renders the Drawer component via the LayerManager portal.
|
|
260
|
+
*/
|
|
108
261
|
render() {
|
|
109
262
|
if (this.state.open && this.layer) {
|
|
110
263
|
const [Component] = this.layer;
|
|
@@ -113,26 +266,7 @@ class Drawer extends React.Component {
|
|
|
113
266
|
return null;
|
|
114
267
|
}
|
|
115
268
|
}
|
|
116
|
-
Drawer.propTypes =
|
|
117
|
-
/** Opens the drawer */
|
|
118
|
-
open: PropTypes.bool.isRequired,
|
|
119
|
-
/** position of the drawer */
|
|
120
|
-
position: PropTypes.oneOf([
|
|
121
|
-
DRAWER_POSITION.LEFT,
|
|
122
|
-
DRAWER_POSITION.RIGHT,
|
|
123
|
-
DRAWER_POSITION.BOTTOM,
|
|
124
|
-
]),
|
|
125
|
-
/** size of the drawer */
|
|
126
|
-
size: PropTypes.string,
|
|
127
|
-
/** Shows an overlay behind the drawer. */
|
|
128
|
-
overlay: PropTypes.bool,
|
|
129
|
-
/** Closes the drawer on esc */
|
|
130
|
-
closeOnEsc: PropTypes.bool,
|
|
131
|
-
/** Closes the drawer on overlay click */
|
|
132
|
-
closeOnOverlayClick: PropTypes.bool,
|
|
133
|
-
/** Call back function called when the drawer closes. */
|
|
134
|
-
onClose: PropTypes.func,
|
|
135
|
-
};
|
|
269
|
+
Drawer.propTypes = drawerPropTypes;
|
|
136
270
|
Drawer.defaultProps = {
|
|
137
271
|
overlay: true,
|
|
138
272
|
position: DRAWER_POSITION.LEFT,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Drawer.js","sourceRoot":"","sources":["../../../src/components/Drawer/Drawer.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\nimport PropTypes from 'prop-types';\nimport styled from '@emotion/styled';\nimport constants from '../../shared/constants';\nimport LayerManager, { LAYER_POSITION } from '../../shared/LayerManager';\n\nexport {\n Header as DrawerHeader,\n Body as DrawerBody,\n Footer as DrawerFooter,\n} from '../../shared/styles';\n\nexport enum DRAWER_POSITION {\n LEFT = 'LEFT',\n RIGHT = 'RIGHT',\n BOTTOM = 'BOTTOM',\n}\n\nconst positionStyle = (size: string) => ({\n [DRAWER_POSITION.LEFT]: {\n before: `height: 100vh; min-width: ${size || '300px'}; transform: translateX(-100%);`,\n after: 'transform: translateX(0%);',\n },\n [DRAWER_POSITION.RIGHT]: {\n before: `height: 100vh; min-width: ${size || '300px'}; transform: translateX(100%);`,\n after: 'transform: translateX(0%);',\n },\n [DRAWER_POSITION.BOTTOM]: {\n before: `\n position: absolute;\n bottom: 0;\n width: 100%;\n height: ${size || '90vh'};\n transform: translateY(100%);\n border-radius: 15px 15px 0 0; \n `,\n after: 'transform: translateX(0%);',\n },\n});\n\nconst DrawerDiv = styled.div<{ position: DRAWER_POSITION; size: string }>`\n display: flex;\n flex-direction: column;\n background-color: #fff;\n transition: transform 0.3s ease;\n box-shadow: var(--modal-shadow, ${constants.MODAL_SHADOW});\n ${(props) => positionStyle(props.size)[props.position].before}\n\n .nf-layer-enter & {\n transform: translateX(0%);\n ${(props) => positionStyle(props.size)[props.position].after}\n }\n`;\n\ntype DrawerProps = PropTypes.InferProps<typeof Drawer.propTypes>;\ninterface DrawerState {\n open: boolean;\n}\n\nconst positionMap = {\n [DRAWER_POSITION.LEFT]: LAYER_POSITION.TOP_LEFT,\n [DRAWER_POSITION.RIGHT]: LAYER_POSITION.TOP_RIGHT,\n [DRAWER_POSITION.BOTTOM]: LAYER_POSITION.BOTTOM_LEFT,\n};\n\nexport default class Drawer extends React.Component<\n React.PropsWithChildren<DrawerProps>,\n DrawerState\n> {\n state = {\n open: false,\n };\n\n static propTypes = {\n /** Opens the drawer */\n open: PropTypes.bool.isRequired,\n /** position of the drawer */\n position: PropTypes.oneOf([\n DRAWER_POSITION.LEFT,\n DRAWER_POSITION.RIGHT,\n DRAWER_POSITION.BOTTOM,\n ]),\n /** size of the drawer */\n size: PropTypes.string,\n /** Shows an overlay behind the drawer. */\n overlay: PropTypes.bool,\n /** Closes the drawer on esc */\n closeOnEsc: PropTypes.bool,\n /** Closes the drawer on overlay click */\n closeOnOverlayClick: PropTypes.bool,\n /** Call back function called when the drawer closes. */\n onClose: PropTypes.func,\n };\n\n static defaultProps = {\n overlay: true,\n position: DRAWER_POSITION.LEFT,\n closeOnEsc: true,\n closeOnOverlayClick: true,\n };\n\n static getDerivedStateFromProps(props: DrawerProps) {\n if (props.open) {\n return {\n open: true,\n };\n }\n return null;\n }\n\n private layer: ReturnType<typeof LayerManager.renderLayer>;\n\n private closeCallback: (resp?: unknown) => void;\n\n private onClose = () => {\n this.setState({\n open: false,\n });\n this.props.onClose?.();\n this.closeCallback = null;\n this.layer = null;\n };\n\n getSnapshotBeforeUpdate(prevProps: DrawerProps) {\n const {\n open,\n closeOnEsc,\n closeOnOverlayClick,\n overlay,\n position,\n children,\n size,\n ...rest\n } = this.props;\n\n if (prevProps.open && !open) {\n this.closeCallback?.();\n }\n\n if (!prevProps.open && open) {\n this.layer = LayerManager.renderLayer({\n overlay,\n exitDelay: 300,\n position: positionMap[position],\n closeCallback: this.onClose,\n closeOnEsc,\n closeOnOverlayClick,\n component: (\n <DrawerDiv\n {...rest}\n position={position}\n size={size}\n onClick={(e) => e.stopPropagation()}\n >\n {children}\n </DrawerDiv>\n ),\n });\n this.closeCallback = this.layer[1];\n this.forceUpdate();\n }\n }\n\n render() {\n if (this.state.open && this.layer) {\n const [Component] = this.layer;\n return <Component />;\n }\n\n return null;\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"Drawer.js","sourceRoot":"","sources":["../../../src/components/Drawer/Drawer.tsx"],"names":[],"mappings":"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","sourcesContent":["import React from 'react';\nimport PropTypes from 'prop-types';\nimport styled from '@emotion/styled';\nimport { getThemeValue, THEME_NAME } from '../../shared/constants';\nimport LayerManager, { LAYER_POSITION } from '../../shared/LayerManager';\n\nexport {\n Header as DrawerHeader,\n Body as DrawerBody,\n Footer as DrawerFooter,\n} from '../../shared/styles';\n\nexport enum DRAWER_POSITION {\n LEFT = 'LEFT',\n RIGHT = 'RIGHT',\n BOTTOM = 'BOTTOM',\n}\n\nconst positionStyle = (size: string) => ({\n [DRAWER_POSITION.LEFT]: {\n before: `height: 100vh; min-width: ${size || '300px'}; transform: translateX(-100%);`,\n after: 'transform: translateX(0%);',\n },\n [DRAWER_POSITION.RIGHT]: {\n before: `height: 100vh; min-width: ${size || '300px'}; transform: translateX(100%);`,\n after: 'transform: translateX(0%);',\n },\n [DRAWER_POSITION.BOTTOM]: {\n before: `\n position: absolute;\n bottom: 0;\n width: 100%;\n height: ${size || '90vh'};\n transform: translateY(100%);\n border-radius: 15px 15px 0 0; \n `,\n after: 'transform: translateX(0%);',\n },\n});\n\nconst DrawerDiv = styled.div<{ position: DRAWER_POSITION; size: string }>`\n display: flex;\n flex-direction: column;\n background-color: ${getThemeValue(THEME_NAME.BACKGROUND)};\n transition: transform 0.3s ease;\n box-shadow: ${getThemeValue(THEME_NAME.MODAL_SHADOW)};\n ${(props) => positionStyle(props.size)[props.position].before}\n\n .nf-layer-enter & {\n transform: translateX(0%);\n ${(props) => positionStyle(props.size)[props.position].after}\n }\n`;\n\nconst drawerPropTypes = {\n /** Opens the drawer */\n open: PropTypes.bool.isRequired,\n /** position of the drawer */\n position: PropTypes.oneOf([\n DRAWER_POSITION.LEFT,\n DRAWER_POSITION.RIGHT,\n DRAWER_POSITION.BOTTOM,\n ]),\n /** size of the drawer */\n size: PropTypes.string,\n /** Shows an overlay behind the drawer. */\n overlay: PropTypes.bool,\n /** Closes the drawer on esc */\n closeOnEsc: PropTypes.bool,\n /** Closes the drawer on overlay click */\n closeOnOverlayClick: PropTypes.bool,\n /** Call back function called when the drawer closes. */\n onClose: PropTypes.func,\n};\n\ntype DrawerProps = PropTypes.InferProps<typeof drawerPropTypes>;\n\ninterface DrawerState {\n open: boolean;\n}\n\nconst positionMap = {\n [DRAWER_POSITION.LEFT]: LAYER_POSITION.TOP_LEFT,\n [DRAWER_POSITION.RIGHT]: LAYER_POSITION.TOP_RIGHT,\n [DRAWER_POSITION.BOTTOM]: LAYER_POSITION.BOTTOM_LEFT,\n};\n\n/**\n * Drawer component\n *\n * A panel that slides in from the edge of the screen.\n * It sits on top of the application content and is often used for navigation or details.\n *\n * Accessibility:\n * - Implements ARIA `role=\"dialog\"` and `aria-modal=\"true\"`.\n * - Traps focus effectively within the drawer while open.\n * - Restores focus to the triggering element upon closure.\n * - Supports closing via ESC key and overlay click.\n */\nexport default class Drawer extends React.Component<\n React.PropsWithChildren<DrawerProps>,\n DrawerState\n> {\n state = {\n open: false,\n };\n\n static propTypes = drawerPropTypes;\n\n static defaultProps = {\n overlay: true,\n position: DRAWER_POSITION.LEFT,\n closeOnEsc: true,\n closeOnOverlayClick: true,\n };\n\n /**\n * Syncs state with props.\n */\n static getDerivedStateFromProps(props: DrawerProps) {\n if (props.open) {\n return {\n open: true,\n };\n }\n return null;\n }\n\n private layer: ReturnType<typeof LayerManager.renderLayer>;\n\n private closeCallback: (resp?: unknown) => void;\n\n /**\n * Internal close handler.\n * Restores focus and calls the external onClose callback.\n */\n private onClose = () => {\n this.restoreFocus();\n this.setState({\n open: false,\n });\n this.props.onClose?.();\n this.closeCallback = null;\n this.layer = null;\n };\n\n private lastFocusedElement: HTMLElement | null = null;\n private drawerRef = React.createRef<HTMLDivElement>();\n\n /**\n * Retrieves all focusable elements within the drawer.\n */\n private getFocusableElements = (): HTMLElement[] => {\n if (!this.drawerRef.current) return [];\n return Array.from(\n this.drawerRef.current.querySelectorAll(\n 'button, [href], input, select, textarea, [tabindex]:not([tabindex=\"-1\"])',\n ),\n ) as HTMLElement[];\n };\n\n /**\n * Handles keydown events to implement the focus trap.\n * Traps Tab and Shift+Tab within the drawer.\n */\n private handleKeyDown = (e: React.KeyboardEvent) => {\n if (e.key === 'Tab') {\n const focusableElements = this.getFocusableElements();\n if (focusableElements.length === 0) return;\n\n const firstElement = focusableElements[0];\n const lastElement = focusableElements[focusableElements.length - 1];\n\n if (e.shiftKey) {\n if (document.activeElement === firstElement) {\n lastElement.focus();\n e.preventDefault();\n }\n } else {\n if (document.activeElement === lastElement) {\n firstElement.focus();\n e.preventDefault();\n }\n }\n }\n };\n\n /**\n * Lifecycle method to save the currently focused element when the drawer mounts while open.\n */\n componentDidMount() {\n if (this.props.open) {\n this.lastFocusedElement = document.activeElement as HTMLElement;\n }\n }\n\n /**\n * Lifecycle method to restore focus when the drawer unmounts.\n */\n componentWillUnmount() {\n if (this.props.open) {\n this.restoreFocus();\n }\n }\n\n /**\n * Restores focus to the element that was focused before the drawer opened.\n */\n private restoreFocus = () => {\n if (this.lastFocusedElement) {\n // Check if the element is still in the document\n const elementToBeFocused = this.lastFocusedElement;\n this.lastFocusedElement = null;\n setTimeout(() => {\n if (document.body.contains(elementToBeFocused)) {\n elementToBeFocused.focus();\n }\n }, 100);\n }\n };\n\n /**\n * Callback ref to capture the Drawer DOM element.\n * Triggers initial focus setting when the element mounts.\n */\n private setDrawerRef = (node: HTMLDivElement | null) => {\n // Update ref\n (this.drawerRef as React.MutableRefObject<HTMLDivElement | null>).current = node;\n\n if (node) {\n // Set initial focus when the node is mounted\n this.setInitialFocus(node);\n }\n };\n\n /**\n * Sets initial focus within the drawer.\n * Tries to focus the header first, then the first interactive element, or falls back to the container.\n */\n private setInitialFocus = (root: HTMLElement) => {\n // Try to find the header (assumed to be the first child)\n const firstChild = root.firstElementChild as HTMLElement;\n if (firstChild) {\n // Ensure it's focusable\n if (firstChild.getAttribute('tabindex') === null) {\n firstChild.setAttribute('tabindex', '-1');\n }\n firstChild.focus();\n return;\n }\n\n // Fallback to focusable elements\n const focusableElements = this.getFocusableElements();\n if (focusableElements.length > 0) {\n focusableElements[0].focus();\n } else {\n // Fallback to container\n root.focus();\n }\n };\n\n /**\n * Lifecycle method to handle Drawer updates.\n * Manages opening/closing logic via LayerManager and focus preservation.\n */\n getSnapshotBeforeUpdate(prevProps: DrawerProps) {\n const {\n open,\n closeOnEsc,\n closeOnOverlayClick,\n overlay,\n position,\n children,\n size,\n ...rest\n } = this.props;\n\n if (prevProps.open && !open) {\n this.closeCallback?.();\n this.restoreFocus();\n }\n\n if (!prevProps.open && open) {\n // Save current focus\n this.lastFocusedElement = document.activeElement as HTMLElement;\n\n this.layer = LayerManager.renderLayer({\n overlay,\n exitDelay: 300,\n position: positionMap[position],\n closeCallback: this.onClose,\n closeOnEsc,\n closeOnOverlayClick,\n component: (\n <DrawerDiv\n {...rest}\n ref={this.setDrawerRef}\n role=\"dialog\"\n aria-modal=\"true\"\n tabIndex={-1}\n onKeyDown={this.handleKeyDown}\n position={position}\n size={size}\n onClick={(e) => e.stopPropagation()}\n >\n {children}\n </DrawerDiv>\n ),\n });\n this.closeCallback = this.layer[1];\n this.forceUpdate();\n }\n }\n\n /**\n * Renders the Drawer component via the LayerManager portal.\n */\n render() {\n if (this.state.open && this.layer) {\n const [Component] = this.layer;\n return <Component />;\n }\n\n return null;\n }\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Group.d.ts","sourceRoot":"","sources":["../../../src/components/Groups/Group.tsx"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"Group.d.ts","sourceRoot":"","sources":["../../../src/components/Groups/Group.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAgB,MAAM,OAAO,CAAC;AACrC,OAAO,SAAS,MAAM,YAAY,CAAC;AA4FnC,iBAAwB,KAAK,CACzB,KAAK,EAAE,KAAK,CAAC,iBAAiB,CAAC,SAAS,CAAC,UAAU,CAAC,OAAO,KAAK,CAAC,SAAS,CAAC,CAAC,oDAY/E;kBAbuB,KAAK;;QAgBzB,kCAAkC;;;;eAhBd,KAAK"}
|
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "@emotion/react/jsx-runtime";
|
|
2
|
+
import { useId } from 'react';
|
|
2
3
|
import PropTypes from 'prop-types';
|
|
3
4
|
import styled from '@emotion/styled';
|
|
4
|
-
import
|
|
5
|
+
import { getThemeValue, THEME_NAME } from '../../shared/constants';
|
|
5
6
|
const Container = styled.div `
|
|
6
7
|
display: inline-flex;
|
|
7
|
-
border: 1px solid
|
|
8
|
+
border: 1px solid ${getThemeValue(THEME_NAME.BORDER_COLOR)};
|
|
8
9
|
border-radius: 3px;
|
|
9
10
|
margin: 5px;
|
|
10
11
|
|
|
@@ -14,7 +15,7 @@ const Container = styled.div `
|
|
|
14
15
|
margin: 0;
|
|
15
16
|
border: none;
|
|
16
17
|
border-radius: 0;
|
|
17
|
-
border-left: 1px solid
|
|
18
|
+
border-left: 1px solid ${getThemeValue(THEME_NAME.BORDER_COLOR)};
|
|
18
19
|
box-shadow: none;
|
|
19
20
|
height: 32px;
|
|
20
21
|
}
|
|
@@ -69,26 +70,27 @@ const Container = styled.div `
|
|
|
69
70
|
|
|
70
71
|
&:focus-within,
|
|
71
72
|
&:hover {
|
|
72
|
-
box-shadow:
|
|
73
|
+
box-shadow: ${getThemeValue(THEME_NAME.HOVER_SHADOW)};
|
|
73
74
|
}
|
|
74
75
|
|
|
75
76
|
${(props) => props.errorText
|
|
76
77
|
? `
|
|
77
|
-
border-color:
|
|
78
|
+
border-color: ${getThemeValue(THEME_NAME.ERROR)};
|
|
78
79
|
|
|
79
80
|
& > button, & > label {
|
|
80
|
-
border-color:
|
|
81
|
+
border-color: ${getThemeValue(THEME_NAME.ERROR)};
|
|
81
82
|
}
|
|
82
83
|
`
|
|
83
84
|
: ''}
|
|
84
85
|
`;
|
|
85
86
|
const ErrorContainer = styled.div `
|
|
86
|
-
color:
|
|
87
|
+
color: ${getThemeValue(THEME_NAME.ERROR)};
|
|
87
88
|
margin-left: 8px;
|
|
88
89
|
font-size: 12px;
|
|
89
90
|
`;
|
|
90
91
|
export default function Group(props) {
|
|
91
|
-
|
|
92
|
+
const errorId = useId();
|
|
93
|
+
return (_jsxs(_Fragment, { children: [_jsx(Container, Object.assign({}, props, { "aria-describedby": props.errorText ? errorId : undefined, children: props.children })), props.errorText && _jsx(ErrorContainer, { id: errorId, children: props.errorText })] }));
|
|
92
94
|
}
|
|
93
95
|
Group.propTypes = {
|
|
94
96
|
/** Error Message for the group */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Group.js","sourceRoot":"","sources":["../../../src/components/Groups/Group.tsx"],"names":[],"mappings":";
|
|
1
|
+
{"version":3,"file":"Group.js","sourceRoot":"","sources":["../../../src/components/Groups/Group.tsx"],"names":[],"mappings":";AAAA,OAAc,EAAE,KAAK,EAAE,MAAM,OAAO,CAAC;AACrC,OAAO,SAAS,MAAM,YAAY,CAAC;AACnC,OAAO,MAAM,MAAM,iBAAiB,CAAC;AACrC,OAAO,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAEnE,MAAM,SAAS,GAAG,MAAM,CAAC,GAAG,CAA8C;;wBAElD,aAAa,CAAC,UAAU,CAAC,YAAY,CAAC;;;;;;;;;;iCAU7B,aAAa,CAAC,UAAU,CAAC,YAAY,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;sBAuDjD,aAAa,CAAC,UAAU,CAAC,YAAY,CAAC;;;MAGtD,CAAC,KAAK,EAAE,EAAE,CACR,KAAK,CAAC,SAAS;IACX,CAAC,CAAC;wBACU,aAAa,CAAC,UAAU,CAAC,KAAK,CAAC;;;4BAG3B,aAAa,CAAC,UAAU,CAAC,KAAK,CAAC;;KAEtD;IACO,CAAC,CAAC,EAAE;CACf,CAAC;AAEF,MAAM,cAAc,GAAG,MAAM,CAAC,GAAG,CAAA;aACpB,aAAa,CAAC,UAAU,CAAC,KAAK,CAAC;;;CAG3C,CAAC;AAEF,MAAM,CAAC,OAAO,UAAU,KAAK,CACzB,KAA4E;IAE5E,MAAM,OAAO,GAAG,KAAK,EAAE,CAAC;IAExB,OAAO,CACH,8BACI,KAAC,SAAS,oBAAK,KAAK,wBAAoB,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,YACxE,KAAK,CAAC,QAAQ,IACP,EACX,KAAK,CAAC,SAAS,IAAI,KAAC,cAAc,IAAC,EAAE,EAAE,OAAO,YAAG,KAAK,CAAC,SAAS,GAAkB,IACpF,CACN,CAAC;AACN,CAAC;AAED,KAAK,CAAC,SAAS,GAAG;IACd,kCAAkC;IAClC,SAAS,EAAE,SAAS,CAAC,MAAM;CAC9B,CAAC","sourcesContent":["import React, { useId } from 'react';\nimport PropTypes from 'prop-types';\nimport styled from '@emotion/styled';\nimport { getThemeValue, THEME_NAME } from '../../shared/constants';\n\nconst Container = styled.div<PropTypes.InferProps<typeof Group.propTypes>>`\n display: inline-flex;\n border: 1px solid ${getThemeValue(THEME_NAME.BORDER_COLOR)};\n border-radius: 3px;\n margin: 5px;\n\n /* overrides */\n & button,\n & label {\n margin: 0;\n border: none;\n border-radius: 0;\n border-left: 1px solid ${getThemeValue(THEME_NAME.BORDER_COLOR)};\n box-shadow: none;\n height: 32px;\n }\n\n & > div button {\n border-left: none;\n }\n\n & input,\n & select {\n border: none;\n height: 32px;\n }\n\n & input,\n & select {\n border-radius: 0;\n }\n\n & input:active,\n & select:active {\n box-shadow: none;\n }\n\n & > div > span {\n top: 8px;\n }\n\n /* Handling for first and last child */\n & > *:first-child,\n & > label:first-child input,\n & > label:first-child select,\n & > *:first-child label,\n & > *:first-child input {\n border-left: none;\n border-radius: 2px 0 0 2px;\n }\n\n & > *:last-child,\n & > label:last-child input,\n & > label:last-child select,\n & > *:last-child label,\n & > *:last-child input {\n border-radius: 0 2px 2px 0;\n }\n\n /* focus */\n & *:focus,\n & *:focus + span {\n z-index: 1;\n }\n\n &:focus-within,\n &:hover {\n box-shadow: ${getThemeValue(THEME_NAME.HOVER_SHADOW)};\n }\n\n ${(props) =>\n props.errorText\n ? `\n border-color: ${getThemeValue(THEME_NAME.ERROR)};\n\n & > button, & > label {\n border-color: ${getThemeValue(THEME_NAME.ERROR)};\n }\n `\n : ''}\n`;\n\nconst ErrorContainer = styled.div`\n color: ${getThemeValue(THEME_NAME.ERROR)};\n margin-left: 8px;\n font-size: 12px;\n`;\n\nexport default function Group(\n props: React.PropsWithChildren<PropTypes.InferProps<typeof Group.propTypes>>,\n) {\n const errorId = useId();\n\n return (\n <>\n <Container {...props} aria-describedby={props.errorText ? errorId : undefined}>\n {props.children}\n </Container>\n {props.errorText && <ErrorContainer id={errorId}>{props.errorText}</ErrorContainer>}\n </>\n );\n}\n\nGroup.propTypes = {\n /** Error Message for the group */\n errorText: PropTypes.string,\n};\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GroupLabel.d.ts","sourceRoot":"","sources":["../../../src/components/Groups/GroupLabel.tsx"],"names":[],"mappings":";;
|
|
1
|
+
{"version":3,"file":"GroupLabel.d.ts","sourceRoot":"","sources":["../../../src/components/Groups/GroupLabel.tsx"],"names":[],"mappings":";;SAmByH,MAAO,WAAW;;AAhB3I,wBAeE"}
|
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
import styled from '@emotion/styled';
|
|
2
|
-
import
|
|
2
|
+
import { getThemeValue, THEME_NAME } from '../../shared/constants';
|
|
3
3
|
export default styled.label `
|
|
4
4
|
height: 32px;
|
|
5
|
-
background-color: ${
|
|
5
|
+
background-color: ${getThemeValue(THEME_NAME.DISABLED_BACKGROUND)};
|
|
6
6
|
padding: 0 4px;
|
|
7
7
|
line-height: 32px;
|
|
8
8
|
min-width: 24px;
|
|
9
9
|
text-align: center;
|
|
10
|
-
color: ${
|
|
10
|
+
color: ${getThemeValue(THEME_NAME.BORDER_COLOR)};
|
|
11
11
|
|
|
12
12
|
& > svg {
|
|
13
13
|
height: 24px;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"GroupLabel.js","sourceRoot":"","sources":["../../../src/components/Groups/GroupLabel.tsx"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,iBAAiB,CAAC;AACrC,OAAO,
|
|
1
|
+
{"version":3,"file":"GroupLabel.js","sourceRoot":"","sources":["../../../src/components/Groups/GroupLabel.tsx"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,iBAAiB,CAAC;AACrC,OAAO,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAEnE,eAAe,MAAM,CAAC,KAAK,CAAA;;wBAEH,aAAa,CAAC,UAAU,CAAC,mBAAmB,CAAC;;;;;aAKxD,aAAa,CAAC,UAAU,CAAC,YAAY,CAAC;;;;;;;;CAQlD,CAAC","sourcesContent":["import styled from '@emotion/styled';\nimport { getThemeValue, THEME_NAME } from '../../shared/constants';\n\nexport default styled.label`\n height: 32px;\n background-color: ${getThemeValue(THEME_NAME.DISABLED_BACKGROUND)};\n padding: 0 4px;\n line-height: 32px;\n min-width: 24px;\n text-align: center;\n color: ${getThemeValue(THEME_NAME.BORDER_COLOR)};\n\n & > svg {\n height: 24px;\n width: 24px;\n vertical-align: middle;\n fill: currentColor;\n }\n`;\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Checkbox.d.ts","sourceRoot":"","sources":["../../../src/components/Input/Checkbox.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAsB,MAAM,OAAO,CAAC;AAC3C,OAAO,SAAS,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"Checkbox.d.ts","sourceRoot":"","sources":["../../../src/components/Input/Checkbox.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAsB,MAAM,OAAO,CAAC;AAC3C,OAAO,SAAS,MAAM,YAAY,CAAC;AA8GnC,KAAK,aAAa,GAAG,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,gBAAgB,CAAC,EAAE,IAAI,CAAC,GAC9D,SAAS,CAAC,UAAU,CAAC,OAAO,QAAQ,CAAC,SAAS,CAAC,CAAC;AAEpD,iBAAwB,QAAQ,CAAC,KAAK,EAAE,aAAa,oDAwBpD;kBAxBuB,QAAQ;;QA2B5B,0BAA0B;;QAE1B,6CAA6C;;;;;;;;eA7BzB,QAAQ"}
|