@asharca/ui 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/LICENSE +21 -0
- package/README.md +136 -0
- package/dist/Brand.d.ts +6 -0
- package/dist/Brand.js +5 -0
- package/dist/ChatShell.d.ts +21 -0
- package/dist/ChatShell.js +29 -0
- package/dist/ChatThread.d.ts +96 -0
- package/dist/ChatThread.js +306 -0
- package/dist/ContentPage.d.ts +6 -0
- package/dist/ContentPage.js +4 -0
- package/dist/Controls.d.ts +68 -0
- package/dist/Controls.js +99 -0
- package/dist/ConversationSidebar.d.ts +43 -0
- package/dist/ConversationSidebar.js +67 -0
- package/dist/Dialog.d.ts +9 -0
- package/dist/Dialog.js +35 -0
- package/dist/Feedback.d.ts +22 -0
- package/dist/Feedback.js +48 -0
- package/dist/Forms.d.ts +38 -0
- package/dist/Forms.js +99 -0
- package/dist/Layout.d.ts +73 -0
- package/dist/Layout.js +53 -0
- package/dist/MermaidAssistantText.d.ts +1 -0
- package/dist/MermaidAssistantText.js +15 -0
- package/dist/Navigation.d.ts +39 -0
- package/dist/Navigation.js +60 -0
- package/dist/Overlays.d.ts +24 -0
- package/dist/Overlays.js +62 -0
- package/dist/RotatingHeadline.d.ts +4 -0
- package/dist/RotatingHeadline.js +17 -0
- package/dist/SafeStreamdown.d.ts +5 -0
- package/dist/SafeStreamdown.js +57 -0
- package/dist/Sidebar.d.ts +9 -0
- package/dist/Sidebar.js +24 -0
- package/dist/WorkspaceTabBar.d.ts +33 -0
- package/dist/WorkspaceTabBar.js +56 -0
- package/dist/chat-markdown.d.ts +1 -0
- package/dist/chat-markdown.js +4 -0
- package/dist/index.d.ts +17 -0
- package/dist/index.js +17 -0
- package/package.json +107 -0
- package/src/styles.css +693 -0
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { ContextMenu as ContextMenuPrimitive, HoverCard as HoverCardPrimitive, Popover as PopoverPrimitive, Tooltip as TooltipPrimitive } from 'radix-ui';
|
|
2
|
+
export declare const Popover: import("react").FC<PopoverPrimitive.PopoverProps>;
|
|
3
|
+
export declare const PopoverTrigger: import("react").ForwardRefExoticComponent<PopoverPrimitive.PopoverTriggerProps & import("react").RefAttributes<HTMLButtonElement>>;
|
|
4
|
+
export declare const PopoverPortal: import("react").FC<PopoverPrimitive.PopoverPortalProps>;
|
|
5
|
+
export declare const PopoverClose: import("react").ForwardRefExoticComponent<PopoverPrimitive.PopoverCloseProps & import("react").RefAttributes<HTMLButtonElement>>;
|
|
6
|
+
export declare const PopoverContent: import("react").ForwardRefExoticComponent<Omit<PopoverPrimitive.PopoverContentProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
7
|
+
export declare const TooltipProvider: import("react").FC<TooltipPrimitive.TooltipProviderProps>;
|
|
8
|
+
export declare const Tooltip: import("react").FC<TooltipPrimitive.TooltipProps>;
|
|
9
|
+
export declare const TooltipTrigger: import("react").ForwardRefExoticComponent<TooltipPrimitive.TooltipTriggerProps & import("react").RefAttributes<HTMLButtonElement>>;
|
|
10
|
+
export declare const TooltipPortal: import("react").FC<TooltipPrimitive.TooltipPortalProps>;
|
|
11
|
+
export declare const TooltipContent: import("react").ForwardRefExoticComponent<Omit<TooltipPrimitive.TooltipContentProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
12
|
+
export declare const ContextMenu: import("react").FC<ContextMenuPrimitive.ContextMenuProps>;
|
|
13
|
+
export declare const ContextMenuTrigger: import("react").ForwardRefExoticComponent<ContextMenuPrimitive.ContextMenuTriggerProps & import("react").RefAttributes<HTMLSpanElement>>;
|
|
14
|
+
export declare const ContextMenuPortal: import("react").FC<ContextMenuPrimitive.ContextMenuPortalProps>;
|
|
15
|
+
export declare const ContextMenuSub: import("react").FC<ContextMenuPrimitive.ContextMenuSubProps>;
|
|
16
|
+
export declare const ContextMenuContent: import("react").ForwardRefExoticComponent<Omit<ContextMenuPrimitive.ContextMenuContentProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
17
|
+
export declare const ContextMenuItem: import("react").ForwardRefExoticComponent<Omit<ContextMenuPrimitive.ContextMenuItemProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
18
|
+
export declare const ContextMenuSeparator: import("react").ForwardRefExoticComponent<Omit<ContextMenuPrimitive.ContextMenuSeparatorProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
19
|
+
export declare const ContextMenuSubTrigger: import("react").ForwardRefExoticComponent<Omit<ContextMenuPrimitive.ContextMenuSubTriggerProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
20
|
+
export declare const ContextMenuSubContent: import("react").ForwardRefExoticComponent<Omit<ContextMenuPrimitive.ContextMenuSubContentProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
|
21
|
+
export declare const HoverCard: import("react").FC<HoverCardPrimitive.HoverCardProps>;
|
|
22
|
+
export declare const HoverCardTrigger: import("react").ForwardRefExoticComponent<HoverCardPrimitive.HoverCardTriggerProps & import("react").RefAttributes<HTMLAnchorElement>>;
|
|
23
|
+
export declare const HoverCardPortal: import("react").FC<HoverCardPrimitive.HoverCardPortalProps>;
|
|
24
|
+
export declare const HoverCardContent: import("react").ForwardRefExoticComponent<Omit<HoverCardPrimitive.HoverCardContentProps & import("react").RefAttributes<HTMLDivElement>, "ref"> & import("react").RefAttributes<HTMLDivElement>>;
|
package/dist/Overlays.js
ADDED
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
var __rest = (this && this.__rest) || function (s, e) {
|
|
3
|
+
var t = {};
|
|
4
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
5
|
+
t[p] = s[p];
|
|
6
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
7
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
8
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
9
|
+
t[p[i]] = s[p[i]];
|
|
10
|
+
}
|
|
11
|
+
return t;
|
|
12
|
+
};
|
|
13
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
14
|
+
import { forwardRef, } from 'react';
|
|
15
|
+
import { ContextMenu as ContextMenuPrimitive, HoverCard as HoverCardPrimitive, Popover as PopoverPrimitive, Tooltip as TooltipPrimitive, } from 'radix-ui';
|
|
16
|
+
export const Popover = PopoverPrimitive.Root;
|
|
17
|
+
export const PopoverTrigger = PopoverPrimitive.Trigger;
|
|
18
|
+
export const PopoverPortal = PopoverPrimitive.Portal;
|
|
19
|
+
export const PopoverClose = PopoverPrimitive.Close;
|
|
20
|
+
export const PopoverContent = forwardRef(function PopoverContent(_a, ref) {
|
|
21
|
+
var { className, sideOffset = 4, collisionPadding = 8 } = _a, props = __rest(_a, ["className", "sideOffset", "collisionPadding"]);
|
|
22
|
+
return (_jsx(PopoverPrimitive.Content, Object.assign({}, props, { ref: ref, sideOffset: sideOffset, collisionPadding: collisionPadding, "data-toolplane-ui": "popover-content", className: `z-50 max-h-[var(--radix-popover-content-available-height)] max-w-[calc(100vw-1rem)] origin-[var(--radix-popover-content-transform-origin)] overflow-auto rounded-lg border border-border bg-popover p-3 text-popover-foreground shadow-lg outline-none data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
23
|
+
});
|
|
24
|
+
export const TooltipProvider = TooltipPrimitive.Provider;
|
|
25
|
+
export const Tooltip = TooltipPrimitive.Root;
|
|
26
|
+
export const TooltipTrigger = TooltipPrimitive.Trigger;
|
|
27
|
+
export const TooltipPortal = TooltipPrimitive.Portal;
|
|
28
|
+
export const TooltipContent = forwardRef(function TooltipContent(_a, ref) {
|
|
29
|
+
var { className, sideOffset = 6, collisionPadding = 8 } = _a, props = __rest(_a, ["className", "sideOffset", "collisionPadding"]);
|
|
30
|
+
return (_jsx(TooltipPrimitive.Content, Object.assign({}, props, { ref: ref, sideOffset: sideOffset, collisionPadding: collisionPadding, "data-toolplane-ui": "tooltip-content", className: `z-50 max-w-xs origin-[var(--radix-tooltip-content-transform-origin)] rounded-lg border border-border bg-popover px-3 py-2 text-xs text-popover-foreground shadow-lg outline-none data-[state=closed]:animate-out data-[state=delayed-open]:animate-in data-[state=closed]:fade-out-0 data-[state=delayed-open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=delayed-open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
31
|
+
});
|
|
32
|
+
export const ContextMenu = ContextMenuPrimitive.Root;
|
|
33
|
+
export const ContextMenuTrigger = ContextMenuPrimitive.Trigger;
|
|
34
|
+
export const ContextMenuPortal = ContextMenuPrimitive.Portal;
|
|
35
|
+
export const ContextMenuSub = ContextMenuPrimitive.Sub;
|
|
36
|
+
export const ContextMenuContent = forwardRef(function ContextMenuContent(_a, ref) {
|
|
37
|
+
var { className, collisionPadding = 8 } = _a, props = __rest(_a, ["className", "collisionPadding"]);
|
|
38
|
+
return (_jsx(ContextMenuPrimitive.Content, Object.assign({}, props, { ref: ref, collisionPadding: collisionPadding, "data-toolplane-ui": "context-menu-content", className: `z-50 max-h-[var(--radix-context-menu-content-available-height)] min-w-40 origin-[var(--radix-context-menu-content-transform-origin)] overflow-x-hidden overflow-y-auto rounded-md border border-border bg-popover p-1 text-popover-foreground shadow-md outline-none data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
39
|
+
});
|
|
40
|
+
export const ContextMenuItem = forwardRef(function ContextMenuItem(_a, ref) {
|
|
41
|
+
var { className } = _a, props = __rest(_a, ["className"]);
|
|
42
|
+
return (_jsx(ContextMenuPrimitive.Item, Object.assign({}, props, { ref: ref, "data-toolplane-ui": "context-menu-item", className: `relative flex min-h-8 cursor-default select-none items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 data-[highlighted]:bg-accent data-[highlighted]:text-accent-foreground ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
43
|
+
});
|
|
44
|
+
export const ContextMenuSeparator = forwardRef(function ContextMenuSeparator(_a, ref) {
|
|
45
|
+
var { className } = _a, props = __rest(_a, ["className"]);
|
|
46
|
+
return (_jsx(ContextMenuPrimitive.Separator, Object.assign({}, props, { ref: ref, "data-toolplane-ui": "context-menu-separator", className: `my-1 h-px bg-border ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
47
|
+
});
|
|
48
|
+
export const ContextMenuSubTrigger = forwardRef(function ContextMenuSubTrigger(_a, ref) {
|
|
49
|
+
var { className } = _a, props = __rest(_a, ["className"]);
|
|
50
|
+
return (_jsx(ContextMenuPrimitive.SubTrigger, Object.assign({}, props, { ref: ref, "data-toolplane-ui": "context-menu-sub-trigger", className: `relative flex min-h-8 cursor-default select-none items-center gap-2 rounded-sm px-2 py-1.5 text-sm outline-none data-[disabled]:pointer-events-none data-[disabled]:opacity-50 data-[highlighted]:bg-accent data-[highlighted]:text-accent-foreground data-[state=open]:bg-accent ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
51
|
+
});
|
|
52
|
+
export const ContextMenuSubContent = forwardRef(function ContextMenuSubContent(_a, ref) {
|
|
53
|
+
var { className, collisionPadding = 8 } = _a, props = __rest(_a, ["className", "collisionPadding"]);
|
|
54
|
+
return (_jsx(ContextMenuPrimitive.SubContent, Object.assign({}, props, { ref: ref, collisionPadding: collisionPadding, "data-toolplane-ui": "context-menu-sub-content", className: `z-50 min-w-40 overflow-hidden rounded-md border border-border bg-popover p-1 text-popover-foreground shadow-md outline-none data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
55
|
+
});
|
|
56
|
+
export const HoverCard = HoverCardPrimitive.Root;
|
|
57
|
+
export const HoverCardTrigger = HoverCardPrimitive.Trigger;
|
|
58
|
+
export const HoverCardPortal = HoverCardPrimitive.Portal;
|
|
59
|
+
export const HoverCardContent = forwardRef(function HoverCardContent(_a, ref) {
|
|
60
|
+
var { className, sideOffset = 8, collisionPadding = 8 } = _a, props = __rest(_a, ["className", "sideOffset", "collisionPadding"]);
|
|
61
|
+
return (_jsx(HoverCardPrimitive.Content, Object.assign({}, props, { ref: ref, sideOffset: sideOffset, collisionPadding: collisionPadding, "data-toolplane-ui": "hover-card-content", className: `z-50 max-w-[calc(100vw-1rem)] origin-[var(--radix-hover-card-content-transform-origin)] rounded-lg border border-border bg-popover p-3 text-popover-foreground shadow-xl outline-none data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0 data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95 data-[side=bottom]:slide-in-from-top-2 data-[side=left]:slide-in-from-right-2 data-[side=right]:slide-in-from-left-2 data-[side=top]:slide-in-from-bottom-2 ${className !== null && className !== void 0 ? className : ''}`.trim() })));
|
|
62
|
+
});
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { useEffect, useState } from 'react';
|
|
4
|
+
export function RotatingHeadline({ words }) {
|
|
5
|
+
var _a, _b;
|
|
6
|
+
const [wordIndex, setWordIndex] = useState(0);
|
|
7
|
+
useEffect(() => {
|
|
8
|
+
if (typeof window.matchMedia === 'function'
|
|
9
|
+
&& window.matchMedia('(prefers-reduced-motion: reduce)').matches) {
|
|
10
|
+
return;
|
|
11
|
+
}
|
|
12
|
+
const timers = words.slice(1).map((_, index) => window.setTimeout(() => setWordIndex(index + 1), (index + 1) * 950));
|
|
13
|
+
return () => timers.forEach(window.clearTimeout);
|
|
14
|
+
}, [words]);
|
|
15
|
+
const activeWord = (_b = (_a = words[wordIndex]) !== null && _a !== void 0 ? _a : words[0]) !== null && _b !== void 0 ? _b : '';
|
|
16
|
+
return (_jsxs("span", { "data-toolplane-ui": "rotating-headline", className: "relative inline-grid text-muted-foreground", children: [words.map((word) => (_jsx("span", { "aria-hidden": true, className: "invisible col-start-1 row-start-1", children: word }, word))), _jsx("span", { "aria-hidden": true, className: "tp-rotating-headline__word col-start-1 row-start-1", children: activeWord }, activeWord)] }));
|
|
17
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { type StreamdownProps } from 'streamdown';
|
|
2
|
+
export type SafeStreamdownProps = StreamdownProps & {
|
|
3
|
+
preserveSoftBreaks?: boolean;
|
|
4
|
+
};
|
|
5
|
+
export declare function SafeStreamdown({ allowElement, components, disallowedElements, preserveSoftBreaks, remarkPlugins, ...props }: SafeStreamdownProps): import("react").JSX.Element;
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
var __rest = (this && this.__rest) || function (s, e) {
|
|
3
|
+
var t = {};
|
|
4
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
5
|
+
t[p] = s[p];
|
|
6
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
7
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
8
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
9
|
+
t[p[i]] = s[p[i]];
|
|
10
|
+
}
|
|
11
|
+
return t;
|
|
12
|
+
};
|
|
13
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
14
|
+
import { useCallback, useMemo } from 'react';
|
|
15
|
+
import remarkBreaks from 'remark-breaks';
|
|
16
|
+
import { defaultRemarkPlugins, Streamdown } from 'streamdown';
|
|
17
|
+
const BLOCKED_RAW_HTML_ELEMENTS = [
|
|
18
|
+
'base',
|
|
19
|
+
'embed',
|
|
20
|
+
'iframe',
|
|
21
|
+
'link',
|
|
22
|
+
'meta',
|
|
23
|
+
'object',
|
|
24
|
+
'script',
|
|
25
|
+
'style',
|
|
26
|
+
];
|
|
27
|
+
const BLOCKED_RAW_HTML_ELEMENT_SET = new Set(BLOCKED_RAW_HTML_ELEMENTS);
|
|
28
|
+
function BlockedRawHtmlElement() {
|
|
29
|
+
return null;
|
|
30
|
+
}
|
|
31
|
+
const BLOCKED_RAW_HTML_COMPONENTS = Object.fromEntries(BLOCKED_RAW_HTML_ELEMENTS.map((tag) => [tag, BlockedRawHtmlElement]));
|
|
32
|
+
const SOFT_BREAK_REMARK_PLUGINS = [
|
|
33
|
+
...Object.values(defaultRemarkPlugins),
|
|
34
|
+
remarkBreaks,
|
|
35
|
+
];
|
|
36
|
+
export function SafeStreamdown(_a) {
|
|
37
|
+
var { allowElement, components, disallowedElements, preserveSoftBreaks = false, remarkPlugins } = _a, props = __rest(_a, ["allowElement", "components", "disallowedElements", "preserveSoftBreaks", "remarkPlugins"]);
|
|
38
|
+
const safeComponents = useMemo(() => (Object.assign(Object.assign({}, components), BLOCKED_RAW_HTML_COMPONENTS)), [components]);
|
|
39
|
+
const safeDisallowedElements = useMemo(() => {
|
|
40
|
+
const tags = new Set(disallowedElements !== null && disallowedElements !== void 0 ? disallowedElements : []);
|
|
41
|
+
BLOCKED_RAW_HTML_ELEMENTS.forEach((tag) => tags.add(tag));
|
|
42
|
+
return Array.from(tags);
|
|
43
|
+
}, [disallowedElements]);
|
|
44
|
+
const safeAllowElement = useCallback((element, index, parent) => {
|
|
45
|
+
var _a;
|
|
46
|
+
if (BLOCKED_RAW_HTML_ELEMENT_SET.has(element.tagName.toLowerCase())) {
|
|
47
|
+
return false;
|
|
48
|
+
}
|
|
49
|
+
return (_a = allowElement === null || allowElement === void 0 ? void 0 : allowElement(element, index, parent)) !== null && _a !== void 0 ? _a : true;
|
|
50
|
+
}, [allowElement]);
|
|
51
|
+
const effectiveRemarkPlugins = useMemo(() => {
|
|
52
|
+
if (!preserveSoftBreaks)
|
|
53
|
+
return remarkPlugins;
|
|
54
|
+
return remarkPlugins ? [...remarkPlugins, remarkBreaks] : SOFT_BREAK_REMARK_PLUGINS;
|
|
55
|
+
}, [preserveSoftBreaks, remarkPlugins]);
|
|
56
|
+
return (_jsx(Streamdown, Object.assign({}, props, { allowElement: safeAllowElement, components: safeComponents, disallowedElements: safeDisallowedElements, remarkPlugins: effectiveRemarkPlugins })));
|
|
57
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { type ButtonHTMLAttributes, type HTMLAttributes } from 'react';
|
|
2
|
+
export type SidebarActionRailProps = HTMLAttributes<HTMLDivElement> & {
|
|
3
|
+
active?: boolean;
|
|
4
|
+
hasLeadingSlot?: boolean;
|
|
5
|
+
revealOnCellFocus?: boolean;
|
|
6
|
+
};
|
|
7
|
+
export declare function SidebarActionRail({ active, children, className, hasLeadingSlot, revealOnCellFocus, ...props }: SidebarActionRailProps): import("react").JSX.Element;
|
|
8
|
+
export type SidebarActionButtonProps = ButtonHTMLAttributes<HTMLButtonElement>;
|
|
9
|
+
export declare const SidebarActionButton: import("react").ForwardRefExoticComponent<SidebarActionButtonProps & import("react").RefAttributes<HTMLButtonElement>>;
|
package/dist/Sidebar.js
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
var __rest = (this && this.__rest) || function (s, e) {
|
|
2
|
+
var t = {};
|
|
3
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
4
|
+
t[p] = s[p];
|
|
5
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
6
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
7
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
8
|
+
t[p[i]] = s[p[i]];
|
|
9
|
+
}
|
|
10
|
+
return t;
|
|
11
|
+
};
|
|
12
|
+
import { jsx as _jsx } from "react/jsx-runtime";
|
|
13
|
+
import { forwardRef, } from 'react';
|
|
14
|
+
function cx(...classes) {
|
|
15
|
+
return classes.filter(Boolean).join(' ');
|
|
16
|
+
}
|
|
17
|
+
export function SidebarActionRail(_a) {
|
|
18
|
+
var { active = false, children, className, hasLeadingSlot = false, revealOnCellFocus = false } = _a, props = __rest(_a, ["active", "children", "className", "hasLeadingSlot", "revealOnCellFocus"]);
|
|
19
|
+
return (_jsx("div", Object.assign({}, props, { "data-active": active || undefined, "data-toolplane-ui": "sidebar-action-rail", className: cx('-ml-1.5 pointer-events-none grid shrink-0 grid-cols-[0fr] opacity-0 transition-[grid-template-columns,opacity] duration-150 motion-reduce:transition-none', hasLeadingSlot ? 'mr-0' : '-mr-1', 'focus-within:pointer-events-auto focus-within:grid-cols-[1fr] focus-within:opacity-100 group-hover:pointer-events-auto group-hover:grid-cols-[1fr] group-hover:opacity-100', 'has-data-[state=open]:pointer-events-auto has-data-[state=open]:grid-cols-[1fr] has-data-[state=open]:opacity-100 group-data-[state=open]:pointer-events-auto group-data-[state=open]:grid-cols-[1fr] group-data-[state=open]:opacity-100', 'data-[active=true]:pointer-events-auto data-[active=true]:grid-cols-[1fr] data-[active=true]:opacity-100', revealOnCellFocus && 'group-has-[:focus-visible]:pointer-events-auto group-has-[:focus-visible]:grid-cols-[1fr] group-has-[:focus-visible]:opacity-100', className), children: _jsx("div", { className: "flex min-w-0 items-center overflow-hidden", children: children }) })));
|
|
20
|
+
}
|
|
21
|
+
export const SidebarActionButton = forwardRef(function SidebarActionButton(_a, ref) {
|
|
22
|
+
var { className, type = 'button' } = _a, props = __rest(_a, ["className", "type"]);
|
|
23
|
+
return (_jsx("button", Object.assign({}, props, { ref: ref, type: type, "data-toolplane-ui": "sidebar-action-button", className: cx('pointer-events-none flex size-5 shrink-0 items-center justify-center rounded-lg text-muted-foreground opacity-0 outline-none transition-all duration-150', 'hover:bg-accent hover:text-foreground focus-visible:pointer-events-auto focus-visible:bg-accent focus-visible:text-foreground focus-visible:opacity-100', 'group-hover:pointer-events-auto group-hover:opacity-100 group-data-[state=open]:pointer-events-auto group-data-[state=open]:opacity-100 data-[active=true]:pointer-events-auto data-[active=true]:opacity-100 data-[deleting=true]:pointer-events-auto data-[deleting=true]:opacity-100', className) })));
|
|
24
|
+
});
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { type ComponentType, type ReactNode } from 'react';
|
|
2
|
+
type Icon = ComponentType<{
|
|
3
|
+
className?: string;
|
|
4
|
+
}>;
|
|
5
|
+
export type WorkspaceTab = {
|
|
6
|
+
id: string;
|
|
7
|
+
icon: Icon;
|
|
8
|
+
label: string;
|
|
9
|
+
pinned: boolean;
|
|
10
|
+
};
|
|
11
|
+
export type WorkspaceTabBarLabels = {
|
|
12
|
+
close: (label: string) => string;
|
|
13
|
+
navigation: string;
|
|
14
|
+
newTab: string;
|
|
15
|
+
openInNewWindow: (label: string) => string;
|
|
16
|
+
pin: (label: string) => string;
|
|
17
|
+
unpin: (label: string) => string;
|
|
18
|
+
};
|
|
19
|
+
export declare const workspaceTabBarDefaultLabels: WorkspaceTabBarLabels;
|
|
20
|
+
export type WorkspaceTabBarProps = {
|
|
21
|
+
actions?: ReactNode;
|
|
22
|
+
activeTabId: string;
|
|
23
|
+
labels?: Partial<WorkspaceTabBarLabels>;
|
|
24
|
+
onClose: (id: string) => void;
|
|
25
|
+
onNewTab: () => void;
|
|
26
|
+
onOpenInNewWindow: (id: string) => void;
|
|
27
|
+
onReorder: (sourceId: string, targetId: string) => void;
|
|
28
|
+
onSelect: (id: string) => void;
|
|
29
|
+
onTogglePinned: (id: string) => void;
|
|
30
|
+
tabs: WorkspaceTab[];
|
|
31
|
+
};
|
|
32
|
+
export declare function WorkspaceTabBar({ actions, activeTabId, labels: labelsOverride, onClose, onNewTab, onOpenInNewWindow, onReorder, onSelect, onTogglePinned, tabs, }: WorkspaceTabBarProps): import("react").JSX.Element;
|
|
33
|
+
export {};
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { ExternalLink, Pin, Plus, X } from 'lucide-react';
|
|
4
|
+
import { useEffect, useRef, useState, } from 'react';
|
|
5
|
+
export const workspaceTabBarDefaultLabels = {
|
|
6
|
+
close: (label) => `Close ${label}`,
|
|
7
|
+
navigation: 'Open pages',
|
|
8
|
+
newTab: 'New tab',
|
|
9
|
+
openInNewWindow: (label) => `Open ${label} in new window`,
|
|
10
|
+
pin: (label) => `Pin ${label}`,
|
|
11
|
+
unpin: (label) => `Unpin ${label}`,
|
|
12
|
+
};
|
|
13
|
+
export function WorkspaceTabBar({ actions, activeTabId, labels: labelsOverride, onClose, onNewTab, onOpenInNewWindow, onReorder, onSelect, onTogglePinned, tabs, }) {
|
|
14
|
+
const labels = Object.assign(Object.assign({}, workspaceTabBarDefaultLabels), labelsOverride);
|
|
15
|
+
const [draggingId, setDraggingId] = useState(null);
|
|
16
|
+
const activeRef = useRef(null);
|
|
17
|
+
useEffect(() => {
|
|
18
|
+
var _a, _b;
|
|
19
|
+
(_b = (_a = activeRef.current) === null || _a === void 0 ? void 0 : _a.scrollIntoView) === null || _b === void 0 ? void 0 : _b.call(_a, { block: 'nearest', inline: 'nearest' });
|
|
20
|
+
}, [activeTabId, tabs.length]);
|
|
21
|
+
return (_jsxs("nav", { "aria-label": labels.navigation, "data-toolplane-ui": "workspace-tab-bar", className: "flex h-11 shrink-0 bg-shell px-2", children: [_jsxs("ol", { className: "flex min-w-0 flex-1 items-center gap-1 overflow-x-auto py-1 [&::-webkit-scrollbar]:hidden", children: [tabs.map((tab) => (_jsx(WorkspaceTabButton, { tab: tab, active: tab.id === activeTabId, canClose: tabs.length > 1, draggingId: draggingId, labels: labels, onClose: onClose, onDragChange: setDraggingId, onNewWindow: onOpenInNewWindow, onReorder: onReorder, onSelect: onSelect, onTogglePinned: onTogglePinned, activeButtonRef: tab.id === activeTabId ? activeRef : undefined }, tab.id))), _jsx("li", { className: "shrink-0", children: _jsx("button", { type: "button", "aria-label": labels.newTab, title: labels.newTab, onClick: onNewTab, className: "ui-button-ghost ui-icon-button", children: _jsx(Plus, { className: "size-4" }) }) })] }), actions] }));
|
|
22
|
+
}
|
|
23
|
+
function WorkspaceTabButton({ active, activeButtonRef, canClose, draggingId, labels, onClose, onDragChange, onNewWindow, onReorder, onSelect, onTogglePinned, tab, }) {
|
|
24
|
+
const dragAllowed = Boolean(draggingId && draggingId !== tab.id);
|
|
25
|
+
const controls = active || draggingId === tab.id;
|
|
26
|
+
const stop = (event) => event.stopPropagation();
|
|
27
|
+
const Icon = tab.icon;
|
|
28
|
+
return (_jsxs("li", { "data-tab-id": tab.id, "data-active": active ? 'true' : undefined, draggable: true, onDragEnd: () => onDragChange(null), onDragStart: (event) => {
|
|
29
|
+
event.dataTransfer.effectAllowed = 'move';
|
|
30
|
+
event.dataTransfer.setData('text/plain', tab.id);
|
|
31
|
+
onDragChange(tab.id);
|
|
32
|
+
}, onDragOver: (event) => {
|
|
33
|
+
if (!dragAllowed)
|
|
34
|
+
return;
|
|
35
|
+
event.preventDefault();
|
|
36
|
+
event.dataTransfer.dropEffect = 'move';
|
|
37
|
+
}, onDrop: (event) => {
|
|
38
|
+
if (!draggingId || draggingId === tab.id)
|
|
39
|
+
return;
|
|
40
|
+
event.preventDefault();
|
|
41
|
+
onReorder(draggingId, tab.id);
|
|
42
|
+
onDragChange(null);
|
|
43
|
+
}, className: `group flex h-[30px] min-w-24 max-w-56 shrink-0 items-center rounded-[10px] transition-[background-color,color,transform] duration-150 ${active ? 'bg-background text-foreground ring-1 ring-border/70' : 'text-muted-foreground hover:bg-accent/70 hover:text-foreground'} ${draggingId === tab.id ? 'scale-[0.98] opacity-50' : ''}`, children: [_jsxs("button", { ref: activeButtonRef, type: "button", "aria-current": active ? 'page' : undefined, title: tab.label, onAuxClick: (event) => {
|
|
44
|
+
if (event.button === 1)
|
|
45
|
+
onClose(tab.id);
|
|
46
|
+
}, onClick: () => onSelect(tab.id), onDoubleClick: () => onClose(tab.id), className: "flex min-w-0 flex-1 items-center gap-1.5 px-2 text-left text-xs", children: [_jsx(Icon, { className: "size-3.5 shrink-0" }), _jsx("span", { className: "truncate", children: tab.label })] }), _jsxs("div", { className: "mr-1 flex shrink-0 items-center", children: [_jsx("button", { type: "button", "aria-pressed": tab.pinned, "aria-label": tab.pinned ? labels.unpin(tab.label) : labels.pin(tab.label), title: tab.pinned ? labels.unpin(tab.label) : labels.pin(tab.label), onClick: (event) => {
|
|
47
|
+
stop(event);
|
|
48
|
+
onTogglePinned(tab.id);
|
|
49
|
+
}, className: `flex size-[18px] items-center justify-center rounded-sm transition-colors hover:bg-foreground/10 ${tab.pinned ? (controls ? 'bg-brand-soft text-accent-foreground' : 'bg-brand-soft/50 text-accent-foreground/60 group-hover:bg-brand-soft group-hover:text-accent-foreground group-focus-within:bg-brand-soft group-focus-within:text-accent-foreground') : (controls ? '' : 'opacity-0 group-hover:opacity-100 group-focus-within:opacity-100')}`, children: _jsx(Pin, { className: `size-3 ${tab.pinned ? 'fill-current' : ''}` }) }), _jsxs("div", { className: `flex items-center transition-opacity ${controls ? 'opacity-100' : 'opacity-0 group-hover:opacity-100 group-focus-within:opacity-100'}`, children: [_jsx("button", { type: "button", "aria-label": labels.openInNewWindow(tab.label), title: labels.openInNewWindow(tab.label), onClick: (event) => {
|
|
50
|
+
stop(event);
|
|
51
|
+
onNewWindow(tab.id);
|
|
52
|
+
}, className: "flex size-[18px] items-center justify-center rounded-sm hover:bg-foreground/10", children: _jsx(ExternalLink, { className: "size-3" }) }), canClose ? (_jsx("button", { type: "button", "aria-label": labels.close(tab.label), title: labels.close(tab.label), onClick: (event) => {
|
|
53
|
+
stop(event);
|
|
54
|
+
onClose(tab.id);
|
|
55
|
+
}, className: "flex size-[18px] items-center justify-center rounded-sm hover:bg-foreground/10", children: _jsx(X, { className: "size-3" }) })) : null] })] })] }));
|
|
56
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export declare function hasMermaidFence(markdown: string): boolean;
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export * from './Brand.js';
|
|
2
|
+
export * from './ChatShell.js';
|
|
3
|
+
export * from './ChatThread.js';
|
|
4
|
+
export * from './chat-markdown.js';
|
|
5
|
+
export * from './ContentPage.js';
|
|
6
|
+
export * from './Controls.js';
|
|
7
|
+
export * from './ConversationSidebar.js';
|
|
8
|
+
export * from './Dialog.js';
|
|
9
|
+
export * from './Feedback.js';
|
|
10
|
+
export * from './Forms.js';
|
|
11
|
+
export * from './Layout.js';
|
|
12
|
+
export * from './Navigation.js';
|
|
13
|
+
export * from './Overlays.js';
|
|
14
|
+
export * from './RotatingHeadline.js';
|
|
15
|
+
export * from './SafeStreamdown.js';
|
|
16
|
+
export * from './Sidebar.js';
|
|
17
|
+
export * from './WorkspaceTabBar.js';
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export * from "./Brand.js";
|
|
2
|
+
export * from "./ChatShell.js";
|
|
3
|
+
export * from "./ChatThread.js";
|
|
4
|
+
export * from "./chat-markdown.js";
|
|
5
|
+
export * from "./ContentPage.js";
|
|
6
|
+
export * from "./Controls.js";
|
|
7
|
+
export * from "./ConversationSidebar.js";
|
|
8
|
+
export * from "./Dialog.js";
|
|
9
|
+
export * from "./Feedback.js";
|
|
10
|
+
export * from "./Forms.js";
|
|
11
|
+
export * from "./Layout.js";
|
|
12
|
+
export * from "./Navigation.js";
|
|
13
|
+
export * from "./Overlays.js";
|
|
14
|
+
export * from "./RotatingHeadline.js";
|
|
15
|
+
export * from "./SafeStreamdown.js";
|
|
16
|
+
export * from "./Sidebar.js";
|
|
17
|
+
export * from "./WorkspaceTabBar.js";
|
package/package.json
ADDED
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@asharca/ui",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Reusable ToolPlane components and chat UI for React applications.",
|
|
5
|
+
"license": "MIT",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"main": "./dist/index.js",
|
|
8
|
+
"types": "./dist/index.d.ts",
|
|
9
|
+
"keywords": [
|
|
10
|
+
"toolplane",
|
|
11
|
+
"react",
|
|
12
|
+
"ui",
|
|
13
|
+
"chat",
|
|
14
|
+
"assistant-ui",
|
|
15
|
+
"tailwindcss"
|
|
16
|
+
],
|
|
17
|
+
"repository": {
|
|
18
|
+
"type": "git",
|
|
19
|
+
"url": "git+https://github.com/asharca/ToolPlane.git",
|
|
20
|
+
"directory": "packages/ui"
|
|
21
|
+
},
|
|
22
|
+
"homepage": "https://github.com/asharca/ToolPlane/tree/main/packages/ui",
|
|
23
|
+
"bugs": {
|
|
24
|
+
"url": "https://github.com/asharca/ToolPlane/issues"
|
|
25
|
+
},
|
|
26
|
+
"engines": {
|
|
27
|
+
"node": ">=20"
|
|
28
|
+
},
|
|
29
|
+
"sideEffects": [
|
|
30
|
+
"./src/styles.css"
|
|
31
|
+
],
|
|
32
|
+
"files": [
|
|
33
|
+
"dist",
|
|
34
|
+
"src/styles.css",
|
|
35
|
+
"README.md",
|
|
36
|
+
"LICENSE"
|
|
37
|
+
],
|
|
38
|
+
"exports": {
|
|
39
|
+
".": {
|
|
40
|
+
"types": "./dist/index.d.ts",
|
|
41
|
+
"import": "./dist/index.js"
|
|
42
|
+
},
|
|
43
|
+
"./controls": {
|
|
44
|
+
"types": "./dist/Controls.d.ts",
|
|
45
|
+
"import": "./dist/Controls.js"
|
|
46
|
+
},
|
|
47
|
+
"./dialog": {
|
|
48
|
+
"types": "./dist/Dialog.d.ts",
|
|
49
|
+
"import": "./dist/Dialog.js"
|
|
50
|
+
},
|
|
51
|
+
"./feedback": {
|
|
52
|
+
"types": "./dist/Feedback.d.ts",
|
|
53
|
+
"import": "./dist/Feedback.js"
|
|
54
|
+
},
|
|
55
|
+
"./forms": {
|
|
56
|
+
"types": "./dist/Forms.d.ts",
|
|
57
|
+
"import": "./dist/Forms.js"
|
|
58
|
+
},
|
|
59
|
+
"./layout": {
|
|
60
|
+
"types": "./dist/Layout.d.ts",
|
|
61
|
+
"import": "./dist/Layout.js"
|
|
62
|
+
},
|
|
63
|
+
"./navigation": {
|
|
64
|
+
"types": "./dist/Navigation.d.ts",
|
|
65
|
+
"import": "./dist/Navigation.js"
|
|
66
|
+
},
|
|
67
|
+
"./overlays": {
|
|
68
|
+
"types": "./dist/Overlays.d.ts",
|
|
69
|
+
"import": "./dist/Overlays.js"
|
|
70
|
+
},
|
|
71
|
+
"./chat-shell": {
|
|
72
|
+
"types": "./dist/ChatShell.d.ts",
|
|
73
|
+
"import": "./dist/ChatShell.js"
|
|
74
|
+
},
|
|
75
|
+
"./chat-thread": {
|
|
76
|
+
"types": "./dist/ChatThread.d.ts",
|
|
77
|
+
"import": "./dist/ChatThread.js"
|
|
78
|
+
},
|
|
79
|
+
"./conversation-sidebar": {
|
|
80
|
+
"types": "./dist/ConversationSidebar.d.ts",
|
|
81
|
+
"import": "./dist/ConversationSidebar.js"
|
|
82
|
+
},
|
|
83
|
+
"./styles.css": "./src/styles.css"
|
|
84
|
+
},
|
|
85
|
+
"publishConfig": {
|
|
86
|
+
"access": "public"
|
|
87
|
+
},
|
|
88
|
+
"peerDependencies": {
|
|
89
|
+
"@assistant-ui/react": "^0.14.26",
|
|
90
|
+
"react": "^19.0.0",
|
|
91
|
+
"react-dom": "^19.0.0",
|
|
92
|
+
"tailwindcss": "^4.0.0"
|
|
93
|
+
},
|
|
94
|
+
"dependencies": {
|
|
95
|
+
"@assistant-ui/react-streamdown": "0.3.5",
|
|
96
|
+
"@streamdown/code": "^1.1.1",
|
|
97
|
+
"@streamdown/mermaid": "^1.0.2",
|
|
98
|
+
"lucide-react": "^1.21.0",
|
|
99
|
+
"radix-ui": "1.6.2",
|
|
100
|
+
"remark-breaks": "^4.0.0",
|
|
101
|
+
"streamdown": "^2.5.0"
|
|
102
|
+
},
|
|
103
|
+
"scripts": {
|
|
104
|
+
"build": "node --input-type=module -e \"import { rmSync } from 'node:fs'; rmSync('dist', { recursive: true, force: true })\" && tsc -p tsconfig.json",
|
|
105
|
+
"postbuild": "node --input-type=module -e \"import { readFileSync, writeFileSync } from 'node:fs'; const path = 'dist/index.d.ts'; writeFileSync(path, readFileSync(path, 'utf8').replaceAll('.tsx', '.js').replaceAll('.ts', '.js'))\""
|
|
106
|
+
}
|
|
107
|
+
}
|