@launchpad-ui/drawer 0.1.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 ADDED
@@ -0,0 +1,14 @@
1
+ # @launchpad-ui/drawer
2
+
3
+ > A partial overlay that appears from the right side of the screen.
4
+
5
+ [![See it on NPM!](https://img.shields.io/npm/v/@launchpad-ui/drawer?style=for-the-badge)](https://www.npmjs.com/package/@launchpad-ui/drawer)
6
+ [![How big is this package in your project?](https://img.shields.io/bundlephobia/minzip/@launchpad-ui/drawer?style=for-the-badge)](https://bundlephobia.com/result?p=@launchpad-ui/drawer)
7
+
8
+ ## Installation
9
+
10
+ ```sh
11
+ $ yarn add @launchpad-ui/drawer
12
+ # or
13
+ $ npm install @launchpad-ui/drawer
14
+ ```
@@ -0,0 +1,12 @@
1
+ import type { ReactNode } from 'react';
2
+ declare type DrawerProps = {
3
+ children?: ReactNode;
4
+ className?: string;
5
+ onCancel?(): void;
6
+ 'data-test-id'?: string;
7
+ size?: 'small' | 'medium' | 'large' | 'xLarge' | 'full';
8
+ };
9
+ declare const Drawer: ({ className, children, onCancel, size, "data-test-id": testId, }: DrawerProps) => JSX.Element;
10
+ export { Drawer };
11
+ export type { DrawerProps };
12
+ //# sourceMappingURL=Drawer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Drawer.d.ts","sourceRoot":"","sources":["../src/Drawer.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAc,SAAS,EAAE,MAAM,OAAO,CAAC;AAoCnD,aAAK,WAAW,GAAG;IACjB,QAAQ,CAAC,EAAE,SAAS,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,QAAQ,CAAC,IAAI,IAAI,CAAC;IAClB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,IAAI,CAAC,EAAE,OAAO,GAAG,QAAQ,GAAG,OAAO,GAAG,QAAQ,GAAG,MAAM,CAAC;CACzD,CAAC;AAEF,QAAA,MAAM,MAAM,qEAMT,WAAW,gBA6Eb,CAAC;AAEF,OAAO,EAAE,MAAM,EAAE,CAAC;AAClB,YAAY,EAAE,WAAW,EAAE,CAAC"}
@@ -0,0 +1,12 @@
1
+ import type { HTMLAttributes } from 'react';
2
+ declare type DrawerHeaderProps = HTMLAttributes<HTMLDivElement> & {
3
+ closeable?: boolean;
4
+ titleID?: string;
5
+ titleClassName?: string;
6
+ onClose?(): void;
7
+ 'data-test-id'?: string;
8
+ };
9
+ declare const DrawerHeader: ({ className, children, titleID, titleClassName, "data-test-id": testId, ...rest }: DrawerHeaderProps) => JSX.Element;
10
+ export { DrawerHeader };
11
+ export type { DrawerHeaderProps };
12
+ //# sourceMappingURL=DrawerHeader.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"DrawerHeader.d.ts","sourceRoot":"","sources":["../src/DrawerHeader.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,OAAO,CAAC;AAI5C,aAAK,iBAAiB,GAAG,cAAc,CAAC,cAAc,CAAC,GAAG;IACxD,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,OAAO,CAAC,IAAI,IAAI,CAAC;IACjB,cAAc,CAAC,EAAE,MAAM,CAAC;CACzB,CAAC;AAEF,QAAA,MAAM,YAAY,sFAOf,iBAAiB,gBAQnB,CAAC;AAEF,OAAO,EAAE,YAAY,EAAE,CAAC;AACxB,YAAY,EAAE,iBAAiB,EAAE,CAAC"}
@@ -0,0 +1,12 @@
1
+ import type { HTMLAttributes } from 'react';
2
+ declare type DrawerPortalProps = HTMLAttributes<HTMLDivElement> & {
3
+ container?: HTMLElement | null;
4
+ 'data-test-id'?: string;
5
+ };
6
+ declare const DrawerPortal: import("react").ForwardRefExoticComponent<HTMLAttributes<HTMLDivElement> & {
7
+ container?: HTMLElement | null | undefined;
8
+ 'data-test-id'?: string | undefined;
9
+ } & import("react").RefAttributes<HTMLDivElement>>;
10
+ export { DrawerPortal };
11
+ export type { DrawerPortalProps };
12
+ //# sourceMappingURL=DrawerPortal.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"DrawerPortal.d.ts","sourceRoot":"","sources":["../src/DrawerPortal.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,OAAO,CAAC;AAK5C,aAAK,iBAAiB,GAAG,cAAc,CAAC,cAAc,CAAC,GAAG;IACxD,SAAS,CAAC,EAAE,WAAW,GAAG,IAAI,CAAC;IAC/B,cAAc,CAAC,EAAE,MAAM,CAAC;CACzB,CAAC;AAEF,QAAA,MAAM,YAAY;;;kDAejB,CAAC;AAIF,OAAO,EAAE,YAAY,EAAE,CAAC;AACxB,YAAY,EAAE,iBAAiB,EAAE,CAAC"}
@@ -0,0 +1,2 @@
1
+ export declare const DRAWER_LABELLED_BY = "drawer-title";
2
+ //# sourceMappingURL=constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../src/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,kBAAkB,iBAAiB,CAAC"}
@@ -0,0 +1,5 @@
1
+ export type { DrawerProps } from './Drawer';
2
+ export { Drawer } from './Drawer';
3
+ export type { DrawerHeaderProps } from './DrawerHeader';
4
+ export { DrawerHeader } from './DrawerHeader';
5
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,YAAY,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AAC5C,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAC;AAClC,YAAY,EAAE,iBAAiB,EAAE,MAAM,gBAAgB,CAAC;AACxD,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC"}
@@ -0,0 +1,186 @@
1
+ import './style.css';
2
+ import { IconButton } from "@launchpad-ui/button";
3
+ import { FocusTrap } from "@launchpad-ui/focus-trap";
4
+ import { Close } from "@launchpad-ui/icons";
5
+ import { Progress } from "@launchpad-ui/progress";
6
+ import { usePreventScroll } from "@react-aria/overlays";
7
+ import { cx } from "classix";
8
+ import { LazyMotion, m } from "framer-motion";
9
+ import { forwardRef, useState, useEffect, useRef, Suspense } from "react";
10
+ import { createPortal } from "react-dom";
11
+ import { jsx, jsxs } from "react/jsx-runtime";
12
+ const DrawerPortal = forwardRef(({
13
+ container = ((_a) => (_a = globalThis == null ? void 0 : globalThis.document) == null ? void 0 : _a.body)(),
14
+ "data-test-id": testId = "drawer-portal",
15
+ ...props
16
+ }, ref) => {
17
+ const [mounted, setMounted] = useState(false);
18
+ useEffect(() => {
19
+ setMounted(true);
20
+ }, []);
21
+ return mounted && container ? createPortal(/* @__PURE__ */ jsx("div", {
22
+ ...props,
23
+ ref,
24
+ "data-test-id": testId
25
+ }), container) : null;
26
+ });
27
+ DrawerPortal.displayName = "DrawerPortal";
28
+ const DRAWER_LABELLED_BY = "drawer-title";
29
+ const drawer = "_drawer_1ha46_17";
30
+ const overlay$1 = "_overlay_1ha46_27";
31
+ const content = "_content_1ha46_36";
32
+ const small = "_small_1ha46_49";
33
+ const medium = "_medium_1ha46_53";
34
+ const large = "_large_1ha46_57";
35
+ const xLarge = "_xLarge_1ha46_61";
36
+ const full = "_full_1ha46_65";
37
+ const closeButton = "_closeButton_1ha46_79";
38
+ const styles = {
39
+ drawer,
40
+ overlay: overlay$1,
41
+ content,
42
+ small,
43
+ medium,
44
+ large,
45
+ xLarge,
46
+ full,
47
+ closeButton
48
+ };
49
+ const overlay = {
50
+ visible: {
51
+ opacity: 1,
52
+ transition: {
53
+ duration: 0.15
54
+ }
55
+ },
56
+ hidden: {
57
+ opacity: 0
58
+ }
59
+ };
60
+ const slideRight = {
61
+ hidden: {
62
+ opacity: 0,
63
+ x: "25%"
64
+ },
65
+ visible: {
66
+ opacity: 1,
67
+ x: "0%",
68
+ transition: {
69
+ type: "spring",
70
+ delay: 0.15,
71
+ duration: 0.2,
72
+ bounce: 0
73
+ }
74
+ }
75
+ };
76
+ const loadFeatures = () => import(
77
+ /* webpackChunkName: "lp-drawer-framer-features" */
78
+ /* webpackExports: "domAnimation" */
79
+ "framer-motion"
80
+ ).then((res) => res.domAnimation);
81
+ const Drawer = ({
82
+ className,
83
+ children,
84
+ onCancel,
85
+ size = "small",
86
+ "data-test-id": testId = "drawer"
87
+ }) => {
88
+ const ref = useRef(null);
89
+ usePreventScroll();
90
+ useEffect(() => {
91
+ const handleEscape = (event) => {
92
+ event.stopImmediatePropagation();
93
+ const latest = [...document.querySelectorAll("[data-drawer]")].pop();
94
+ if (event.key === "Escape" && latest === ref.current) {
95
+ close();
96
+ }
97
+ };
98
+ const close = () => {
99
+ onCancel == null ? void 0 : onCancel();
100
+ };
101
+ document.body.classList.add("has-overlay");
102
+ document.addEventListener("keydown", handleEscape);
103
+ return () => {
104
+ document.body.classList.remove("has-overlay");
105
+ document.removeEventListener("keydown", handleEscape);
106
+ };
107
+ }, [onCancel, testId]);
108
+ const handleOverlayClick = (event) => {
109
+ if (event.target === event.currentTarget) {
110
+ onCancel && onCancel();
111
+ }
112
+ };
113
+ return /* @__PURE__ */ jsx(DrawerPortal, {
114
+ children: /* @__PURE__ */ jsx(LazyMotion, {
115
+ strict: true,
116
+ features: loadFeatures,
117
+ children: /* @__PURE__ */ jsx("div", {
118
+ className: cx(styles.drawer, styles[size], className),
119
+ "data-drawer": true,
120
+ "data-test-id": testId,
121
+ ref,
122
+ children: /* @__PURE__ */ jsx(m.div, {
123
+ initial: "hidden",
124
+ animate: "visible",
125
+ variants: overlay,
126
+ transition: {
127
+ duration: 0.15
128
+ },
129
+ role: "presentation",
130
+ className: styles.overlay,
131
+ onMouseDown: handleOverlayClick,
132
+ children: /* @__PURE__ */ jsx(FocusTrap, {
133
+ autoFocus: true,
134
+ restoreFocus: true,
135
+ children: /* @__PURE__ */ jsxs(m.div, {
136
+ initial: "hidden",
137
+ animate: "visible",
138
+ variants: slideRight,
139
+ role: "dialog",
140
+ "aria-labelledby": DRAWER_LABELLED_BY,
141
+ "aria-modal": true,
142
+ className: styles.content,
143
+ tabIndex: -1,
144
+ children: [/* @__PURE__ */ jsx(IconButton, {
145
+ "aria-label": "close",
146
+ icon: /* @__PURE__ */ jsx(Close, {
147
+ size: "medium"
148
+ }),
149
+ className: styles.closeButton,
150
+ onClick: onCancel,
151
+ "data-test-id": "drawer-close-button"
152
+ }), /* @__PURE__ */ jsx(Suspense, {
153
+ fallback: /* @__PURE__ */ jsx(Progress, {}),
154
+ children
155
+ })]
156
+ })
157
+ })
158
+ })
159
+ })
160
+ })
161
+ });
162
+ };
163
+ const DrawerHeader = ({
164
+ className,
165
+ children,
166
+ titleID,
167
+ titleClassName,
168
+ "data-test-id": testId = "drawer-header",
169
+ ...rest
170
+ }) => {
171
+ return /* @__PURE__ */ jsx("div", {
172
+ "data-test-id": testId,
173
+ className,
174
+ ...rest,
175
+ children: /* @__PURE__ */ jsx("h2", {
176
+ id: DRAWER_LABELLED_BY,
177
+ className: titleClassName,
178
+ children
179
+ })
180
+ });
181
+ };
182
+ export {
183
+ Drawer,
184
+ DrawerHeader
185
+ };
186
+ //# sourceMappingURL=index.es.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.es.js","sources":["../src/DrawerPortal.tsx","../src/constants.ts","../src/Drawer.tsx","../src/DrawerHeader.tsx"],"sourcesContent":["import type { HTMLAttributes } from 'react';\n\nimport { forwardRef, useEffect, useState } from 'react';\nimport { createPortal } from 'react-dom';\n\ntype DrawerPortalProps = HTMLAttributes<HTMLDivElement> & {\n container?: HTMLElement | null;\n 'data-test-id'?: string;\n};\n\nconst DrawerPortal = forwardRef<HTMLDivElement, DrawerPortalProps>(\n (\n { container = globalThis?.document?.body, 'data-test-id': testId = 'drawer-portal', ...props },\n ref\n ) => {\n const [mounted, setMounted] = useState(false);\n\n useEffect(() => {\n setMounted(true);\n }, []);\n\n return mounted && container\n ? createPortal(<div {...props} ref={ref} data-test-id={testId} />, container)\n : null;\n }\n);\n\nDrawerPortal.displayName = 'DrawerPortal';\n\nexport { DrawerPortal };\nexport type { DrawerPortalProps };\n","export const DRAWER_LABELLED_BY = 'drawer-title';\n","import type { Variants } from 'framer-motion';\nimport type { MouseEvent, ReactNode } from 'react';\n\nimport { IconButton } from '@launchpad-ui/button';\nimport { FocusTrap } from '@launchpad-ui/focus-trap';\nimport { Close } from '@launchpad-ui/icons';\nimport { Progress } from '@launchpad-ui/progress';\nimport { usePreventScroll } from '@react-aria/overlays';\nimport { cx } from 'classix';\nimport { LazyMotion, m } from 'framer-motion';\nimport { Suspense, useEffect, useRef } from 'react';\n\nimport { DrawerPortal } from './DrawerPortal';\nimport { DRAWER_LABELLED_BY } from './constants';\nimport styles from './styles/Drawer.module.css';\n\nconst overlay: Variants = {\n visible: { opacity: 1, transition: { duration: 0.15 } },\n hidden: { opacity: 0 },\n};\n\nconst slideRight: Variants = {\n hidden: { opacity: 0, x: '25%' },\n visible: {\n opacity: 1,\n x: '0%',\n transition: { type: 'spring', delay: 0.15, duration: 0.2, bounce: 0 },\n },\n};\n\nconst loadFeatures = () =>\n import(\n /* webpackChunkName: \"lp-drawer-framer-features\" */\n /* webpackExports: \"domAnimation\" */\n 'framer-motion'\n ).then((res) => res.domAnimation);\n\ntype DrawerProps = {\n children?: ReactNode;\n className?: string;\n onCancel?(): void;\n 'data-test-id'?: string;\n size?: 'small' | 'medium' | 'large' | 'xLarge' | 'full';\n};\n\nconst Drawer = ({\n className,\n children,\n onCancel,\n size = 'small',\n 'data-test-id': testId = 'drawer',\n}: DrawerProps) => {\n const ref = useRef<HTMLDivElement>(null);\n\n usePreventScroll();\n\n useEffect(() => {\n const handleEscape = (event: KeyboardEvent) => {\n event.stopImmediatePropagation();\n const latest = [...document.querySelectorAll('[data-drawer]')].pop();\n if (event.key === 'Escape' && latest === ref.current) {\n close();\n }\n };\n\n const close = () => {\n onCancel?.();\n };\n\n document.body.classList.add('has-overlay');\n document.addEventListener('keydown', handleEscape);\n\n return () => {\n document.body.classList.remove('has-overlay');\n document.removeEventListener('keydown', handleEscape);\n };\n }, [onCancel, testId]);\n\n const handleOverlayClick = (event: MouseEvent<HTMLDivElement>) => {\n if (event.target === event.currentTarget) {\n onCancel && onCancel();\n }\n };\n\n return (\n <DrawerPortal>\n <LazyMotion strict features={loadFeatures}>\n <div\n className={cx(styles.drawer, styles[size], className)}\n data-drawer\n data-test-id={testId}\n ref={ref}\n >\n <m.div\n initial=\"hidden\"\n animate=\"visible\"\n variants={overlay}\n transition={{ duration: 0.15 }}\n role=\"presentation\"\n className={styles.overlay}\n onMouseDown={handleOverlayClick}\n >\n <FocusTrap autoFocus restoreFocus>\n <m.div\n initial=\"hidden\"\n animate=\"visible\"\n variants={slideRight}\n role=\"dialog\"\n aria-labelledby={DRAWER_LABELLED_BY}\n aria-modal\n className={styles.content}\n tabIndex={-1}\n >\n <IconButton\n aria-label=\"close\"\n icon={<Close size=\"medium\" />}\n className={styles.closeButton}\n onClick={onCancel}\n data-test-id=\"drawer-close-button\"\n />\n <Suspense fallback={<Progress />}>{children}</Suspense>\n </m.div>\n </FocusTrap>\n </m.div>\n </div>\n </LazyMotion>\n </DrawerPortal>\n );\n};\n\nexport { Drawer };\nexport type { DrawerProps };\n","import type { HTMLAttributes } from 'react';\n\nimport { DRAWER_LABELLED_BY } from './constants';\n\ntype DrawerHeaderProps = HTMLAttributes<HTMLDivElement> & {\n closeable?: boolean;\n titleID?: string;\n titleClassName?: string;\n onClose?(): void;\n 'data-test-id'?: string;\n};\n\nconst DrawerHeader = ({\n className,\n children,\n titleID,\n titleClassName,\n 'data-test-id': testId = 'drawer-header',\n ...rest\n}: DrawerHeaderProps) => {\n return (\n <div data-test-id={testId} className={className} {...rest}>\n <h2 id={DRAWER_LABELLED_BY} className={titleClassName}>\n {children}\n </h2>\n </div>\n );\n};\n\nexport { DrawerHeader };\nexport type { DrawerHeaderProps };\n"],"names":["DrawerPortal","forwardRef","container","globalThis","document","body","testId","props","ref","mounted","setMounted","useState","useEffect","createPortal","_jsx","displayName","overlay","visible","opacity","transition","duration","hidden","slideRight","x","type","delay","bounce","loadFeatures","then","res","domAnimation","Drawer","className","children","onCancel","size","useRef","handleEscape","event","stopImmediatePropagation","latest","querySelectorAll","pop","key","current","close","classList","add","addEventListener","remove","removeEventListener","handleOverlayClick","target","currentTarget","cx","styles","drawer","_jsxs","DRAWER_LABELLED_BY","content","closeButton","DrawerHeader","titleID","titleClassName","rest"],"mappings":"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"}
package/dist/index.js ADDED
@@ -0,0 +1,202 @@
1
+ require('./style.css');
2
+ "use strict";
3
+ Object.defineProperties(exports, { __esModule: { value: true }, [Symbol.toStringTag]: { value: "Module" } });
4
+ const button = require("@launchpad-ui/button");
5
+ const focusTrap = require("@launchpad-ui/focus-trap");
6
+ const icons = require("@launchpad-ui/icons");
7
+ const progress = require("@launchpad-ui/progress");
8
+ const overlays = require("@react-aria/overlays");
9
+ const classix = require("classix");
10
+ const framerMotion = require("framer-motion");
11
+ const react = require("react");
12
+ const reactDom = require("react-dom");
13
+ const jsxRuntime = require("react/jsx-runtime");
14
+ function _interopNamespace(e) {
15
+ if (e && e.__esModule)
16
+ return e;
17
+ const n = Object.create(null, { [Symbol.toStringTag]: { value: "Module" } });
18
+ if (e) {
19
+ for (const k in e) {
20
+ if (k !== "default") {
21
+ const d = Object.getOwnPropertyDescriptor(e, k);
22
+ Object.defineProperty(n, k, d.get ? d : {
23
+ enumerable: true,
24
+ get: () => e[k]
25
+ });
26
+ }
27
+ }
28
+ }
29
+ n.default = e;
30
+ return Object.freeze(n);
31
+ }
32
+ const DrawerPortal = react.forwardRef(({
33
+ container = ((_a) => (_a = globalThis == null ? void 0 : globalThis.document) == null ? void 0 : _a.body)(),
34
+ "data-test-id": testId = "drawer-portal",
35
+ ...props
36
+ }, ref) => {
37
+ const [mounted, setMounted] = react.useState(false);
38
+ react.useEffect(() => {
39
+ setMounted(true);
40
+ }, []);
41
+ return mounted && container ? reactDom.createPortal(/* @__PURE__ */ jsxRuntime.jsx("div", {
42
+ ...props,
43
+ ref,
44
+ "data-test-id": testId
45
+ }), container) : null;
46
+ });
47
+ DrawerPortal.displayName = "DrawerPortal";
48
+ const DRAWER_LABELLED_BY = "drawer-title";
49
+ const drawer = "_drawer_1ha46_17";
50
+ const overlay$1 = "_overlay_1ha46_27";
51
+ const content = "_content_1ha46_36";
52
+ const small = "_small_1ha46_49";
53
+ const medium = "_medium_1ha46_53";
54
+ const large = "_large_1ha46_57";
55
+ const xLarge = "_xLarge_1ha46_61";
56
+ const full = "_full_1ha46_65";
57
+ const closeButton = "_closeButton_1ha46_79";
58
+ const styles = {
59
+ drawer,
60
+ overlay: overlay$1,
61
+ content,
62
+ small,
63
+ medium,
64
+ large,
65
+ xLarge,
66
+ full,
67
+ closeButton
68
+ };
69
+ const overlay = {
70
+ visible: {
71
+ opacity: 1,
72
+ transition: {
73
+ duration: 0.15
74
+ }
75
+ },
76
+ hidden: {
77
+ opacity: 0
78
+ }
79
+ };
80
+ const slideRight = {
81
+ hidden: {
82
+ opacity: 0,
83
+ x: "25%"
84
+ },
85
+ visible: {
86
+ opacity: 1,
87
+ x: "0%",
88
+ transition: {
89
+ type: "spring",
90
+ delay: 0.15,
91
+ duration: 0.2,
92
+ bounce: 0
93
+ }
94
+ }
95
+ };
96
+ const loadFeatures = () => Promise.resolve().then(() => /* @__PURE__ */ _interopNamespace(require(
97
+ "framer-motion"
98
+ ))).then((res) => res.domAnimation);
99
+ const Drawer = ({
100
+ className,
101
+ children,
102
+ onCancel,
103
+ size = "small",
104
+ "data-test-id": testId = "drawer"
105
+ }) => {
106
+ const ref = react.useRef(null);
107
+ overlays.usePreventScroll();
108
+ react.useEffect(() => {
109
+ const handleEscape = (event) => {
110
+ event.stopImmediatePropagation();
111
+ const latest = [...document.querySelectorAll("[data-drawer]")].pop();
112
+ if (event.key === "Escape" && latest === ref.current) {
113
+ close();
114
+ }
115
+ };
116
+ const close = () => {
117
+ onCancel == null ? void 0 : onCancel();
118
+ };
119
+ document.body.classList.add("has-overlay");
120
+ document.addEventListener("keydown", handleEscape);
121
+ return () => {
122
+ document.body.classList.remove("has-overlay");
123
+ document.removeEventListener("keydown", handleEscape);
124
+ };
125
+ }, [onCancel, testId]);
126
+ const handleOverlayClick = (event) => {
127
+ if (event.target === event.currentTarget) {
128
+ onCancel && onCancel();
129
+ }
130
+ };
131
+ return /* @__PURE__ */ jsxRuntime.jsx(DrawerPortal, {
132
+ children: /* @__PURE__ */ jsxRuntime.jsx(framerMotion.LazyMotion, {
133
+ strict: true,
134
+ features: loadFeatures,
135
+ children: /* @__PURE__ */ jsxRuntime.jsx("div", {
136
+ className: classix.cx(styles.drawer, styles[size], className),
137
+ "data-drawer": true,
138
+ "data-test-id": testId,
139
+ ref,
140
+ children: /* @__PURE__ */ jsxRuntime.jsx(framerMotion.m.div, {
141
+ initial: "hidden",
142
+ animate: "visible",
143
+ variants: overlay,
144
+ transition: {
145
+ duration: 0.15
146
+ },
147
+ role: "presentation",
148
+ className: styles.overlay,
149
+ onMouseDown: handleOverlayClick,
150
+ children: /* @__PURE__ */ jsxRuntime.jsx(focusTrap.FocusTrap, {
151
+ autoFocus: true,
152
+ restoreFocus: true,
153
+ children: /* @__PURE__ */ jsxRuntime.jsxs(framerMotion.m.div, {
154
+ initial: "hidden",
155
+ animate: "visible",
156
+ variants: slideRight,
157
+ role: "dialog",
158
+ "aria-labelledby": DRAWER_LABELLED_BY,
159
+ "aria-modal": true,
160
+ className: styles.content,
161
+ tabIndex: -1,
162
+ children: [/* @__PURE__ */ jsxRuntime.jsx(button.IconButton, {
163
+ "aria-label": "close",
164
+ icon: /* @__PURE__ */ jsxRuntime.jsx(icons.Close, {
165
+ size: "medium"
166
+ }),
167
+ className: styles.closeButton,
168
+ onClick: onCancel,
169
+ "data-test-id": "drawer-close-button"
170
+ }), /* @__PURE__ */ jsxRuntime.jsx(react.Suspense, {
171
+ fallback: /* @__PURE__ */ jsxRuntime.jsx(progress.Progress, {}),
172
+ children
173
+ })]
174
+ })
175
+ })
176
+ })
177
+ })
178
+ })
179
+ });
180
+ };
181
+ const DrawerHeader = ({
182
+ className,
183
+ children,
184
+ titleID,
185
+ titleClassName,
186
+ "data-test-id": testId = "drawer-header",
187
+ ...rest
188
+ }) => {
189
+ return /* @__PURE__ */ jsxRuntime.jsx("div", {
190
+ "data-test-id": testId,
191
+ className,
192
+ ...rest,
193
+ children: /* @__PURE__ */ jsxRuntime.jsx("h2", {
194
+ id: DRAWER_LABELLED_BY,
195
+ className: titleClassName,
196
+ children
197
+ })
198
+ });
199
+ };
200
+ exports.Drawer = Drawer;
201
+ exports.DrawerHeader = DrawerHeader;
202
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sources":["../src/DrawerPortal.tsx","../src/constants.ts","../src/Drawer.tsx","../src/DrawerHeader.tsx"],"sourcesContent":["import type { HTMLAttributes } from 'react';\n\nimport { forwardRef, useEffect, useState } from 'react';\nimport { createPortal } from 'react-dom';\n\ntype DrawerPortalProps = HTMLAttributes<HTMLDivElement> & {\n container?: HTMLElement | null;\n 'data-test-id'?: string;\n};\n\nconst DrawerPortal = forwardRef<HTMLDivElement, DrawerPortalProps>(\n (\n { container = globalThis?.document?.body, 'data-test-id': testId = 'drawer-portal', ...props },\n ref\n ) => {\n const [mounted, setMounted] = useState(false);\n\n useEffect(() => {\n setMounted(true);\n }, []);\n\n return mounted && container\n ? createPortal(<div {...props} ref={ref} data-test-id={testId} />, container)\n : null;\n }\n);\n\nDrawerPortal.displayName = 'DrawerPortal';\n\nexport { DrawerPortal };\nexport type { DrawerPortalProps };\n","export const DRAWER_LABELLED_BY = 'drawer-title';\n","import type { Variants } from 'framer-motion';\nimport type { MouseEvent, ReactNode } from 'react';\n\nimport { IconButton } from '@launchpad-ui/button';\nimport { FocusTrap } from '@launchpad-ui/focus-trap';\nimport { Close } from '@launchpad-ui/icons';\nimport { Progress } from '@launchpad-ui/progress';\nimport { usePreventScroll } from '@react-aria/overlays';\nimport { cx } from 'classix';\nimport { LazyMotion, m } from 'framer-motion';\nimport { Suspense, useEffect, useRef } from 'react';\n\nimport { DrawerPortal } from './DrawerPortal';\nimport { DRAWER_LABELLED_BY } from './constants';\nimport styles from './styles/Drawer.module.css';\n\nconst overlay: Variants = {\n visible: { opacity: 1, transition: { duration: 0.15 } },\n hidden: { opacity: 0 },\n};\n\nconst slideRight: Variants = {\n hidden: { opacity: 0, x: '25%' },\n visible: {\n opacity: 1,\n x: '0%',\n transition: { type: 'spring', delay: 0.15, duration: 0.2, bounce: 0 },\n },\n};\n\nconst loadFeatures = () =>\n import(\n /* webpackChunkName: \"lp-drawer-framer-features\" */\n /* webpackExports: \"domAnimation\" */\n 'framer-motion'\n ).then((res) => res.domAnimation);\n\ntype DrawerProps = {\n children?: ReactNode;\n className?: string;\n onCancel?(): void;\n 'data-test-id'?: string;\n size?: 'small' | 'medium' | 'large' | 'xLarge' | 'full';\n};\n\nconst Drawer = ({\n className,\n children,\n onCancel,\n size = 'small',\n 'data-test-id': testId = 'drawer',\n}: DrawerProps) => {\n const ref = useRef<HTMLDivElement>(null);\n\n usePreventScroll();\n\n useEffect(() => {\n const handleEscape = (event: KeyboardEvent) => {\n event.stopImmediatePropagation();\n const latest = [...document.querySelectorAll('[data-drawer]')].pop();\n if (event.key === 'Escape' && latest === ref.current) {\n close();\n }\n };\n\n const close = () => {\n onCancel?.();\n };\n\n document.body.classList.add('has-overlay');\n document.addEventListener('keydown', handleEscape);\n\n return () => {\n document.body.classList.remove('has-overlay');\n document.removeEventListener('keydown', handleEscape);\n };\n }, [onCancel, testId]);\n\n const handleOverlayClick = (event: MouseEvent<HTMLDivElement>) => {\n if (event.target === event.currentTarget) {\n onCancel && onCancel();\n }\n };\n\n return (\n <DrawerPortal>\n <LazyMotion strict features={loadFeatures}>\n <div\n className={cx(styles.drawer, styles[size], className)}\n data-drawer\n data-test-id={testId}\n ref={ref}\n >\n <m.div\n initial=\"hidden\"\n animate=\"visible\"\n variants={overlay}\n transition={{ duration: 0.15 }}\n role=\"presentation\"\n className={styles.overlay}\n onMouseDown={handleOverlayClick}\n >\n <FocusTrap autoFocus restoreFocus>\n <m.div\n initial=\"hidden\"\n animate=\"visible\"\n variants={slideRight}\n role=\"dialog\"\n aria-labelledby={DRAWER_LABELLED_BY}\n aria-modal\n className={styles.content}\n tabIndex={-1}\n >\n <IconButton\n aria-label=\"close\"\n icon={<Close size=\"medium\" />}\n className={styles.closeButton}\n onClick={onCancel}\n data-test-id=\"drawer-close-button\"\n />\n <Suspense fallback={<Progress />}>{children}</Suspense>\n </m.div>\n </FocusTrap>\n </m.div>\n </div>\n </LazyMotion>\n </DrawerPortal>\n );\n};\n\nexport { Drawer };\nexport type { DrawerProps };\n","import type { HTMLAttributes } from 'react';\n\nimport { DRAWER_LABELLED_BY } from './constants';\n\ntype DrawerHeaderProps = HTMLAttributes<HTMLDivElement> & {\n closeable?: boolean;\n titleID?: string;\n titleClassName?: string;\n onClose?(): void;\n 'data-test-id'?: string;\n};\n\nconst DrawerHeader = ({\n className,\n children,\n titleID,\n titleClassName,\n 'data-test-id': testId = 'drawer-header',\n ...rest\n}: DrawerHeaderProps) => {\n return (\n <div data-test-id={testId} className={className} {...rest}>\n <h2 id={DRAWER_LABELLED_BY} className={titleClassName}>\n {children}\n </h2>\n </div>\n );\n};\n\nexport { DrawerHeader };\nexport type { DrawerHeaderProps };\n"],"names":["DrawerPortal","forwardRef","container","globalThis","document","body","testId","props","ref","mounted","setMounted","useState","useEffect","createPortal","_jsx","displayName","overlay","visible","opacity","transition","duration","hidden","slideRight","x","type","delay","bounce","loadFeatures","then","res","domAnimation","Drawer","className","children","onCancel","size","useRef","usePreventScroll","handleEscape","event","stopImmediatePropagation","latest","querySelectorAll","pop","key","current","close","classList","add","addEventListener","remove","removeEventListener","handleOverlayClick","target","currentTarget","LazyMotion","cx","styles","drawer","m","FocusTrap","_jsxs","DRAWER_LABELLED_BY","content","IconButton","Close","closeButton","Suspense","Progress","DrawerHeader","titleID","titleClassName","rest"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAUA,MAAMA,eAAeC,iBACnB,CACE;AAAA,EAAEC,aAAYC,uDAAYC,aAAZD,mBAAsBE;AAAAA,EAAM,gBAAgBC,SAAS;AAAA,KAAoBC;AAAM,GAC7FC,QACG;AACH,QAAM,CAACC,SAASC,UAAU,IAAIC,eAAS,KAAK;AAE5CC,QAAAA,UAAU,MAAM;AACdF,eAAW,IAAI;AAAA,EACjB,GAAG,CAAE,CAAA;AAEL,SAAOD,WAAWP,YACdW,sBAAaC,2BAAAA,IAAA,OAAA;AAAA,IAAA,GAASP;AAAAA,IAAO;AAAA,IAAU,gBAAcD;AAAAA,EAAAA,CAAO,GAAKJ,SAAS,IAC1E;AACN,CAAC;AAGHF,aAAae,cAAc;AC3BpB,MAAM,qBAAqB;;;;;;;;;;;;;;;;;;;;;ACgBlC,MAAMC,UAAoB;AAAA,EACxBC,SAAS;AAAA,IAAEC,SAAS;AAAA,IAAGC,YAAY;AAAA,MAAEC,UAAU;AAAA,IAAK;AAAA,EAAE;AAAA,EACtDC,QAAQ;AAAA,IAAEH,SAAS;AAAA,EAAE;AACvB;AAEA,MAAMI,aAAuB;AAAA,EAC3BD,QAAQ;AAAA,IAAEH,SAAS;AAAA,IAAGK,GAAG;AAAA,EAAM;AAAA,EAC/BN,SAAS;AAAA,IACPC,SAAS;AAAA,IACTK,GAAG;AAAA,IACHJ,YAAY;AAAA,MAAEK,MAAM;AAAA,MAAUC,OAAO;AAAA,MAAML,UAAU;AAAA,MAAKM,QAAQ;AAAA,IAAE;AAAA,EACtE;AACF;AAEA,MAAMC,eAAe,MACnB,QAAA,QAAA,EAAA,KAAA,MAAA,kCAAA;AAAA,EAGE;AAAA,CACAC,CAAAA,EAAAA,KAAMC,CAAQA,QAAAA,IAAIC,YAAY;AAUlC,MAAMC,SAAS,CAAC;AAAA,EACdC;AAAAA,EACAC;AAAAA,EACAC;AAAAA,EACAC,OAAO;AAAA,EACP,gBAAgB7B,SAAS;AACd,MAAM;AACXE,QAAAA,MAAM4B,aAAuB,IAAI;AAErBC,WAAAA;AAElBzB,QAAAA,UAAU,MAAM;AACR0B,UAAAA,eAAe,CAACC,UAAyB;AAC7CA,YAAMC,yBAA0B;AAC1BC,YAAAA,SAAS,CAAC,GAAGrC,SAASsC,iBAAiB,eAAe,CAAC,EAAEC;AAC/D,UAAIJ,MAAMK,QAAQ,YAAYH,WAAWjC,IAAIqC,SAAS;AAC7C;MACT;AAAA,IAAA;AAGF,UAAMC,QAAQ,MAAM;AACN;AAAA,IAAA;AAGLzC,aAAAA,KAAK0C,UAAUC,IAAI,aAAa;AAChCC,aAAAA,iBAAiB,WAAWX,YAAY;AAEjD,WAAO,MAAM;AACFjC,eAAAA,KAAK0C,UAAUG,OAAO,aAAa;AACnCC,eAAAA,oBAAoB,WAAWb,YAAY;AAAA,IAAA;AAAA,EACtD,GACC,CAACJ,UAAU5B,MAAM,CAAC;AAEf8C,QAAAA,qBAAqB,CAACb,UAAsC;AAC5DA,QAAAA,MAAMc,WAAWd,MAAMe,eAAe;AACxCpB,kBAAYA,SAAU;AAAA,IACxB;AAAA,EAAA;AAGF,wCACG,cAAY;AAAA,IAAA,yCACVqB,yBAAU;AAAA,MAAC,QAAM;AAAA,MAAC,UAAU5B;AAAAA,MAAa,yCACxC,OAAA;AAAA,QACE,WAAW6B,QAAGC,GAAAA,OAAOC,QAAQD,OAAOtB,OAAOH,SAAS;AAAA,QACpD,eAAW;AAAA,QACX,gBAAc1B;AAAAA,QACd;AAAA,QAAS,UAERQ,2BAAAA,IAAA6C,aAAA,EAAE,KAAG;AAAA,UACJ,SAAQ;AAAA,UACR,SAAQ;AAAA,UACR,UAAU3C;AAAAA,UACV,YAAY;AAAA,YAAEI,UAAU;AAAA,UAAK;AAAA,UAC7B,MAAK;AAAA,UACL,WAAWqC,OAAOzC;AAAAA,UAClB,aAAaoC;AAAAA,UAAmB,yCAE/BQ,qBAAS;AAAA,YAAC,WAAS;AAAA,YAAC,cAAY;AAAA,YAAA,UAC9BC,2BAAAA,KAAAF,aAAA,EAAE,KAAG;AAAA,cACJ,SAAQ;AAAA,cACR,SAAQ;AAAA,cACR,UAAUrC;AAAAA,cACV,MAAK;AAAA,cACL,mBAAiBwC;AAAAA,cACjB,cAAU;AAAA,cACV,WAAWL,OAAOM;AAAAA,cAClB,UAAU;AAAA,cAAG,UAAA,CAEbjD,2BAAA,IAACkD,mBAAU;AAAA,gBACT,cAAW;AAAA,gBACX,qCAAOC,aAAK;AAAA,kBAAC,MAAK;AAAA,gBAAA,CAAY;AAAA,gBAC9B,WAAWR,OAAOS;AAAAA,gBAClB,SAAShC;AAAAA,gBACT,gBAAa;AAAA,cAAA,CACb,GACFpB,2BAAA,IAACqD,gBAAQ;AAAA,gBAAC,UAAUrD,2BAAAA,IAACsD,SAAY,UAAA,EAAA;AAAA,gBAAA;AAAA,cAAA,CAAsB,CAAA;AAAA,YAAA,CAAA;AAAA,UAAA,CACjD;AAAA,QAAA,CACE;AAAA,MAAA,CACN;AAAA,IAAA,CACJ;AAAA,EAAA,CAEK;AAEnB;ACpHA,MAAMC,eAAe,CAAC;AAAA,EACpBrC;AAAAA,EACAC;AAAAA,EACAqC;AAAAA,EACAC;AAAAA,EACA,gBAAgBjE,SAAS;AAAA,KACtBkE;AACc,MAAM;AACvB,wCACE,OAAA;AAAA,IAAK,gBAAclE;AAAAA,IAAQ;AAAA,IAAqB,GAAKkE;AAAAA,IAAI,yCACvD,MAAA;AAAA,MAAI,IAAIV;AAAAA,MAAoB,WAAWS;AAAAA,MAAe;AAAA,IAAA,CAC3C;AAAA,EAAA,CAEP;AAEV;;;"}
package/dist/style.css ADDED
@@ -0,0 +1,74 @@
1
+ :root {
2
+ --page-gutter-width: 1rem;
3
+ }
4
+ @media screen and (min-width: 740px) {
5
+ :root {
6
+ --page-gutter-width: 4rem;
7
+ }
8
+ }
9
+ .has-overlay {
10
+ overflow: hidden;
11
+ }
12
+ ._drawer_1ha46_17 {
13
+ z-index: 10000;
14
+ position: fixed;
15
+ top: 0;
16
+ right: 0;
17
+ bottom: 0;
18
+ left: 0;
19
+ transform: translateZ(0);
20
+ }
21
+ ._overlay_1ha46_27 {
22
+ position: fixed;
23
+ top: 0;
24
+ right: 0;
25
+ bottom: 0;
26
+ left: 0;
27
+ background-color: hsla(0, 0%, 20%, 0.5);
28
+ }
29
+ ._content_1ha46_36 {
30
+ background-color: var(--lp-color-background);
31
+ position: absolute;
32
+ top: 0;
33
+ bottom: 0;
34
+ right: 0;
35
+ overflow: auto;
36
+ width: 100vw;
37
+ max-width: 100vw;
38
+ box-shadow: -1px 0 4px var(--lp-color-gray-700);
39
+ }
40
+ @media screen and (min-width: 740px) {
41
+ ._small_1ha46_49 ._content_1ha46_36 {
42
+ width: 45rem;
43
+ }
44
+
45
+ ._medium_1ha46_53 ._content_1ha46_36 {
46
+ width: 65rem;
47
+ }
48
+
49
+ ._large_1ha46_57 ._content_1ha46_36 {
50
+ width: 80rem;
51
+ }
52
+
53
+ ._xLarge_1ha46_61 ._content_1ha46_36 {
54
+ width: 120rem;
55
+ }
56
+
57
+ ._full_1ha46_65 ._content_1ha46_36 {
58
+ width: 100%;
59
+ max-width: none;
60
+ max-width: initial;
61
+ }
62
+ }
63
+ ._content_1ha46_36 section {
64
+ padding: 3.2rem 1rem;
65
+ padding: 3.2rem var(--page-gutter-width);
66
+ }
67
+ ._content_1ha46_36 section + section {
68
+ border-top: 1px dotted var(--lp-color-gray-100);
69
+ }
70
+ ._closeButton_1ha46_79 {
71
+ position: absolute;
72
+ right: 1rem;
73
+ top: 1rem;
74
+ }
package/package.json ADDED
@@ -0,0 +1,52 @@
1
+ {
2
+ "name": "@launchpad-ui/drawer",
3
+ "version": "0.1.0",
4
+ "status": "alpha",
5
+ "publishConfig": {
6
+ "access": "public"
7
+ },
8
+ "description": "A partial overlay that appears from the right side of the screen.",
9
+ "files": [
10
+ "dist"
11
+ ],
12
+ "main": "dist/index.js",
13
+ "module": "dist/index.es.js",
14
+ "types": "dist/index.d.ts",
15
+ "sideEffects": [
16
+ "**/*.css"
17
+ ],
18
+ "exports": {
19
+ ".": {
20
+ "types": "./dist/index.d.ts",
21
+ "import": "./dist/index.es.js",
22
+ "require": "./dist/index.js"
23
+ },
24
+ "./package.json": "./package.json",
25
+ "./style.css": "./dist/style.css"
26
+ },
27
+ "source": "src/index.ts",
28
+ "dependencies": {
29
+ "@launchpad-ui/button": "~0.7.5",
30
+ "@launchpad-ui/focus-trap": "~0.1.1",
31
+ "@launchpad-ui/icons": "~0.5.9",
32
+ "@launchpad-ui/progress": "~0.5.3",
33
+ "@launchpad-ui/tokens": "~0.2.0",
34
+ "@react-aria/overlays": "^3.11.0",
35
+ "classix": "^2.1.13",
36
+ "framer-motion": "^7.6.1"
37
+ },
38
+ "peerDependencies": {
39
+ "react": "^18.0.0",
40
+ "react-dom": "^18.0.0"
41
+ },
42
+ "devDependencies": {
43
+ "react": "^18.2.0",
44
+ "react-dom": "^18.2.0"
45
+ },
46
+ "scripts": {
47
+ "build": "vite build -c ../../vite.config.ts && tsc --project tsconfig.build.json",
48
+ "clean": "rm -rf dist",
49
+ "lint": "eslint '**/*.{ts,tsx,js}' && stylelint '**/*.css' --ignore-path ../../.stylelintignore",
50
+ "test": "vitest run --coverage"
51
+ }
52
+ }