@botiverse/raft-ui 0.83.0 → 0.84.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/CHANGELOG.md +105 -0
- package/dist/components/app-link-card/app-link-card.mjs +19 -37
- package/dist/components/banner/banner.mjs +15 -2
- package/dist/components/drag/drag.recipe.mjs +1 -1
- package/dist/components/fit-toolbar/fit-toolbar.d.mts +63 -8
- package/dist/components/fit-toolbar/fit-toolbar.mjs +310 -43
- package/dist/components/fit-toolbar/fit-toolbar.recipe.mjs +21 -7
- package/dist/components/fit-toolbar/index.d.mts +2 -2
- package/dist/components/lightbox/index.d.mts +2 -2
- package/dist/components/lightbox/lightbox.d.mts +70 -4
- package/dist/components/lightbox/lightbox.mjs +285 -91
- package/dist/components/list-row/list-row.d.mts +14 -1
- package/dist/components/list-row/list-row.mjs +4 -2
- package/dist/components/list-row/list-row.recipe.d.mts +12 -0
- package/dist/components/list-row/list-row.recipe.mjs +19 -7
- package/dist/components/message-action-card/message-action-card-content.recipe.mjs +3 -3
- package/dist/components/message-action-card/message-action-card.mjs +7 -3
- package/dist/components/message-action-card/message-action-card.recipe.mjs +2 -6
- package/dist/components/message-embed/index.d.mts +2 -1
- package/dist/components/message-embed/message-embed.d.mts +8 -1
- package/dist/components/message-embed/message-embed.mjs +2 -2
- package/dist/components/message-embed/message-embed.recipe.d.mts +160 -0
- package/dist/components/message-embed/message-embed.recipe.mjs +49 -10
- package/dist/components/message-forwarded-bundle/message-forwarded-bundle.mjs +1 -0
- package/dist/components/message-forwarded-bundle/message-forwarded-bundle.recipe.mjs +1 -1
- package/dist/components/message-quoted-preview/message-quoted-preview.mjs +2 -0
- package/dist/components/message-replies/message-replies.mjs +1 -1
- package/dist/components/message-replies/message-replies.recipe.mjs +1 -1
- package/dist/components/popover/popover.d.mts +11 -2
- package/dist/components/popover/popover.mjs +51 -38
- package/dist/components/preview-card/preview-card.d.mts +5 -1
- package/dist/components/preview-card/preview-card.mjs +24 -27
- package/dist/components/save-status/save-status.d.mts +16 -9
- package/dist/components/save-status/save-status.mjs +19 -30
- package/dist/components/segmented-control/segmented-control.mjs +45 -8
- package/dist/components/task-board/task-board.d.mts +5 -0
- package/dist/components/task-board/task-board.mjs +8 -1
- package/dist/components/task-dnd/task-dnd.d.mts +10 -1
- package/dist/components/task-dnd/task-dnd.mjs +2 -1
- package/dist/components/toast/toast.mjs +2 -2
- package/dist/index.d.mts +2 -1
- package/dist/index.mjs +2 -1
- package/dist/lib/laid-out-children.mjs +32 -0
- package/dist/lib/stacked-actions.mjs +7 -4
- package/dist/wip.d.mts +4 -2
- package/dist/wip.mjs +3 -2
- package/package.json +1 -1
|
@@ -28,7 +28,11 @@ export declare function PreviewCardDescription({ className, ...props }: PreviewC
|
|
|
28
28
|
export type PreviewCardArrowProps = StyledProps<PreviewCard.Arrow.Props>;
|
|
29
29
|
export declare function PreviewCardArrow({ className, ...props }: PreviewCardArrowProps): import("react").JSX.Element;
|
|
30
30
|
export type PreviewCardBodyProps = ComponentPropsWithRef<"div">;
|
|
31
|
-
/**
|
|
31
|
+
/**
|
|
32
|
+
* The item card's block: the id line, the title and the details row, in that
|
|
33
|
+
* order. Its parts are a card's in a message (AppLinkCard), so the two read
|
|
34
|
+
* the same.
|
|
35
|
+
*/
|
|
32
36
|
export declare function PreviewCardBody({ className, ...props }: PreviewCardBodyProps): import("react").JSX.Element;
|
|
33
37
|
export type PreviewCardEyebrowProps = ComponentPropsWithRef<"p">;
|
|
34
38
|
/** The muted line above the title that identifies the item, such as its id. One line, truncated. */
|
|
@@ -2,6 +2,8 @@ import { tv } from "../../lib/tv.mjs";
|
|
|
2
2
|
import { useTheme } from "../../lib/theme/use-theme.mjs";
|
|
3
3
|
import { resolveThemeScopeProps, useThemeScopeProps } from "../../lib/theme/theme-scope.mjs";
|
|
4
4
|
import { usePopupCollision } from "../../lib/frame-insets.mjs";
|
|
5
|
+
import { messageCard } from "../message-embed/message-embed.recipe.mjs";
|
|
6
|
+
import { createContext, useContext } from "react";
|
|
5
7
|
import { jsx } from "react/jsx-runtime";
|
|
6
8
|
import { PreviewCard } from "@base-ui/react/preview-card";
|
|
7
9
|
//#region src/components/preview-card/preview-card.tsx
|
|
@@ -24,24 +26,11 @@ const previewCard = tv({
|
|
|
24
26
|
separator: ["border-t", "border-line-hairline"],
|
|
25
27
|
title: ["m-0 truncate", "font-sans text-headline font-bold text-foreground"],
|
|
26
28
|
description: ["m-0 truncate", "px-4 py-3 last:pb-4 font-sans text-callout text-foreground-muted"],
|
|
27
|
-
arrow: ["size-2 rotate-45", "border-l border-t border-line-seam bg-layer-popover"]
|
|
28
|
-
body: [
|
|
29
|
-
"flex min-w-0 flex-col gap-1.5",
|
|
30
|
-
"px-4 pt-4 pb-3 last:pb-4",
|
|
31
|
-
"*:data-[slot=preview-card-title]:line-clamp-2 *:data-[slot=preview-card-title]:whitespace-normal"
|
|
32
|
-
],
|
|
33
|
-
eyebrow: ["m-0 truncate", "font-mono text-mono-meta text-foreground-muted"],
|
|
34
|
-
meta: ["flex min-w-0 flex-wrap items-center gap-x-2 gap-y-1", "m-0 font-sans text-callout text-foreground-muted"],
|
|
35
|
-
actions: ["flex flex-wrap items-center justify-end gap-2", "px-4 pb-3 last:pb-4"],
|
|
36
|
-
footer: [
|
|
37
|
-
"m-0 truncate",
|
|
38
|
-
"border-t border-line-hairline px-4 py-2",
|
|
39
|
-
"font-sans text-caption text-foreground-muted"
|
|
40
|
-
]
|
|
29
|
+
arrow: ["size-2 rotate-45", "border-l border-t border-line-seam bg-layer-popover"]
|
|
41
30
|
},
|
|
42
31
|
variants: { size: {
|
|
43
32
|
profile: { popup: "w-[300px]" },
|
|
44
|
-
item: { popup:
|
|
33
|
+
item: { popup: messageCard().popover() }
|
|
45
34
|
} },
|
|
46
35
|
defaultVariants: { size: "profile" }
|
|
47
36
|
});
|
|
@@ -132,8 +121,9 @@ function PreviewCardSeparator({ className, ...props }) {
|
|
|
132
121
|
...props
|
|
133
122
|
});
|
|
134
123
|
}
|
|
124
|
+
const InItemBody = createContext(false);
|
|
135
125
|
function PreviewCardTitle({ className, ...props }) {
|
|
136
|
-
const
|
|
126
|
+
const title = useContext(InItemBody) ? messageCard().title : previewCard().title;
|
|
137
127
|
return /* @__PURE__ */ jsx("p", {
|
|
138
128
|
"data-slot": "preview-card-title",
|
|
139
129
|
className: title({ className }),
|
|
@@ -156,18 +146,25 @@ function PreviewCardArrow({ className, ...props }) {
|
|
|
156
146
|
...props
|
|
157
147
|
});
|
|
158
148
|
}
|
|
159
|
-
/**
|
|
149
|
+
/**
|
|
150
|
+
* The item card's block: the id line, the title and the details row, in that
|
|
151
|
+
* order. Its parts are a card's in a message (AppLinkCard), so the two read
|
|
152
|
+
* the same.
|
|
153
|
+
*/
|
|
160
154
|
function PreviewCardBody({ className, ...props }) {
|
|
161
|
-
const { body } =
|
|
162
|
-
return /* @__PURE__ */ jsx(
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
155
|
+
const { body } = messageCard();
|
|
156
|
+
return /* @__PURE__ */ jsx(InItemBody.Provider, {
|
|
157
|
+
value: true,
|
|
158
|
+
children: /* @__PURE__ */ jsx("div", {
|
|
159
|
+
"data-slot": "preview-card-body",
|
|
160
|
+
className: body({ className }),
|
|
161
|
+
...props
|
|
162
|
+
})
|
|
166
163
|
});
|
|
167
164
|
}
|
|
168
165
|
/** The muted line above the title that identifies the item, such as its id. One line, truncated. */
|
|
169
166
|
function PreviewCardEyebrow({ className, ...props }) {
|
|
170
|
-
const { eyebrow } =
|
|
167
|
+
const { eyebrow } = messageCard();
|
|
171
168
|
return /* @__PURE__ */ jsx("p", {
|
|
172
169
|
"data-slot": "preview-card-eyebrow",
|
|
173
170
|
className: eyebrow({ className }),
|
|
@@ -176,7 +173,7 @@ function PreviewCardEyebrow({ className, ...props }) {
|
|
|
176
173
|
}
|
|
177
174
|
/** The row under the title: one state chip, then muted details. Wraps when it runs out of room. */
|
|
178
175
|
function PreviewCardMeta({ className, ...props }) {
|
|
179
|
-
const { meta } =
|
|
176
|
+
const { meta } = messageCard();
|
|
180
177
|
return /* @__PURE__ */ jsx("div", {
|
|
181
178
|
"data-slot": "preview-card-meta",
|
|
182
179
|
className: meta({ className }),
|
|
@@ -185,7 +182,7 @@ function PreviewCardMeta({ className, ...props }) {
|
|
|
185
182
|
}
|
|
186
183
|
/** The row of at most two buttons. */
|
|
187
184
|
function PreviewCardActions({ className, ...props }) {
|
|
188
|
-
const { actions } =
|
|
185
|
+
const { actions } = messageCard();
|
|
189
186
|
return /* @__PURE__ */ jsx("div", {
|
|
190
187
|
"data-slot": "preview-card-actions",
|
|
191
188
|
className: actions({ className }),
|
|
@@ -194,10 +191,10 @@ function PreviewCardActions({ className, ...props }) {
|
|
|
194
191
|
}
|
|
195
192
|
/** The caption under a hairline at the bottom of the card: where the item comes from. */
|
|
196
193
|
function PreviewCardFooter({ className, ...props }) {
|
|
197
|
-
const {
|
|
194
|
+
const { sourceFooter } = messageCard();
|
|
198
195
|
return /* @__PURE__ */ jsx("p", {
|
|
199
196
|
"data-slot": "preview-card-footer",
|
|
200
|
-
className:
|
|
197
|
+
className: sourceFooter({ className }),
|
|
201
198
|
...props
|
|
202
199
|
});
|
|
203
200
|
}
|
|
@@ -2,22 +2,29 @@ import { ComponentPropsWithRef } from "react";
|
|
|
2
2
|
//#region src/components/save-status/save-status.d.ts
|
|
3
3
|
export type SaveStatusProps = ComponentPropsWithRef<"span">;
|
|
4
4
|
/**
|
|
5
|
-
* The
|
|
6
|
-
*
|
|
7
|
-
*
|
|
5
|
+
* The line under a setting that applies at once. Render it whatever the
|
|
6
|
+
* setting's state, with `SaveStatusError` inside when the change failed and
|
|
7
|
+
* nothing inside otherwise: empty, it is hidden and takes no height. A `span`
|
|
8
|
+
* (shown as a block), like every ListRow part, so it stays valid inside a
|
|
9
|
+
* row's body; give it an `id` for the control's `aria-describedby`.
|
|
8
10
|
*/
|
|
9
11
|
export declare function SaveStatus({ className, ...props }: SaveStatusProps): import("react").JSX.Element;
|
|
10
12
|
export type SaveStatusSavedProps = ComponentPropsWithRef<"span">;
|
|
11
13
|
/**
|
|
12
|
-
*
|
|
13
|
-
*
|
|
14
|
-
*
|
|
14
|
+
* @deprecated A setting that applies at once no longer says "Saved": the
|
|
15
|
+
* control showing its new value is the confirmation (Forms, settings that
|
|
16
|
+
* apply at once). Renders nothing, whatever its children, so its
|
|
17
|
+
* `SaveStatus` stays empty and takes no height. Leave it out: render
|
|
18
|
+
* `SaveStatusError` when the change failed and nothing otherwise. It drops
|
|
19
|
+
* every prop, its `id` too: point a control's `aria-describedby` at the
|
|
20
|
+
* `SaveStatus` instead.
|
|
15
21
|
*/
|
|
16
|
-
export declare function SaveStatusSaved(
|
|
22
|
+
export declare function SaveStatusSaved(_props: SaveStatusSavedProps): null;
|
|
17
23
|
export type SaveStatusErrorProps = ComponentPropsWithRef<"span">;
|
|
18
24
|
/**
|
|
19
|
-
* What failed
|
|
20
|
-
*
|
|
25
|
+
* What failed. It is an alert, announced when it appears, and stays until
|
|
26
|
+
* the next change. Its line appears with it, so the setting grows by one
|
|
27
|
+
* line while it shows.
|
|
21
28
|
*/
|
|
22
29
|
export declare function SaveStatusError({ className, role, ...props }: SaveStatusErrorProps): import("react").JSX.Element;
|
|
23
30
|
//#endregion
|
|
@@ -1,24 +1,20 @@
|
|
|
1
1
|
import { tv } from "../../lib/tv.mjs";
|
|
2
|
-
import {
|
|
3
|
-
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
import { jsx } from "react/jsx-runtime";
|
|
4
3
|
//#region src/components/save-status/save-status.tsx
|
|
5
4
|
const saveStatus = tv({ slots: {
|
|
6
5
|
root: [
|
|
7
|
-
"block min-
|
|
6
|
+
"block min-w-0 empty:hidden",
|
|
8
7
|
"mt-1 [[data-slot=field]>&]:-mt-0.5 [[data-slot=list-row-body]>&]:mt-0.5",
|
|
9
8
|
"text-footnote"
|
|
10
9
|
],
|
|
11
|
-
saved: [
|
|
12
|
-
"flex min-w-0 items-center gap-1",
|
|
13
|
-
"text-foreground-muted",
|
|
14
|
-
"[&>svg]:size-3 [&>svg]:shrink-0"
|
|
15
|
-
],
|
|
16
10
|
error: ["block wrap-anywhere", "text-danger-strong"]
|
|
17
11
|
} });
|
|
18
12
|
/**
|
|
19
|
-
* The
|
|
20
|
-
*
|
|
21
|
-
*
|
|
13
|
+
* The line under a setting that applies at once. Render it whatever the
|
|
14
|
+
* setting's state, with `SaveStatusError` inside when the change failed and
|
|
15
|
+
* nothing inside otherwise: empty, it is hidden and takes no height. A `span`
|
|
16
|
+
* (shown as a block), like every ListRow part, so it stays valid inside a
|
|
17
|
+
* row's body; give it an `id` for the control's `aria-describedby`.
|
|
22
18
|
*/
|
|
23
19
|
function SaveStatus({ className, ...props }) {
|
|
24
20
|
const { root } = saveStatus();
|
|
@@ -29,28 +25,21 @@ function SaveStatus({ className, ...props }) {
|
|
|
29
25
|
});
|
|
30
26
|
}
|
|
31
27
|
/**
|
|
32
|
-
*
|
|
33
|
-
*
|
|
34
|
-
*
|
|
28
|
+
* @deprecated A setting that applies at once no longer says "Saved": the
|
|
29
|
+
* control showing its new value is the confirmation (Forms, settings that
|
|
30
|
+
* apply at once). Renders nothing, whatever its children, so its
|
|
31
|
+
* `SaveStatus` stays empty and takes no height. Leave it out: render
|
|
32
|
+
* `SaveStatusError` when the change failed and nothing otherwise. It drops
|
|
33
|
+
* every prop, its `id` too: point a control's `aria-describedby` at the
|
|
34
|
+
* `SaveStatus` instead.
|
|
35
35
|
*/
|
|
36
|
-
function SaveStatusSaved(
|
|
37
|
-
|
|
38
|
-
const hasContent = children !== null && children !== void 0 && children !== false && children !== "";
|
|
39
|
-
return /* @__PURE__ */ jsxs("span", {
|
|
40
|
-
"data-slot": "save-status-saved",
|
|
41
|
-
role: "status",
|
|
42
|
-
"aria-live": "polite",
|
|
43
|
-
className: saved({ className }),
|
|
44
|
-
...props,
|
|
45
|
-
children: [hasContent ? /* @__PURE__ */ jsx(CircleCheck, {
|
|
46
|
-
"aria-hidden": "true",
|
|
47
|
-
"data-slot": "save-status-icon"
|
|
48
|
-
}) : null, children]
|
|
49
|
-
});
|
|
36
|
+
function SaveStatusSaved(_props) {
|
|
37
|
+
return null;
|
|
50
38
|
}
|
|
51
39
|
/**
|
|
52
|
-
* What failed
|
|
53
|
-
*
|
|
40
|
+
* What failed. It is an alert, announced when it appears, and stays until
|
|
41
|
+
* the next change. Its line appears with it, so the setting grows by one
|
|
42
|
+
* line while it shows.
|
|
54
43
|
*/
|
|
55
44
|
function SaveStatusError({ className, role = "alert", ...props }) {
|
|
56
45
|
const { error } = saveStatus();
|
|
@@ -3,8 +3,9 @@ import { useMergedRef } from "../../lib/use-merged-ref.mjs";
|
|
|
3
3
|
import { useTapActivation } from "../../lib/tap-activation.mjs";
|
|
4
4
|
import { Tooltip, TooltipContent, TooltipTrigger } from "../tooltip/tooltip.mjs";
|
|
5
5
|
import { useInFitToolbar } from "../fit-toolbar/fit-toolbar.mjs";
|
|
6
|
-
import { createContext, use, useCallback, useLayoutEffect, useRef, useState } from "react";
|
|
6
|
+
import { cloneElement, createContext, use, useCallback, useLayoutEffect, useRef, useState } from "react";
|
|
7
7
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
8
|
+
import { Toolbar } from "@base-ui/react/toolbar";
|
|
8
9
|
import { Radio } from "@base-ui/react/radio";
|
|
9
10
|
import { RadioGroup } from "@base-ui/react/radio-group";
|
|
10
11
|
//#region src/components/segmented-control/segmented-control.tsx
|
|
@@ -73,6 +74,11 @@ function isIconsOnlyPreset(value) {
|
|
|
73
74
|
}
|
|
74
75
|
const SegmentedControlIconsOnlyContext = createContext(false);
|
|
75
76
|
/**
|
|
77
|
+
* In a FitToolbar: whether the control holds the toolbar's one tab stop
|
|
78
|
+
* (`undefined` outside a toolbar, where the radio group keeps its own).
|
|
79
|
+
*/
|
|
80
|
+
const SegmentedControlToolbarStopContext = createContext(void 0);
|
|
81
|
+
/**
|
|
76
82
|
* A length threshold in CSS pixels, or `undefined` for a value that isn't a
|
|
77
83
|
* `px`, `rem` or `em` length. `em` is the container's font size, as in a
|
|
78
84
|
* container query.
|
|
@@ -250,21 +256,51 @@ function SegmentedControl({ disabled = false, iconsOnlyBelow: iconsOnlyBelowProp
|
|
|
250
256
|
if (start < track.scrollLeft) track.scrollLeft = start;
|
|
251
257
|
else if (end > track.scrollLeft + track.clientWidth) track.scrollLeft = end - track.clientWidth;
|
|
252
258
|
}, [overflowing, value]);
|
|
259
|
+
const group = /* @__PURE__ */ jsx(RadioGroup, {
|
|
260
|
+
ref: setRef,
|
|
261
|
+
disabled,
|
|
262
|
+
"data-slot": "segmented-control",
|
|
263
|
+
"data-overflowing": overflowing ? "" : void 0,
|
|
264
|
+
"data-fit-needs-icon": inFitToolbar ? "" : void 0,
|
|
265
|
+
className: root({ className }),
|
|
266
|
+
...props
|
|
267
|
+
});
|
|
253
268
|
return /* @__PURE__ */ jsx(SegmentedControlIconsOnlyContext, {
|
|
254
269
|
value: inFitToolbar || iconsOnlyBelow !== void 0,
|
|
255
|
-
children: /* @__PURE__ */ jsx(
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
270
|
+
children: inFitToolbar ? /* @__PURE__ */ jsx(ToolbarItem, { group }) : group
|
|
271
|
+
});
|
|
272
|
+
}
|
|
273
|
+
/**
|
|
274
|
+
* In a FitToolbar the control is one item of the toolbar's list (Base UI
|
|
275
|
+
* Toolbar), so the toolbar keeps one tab stop: its segments are reachable by
|
|
276
|
+
* Tab only while the control holds it, and the toolbar's arrow keys reach
|
|
277
|
+
* them. Registered through `Toolbar.Link`'s render function, the one toolbar
|
|
278
|
+
* part that adds no role or keys of its own: the radio group is the item. Its
|
|
279
|
+
* own tab stop is the segments', never the group's.
|
|
280
|
+
*/
|
|
281
|
+
function ToolbarItem({ group }) {
|
|
282
|
+
const render = useCallback(({ ref, tabIndex, ...itemProps }) => /* @__PURE__ */ jsx(ToolbarItemGroup, {
|
|
283
|
+
group,
|
|
284
|
+
itemProps,
|
|
285
|
+
itemRef: ref,
|
|
286
|
+
stop: tabIndex === 0
|
|
287
|
+
}), [group]);
|
|
288
|
+
return /* @__PURE__ */ jsx(Toolbar.Link, { render });
|
|
289
|
+
}
|
|
290
|
+
function ToolbarItemGroup({ group, itemProps, itemRef, stop }) {
|
|
291
|
+
const [setRef] = useMergedRef(itemRef, group.props.ref);
|
|
292
|
+
return /* @__PURE__ */ jsx(SegmentedControlToolbarStopContext, {
|
|
293
|
+
value: stop,
|
|
294
|
+
children: cloneElement(group, {
|
|
295
|
+
...itemProps,
|
|
296
|
+
ref: setRef
|
|
262
297
|
})
|
|
263
298
|
});
|
|
264
299
|
}
|
|
265
300
|
function SegmentedControlItem({ className, ref, ...props }) {
|
|
266
301
|
const { item } = segmentedControl();
|
|
267
302
|
const iconsOnly = use(SegmentedControlIconsOnlyContext);
|
|
303
|
+
const toolbarStop = use(SegmentedControlToolbarStopContext);
|
|
268
304
|
const tapRef = useTapActivation();
|
|
269
305
|
const [setRef] = useMergedRef(tapRef, ref);
|
|
270
306
|
const radio = /* @__PURE__ */ jsx(Radio.Root, {
|
|
@@ -273,6 +309,7 @@ function SegmentedControlItem({ className, ref, ...props }) {
|
|
|
273
309
|
nativeButton: true,
|
|
274
310
|
"data-slot": "segmented-control-item",
|
|
275
311
|
className: item({ className: `group/segmented-control-item ${className ?? ""}`.trim() }),
|
|
312
|
+
...toolbarStop === false ? { tabIndex: -1 } : {},
|
|
276
313
|
...props
|
|
277
314
|
});
|
|
278
315
|
return iconsOnly ? /* @__PURE__ */ jsx(SegmentedControlItemTooltip, { children: radio }) : radio;
|
|
@@ -22,6 +22,11 @@ export declare function TaskBoardColumnBadge({ status, children, className, rend
|
|
|
22
22
|
export type TaskBoardColumnCountProps = useRender.ComponentProps<"span">;
|
|
23
23
|
export declare function TaskBoardColumnCount({ className, render, ...props }: TaskBoardColumnCountProps): import("react").ReactElement<unknown, string | import("react").JSXElementConstructor<any>>;
|
|
24
24
|
export type TaskBoardColumnChevronProps = useRender.ComponentProps<"span">;
|
|
25
|
+
/**
|
|
26
|
+
* The arrow that shows whether the column is open: right while it is collapsed, down while it is open. It draws a
|
|
27
|
+
* `ChevronDown` when given no children, so a column heading always has it: a collapsed column shows only its heading,
|
|
28
|
+
* and without the arrow "Closed 2" over an empty space reads as two tasks that failed to load.
|
|
29
|
+
*/
|
|
25
30
|
export declare function TaskBoardColumnChevron({ className, render, ...props }: TaskBoardColumnChevronProps): import("react").ReactElement<unknown, string | import("react").JSXElementConstructor<any>>;
|
|
26
31
|
export type TaskBoardColumnPanelProps = Omit<ComponentProps<typeof Collapsible.Panel>, "className"> & {
|
|
27
32
|
className?: string;
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { cn } from "../../cn.mjs";
|
|
2
2
|
import { TaskStatusIcon } from "../tasks/task-status-icon.mjs";
|
|
3
3
|
import { taskBoardColumn } from "./task-board-column.recipe.mjs";
|
|
4
|
+
import { ChevronDown } from "lucide-react";
|
|
4
5
|
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
5
6
|
import { mergeProps } from "@base-ui/react/merge-props";
|
|
6
7
|
import { useRender } from "@base-ui/react/use-render";
|
|
@@ -71,11 +72,17 @@ function TaskBoardColumnCount({ className, render, ...props }) {
|
|
|
71
72
|
props: mergeProps(defaultProps, props)
|
|
72
73
|
});
|
|
73
74
|
}
|
|
75
|
+
/**
|
|
76
|
+
* The arrow that shows whether the column is open: right while it is collapsed, down while it is open. It draws a
|
|
77
|
+
* `ChevronDown` when given no children, so a column heading always has it: a collapsed column shows only its heading,
|
|
78
|
+
* and without the arrow "Closed 2" over an empty space reads as two tasks that failed to load.
|
|
79
|
+
*/
|
|
74
80
|
function TaskBoardColumnChevron({ className, render, ...props }) {
|
|
75
81
|
const { chevron } = taskBoardColumn();
|
|
76
82
|
const defaultProps = {
|
|
77
83
|
"data-slot": "task-board-column-chevron",
|
|
78
|
-
className: chevron({ className })
|
|
84
|
+
className: chevron({ className }),
|
|
85
|
+
children: /* @__PURE__ */ jsx(ChevronDown, { "aria-hidden": true })
|
|
79
86
|
};
|
|
80
87
|
return useRender({
|
|
81
88
|
defaultTagName: "span",
|
|
@@ -52,8 +52,17 @@ export type TaskDropZoneProps = useRender.ComponentProps<"div", TaskDropZoneStat
|
|
|
52
52
|
id: UniqueIdentifier;
|
|
53
53
|
disabled?: boolean;
|
|
54
54
|
data?: TaskDropData;
|
|
55
|
+
/**
|
|
56
|
+
* The zone is itself the place, as a column sorted by a field is: its
|
|
57
|
+
* cards carry no `dropId` and no placeholder opens between them. While a
|
|
58
|
+
* card it allows is over it, it carries `data-drag-into` and takes
|
|
59
|
+
* `fill-subtle`; never at rest, and never while it refuses the card.
|
|
60
|
+
* Without it the zone is never filled, and only a `TaskDropPlaceholder`
|
|
61
|
+
* says where the card lands.
|
|
62
|
+
*/
|
|
63
|
+
dragInto?: boolean;
|
|
55
64
|
};
|
|
56
|
-
export declare function TaskDropZone({ id, data, disabled, render, ...props }: TaskDropZoneProps): import("react").ReactElement<unknown, string | import("react").JSXElementConstructor<any>>;
|
|
65
|
+
export declare function TaskDropZone({ id, data, disabled, dragInto, render, ...props }: TaskDropZoneProps): import("react").ReactElement<unknown, string | import("react").JSXElementConstructor<any>>;
|
|
57
66
|
export type TaskDropPlaceholderProps = useRender.ComponentProps<"div", TaskDropZoneState> & {
|
|
58
67
|
id: UniqueIdentifier;
|
|
59
68
|
placement?: TaskDropPlacement;
|
|
@@ -174,7 +174,7 @@ function assignRef(ref, value) {
|
|
|
174
174
|
if (typeof ref === "function") ref(value);
|
|
175
175
|
else if (ref) ref.current = value;
|
|
176
176
|
}
|
|
177
|
-
function TaskDropZone({ id, data, disabled = false, render, ...props }) {
|
|
177
|
+
function TaskDropZone({ id, data, disabled = false, dragInto = false, render, ...props }) {
|
|
178
178
|
const context = use(TaskDndContext);
|
|
179
179
|
const { setNodeRef, isOver } = useDroppable({
|
|
180
180
|
id,
|
|
@@ -190,6 +190,7 @@ function TaskDropZone({ id, data, disabled = false, render, ...props }) {
|
|
|
190
190
|
props: {
|
|
191
191
|
"data-slot": "task-drop-zone",
|
|
192
192
|
"data-drop-state": dropState,
|
|
193
|
+
"data-drag-into": dragInto && dropState === "allowed" ? "" : void 0,
|
|
193
194
|
...props
|
|
194
195
|
}
|
|
195
196
|
});
|
|
@@ -10,8 +10,8 @@ import { Toast } from "@base-ui/react/toast";
|
|
|
10
10
|
//#region src/components/toast/toast.tsx
|
|
11
11
|
const toastStyles = tv({
|
|
12
12
|
slots: {
|
|
13
|
-
viewport: ["pointer-events-none isolate z-
|
|
14
|
-
positioner: ["isolate z-[calc(
|
|
13
|
+
viewport: ["pointer-events-none isolate z-80 w-[min(24rem,calc(100vw-2rem))]", "outline-none"],
|
|
14
|
+
positioner: ["isolate z-[calc(80-var(--toast-index))] outline-none"],
|
|
15
15
|
root: [
|
|
16
16
|
"group/toast pointer-events-auto",
|
|
17
17
|
"select-text",
|