@mcp-b/react-components 0.1.1 → 0.1.3
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/Button-QCM8ZKgR.d.ts +98 -0
- package/dist/CodeBlock-CttHhWcb.js +356 -0
- package/dist/CodeBlock-V6pgafSS.d.ts +174 -0
- package/dist/Select-CRsKCJ9x.d.ts +200 -0
- package/dist/class-names-9UtZwb0J.js +12 -0
- package/dist/components/Accordion.d.ts +81 -0
- package/dist/components/Accordion.js +97 -0
- package/dist/components/AgentConnection.d.ts +69 -0
- package/dist/components/AgentConnection.js +176 -0
- package/dist/components/AlertDialog.d.ts +148 -0
- package/dist/components/AlertDialog.js +141 -0
- package/dist/components/Artifact.d.ts +128 -0
- package/dist/components/Artifact.js +115 -0
- package/dist/components/Autocomplete.d.ts +186 -0
- package/dist/components/Autocomplete.js +186 -0
- package/dist/components/Avatar.d.ts +134 -0
- package/dist/components/Avatar.js +118 -0
- package/dist/components/Badge.d.ts +68 -0
- package/dist/components/Badge.js +108 -0
- package/dist/components/Button.d.ts +2 -0
- package/dist/components/Button.js +73 -0
- package/dist/components/Card.d.ts +87 -0
- package/dist/components/Card.js +81 -0
- package/dist/components/ChainOfThought.d.ts +153 -0
- package/dist/components/ChainOfThought.js +157 -0
- package/dist/components/Checkbox.d.ts +35 -0
- package/dist/components/Checkbox.js +47 -0
- package/dist/components/CheckboxGroup.d.ts +76 -0
- package/dist/components/CheckboxGroup.js +69 -0
- package/dist/components/CodeBlock.d.ts +2 -0
- package/dist/components/CodeBlock.js +2 -0
- package/dist/components/Collapsible.d.ts +127 -0
- package/dist/components/Collapsible.js +103 -0
- package/dist/components/Combobox.d.ts +177 -0
- package/dist/components/Combobox.js +179 -0
- package/dist/components/Commit.d.ts +265 -0
- package/dist/components/Commit.js +282 -0
- package/dist/components/Context.d.ts +129 -0
- package/dist/components/Context.js +309 -0
- package/dist/components/ContextMenu.d.ts +282 -0
- package/dist/components/ContextMenu.js +270 -0
- package/dist/components/Conversation.d.ts +166 -0
- package/dist/components/Conversation.js +202 -0
- package/dist/components/Dialog.d.ts +120 -0
- package/dist/components/Dialog.js +114 -0
- package/dist/components/EnvironmentVariables.d.ts +176 -0
- package/dist/components/EnvironmentVariables.js +221 -0
- package/dist/components/Field.d.ts +281 -0
- package/dist/components/Field.js +274 -0
- package/dist/components/Fieldset.d.ts +93 -0
- package/dist/components/Fieldset.js +81 -0
- package/dist/components/FileTree.d.ts +116 -0
- package/dist/components/FileTree.js +310 -0
- package/dist/components/Form.d.ts +94 -0
- package/dist/components/Form.js +88 -0
- package/dist/components/GithubMotionMark.d.ts +13 -0
- package/dist/components/GithubMotionMark.js +23 -0
- package/dist/components/Input.d.ts +33 -0
- package/dist/components/Input.js +27 -0
- package/dist/components/Label.d.ts +44 -0
- package/dist/components/Label.js +41 -0
- package/dist/components/Menu.d.ts +395 -0
- package/dist/components/Menu.js +338 -0
- package/dist/components/Menubar.d.ts +331 -0
- package/dist/components/Menubar.js +299 -0
- package/dist/components/Message.d.ts +216 -0
- package/dist/components/Message.js +245 -0
- package/dist/components/Meter.d.ts +151 -0
- package/dist/components/Meter.js +121 -0
- package/dist/components/ModelSelector.d.ts +198 -0
- package/dist/components/ModelSelector.js +306 -0
- package/dist/components/NaniteScene.d.ts +33 -0
- package/dist/components/NaniteScene.js +405 -0
- package/dist/components/NavigationMenu.d.ts +256 -0
- package/dist/components/NavigationMenu.js +228 -0
- package/dist/components/NumberField.d.ts +159 -0
- package/dist/components/NumberField.js +123 -0
- package/dist/components/Popover.d.ts +278 -0
- package/dist/components/Popover.js +245 -0
- package/dist/components/PreviewCard.d.ts +156 -0
- package/dist/components/PreviewCard.js +156 -0
- package/dist/components/PricingPage.d.ts +209 -0
- package/dist/components/PricingPage.js +506 -0
- package/dist/components/Progress.d.ts +58 -0
- package/dist/components/Progress.js +51 -0
- package/dist/components/PromptInput.d.ts +399 -0
- package/dist/components/PromptInput.js +737 -0
- package/dist/components/Queue.d.ts +241 -0
- package/dist/components/Queue.js +225 -0
- package/dist/components/RadioGroup.d.ts +78 -0
- package/dist/components/RadioGroup.js +72 -0
- package/dist/components/Reasoning.d.ts +88 -0
- package/dist/components/Reasoning.js +187 -0
- package/dist/components/ScrollArea.d.ts +160 -0
- package/dist/components/ScrollArea.js +145 -0
- package/dist/components/Select.d.ts +2 -0
- package/dist/components/Select.js +260 -0
- package/dist/components/Separator.d.ts +45 -0
- package/dist/components/Separator.js +40 -0
- package/dist/components/Shell.d.ts +163 -0
- package/dist/components/Shell.js +137 -0
- package/dist/components/Slider.d.ts +120 -0
- package/dist/components/Slider.js +115 -0
- package/dist/components/Sources.d.ts +91 -0
- package/dist/components/Sources.js +121 -0
- package/dist/components/Stepper.d.ts +190 -0
- package/dist/components/Stepper.js +315 -0
- package/dist/components/Switch.d.ts +57 -0
- package/dist/components/Switch.js +55 -0
- package/dist/components/Tabs.d.ts +84 -0
- package/dist/components/Tabs.js +78 -0
- package/dist/components/Task.d.ts +100 -0
- package/dist/components/Task.js +120 -0
- package/dist/components/Terminal.d.ts +118 -0
- package/dist/components/Terminal.js +234 -0
- package/dist/components/TestResults.d.ts +236 -0
- package/dist/components/TestResults.js +346 -0
- package/dist/components/Toast.d.ts +192 -0
- package/dist/components/Toast.js +163 -0
- package/dist/components/Toggle.d.ts +69 -0
- package/dist/components/Toggle.js +66 -0
- package/dist/components/ToggleGroup.d.ts +69 -0
- package/dist/components/ToggleGroup.js +99 -0
- package/dist/components/Tool.d.ts +119 -0
- package/dist/components/Tool.js +192 -0
- package/dist/components/Toolbar.d.ts +162 -0
- package/dist/components/Toolbar.js +126 -0
- package/dist/components/Tooltip.d.ts +81 -0
- package/dist/components/Tooltip.js +74 -0
- package/dist/components/WebPreview.d.ts +143 -0
- package/dist/components/WebPreview.js +280 -0
- package/dist/components/useStickToBottom.d.ts +30 -0
- package/dist/components/useStickToBottom.js +95 -0
- package/dist/copy-button-BIATcZWZ.d.ts +16 -0
- package/dist/copy-button-BNgclDrO.js +43 -0
- package/dist/icons-BsWc8g4E.js +221 -0
- package/dist/styles/accordion.css +10 -10
- package/dist/styles/agent-connection.css +18 -17
- package/dist/styles/alert-dialog.css +48 -29
- package/dist/styles/artifact.css +10 -10
- package/dist/styles/autocomplete.css +25 -24
- package/dist/styles/avatar.css +96 -6
- package/dist/styles/badge.css +78 -14
- package/dist/styles/base.css +9 -9
- package/dist/styles/button.css +57 -38
- package/dist/styles/card.css +57 -10
- package/dist/styles/chain-of-thought.css +47 -33
- package/dist/styles/checkbox.css +24 -10
- package/dist/styles/code-block.css +22 -15
- package/dist/styles/collapsible.css +14 -12
- package/dist/styles/combobox.css +26 -25
- package/dist/styles/commit.css +49 -24
- package/dist/styles/context-menu.css +70 -16
- package/dist/styles/context.css +15 -15
- package/dist/styles/conversation.css +12 -12
- package/dist/styles/dialog.css +52 -16
- package/dist/styles/environment-variables.css +19 -19
- package/dist/styles/field.css +184 -22
- package/dist/styles/fieldset.css +5 -4
- package/dist/styles/file-tree.css +17 -17
- package/dist/styles/index.css.d.ts +1 -0
- package/dist/styles/input.css +45 -11
- package/dist/styles/label.css +21 -4
- package/dist/styles/menu.css +55 -32
- package/dist/styles/menubar.css +80 -28
- package/dist/styles/message.css +22 -13
- package/dist/styles/meter.css +8 -8
- package/dist/styles/model-selector.css +33 -21
- package/dist/styles/navigation-menu.css +26 -24
- package/dist/styles/number-field.css +20 -18
- package/dist/styles/popover.css +38 -28
- package/dist/styles/preview-card.css +15 -13
- package/dist/styles/pricing-page.css +53 -53
- package/dist/styles/progress.css +7 -7
- package/dist/styles/prompt-input.css +73 -24
- package/dist/styles/queue.css +58 -32
- package/dist/styles/radio.css +26 -11
- package/dist/styles/reasoning.css +15 -11
- package/dist/styles/scroll-area.css +6 -6
- package/dist/styles/scrollbars.css +4 -4
- package/dist/styles/select.css +84 -25
- package/dist/styles/separator.css +1 -1
- package/dist/styles/shell.css +21 -20
- package/dist/styles/slider.css +35 -11
- package/dist/styles/sources.css +20 -20
- package/dist/styles/stepper.css +22 -22
- package/dist/styles/switch.css +29 -13
- package/dist/styles/tabs.css +23 -16
- package/dist/styles/task.css +27 -23
- package/dist/styles/terminal.css +16 -13
- package/dist/styles/test-results.css +79 -32
- package/dist/styles/toast.css +26 -25
- package/dist/styles/toggle-group.css +12 -12
- package/dist/styles/toggle.css +29 -11
- package/dist/styles/tool.css +54 -32
- package/dist/styles/toolbar.css +30 -28
- package/dist/styles/tooltip.css +10 -8
- package/dist/styles/web-preview.css +37 -21
- package/dist/utils/structured-code.d.ts +10 -0
- package/dist/utils/structured-code.js +81 -0
- package/package.json +17 -8
- package/dist/index.d.ts +0 -7236
- package/dist/index.js +0 -8945
|
@@ -0,0 +1,98 @@
|
|
|
1
|
+
import { ButtonHTMLAttributes, ComponentPropsWithoutRef } from "react";
|
|
2
|
+
import { Button } from "@base-ui/react/button";
|
|
3
|
+
|
|
4
|
+
//#region src/components/Button.d.ts
|
|
5
|
+
/**
|
|
6
|
+
* The visual rendering style of the button.
|
|
7
|
+
*
|
|
8
|
+
* - `normal` - Filled background (default)
|
|
9
|
+
* - `outline` - Low-emphasis with border, transparent background
|
|
10
|
+
* - `ghost` - Minimal style, background appears on hover
|
|
11
|
+
* - `link` - Appears as a text link with underline on hover
|
|
12
|
+
*/
|
|
13
|
+
type ButtonVariant = "normal" | "outline" | "ghost" | "link";
|
|
14
|
+
/**
|
|
15
|
+
* The semantic color intent of the button.
|
|
16
|
+
*
|
|
17
|
+
* - `neutral` - Medium-emphasis actions, muted background
|
|
18
|
+
* - `primary` - High-emphasis actions, uses primary brand color
|
|
19
|
+
* - `destructive` - Dangerous or irreversible actions
|
|
20
|
+
*/
|
|
21
|
+
type ButtonColor = "neutral" | "primary" | "destructive";
|
|
22
|
+
/**
|
|
23
|
+
* Available button sizes.
|
|
24
|
+
*
|
|
25
|
+
* - `xs` - Extra small, 1.75rem height
|
|
26
|
+
* - `sm` - Small, 2rem height
|
|
27
|
+
* - `md` - Medium (default), 2.5rem height
|
|
28
|
+
* - `lg` - Large, 2.75rem height
|
|
29
|
+
* - `xl` - Extra large, 3.25rem height
|
|
30
|
+
* - `icon` - Square button for icon-only content
|
|
31
|
+
*/
|
|
32
|
+
type ButtonSize = "xs" | "sm" | "md" | "lg" | "xl" | "icon" | "icon-xs" | "icon-sm" | "icon-lg";
|
|
33
|
+
type ShadcnButtonVariant = "default" | "destructive" | "outline" | "secondary" | "ghost" | "link";
|
|
34
|
+
type ShadcnButtonSize = "default" | "xs" | "sm" | "lg" | "icon" | "icon-xs" | "icon-sm" | "icon-lg";
|
|
35
|
+
interface ButtonVariantsOptions {
|
|
36
|
+
variant?: ShadcnButtonVariant | ButtonVariant | null;
|
|
37
|
+
color?: ButtonColor | null;
|
|
38
|
+
size?: ShadcnButtonSize | ButtonSize | null;
|
|
39
|
+
className?: string;
|
|
40
|
+
}
|
|
41
|
+
declare function buttonVariants({
|
|
42
|
+
variant,
|
|
43
|
+
color,
|
|
44
|
+
size,
|
|
45
|
+
className
|
|
46
|
+
}?: ButtonVariantsOptions): string;
|
|
47
|
+
/**
|
|
48
|
+
* Props for the Button component.
|
|
49
|
+
*/
|
|
50
|
+
type BaseButtonProps = ComponentPropsWithoutRef<typeof Button>;
|
|
51
|
+
interface ButtonProps extends BaseButtonProps, Omit<ButtonHTMLAttributes<HTMLButtonElement>, keyof BaseButtonProps | "color"> {
|
|
52
|
+
/**
|
|
53
|
+
* The visual rendering style of the button.
|
|
54
|
+
* @default 'default'
|
|
55
|
+
*/
|
|
56
|
+
variant?: ShadcnButtonVariant | ButtonVariant;
|
|
57
|
+
/**
|
|
58
|
+
* The semantic color intent of the button.
|
|
59
|
+
* @default 'primary'
|
|
60
|
+
*/
|
|
61
|
+
color?: ButtonColor;
|
|
62
|
+
/**
|
|
63
|
+
* The size of the button.
|
|
64
|
+
* @default 'md'
|
|
65
|
+
*/
|
|
66
|
+
size?: ShadcnButtonSize | ButtonSize;
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* A button component built on Base UI with semantic styling variants.
|
|
70
|
+
*
|
|
71
|
+
* Separates visual style (`variant`) from color intent (`color`) for
|
|
72
|
+
* maximum flexibility. Supports keyboard navigation, focus management, and
|
|
73
|
+
* accessibility out of the box. Keeps shadcn-compatible variant and size
|
|
74
|
+
* aliases for migration, while styling through Sigvelo CSS tokens.
|
|
75
|
+
*
|
|
76
|
+
* @example
|
|
77
|
+
* ```tsx
|
|
78
|
+
* <Button color="primary">Save changes</Button>
|
|
79
|
+
* <Button color="destructive">Delete account</Button>
|
|
80
|
+
* <Button variant="outline">Cancel</Button>
|
|
81
|
+
* <Button variant="ghost" size="icon"><SearchIcon /></Button>
|
|
82
|
+
* ```
|
|
83
|
+
*
|
|
84
|
+
* @see {@link https://base-ui.com/react/components/button | Base UI Button}
|
|
85
|
+
* @see {@link https://ui.shadcn.com/docs/components/base/button | shadcn/ui Button}
|
|
86
|
+
*/
|
|
87
|
+
declare function Button$1({
|
|
88
|
+
variant,
|
|
89
|
+
color,
|
|
90
|
+
size,
|
|
91
|
+
className,
|
|
92
|
+
ref,
|
|
93
|
+
...props
|
|
94
|
+
}: ButtonProps & {
|
|
95
|
+
ref?: React.Ref<HTMLButtonElement>;
|
|
96
|
+
}): import("react").JSX.Element;
|
|
97
|
+
//#endregion
|
|
98
|
+
export { ButtonVariant as a, ShadcnButtonVariant as c, ButtonSize as i, buttonVariants as l, ButtonColor as n, ButtonVariantsOptions as o, ButtonProps as r, ShadcnButtonSize as s, Button$1 as t };
|
|
@@ -0,0 +1,356 @@
|
|
|
1
|
+
import { Select, SelectContent, SelectItem, SelectList, SelectTrigger, SelectValue } from "./components/Select.js";
|
|
2
|
+
import { t as cx } from "./class-names-9UtZwb0J.js";
|
|
3
|
+
import { t as CopyButton } from "./copy-button-BNgclDrO.js";
|
|
4
|
+
import * as React from "react";
|
|
5
|
+
import { Fragment, jsx, jsxs } from "react/jsx-runtime";
|
|
6
|
+
import { createHighlighter } from "shiki";
|
|
7
|
+
//#region src/components/_internal/shiki.ts
|
|
8
|
+
const CODE_BLOCK_LANGUAGES = [
|
|
9
|
+
"ts",
|
|
10
|
+
"tsx",
|
|
11
|
+
"js",
|
|
12
|
+
"jsx",
|
|
13
|
+
"css",
|
|
14
|
+
"html",
|
|
15
|
+
"json",
|
|
16
|
+
"bash",
|
|
17
|
+
"md"
|
|
18
|
+
];
|
|
19
|
+
const SHIKI_LANGS = [
|
|
20
|
+
"typescript",
|
|
21
|
+
"tsx",
|
|
22
|
+
"javascript",
|
|
23
|
+
"jsx",
|
|
24
|
+
"css",
|
|
25
|
+
"html",
|
|
26
|
+
"json",
|
|
27
|
+
"bash",
|
|
28
|
+
"markdown"
|
|
29
|
+
];
|
|
30
|
+
const LANG_ALIAS = {
|
|
31
|
+
ts: "typescript",
|
|
32
|
+
tsx: "tsx",
|
|
33
|
+
js: "javascript",
|
|
34
|
+
jsx: "jsx",
|
|
35
|
+
css: "css",
|
|
36
|
+
html: "html",
|
|
37
|
+
json: "json",
|
|
38
|
+
bash: "bash",
|
|
39
|
+
md: "markdown"
|
|
40
|
+
};
|
|
41
|
+
let highlighterPromise = null;
|
|
42
|
+
/**
|
|
43
|
+
* Returns a cached Shiki highlighter instance with both light and dark themes.
|
|
44
|
+
* Extra languages are loaded lazily by `loadShikiLanguage`.
|
|
45
|
+
*/
|
|
46
|
+
function getHighlighterInstance() {
|
|
47
|
+
highlighterPromise ??= createHighlighter({
|
|
48
|
+
themes: ["github-light-high-contrast", "github-dark-high-contrast"],
|
|
49
|
+
langs: SHIKI_LANGS
|
|
50
|
+
});
|
|
51
|
+
return highlighterPromise;
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* Loads a Shiki bundled language if it is not already available.
|
|
55
|
+
*/
|
|
56
|
+
async function loadShikiLanguage(highlighter, lang) {
|
|
57
|
+
const shikiLang = toShikiLang(lang);
|
|
58
|
+
if (!highlighter.getLoadedLanguages().includes(shikiLang)) await highlighter.loadLanguage(shikiLang);
|
|
59
|
+
return shikiLang;
|
|
60
|
+
}
|
|
61
|
+
function toShikiLang(lang) {
|
|
62
|
+
return LANG_ALIAS[lang] ?? lang;
|
|
63
|
+
}
|
|
64
|
+
//#endregion
|
|
65
|
+
//#region src/components/CodeBlock.tsx
|
|
66
|
+
const tokensCache = /* @__PURE__ */ new Map();
|
|
67
|
+
const subscribers = /* @__PURE__ */ new Map();
|
|
68
|
+
function getTokensCacheKey(code, language) {
|
|
69
|
+
return JSON.stringify([language, code]);
|
|
70
|
+
}
|
|
71
|
+
function createRawTokens(code) {
|
|
72
|
+
return {
|
|
73
|
+
bg: "transparent",
|
|
74
|
+
fg: "inherit",
|
|
75
|
+
tokens: code.split("\n").map((line) => line ? [{
|
|
76
|
+
content: line,
|
|
77
|
+
color: "inherit"
|
|
78
|
+
}] : [])
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
function resolveCodeBlockLanguage(language) {
|
|
82
|
+
return CODE_BLOCK_LANGUAGES.includes(language) ? toShikiLang(language) : language;
|
|
83
|
+
}
|
|
84
|
+
function highlightCode(code, language, callback) {
|
|
85
|
+
const tokensCacheKey = getTokensCacheKey(code, language);
|
|
86
|
+
const cached = tokensCache.get(tokensCacheKey);
|
|
87
|
+
if (cached) return cached;
|
|
88
|
+
if (callback) {
|
|
89
|
+
const tokenSubscribers = subscribers.get(tokensCacheKey) ?? /* @__PURE__ */ new Set();
|
|
90
|
+
tokenSubscribers.add(callback);
|
|
91
|
+
subscribers.set(tokensCacheKey, tokenSubscribers);
|
|
92
|
+
}
|
|
93
|
+
getHighlighterInstance().then(async (highlighter) => {
|
|
94
|
+
const lang = resolveCodeBlockLanguage(language);
|
|
95
|
+
let result;
|
|
96
|
+
try {
|
|
97
|
+
const loadedLang = await loadShikiLanguage(highlighter, lang);
|
|
98
|
+
result = highlighter.codeToTokens(code, {
|
|
99
|
+
lang: loadedLang,
|
|
100
|
+
themes: {
|
|
101
|
+
light: "github-light-high-contrast",
|
|
102
|
+
dark: "github-dark-high-contrast"
|
|
103
|
+
}
|
|
104
|
+
});
|
|
105
|
+
} catch {
|
|
106
|
+
const raw = createRawTokens(code);
|
|
107
|
+
tokensCache.set(tokensCacheKey, raw);
|
|
108
|
+
notifyTokenSubscribers(tokensCacheKey, raw);
|
|
109
|
+
return;
|
|
110
|
+
}
|
|
111
|
+
const tokenized = {
|
|
112
|
+
tokens: result.tokens,
|
|
113
|
+
fg: result.fg ?? "inherit",
|
|
114
|
+
bg: result.bg ?? "transparent"
|
|
115
|
+
};
|
|
116
|
+
tokensCache.set(tokensCacheKey, tokenized);
|
|
117
|
+
notifyTokenSubscribers(tokensCacheKey, tokenized);
|
|
118
|
+
}).catch(() => {
|
|
119
|
+
const raw = createRawTokens(code);
|
|
120
|
+
tokensCache.set(tokensCacheKey, raw);
|
|
121
|
+
notifyTokenSubscribers(tokensCacheKey, raw);
|
|
122
|
+
});
|
|
123
|
+
return null;
|
|
124
|
+
}
|
|
125
|
+
function notifyTokenSubscribers(tokensCacheKey, result) {
|
|
126
|
+
const tokenSubscribers = subscribers.get(tokensCacheKey);
|
|
127
|
+
if (!tokenSubscribers) return;
|
|
128
|
+
for (const subscriber of tokenSubscribers) subscriber(result);
|
|
129
|
+
subscribers.delete(tokensCacheKey);
|
|
130
|
+
}
|
|
131
|
+
const CodeBlockContext = React.createContext(null);
|
|
132
|
+
function useCodeBlockContext() {
|
|
133
|
+
const ctx = React.useContext(CodeBlockContext);
|
|
134
|
+
if (!ctx) throw new Error("CodeBlock subcomponents must be used inside <CodeBlock>.");
|
|
135
|
+
return ctx;
|
|
136
|
+
}
|
|
137
|
+
function renderPlainCode(code, showLineNumbers) {
|
|
138
|
+
if (!showLineNumbers) return code;
|
|
139
|
+
return code.split("\n").map((line, index) => /* @__PURE__ */ jsx("span", {
|
|
140
|
+
className: "line",
|
|
141
|
+
children: line || " "
|
|
142
|
+
}, `${index}-${line}`));
|
|
143
|
+
}
|
|
144
|
+
function hasCustomCodeBlockContent(children) {
|
|
145
|
+
return React.Children.toArray(children).some((child) => React.isValidElement(child) && (child.type === CodeBlockContainer || child.type === CodeBlockContent));
|
|
146
|
+
}
|
|
147
|
+
/**
|
|
148
|
+
* A syntax-highlighted code block powered by Shiki. Supports line numbers,
|
|
149
|
+
* inline language switching, and a copy-to-clipboard action.
|
|
150
|
+
*
|
|
151
|
+
* Supports Shiki bundled language names plus the short aliases in
|
|
152
|
+
* `CODE_BLOCK_LANGUAGES`. The highlighter is loaded lazily on first render and
|
|
153
|
+
* cached at module scope. Adapted from Vercel AI Elements and restyled with
|
|
154
|
+
* Sigvelo CSS tokens.
|
|
155
|
+
*
|
|
156
|
+
* @example
|
|
157
|
+
* ```tsx
|
|
158
|
+
* <CodeBlock code={"const x = 42;"} language="ts">
|
|
159
|
+
* <CodeBlockHeader>
|
|
160
|
+
* <CodeBlockFilename>example.ts</CodeBlockFilename>
|
|
161
|
+
* <CodeBlockActions>
|
|
162
|
+
* <CodeBlockCopyButton />
|
|
163
|
+
* </CodeBlockActions>
|
|
164
|
+
* </CodeBlockHeader>
|
|
165
|
+
* <CodeBlockContainer>
|
|
166
|
+
* <CodeBlockContent />
|
|
167
|
+
* </CodeBlockContainer>
|
|
168
|
+
* </CodeBlock>
|
|
169
|
+
* ```
|
|
170
|
+
*
|
|
171
|
+
* @see {@link https://elements.ai-sdk.dev/components/code-block | AI Elements Code Block}
|
|
172
|
+
*/
|
|
173
|
+
function CodeBlock({ className, code, language, showLineNumbers = false, isStreaming = false, onLanguageChange, children, ref, ...props }) {
|
|
174
|
+
const [internalLanguage, setInternalLanguage] = React.useState(language);
|
|
175
|
+
React.useEffect(() => {
|
|
176
|
+
setInternalLanguage(language);
|
|
177
|
+
}, [language]);
|
|
178
|
+
const setLanguage = React.useCallback((next) => {
|
|
179
|
+
setInternalLanguage(next);
|
|
180
|
+
onLanguageChange?.(next);
|
|
181
|
+
}, [onLanguageChange]);
|
|
182
|
+
const ctxValue = React.useMemo(() => ({
|
|
183
|
+
code,
|
|
184
|
+
language: internalLanguage,
|
|
185
|
+
setLanguage,
|
|
186
|
+
showLineNumbers,
|
|
187
|
+
isStreaming
|
|
188
|
+
}), [
|
|
189
|
+
code,
|
|
190
|
+
internalLanguage,
|
|
191
|
+
setLanguage,
|
|
192
|
+
showLineNumbers,
|
|
193
|
+
isStreaming
|
|
194
|
+
]);
|
|
195
|
+
const hasCustomContent = hasCustomCodeBlockContent(children);
|
|
196
|
+
return /* @__PURE__ */ jsx(CodeBlockContext.Provider, {
|
|
197
|
+
value: ctxValue,
|
|
198
|
+
children: /* @__PURE__ */ jsxs("div", {
|
|
199
|
+
ref,
|
|
200
|
+
className: cx("code-block", className),
|
|
201
|
+
...props,
|
|
202
|
+
children: [children, !hasCustomContent && /* @__PURE__ */ jsx(CodeBlockContainer, { children: /* @__PURE__ */ jsx(CodeBlockContent, {}) })]
|
|
203
|
+
})
|
|
204
|
+
});
|
|
205
|
+
}
|
|
206
|
+
function CodeBlockHeader({ className, children, ref, ...props }) {
|
|
207
|
+
return /* @__PURE__ */ jsx("div", {
|
|
208
|
+
ref,
|
|
209
|
+
className: cx("code-block__header", className),
|
|
210
|
+
...props,
|
|
211
|
+
children
|
|
212
|
+
});
|
|
213
|
+
}
|
|
214
|
+
function CodeBlockTitle({ className, children, ref, ...props }) {
|
|
215
|
+
return /* @__PURE__ */ jsx("span", {
|
|
216
|
+
ref,
|
|
217
|
+
className: cx("code-block__title", className),
|
|
218
|
+
...props,
|
|
219
|
+
children
|
|
220
|
+
});
|
|
221
|
+
}
|
|
222
|
+
function CodeBlockFilename({ className, children, ref, ...props }) {
|
|
223
|
+
return /* @__PURE__ */ jsx("span", {
|
|
224
|
+
ref,
|
|
225
|
+
className: cx("code-block__filename", className),
|
|
226
|
+
...props,
|
|
227
|
+
children
|
|
228
|
+
});
|
|
229
|
+
}
|
|
230
|
+
function CodeBlockActions({ className, children, ref, ...props }) {
|
|
231
|
+
return /* @__PURE__ */ jsx("div", {
|
|
232
|
+
ref,
|
|
233
|
+
className: cx("code-block__actions", className),
|
|
234
|
+
...props,
|
|
235
|
+
children
|
|
236
|
+
});
|
|
237
|
+
}
|
|
238
|
+
function CodeBlockCopyButton({ className, label = "Copy code", timeout = 2e3, onClick, ...props }) {
|
|
239
|
+
const { code } = useCodeBlockContext();
|
|
240
|
+
return /* @__PURE__ */ jsx(CopyButton, {
|
|
241
|
+
...props,
|
|
242
|
+
text: code,
|
|
243
|
+
label,
|
|
244
|
+
timeout,
|
|
245
|
+
className: cx("code-block__copy", className),
|
|
246
|
+
onClick
|
|
247
|
+
});
|
|
248
|
+
}
|
|
249
|
+
function CodeBlockLanguageSelector({ children, className, languages = CODE_BLOCK_LANGUAGES, onValueChange, ref, value, ...props }) {
|
|
250
|
+
const { language, setLanguage } = useCodeBlockContext();
|
|
251
|
+
const handleValueChange = React.useCallback((next, eventDetails) => {
|
|
252
|
+
setLanguage(next);
|
|
253
|
+
onValueChange?.(next, eventDetails);
|
|
254
|
+
}, [onValueChange, setLanguage]);
|
|
255
|
+
return /* @__PURE__ */ jsx("div", {
|
|
256
|
+
ref,
|
|
257
|
+
className: cx("code-block__language-selector", className),
|
|
258
|
+
children: /* @__PURE__ */ jsx(Select, {
|
|
259
|
+
...props,
|
|
260
|
+
value: value ?? language,
|
|
261
|
+
onValueChange: handleValueChange,
|
|
262
|
+
children: children ?? /* @__PURE__ */ jsxs(Fragment, { children: [/* @__PURE__ */ jsx(CodeBlockLanguageSelectorTrigger, {
|
|
263
|
+
"aria-label": "Code language",
|
|
264
|
+
children: /* @__PURE__ */ jsx(CodeBlockLanguageSelectorValue, {})
|
|
265
|
+
}), /* @__PURE__ */ jsx(CodeBlockLanguageSelectorContent, { children: /* @__PURE__ */ jsx(SelectList, { children: languages.map((lang) => /* @__PURE__ */ jsx(CodeBlockLanguageSelectorItem, {
|
|
266
|
+
value: lang,
|
|
267
|
+
children: lang
|
|
268
|
+
}, lang)) }) })] })
|
|
269
|
+
})
|
|
270
|
+
});
|
|
271
|
+
}
|
|
272
|
+
function CodeBlockLanguageSelectorTrigger({ size = "sm", ...props }) {
|
|
273
|
+
return /* @__PURE__ */ jsx(SelectTrigger, {
|
|
274
|
+
size,
|
|
275
|
+
...props
|
|
276
|
+
});
|
|
277
|
+
}
|
|
278
|
+
function CodeBlockLanguageSelectorValue(props) {
|
|
279
|
+
return /* @__PURE__ */ jsx(SelectValue, { ...props });
|
|
280
|
+
}
|
|
281
|
+
function CodeBlockLanguageSelectorContent({ align = "end", ...props }) {
|
|
282
|
+
return /* @__PURE__ */ jsx(SelectContent, {
|
|
283
|
+
align,
|
|
284
|
+
...props
|
|
285
|
+
});
|
|
286
|
+
}
|
|
287
|
+
function CodeBlockLanguageSelectorItem(props) {
|
|
288
|
+
return /* @__PURE__ */ jsx(SelectItem, { ...props });
|
|
289
|
+
}
|
|
290
|
+
function CodeBlockContainer({ className, children, ref, ...props }) {
|
|
291
|
+
return /* @__PURE__ */ jsx("div", {
|
|
292
|
+
ref,
|
|
293
|
+
className: cx("code-block__container", className),
|
|
294
|
+
...props,
|
|
295
|
+
children
|
|
296
|
+
});
|
|
297
|
+
}
|
|
298
|
+
function CodeBlockContent({ className, ref, ...props }) {
|
|
299
|
+
const { code, language, showLineNumbers, isStreaming } = useCodeBlockContext();
|
|
300
|
+
const [html, setHtml] = React.useState(null);
|
|
301
|
+
const [theme, setTheme] = React.useState(() => typeof document !== "undefined" && document.documentElement.dataset.theme === "dark" ? "github-dark-high-contrast" : "github-light-high-contrast");
|
|
302
|
+
React.useEffect(() => {
|
|
303
|
+
if (typeof document === "undefined") return;
|
|
304
|
+
const update = () => {
|
|
305
|
+
setTheme(document.documentElement.dataset.theme === "dark" ? "github-dark-high-contrast" : "github-light-high-contrast");
|
|
306
|
+
};
|
|
307
|
+
const observer = new MutationObserver(update);
|
|
308
|
+
observer.observe(document.documentElement, {
|
|
309
|
+
attributes: true,
|
|
310
|
+
attributeFilter: ["data-theme"]
|
|
311
|
+
});
|
|
312
|
+
return () => observer.disconnect();
|
|
313
|
+
}, []);
|
|
314
|
+
React.useEffect(() => {
|
|
315
|
+
if (isStreaming) return;
|
|
316
|
+
let cancelled = false;
|
|
317
|
+
(async () => {
|
|
318
|
+
try {
|
|
319
|
+
const highlighter = await getHighlighterInstance();
|
|
320
|
+
const loadedLang = await loadShikiLanguage(highlighter, language);
|
|
321
|
+
const out = highlighter.codeToHtml(code, {
|
|
322
|
+
lang: loadedLang,
|
|
323
|
+
theme
|
|
324
|
+
});
|
|
325
|
+
if (!cancelled) setHtml(out);
|
|
326
|
+
} catch {
|
|
327
|
+
if (!cancelled) setHtml(`<pre>${escapeHtml(code)}</pre>`);
|
|
328
|
+
}
|
|
329
|
+
})();
|
|
330
|
+
return () => {
|
|
331
|
+
cancelled = true;
|
|
332
|
+
};
|
|
333
|
+
}, [
|
|
334
|
+
code,
|
|
335
|
+
language,
|
|
336
|
+
theme,
|
|
337
|
+
isStreaming
|
|
338
|
+
]);
|
|
339
|
+
if (html === null || isStreaming) return /* @__PURE__ */ jsx("pre", {
|
|
340
|
+
ref,
|
|
341
|
+
className: cx("code-block__content", showLineNumbers && "code-block__content--numbered", className),
|
|
342
|
+
...props,
|
|
343
|
+
children: /* @__PURE__ */ jsx("code", { children: renderPlainCode(code, showLineNumbers) })
|
|
344
|
+
});
|
|
345
|
+
return /* @__PURE__ */ jsx("div", {
|
|
346
|
+
ref,
|
|
347
|
+
className: cx("code-block__content code-block__content--highlighted", showLineNumbers && "code-block__content--numbered", className),
|
|
348
|
+
dangerouslySetInnerHTML: { __html: html },
|
|
349
|
+
...props
|
|
350
|
+
});
|
|
351
|
+
}
|
|
352
|
+
function escapeHtml(s) {
|
|
353
|
+
return s.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'");
|
|
354
|
+
}
|
|
355
|
+
//#endregion
|
|
356
|
+
export { CodeBlockCopyButton as a, CodeBlockLanguageSelector as c, CodeBlockLanguageSelectorTrigger as d, CodeBlockLanguageSelectorValue as f, CODE_BLOCK_LANGUAGES as h, CodeBlockContent as i, CodeBlockLanguageSelectorContent as l, highlightCode as m, CodeBlockActions as n, CodeBlockFilename as o, CodeBlockTitle as p, CodeBlockContainer as r, CodeBlockHeader as s, CodeBlock as t, CodeBlockLanguageSelectorItem as u };
|
|
@@ -0,0 +1,174 @@
|
|
|
1
|
+
import { A as SelectTriggerProps, M as SelectValueProps, S as SelectProps, r as SelectContentProps, s as SelectItemProps } from "./Select-CRsKCJ9x.js";
|
|
2
|
+
import { t as CopyButtonProps } from "./copy-button-BIATcZWZ.js";
|
|
3
|
+
import * as React from "react";
|
|
4
|
+
import { BundledLanguage, ThemedToken } from "shiki";
|
|
5
|
+
|
|
6
|
+
//#region src/components/_internal/shiki.d.ts
|
|
7
|
+
/**
|
|
8
|
+
* Supported languages for CodeBlock.
|
|
9
|
+
*
|
|
10
|
+
* These are the default short aliases shown in the language selector. Full
|
|
11
|
+
* Shiki bundled language names are loaded on demand.
|
|
12
|
+
*/
|
|
13
|
+
type CodeBlockLanguage = BundledLanguage | "ts" | "tsx" | "js" | "jsx" | "css" | "html" | "json" | "bash" | "md";
|
|
14
|
+
declare const CODE_BLOCK_LANGUAGES: ReadonlyArray<CodeBlockLanguage>;
|
|
15
|
+
//#endregion
|
|
16
|
+
//#region src/components/CodeBlock.d.ts
|
|
17
|
+
interface TokenizedCode {
|
|
18
|
+
tokens: ThemedToken[][];
|
|
19
|
+
fg: string;
|
|
20
|
+
bg: string;
|
|
21
|
+
}
|
|
22
|
+
declare function highlightCode(code: string, language: CodeBlockLanguage | BundledLanguage, callback?: (result: TokenizedCode) => void): TokenizedCode | null;
|
|
23
|
+
interface CodeBlockProps extends React.HTMLAttributes<HTMLDivElement> {
|
|
24
|
+
/** The source code to display. */
|
|
25
|
+
code: string;
|
|
26
|
+
/** The language to highlight as. */
|
|
27
|
+
language: CodeBlockLanguage;
|
|
28
|
+
/** Whether to render line numbers in the left gutter. */
|
|
29
|
+
showLineNumbers?: boolean;
|
|
30
|
+
/**
|
|
31
|
+
* Skip syntax highlighting while code is actively streaming in. Renders the
|
|
32
|
+
* plain monospace fallback instead. Highlighting runs once when this flips
|
|
33
|
+
* back to false.
|
|
34
|
+
*/
|
|
35
|
+
isStreaming?: boolean;
|
|
36
|
+
/** Fired when the language is changed via the inline selector. */
|
|
37
|
+
onLanguageChange?: (next: CodeBlockLanguage) => void;
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* A syntax-highlighted code block powered by Shiki. Supports line numbers,
|
|
41
|
+
* inline language switching, and a copy-to-clipboard action.
|
|
42
|
+
*
|
|
43
|
+
* Supports Shiki bundled language names plus the short aliases in
|
|
44
|
+
* `CODE_BLOCK_LANGUAGES`. The highlighter is loaded lazily on first render and
|
|
45
|
+
* cached at module scope. Adapted from Vercel AI Elements and restyled with
|
|
46
|
+
* Sigvelo CSS tokens.
|
|
47
|
+
*
|
|
48
|
+
* @example
|
|
49
|
+
* ```tsx
|
|
50
|
+
* <CodeBlock code={"const x = 42;"} language="ts">
|
|
51
|
+
* <CodeBlockHeader>
|
|
52
|
+
* <CodeBlockFilename>example.ts</CodeBlockFilename>
|
|
53
|
+
* <CodeBlockActions>
|
|
54
|
+
* <CodeBlockCopyButton />
|
|
55
|
+
* </CodeBlockActions>
|
|
56
|
+
* </CodeBlockHeader>
|
|
57
|
+
* <CodeBlockContainer>
|
|
58
|
+
* <CodeBlockContent />
|
|
59
|
+
* </CodeBlockContainer>
|
|
60
|
+
* </CodeBlock>
|
|
61
|
+
* ```
|
|
62
|
+
*
|
|
63
|
+
* @see {@link https://elements.ai-sdk.dev/components/code-block | AI Elements Code Block}
|
|
64
|
+
*/
|
|
65
|
+
declare function CodeBlock({
|
|
66
|
+
className,
|
|
67
|
+
code,
|
|
68
|
+
language,
|
|
69
|
+
showLineNumbers,
|
|
70
|
+
isStreaming,
|
|
71
|
+
onLanguageChange,
|
|
72
|
+
children,
|
|
73
|
+
ref,
|
|
74
|
+
...props
|
|
75
|
+
}: CodeBlockProps & {
|
|
76
|
+
ref?: React.Ref<HTMLDivElement>;
|
|
77
|
+
}): React.JSX.Element;
|
|
78
|
+
interface CodeBlockHeaderProps extends React.HTMLAttributes<HTMLDivElement> {}
|
|
79
|
+
declare function CodeBlockHeader({
|
|
80
|
+
className,
|
|
81
|
+
children,
|
|
82
|
+
ref,
|
|
83
|
+
...props
|
|
84
|
+
}: CodeBlockHeaderProps & {
|
|
85
|
+
ref?: React.Ref<HTMLDivElement>;
|
|
86
|
+
}): React.JSX.Element;
|
|
87
|
+
interface CodeBlockTitleProps extends React.HTMLAttributes<HTMLSpanElement> {}
|
|
88
|
+
declare function CodeBlockTitle({
|
|
89
|
+
className,
|
|
90
|
+
children,
|
|
91
|
+
ref,
|
|
92
|
+
...props
|
|
93
|
+
}: CodeBlockTitleProps & {
|
|
94
|
+
ref?: React.Ref<HTMLSpanElement>;
|
|
95
|
+
}): React.JSX.Element;
|
|
96
|
+
interface CodeBlockFilenameProps extends React.HTMLAttributes<HTMLSpanElement> {}
|
|
97
|
+
declare function CodeBlockFilename({
|
|
98
|
+
className,
|
|
99
|
+
children,
|
|
100
|
+
ref,
|
|
101
|
+
...props
|
|
102
|
+
}: CodeBlockFilenameProps & {
|
|
103
|
+
ref?: React.Ref<HTMLSpanElement>;
|
|
104
|
+
}): React.JSX.Element;
|
|
105
|
+
interface CodeBlockActionsProps extends React.HTMLAttributes<HTMLDivElement> {}
|
|
106
|
+
declare function CodeBlockActions({
|
|
107
|
+
className,
|
|
108
|
+
children,
|
|
109
|
+
ref,
|
|
110
|
+
...props
|
|
111
|
+
}: CodeBlockActionsProps & {
|
|
112
|
+
ref?: React.Ref<HTMLDivElement>;
|
|
113
|
+
}): React.JSX.Element;
|
|
114
|
+
interface CodeBlockCopyButtonProps extends Omit<CopyButtonProps, "text" | "label"> {
|
|
115
|
+
label?: string;
|
|
116
|
+
}
|
|
117
|
+
declare function CodeBlockCopyButton({
|
|
118
|
+
className,
|
|
119
|
+
label,
|
|
120
|
+
timeout,
|
|
121
|
+
onClick,
|
|
122
|
+
...props
|
|
123
|
+
}: CodeBlockCopyButtonProps): React.JSX.Element;
|
|
124
|
+
interface CodeBlockLanguageSelectorProps extends Omit<SelectProps, "children" | "onValueChange" | "value"> {
|
|
125
|
+
languages?: ReadonlyArray<CodeBlockLanguage>;
|
|
126
|
+
value?: SelectProps["value"];
|
|
127
|
+
onValueChange?: SelectProps["onValueChange"];
|
|
128
|
+
children?: React.ReactNode;
|
|
129
|
+
className?: string;
|
|
130
|
+
}
|
|
131
|
+
declare function CodeBlockLanguageSelector({
|
|
132
|
+
children,
|
|
133
|
+
className,
|
|
134
|
+
languages,
|
|
135
|
+
onValueChange,
|
|
136
|
+
ref,
|
|
137
|
+
value,
|
|
138
|
+
...props
|
|
139
|
+
}: CodeBlockLanguageSelectorProps & {
|
|
140
|
+
ref?: React.Ref<HTMLDivElement>;
|
|
141
|
+
}): React.JSX.Element;
|
|
142
|
+
type CodeBlockLanguageSelectorTriggerProps = SelectTriggerProps;
|
|
143
|
+
type CodeBlockLanguageSelectorValueProps = SelectValueProps;
|
|
144
|
+
type CodeBlockLanguageSelectorContentProps = SelectContentProps;
|
|
145
|
+
type CodeBlockLanguageSelectorItemProps = SelectItemProps;
|
|
146
|
+
declare function CodeBlockLanguageSelectorTrigger({
|
|
147
|
+
size,
|
|
148
|
+
...props
|
|
149
|
+
}: CodeBlockLanguageSelectorTriggerProps): React.JSX.Element;
|
|
150
|
+
declare function CodeBlockLanguageSelectorValue(props: CodeBlockLanguageSelectorValueProps): React.JSX.Element;
|
|
151
|
+
declare function CodeBlockLanguageSelectorContent({
|
|
152
|
+
align,
|
|
153
|
+
...props
|
|
154
|
+
}: CodeBlockLanguageSelectorContentProps): React.JSX.Element;
|
|
155
|
+
declare function CodeBlockLanguageSelectorItem(props: CodeBlockLanguageSelectorItemProps): React.JSX.Element;
|
|
156
|
+
interface CodeBlockContainerProps extends React.HTMLAttributes<HTMLDivElement> {}
|
|
157
|
+
declare function CodeBlockContainer({
|
|
158
|
+
className,
|
|
159
|
+
children,
|
|
160
|
+
ref,
|
|
161
|
+
...props
|
|
162
|
+
}: CodeBlockContainerProps & {
|
|
163
|
+
ref?: React.Ref<HTMLDivElement>;
|
|
164
|
+
}): React.JSX.Element;
|
|
165
|
+
interface CodeBlockContentProps extends React.HTMLAttributes<HTMLElement> {}
|
|
166
|
+
declare function CodeBlockContent({
|
|
167
|
+
className,
|
|
168
|
+
ref,
|
|
169
|
+
...props
|
|
170
|
+
}: CodeBlockContentProps & {
|
|
171
|
+
ref?: React.Ref<HTMLElement>;
|
|
172
|
+
}): React.JSX.Element;
|
|
173
|
+
//#endregion
|
|
174
|
+
export { CodeBlockLanguage as A, CodeBlockLanguageSelectorValueProps as C, TokenizedCode as D, CodeBlockTitleProps as E, highlightCode as O, CodeBlockLanguageSelectorValue as S, CodeBlockTitle as T, CodeBlockLanguageSelectorItem as _, CodeBlockContainerProps as a, CodeBlockLanguageSelectorTrigger as b, CodeBlockCopyButton as c, CodeBlockFilenameProps as d, CodeBlockHeader as f, CodeBlockLanguageSelectorContentProps as g, CodeBlockLanguageSelectorContent as h, CodeBlockContainer as i, CODE_BLOCK_LANGUAGES as k, CodeBlockCopyButtonProps as l, CodeBlockLanguageSelector as m, CodeBlockActions as n, CodeBlockContent as o, CodeBlockHeaderProps as p, CodeBlockActionsProps as r, CodeBlockContentProps as s, CodeBlock as t, CodeBlockFilename as u, CodeBlockLanguageSelectorItemProps as v, CodeBlockProps as w, CodeBlockLanguageSelectorTriggerProps as x, CodeBlockLanguageSelectorProps as y };
|