@danxbot/ui 3.9.0 → 3.9.1
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.
|
@@ -54,8 +54,16 @@ export interface DataTableProps<TData> {
|
|
|
54
54
|
* styling the table picked — `cn` is tailwind-merge, and the last conflicting
|
|
55
55
|
* utility wins. That is deliberate: a tint that loses to the zebra fill is a
|
|
56
56
|
* tint nobody sees. It also means a background handed over here REPLACES the
|
|
57
|
-
* row's hover fill, so pass the hover with it (`bg-
|
|
58
|
-
* hover:bg-
|
|
57
|
+
* row's hover fill, so pass the hover with it (`bg-danger-subtle
|
|
58
|
+
* hover:bg-danger-subtle-hover`) if the row should still respond.
|
|
59
|
+
*
|
|
60
|
+
* THAT EXAMPLE USED TO NAME `warning`, WHICH HAS NO HOVER STEP. `-subtle`
|
|
61
|
+
* exists for every semantic family; `-subtle-hover` exists for `accent` and
|
|
62
|
+
* `danger` only. A consumer following the old wording got a hover class that
|
|
63
|
+
* compiled to nothing — no rule, no fill, no error anywhere, which is the
|
|
64
|
+
* same silent-nothing failure the theme bridge in `postbuild-css.mjs` exists
|
|
65
|
+
* to prevent one level up. Pick a family that has the step, or supply the
|
|
66
|
+
* hover colour yourself. `token-parity.test.ts` now sweeps this docblock.
|
|
59
67
|
*
|
|
60
68
|
* `index` is the row's position in `data`, not on the current page — the same
|
|
61
69
|
* number `getRowId` receives, so the two never disagree about which row is
|
|
@@ -64,10 +64,31 @@ export declare function Toolbar({ className, children, ref, ...props }: ToolbarP
|
|
|
64
64
|
export declare function ToolbarSeparator({ className }: {
|
|
65
65
|
className?: string;
|
|
66
66
|
}): import("react").JSX.Element;
|
|
67
|
-
|
|
67
|
+
type ToolbarButtonBase = Omit<BaseToolbar.Button.Props, "className" | "nativeButton" | "render"> & {
|
|
68
68
|
className?: string;
|
|
69
69
|
ref?: Ref<HTMLButtonElement>;
|
|
70
|
-
}
|
|
70
|
+
};
|
|
71
|
+
/**
|
|
72
|
+
* TWO FORMS, AND THE TYPE REFUSES TO MIX THEM.
|
|
73
|
+
*
|
|
74
|
+
* Either this renders its own `<button>` and wears `buttonVariants` — in which
|
|
75
|
+
* case `variant` / `size` / `iconOnly` choose which row of that table — or it
|
|
76
|
+
* renders somebody else's control through `render`, in which case that control
|
|
77
|
+
* already carries a variant table and this one must not add a second. The two
|
|
78
|
+
* are mutually exclusive rather than merely discouraged, because a `render`
|
|
79
|
+
* plus a `size` is not a preference somebody expressed: it is two size classes
|
|
80
|
+
* in one attribute with no rule for which wins. See `ToolbarButton`'s own doc
|
|
81
|
+
* for the measurement.
|
|
82
|
+
*/
|
|
83
|
+
export type ToolbarButtonProps = (ToolbarButtonBase & Pick<ButtonProps, "variant" | "size" | "iconOnly"> & {
|
|
84
|
+
/** The styled form owns the element, so there is nothing to render into. */
|
|
85
|
+
render?: undefined;
|
|
86
|
+
}) | (ToolbarButtonBase & {
|
|
87
|
+
render: NonNullable<BaseToolbar.Button.Props["render"]>;
|
|
88
|
+
variant?: never;
|
|
89
|
+
size?: never;
|
|
90
|
+
iconOnly?: never;
|
|
91
|
+
});
|
|
71
92
|
/**
|
|
72
93
|
* A button that is part of the toolbar's rotation.
|
|
73
94
|
*
|
|
@@ -85,8 +106,23 @@ export interface ToolbarButtonProps extends Omit<BaseToolbar.Button.Props, "clas
|
|
|
85
106
|
* ANYTHING ALREADY BUILT ON `Button` GOES IN THROUGH `render`, which is what
|
|
86
107
|
* keeps this from becoming a second button component:
|
|
87
108
|
* `<ToolbarButton render={<IconButton icon={…} label="Bold" />} />` registers
|
|
88
|
-
* exactly the same
|
|
89
|
-
*
|
|
109
|
+
* exactly the same and keeps the tooltip and the `disabledReason`.
|
|
110
|
+
*
|
|
111
|
+
* THAT PATH APPLIES NO VARIANT TABLE AT ALL, and the type enforces it —
|
|
112
|
+
* `variant`, `size` and `iconOnly` are not accepted beside `render`. Base UI's
|
|
113
|
+
* render slot CONCATENATES `className`; it does not run `cn`. So a recipe
|
|
114
|
+
* applied here landed in the same attribute as the rendered component's own,
|
|
115
|
+
* and which one won was decided by Tailwind's emission order rather than by
|
|
116
|
+
* either component. It measured fine while the two happened to agree — a
|
|
117
|
+
* default `render={<IconButton/>}` came out 36×36, identical to a standalone
|
|
118
|
+
* one, while carrying both `aspect-square` and `px-3.5` — and broke visibly the
|
|
119
|
+
* moment they disagreed: `<ToolbarButton size="lg" render={<IconButton
|
|
120
|
+
* size="sm" …/>} />` carried `h-control-lg` AND `h-control-sm` and rendered
|
|
121
|
+
* 48 × 36 with 24px of padding, a squashed oval neither component asked for.
|
|
122
|
+
*
|
|
123
|
+
* Unrepresentable beats documented, and it is free to do NOW: nothing has
|
|
124
|
+
* adopted the pair yet, so narrowing the type costs nothing that removing the
|
|
125
|
+
* props after adoption would have cost.
|
|
90
126
|
*/
|
|
91
127
|
export declare function ToolbarButton({ variant, size, iconOnly, className, children, ref, ...props }: ToolbarButtonProps): import("react").JSX.Element;
|
|
92
128
|
export interface ToolbarInputProps extends Omit<InputProps, "ref">, Pick<BaseToolbar.Input.Props, "focusableWhenDisabled"> {
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { type ReactNode, type Ref } from "react";
|
|
2
2
|
import type { ChatFile } from "./types";
|
|
3
|
+
import type { IconName } from "../Icon";
|
|
3
4
|
export type AttachmentLayout = "tile" | "row";
|
|
4
5
|
export interface AttachmentProps {
|
|
5
6
|
file: ChatFile;
|
|
@@ -24,6 +25,13 @@ export interface AttachmentProps {
|
|
|
24
25
|
* It goes inside the cluster, above the full-card preview trigger — rendered
|
|
25
26
|
* anywhere else it would sit UNDER that trigger and never receive a click.
|
|
26
27
|
* Keep it to a control or two: this is a corner of a tile, not a menu bar.
|
|
28
|
+
*
|
|
29
|
+
* FILL IT WITH `AttachmentAction`, which is exported for exactly this. The
|
|
30
|
+
* built-in download and remove are that component, so anything else lands in
|
|
31
|
+
* the cluster at a different size and, on a tile, without the hover fade the
|
|
32
|
+
* two beside it have. Any node is accepted — the slot has no opinion — but
|
|
33
|
+
* "matches the built-ins" is a real requirement and there is no way to hit it
|
|
34
|
+
* by hand. Pass `tinted` when `layout` is `"tile"`.
|
|
27
35
|
*/
|
|
28
36
|
action?: ReactNode;
|
|
29
37
|
onRemove?: (file: ChatFile) => void;
|
|
@@ -36,6 +44,45 @@ export interface AttachmentProps {
|
|
|
36
44
|
ref?: Ref<HTMLDivElement>;
|
|
37
45
|
}
|
|
38
46
|
export declare function Attachment({ file, layout, meta, action, onRemove, onPreview, onDownload, selected, disabled, className, ref, }: AttachmentProps): import("react").JSX.Element;
|
|
47
|
+
export interface AttachmentActionProps {
|
|
48
|
+
icon: IconName;
|
|
49
|
+
/** The accessible name AND the tooltip. Include the file: "Extract report.pdf". */
|
|
50
|
+
label: string;
|
|
51
|
+
onClick: () => void;
|
|
52
|
+
disabled?: boolean;
|
|
53
|
+
/**
|
|
54
|
+
* On a tile the buttons sit over imagery, so they need their own ground —
|
|
55
|
+
* and they FADE IN on hover rather than sitting permanently over the picture.
|
|
56
|
+
*
|
|
57
|
+
* Pass `layout === "tile"`. Getting it wrong is not a style preference: a
|
|
58
|
+
* tinted control on a row is dark-on-dark, and an untinted one on a tile is
|
|
59
|
+
* a grey glyph over an arbitrary photograph.
|
|
60
|
+
*/
|
|
61
|
+
tinted?: boolean;
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* One control in an attachment's action cluster.
|
|
65
|
+
*
|
|
66
|
+
* THE CONTROL `Attachment.action` IS MEANT TO BE FILLED WITH, and until now it
|
|
67
|
+
* was module-private — so the slot existed with nothing in the library that
|
|
68
|
+
* fits it. A consumer's own `IconButton` is a different size and a different
|
|
69
|
+
* resting state, and on a tile it does not fade in on `group-hover/attachment`
|
|
70
|
+
* with the built-in download and remove beside it, so the one control the
|
|
71
|
+
* consumer added was the one that looked wrong.
|
|
72
|
+
*
|
|
73
|
+
* It is deliberately NOT `IconButton`: `size-6` rather than a control height,
|
|
74
|
+
* no ripple, no `disabledReason`, and a tinted variant that only means anything
|
|
75
|
+
* inside `.group/attachment`. That is a corner-of-a-tile control, not a general
|
|
76
|
+
* one, and generalising it would give the cluster two different buttons again.
|
|
77
|
+
*
|
|
78
|
+
* <Attachment
|
|
79
|
+
* file={file}
|
|
80
|
+
* layout="tile"
|
|
81
|
+
* action={<AttachmentAction icon="sparkles" label={`Extract ${file.name}`}
|
|
82
|
+
* onClick={() => extract(file)} tinted />}
|
|
83
|
+
* />
|
|
84
|
+
*/
|
|
85
|
+
export declare function AttachmentAction({ icon, label, onClick, disabled, tinted, }: AttachmentActionProps): import("react").JSX.Element;
|
|
39
86
|
export interface AttachmentPreviewProps {
|
|
40
87
|
file: ChatFile | null;
|
|
41
88
|
onOpenChange: (open: boolean) => void;
|
package/dist/types/index.d.ts
CHANGED
|
@@ -85,7 +85,7 @@ export { Message, MessagePartView, ToolCall, ChatMarker, type MessageProps, type
|
|
|
85
85
|
export { MessageScroller, type MessageScrollerProps, } from "./components/chat/MessageScroller";
|
|
86
86
|
export { Composer, type ComposerProps } from "./components/chat/Composer";
|
|
87
87
|
export { Markdown, CodeBlock, type MarkdownProps, type CodeBlockProps } from "./components/chat/Markdown";
|
|
88
|
-
export { Attachment, AttachmentList, AttachmentPreview, type AttachmentProps, type AttachmentListProps, type AttachmentPreviewProps, type AttachmentLayout, } from "./components/chat/Attachment";
|
|
88
|
+
export { Attachment, AttachmentAction, AttachmentList, AttachmentPreview, type AttachmentProps, type AttachmentActionProps, type AttachmentListProps, type AttachmentPreviewProps, type AttachmentLayout, } from "./components/chat/Attachment";
|
|
89
89
|
export { ModelSelector, type ModelSelectorProps, type ChatModel, } from "./components/chat/ModelSelector";
|
|
90
90
|
export { EffortControl, DEFAULT_EFFORT_LEVELS, type EffortControlProps, type EffortLevel, } from "./components/chat/EffortControl";
|
|
91
91
|
export { ContextMeter, ChatStatus, type ContextMeterProps, type ContextSegment, type UsageLimit, type ChatStatusProps, } from "./components/chat/ContextMeter";
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@danxbot/ui",
|
|
3
|
-
"version": "3.9.
|
|
3
|
+
"version": "3.9.1",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Danxbot — a domain-agnostic React design system with motion as a first-class primitive.",
|
|
6
6
|
"license": "MIT",
|
|
@@ -66,7 +66,7 @@
|
|
|
66
66
|
"build:types": "tsc -p tsconfig.build.json",
|
|
67
67
|
"build:demo": "vite build",
|
|
68
68
|
"build": "npm run build:lib && npm run build:demo",
|
|
69
|
-
"verify": "npm run typecheck && npm run
|
|
69
|
+
"verify": "npm run typecheck && npm run build && npm run test && npm run typecheck:previews && npm run audit:previews && npm run audit:visual-stale",
|
|
70
70
|
"audit:visual-stale": "node scripts/audit-visual-stale.mjs",
|
|
71
71
|
"preview": "vite preview",
|
|
72
72
|
"preview:built": "vite preview --outDir demo-dist --port 5801 --strictPort",
|