@sproutsocial/seeds-react-drawer 1.2.10 → 2.2.7
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/drawer.css +248 -0
- package/dist/esm/index.js +599 -189
- package/dist/esm/index.js.map +1 -1
- package/dist/index.d.mts +109 -19
- package/dist/index.d.ts +109 -19
- package/dist/index.js +607 -191
- package/dist/index.js.map +1 -1
- package/package.json +24 -12
- package/.eslintignore +0 -6
- package/.eslintrc.js +0 -4
- package/.turbo/turbo-build.log +0 -21
- package/CHANGELOG.md +0 -343
- package/jest.config.js +0 -9
- package/src/Drawer.stories.tsx +0 -474
- package/src/Drawer.tsx +0 -291
- package/src/DrawerTypes.ts +0 -88
- package/src/__tests__/Drawer.test.tsx +0 -339
- package/src/__tests__/Drawer.typetest.tsx +0 -39
- package/src/index.ts +0 -5
- package/src/styles.ts +0 -35
- package/tsconfig.json +0 -15
- package/tsup.config.ts +0 -12
package/dist/drawer.css
ADDED
|
@@ -0,0 +1,248 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Seeds Drawer component classes.
|
|
3
|
+
* Component-scoped port of the styled-components shell in styles.ts. Used by
|
|
4
|
+
* DrawerTailwind.tsx on the Base UI primitives (Backdrop/Viewport/Popup).
|
|
5
|
+
*
|
|
6
|
+
* Requires @sproutsocial/seeds-react-theme/dist/theme-all.css imported for the
|
|
7
|
+
* CSS variable definitions (and dark mode support).
|
|
8
|
+
*
|
|
9
|
+
* Runtime numerics (z-index, and width/offset for side drawers) are applied as
|
|
10
|
+
* inline styles on the popup, not here. The Base-UI-injected custom properties
|
|
11
|
+
* (--drawer-snap-point-offset, --drawer-swipe-movement-y, --drawer-swipe-progress,
|
|
12
|
+
* --nested-drawers, --drawer-height, --drawer-frontmost-height) arrive on the
|
|
13
|
+
* popup at runtime and are read via var(...) below.
|
|
14
|
+
*
|
|
15
|
+
* All rules live in `@layer components` so Tailwind utilities (which the
|
|
16
|
+
* Storybook/racine setup registers in the canonical theme/base/components/
|
|
17
|
+
* utilities layer order) can override these component defaults. Unlayered
|
|
18
|
+
* rules would outrank any layered utility per the CSS cascade-layers spec,
|
|
19
|
+
* so utilities like `mx-200`/`p-300`/`inline-flex` passed via `className`
|
|
20
|
+
* would otherwise have no effect on the popup. Inline-styled geometry
|
|
21
|
+
* (width/offset/zIndex on the popup) is unaffected by layers and stays
|
|
22
|
+
* non-overridable by design.
|
|
23
|
+
*/
|
|
24
|
+
|
|
25
|
+
@layer components {
|
|
26
|
+
/* Viewport ---------------------------------------------------------------- */
|
|
27
|
+
|
|
28
|
+
.seeds-drawer-viewport {
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
.seeds-drawer-viewport--snap {
|
|
32
|
+
position: fixed;
|
|
33
|
+
inset: 0;
|
|
34
|
+
display: flex;
|
|
35
|
+
align-items: flex-end;
|
|
36
|
+
justify-content: center;
|
|
37
|
+
touch-action: none;
|
|
38
|
+
/* The viewport spans the whole screen but the popup only fills part of it.
|
|
39
|
+
Letting clicks fall through the empty area means a nested snap-point drawer
|
|
40
|
+
doesn't block selection/interaction with the parent drawer visible
|
|
41
|
+
underneath. The popup re-enables events. */
|
|
42
|
+
pointer-events: none;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/* Backdrop ---------------------------------------------------------------- */
|
|
46
|
+
|
|
47
|
+
.seeds-drawer-backdrop {
|
|
48
|
+
position: fixed;
|
|
49
|
+
inset: 0;
|
|
50
|
+
background: transparent;
|
|
51
|
+
pointer-events: none;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
/* Drag handle ------------------------------------------------------------- */
|
|
55
|
+
|
|
56
|
+
.seeds-drawer-drag-handle {
|
|
57
|
+
position: absolute;
|
|
58
|
+
top: 8px;
|
|
59
|
+
left: 50%;
|
|
60
|
+
transform: translateX(-50%);
|
|
61
|
+
width: 36px;
|
|
62
|
+
height: 4px;
|
|
63
|
+
border-radius: 2px;
|
|
64
|
+
background-color: var(--color-container-border-base);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/* Popup base -------------------------------------------------------------- */
|
|
68
|
+
|
|
69
|
+
.seeds-drawer-popup {
|
|
70
|
+
display: flex;
|
|
71
|
+
flex-direction: column;
|
|
72
|
+
position: fixed;
|
|
73
|
+
background-color: var(--color-container-bg-base);
|
|
74
|
+
filter: blur(0);
|
|
75
|
+
transition: transform var(--duration-medium) ease,
|
|
76
|
+
border-radius var(--duration-medium) ease,
|
|
77
|
+
height var(--duration-medium) ease;
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
/* Always-on opacity transition so content fades smoothly both into and out of
|
|
81
|
+
stacked state. */
|
|
82
|
+
.seeds-drawer-popup > * {
|
|
83
|
+
transition: opacity var(--duration-medium) ease;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
/* Side (left/right) layout. width + left/right come from inline style. */
|
|
87
|
+
.seeds-drawer-popup--side {
|
|
88
|
+
top: 0;
|
|
89
|
+
height: 100%;
|
|
90
|
+
box-shadow: var(--shadow-medium);
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
/* Bottom layout (non-snap bottom sheet). */
|
|
94
|
+
.seeds-drawer-popup--bottom:not(.seeds-drawer-popup--snap) {
|
|
95
|
+
--bleed: 3rem;
|
|
96
|
+
--stack-scale: 1;
|
|
97
|
+
--translate-y: 0px;
|
|
98
|
+
bottom: 0;
|
|
99
|
+
left: 0;
|
|
100
|
+
right: 0;
|
|
101
|
+
width: 100%;
|
|
102
|
+
height: calc(90vh + var(--bleed));
|
|
103
|
+
margin-bottom: calc(-1 * var(--bleed));
|
|
104
|
+
border-radius: var(--radius-800) var(--radius-800) 0 0;
|
|
105
|
+
transform: translateY(var(--translate-y)) scale(var(--stack-scale));
|
|
106
|
+
transform-origin: 50% calc(100% - var(--bleed));
|
|
107
|
+
box-shadow: 0px -8px 16px rgba(39, 51, 51, 0.25);
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
/* Bottom snap-points layout. Follows base-ui's reference layout. Critical:
|
|
111
|
+
- box-sizing: border-box so offsetHeight ignores padding-bottom; otherwise
|
|
112
|
+
base-ui's ResizeObserver feedback (padding-bottom driven by snap offset)
|
|
113
|
+
grows popupHeight on every measurement and snap math diverges.
|
|
114
|
+
- height (not max-height) so popupHeight is large enough that base-ui's snap
|
|
115
|
+
offset = max(0, popupHeight - snapHeight) distinguishes snap points.
|
|
116
|
+
- position: relative inside the flex-end Viewport so base-ui can measure
|
|
117
|
+
popupHeight vs viewportHeight for snap math. */
|
|
118
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--snap {
|
|
119
|
+
box-sizing: border-box;
|
|
120
|
+
position: relative;
|
|
121
|
+
width: 100%;
|
|
122
|
+
height: calc(100dvh - 1rem);
|
|
123
|
+
padding-bottom: max(
|
|
124
|
+
0px,
|
|
125
|
+
calc(
|
|
126
|
+
var(--drawer-snap-point-offset, 0px) +
|
|
127
|
+
var(--drawer-swipe-movement-y, 0px)
|
|
128
|
+
)
|
|
129
|
+
);
|
|
130
|
+
overflow: visible;
|
|
131
|
+
touch-action: none;
|
|
132
|
+
/* Counterpart to the viewport's pointer-events: none — the popup itself
|
|
133
|
+
stays interactive. */
|
|
134
|
+
pointer-events: auto;
|
|
135
|
+
border-radius: var(--radius-800) var(--radius-800) 0 0;
|
|
136
|
+
box-shadow: 0px -8px 16px rgba(39, 51, 51, 0.25);
|
|
137
|
+
transform: translateY(
|
|
138
|
+
calc(
|
|
139
|
+
var(--drawer-snap-point-offset, 0px) +
|
|
140
|
+
var(--drawer-swipe-movement-y, 0px)
|
|
141
|
+
)
|
|
142
|
+
);
|
|
143
|
+
will-change: transform;
|
|
144
|
+
transition: transform var(--duration-medium) cubic-bezier(0.32, 0.72, 0, 1),
|
|
145
|
+
box-shadow var(--duration-medium) cubic-bezier(0.32, 0.72, 0, 1);
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
/* Enter / exit ------------------------------------------------------------ */
|
|
149
|
+
|
|
150
|
+
.seeds-drawer-popup--right[data-starting-style],
|
|
151
|
+
.seeds-drawer-popup--right[data-ending-style] {
|
|
152
|
+
transform: translateX(100%);
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
.seeds-drawer-popup--left[data-starting-style],
|
|
156
|
+
.seeds-drawer-popup--left[data-ending-style] {
|
|
157
|
+
transform: translateX(-100%);
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
.seeds-drawer-popup--bottom:not(.seeds-drawer-popup--snap)[data-starting-style],
|
|
161
|
+
.seeds-drawer-popup--bottom:not(.seeds-drawer-popup--snap)[data-ending-style] {
|
|
162
|
+
transform: translateY(calc(100% - var(--bleed) + 2px));
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--snap[data-starting-style],
|
|
166
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--snap[data-ending-style] {
|
|
167
|
+
transform: translateY(calc(100% + 2px));
|
|
168
|
+
padding-bottom: 0;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
/* The action rail lives above the popup (position: absolute, bottom: 100% +
|
|
172
|
+
RAIL_OFFSET). Translating the popup by its own height alone leaves the rail
|
|
173
|
+
visible at the bottom of the viewport during enter/exit, so we add the rail's
|
|
174
|
+
outset: RAIL_BUTTON_HEIGHT (32) + RAIL_OFFSET (12) = 44px. */
|
|
175
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--action-rail:not(.seeds-drawer-popup--snap)[data-starting-style],
|
|
176
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--action-rail:not(.seeds-drawer-popup--snap)[data-ending-style] {
|
|
177
|
+
transform: translateY(calc(100% - var(--bleed) + 2px + 44px));
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--snap.seeds-drawer-popup--action-rail[data-starting-style],
|
|
181
|
+
.seeds-drawer-popup--bottom.seeds-drawer-popup--snap.seeds-drawer-popup--action-rail[data-ending-style] {
|
|
182
|
+
transform: translateY(calc(100% + 2px + 44px));
|
|
183
|
+
padding-bottom: 0;
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
/* Swiping ----------------------------------------------------------------- */
|
|
187
|
+
|
|
188
|
+
.seeds-drawer-popup[data-swiping],
|
|
189
|
+
.seeds-drawer-popup[data-nested-drawer-swiping] {
|
|
190
|
+
transition-duration: 0ms;
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
/* Nested drawer open ------------------------------------------------------ */
|
|
194
|
+
|
|
195
|
+
.seeds-drawer-popup[data-nested-drawer-open] {
|
|
196
|
+
border-radius: var(--radius-800);
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
/* Bottom non-snap stacked bottom-sheet animation. Snap-point drawers don't
|
|
200
|
+
participate: the stack math overwrites --translate-y and clips overflow,
|
|
201
|
+
which collides with base-ui's snap-offset transform. */
|
|
202
|
+
.seeds-drawer-popup--bottom:not(.seeds-drawer-popup--snap)[data-nested-drawer-open] {
|
|
203
|
+
--stack-step: 0.05;
|
|
204
|
+
--stack-progress: clamp(0, var(--drawer-swipe-progress), 1);
|
|
205
|
+
/* Override default vars; base transform rule picks them up automatically */
|
|
206
|
+
--stack-scale: max(
|
|
207
|
+
0,
|
|
208
|
+
calc(
|
|
209
|
+
1 - (var(--nested-drawers) * var(--stack-step)) +
|
|
210
|
+
(var(--stack-step) * var(--stack-progress))
|
|
211
|
+
)
|
|
212
|
+
);
|
|
213
|
+
--stack-shrink: calc(1 - var(--stack-scale));
|
|
214
|
+
--stack-height: max(
|
|
215
|
+
0px,
|
|
216
|
+
calc(var(--drawer-frontmost-height, var(--drawer-height)) - var(--bleed))
|
|
217
|
+
);
|
|
218
|
+
--stack-peek-offset: max(
|
|
219
|
+
0px,
|
|
220
|
+
calc((var(--nested-drawers) - var(--stack-progress)) * 1rem)
|
|
221
|
+
);
|
|
222
|
+
--translate-y: calc(
|
|
223
|
+
var(--drawer-swipe-movement-y) - var(--stack-peek-offset) -
|
|
224
|
+
(var(--stack-shrink) * var(--stack-height))
|
|
225
|
+
);
|
|
226
|
+
height: calc(var(--stack-height) + var(--bleed));
|
|
227
|
+
overflow: hidden;
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
/* Side stacked animation. */
|
|
231
|
+
.seeds-drawer-popup--side[data-nested-drawer-open] {
|
|
232
|
+
transform: translateY(calc(var(--nested-drawers) * -20px))
|
|
233
|
+
scale(calc(1 - var(--nested-drawers) * 0.08));
|
|
234
|
+
transform-origin: top center;
|
|
235
|
+
}
|
|
236
|
+
|
|
237
|
+
/* Fade children out while stacked — every direction except snap. */
|
|
238
|
+
.seeds-drawer-popup:not(.seeds-drawer-popup--snap)[data-nested-drawer-open]
|
|
239
|
+
> * {
|
|
240
|
+
opacity: 0;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
/* While actively swiping a nested drawer, keep children visible. Equal
|
|
244
|
+
specificity to the fade-out rule above, so this must come after it. */
|
|
245
|
+
.seeds-drawer-popup[data-nested-drawer-open][data-nested-drawer-swiping] > * {
|
|
246
|
+
opacity: 1;
|
|
247
|
+
}
|
|
248
|
+
}
|