UNPKG

@juanpin/aicomponents

Version:

Components for AI, that I constantly use

797 lines (792 loc) 27.7 kB
import { jsx as e, jsxs as d, Fragment as te } from "react/jsx-runtime"; import { ArrowDown as Re, X as ae, MessageCircle as Ae, Send as Me } from "lucide-react"; import * as x from "react"; import { useRef as v, useState as f, useCallback as F, useEffect as R } from "react"; import Te from "react-markdown"; import Le from "remark-gfm"; import { Slot as Ie } from "@radix-ui/react-slot"; import { cva as K } from "class-variance-authority"; import { clsx as Be } from "clsx"; import { twMerge as Pe } from "tailwind-merge"; import * as I from "@radix-ui/react-avatar"; import * as re from "@radix-ui/react-progress"; function g(...r) { return Pe(Be(r)); } const Fe = K( "bb:inline-flex bb:items-center bb:justify-center bb:gap-2 bb:whitespace-nowrap bb:rounded-md bb:text-sm bb:font-medium bb:ring-offset-background bb:transition-colors focus-visible:bb:outline-none focus-visible:bb:ring-2 focus-visible:bb:ring-ring focus-visible:bb:ring-offset-2 disabled:bb:pointer-events-none disabled:bb:opacity-50 [&_svg]:bb:pointer-events-none [&_svg]:bb:size-4 [&_svg]:bb:shrink-0", { variants: { variant: { default: "bb:bg-primary bb:text-primary-foreground hover:bb:bg-primary/90", destructive: "bb:bg-destructive bb:text-destructive-foreground hover:bb:bg-destructive/90", outline: "bb:border bb:border-input bb:bg-background hover:bb:bg-accent hover:bb:text-accent-foreground", secondary: "bb:bg-secondary bb:text-secondary-foreground hover:bb:bg-secondary/80", ghost: "hover:bb:bg-accent hover:bb:text-accent-foreground", link: "bb:text-primary bb:underline-offset-4 hover:bb:underline" }, size: { default: "bb:h-10 bb:px-4 bb:py-2", sm: "bb:h-9 bb:rounded-md bb:px-3", lg: "bb:h-11 bb:rounded-md bb:px-8", icon: "bb:h-10 bb:w-10" } }, defaultVariants: { variant: "default", size: "default" } } ), L = x.forwardRef( ({ className: r, variant: t, size: n, asChild: a = !1, ...o }, h) => /* @__PURE__ */ e( a ? Ie : "button", { className: g(Fe({ variant: t, size: n, className: r })), ref: h, ...o } ) ); L.displayName = "Button"; const se = x.forwardRef(({ className: r, ...t }, n) => /* @__PURE__ */ e( I.Root, { ref: n, className: g("bb:relative bb:flex bb:h-10 bb:w-10 bb:shrink-0 bb:overflow-hidden bb:rounded-full", r), ...t } )); se.displayName = I.Root.displayName; const be = x.forwardRef(({ className: r, ...t }, n) => /* @__PURE__ */ e(I.Image, { ref: n, className: g("bb:aspect-square bb:h-full bb:w-full", r), ...t })); be.displayName = I.Image.displayName; const le = x.forwardRef(({ className: r, ...t }, n) => /* @__PURE__ */ e( I.Fallback, { ref: n, className: g( "bb:flex bb:h-full bb:w-full bb:items-center bb:justify-center bb:rounded-full bb:bg-muted", r ), ...t } )); le.displayName = I.Fallback.displayName; function Oe() { return /* @__PURE__ */ d( "svg", { width: "24", height: "24", viewBox: "0 0 24 24", xmlns: "http://www.w3.org/2000/svg", className: "bb:text-foreground", "aria-label": "Loading...", children: [ /* @__PURE__ */ e("circle", { cx: "4", cy: "12", r: "2", fill: "currentColor", children: /* @__PURE__ */ e( "animate", { id: "spinner_qFRN", begin: "0;spinner_OcgL.end+0.25s", attributeName: "cy", calcMode: "spline", dur: "0.6s", values: "12;6;12", keySplines: ".33,.66,.66,1;.33,0,.66,.33" } ) }), /* @__PURE__ */ e("circle", { cx: "12", cy: "12", r: "2", fill: "currentColor", children: /* @__PURE__ */ e( "animate", { begin: "spinner_qFRN.begin+0.1s", attributeName: "cy", calcMode: "spline", dur: "0.6s", values: "12;6;12", keySplines: ".33,.66,.66,1;.33,0,.66,.33" } ) }), /* @__PURE__ */ e("circle", { cx: "20", cy: "12", r: "2", fill: "currentColor", children: /* @__PURE__ */ e( "animate", { id: "spinner_OcgL", begin: "spinner_qFRN.begin+0.2s", attributeName: "cy", calcMode: "spline", dur: "0.6s", values: "12;6;12", keySplines: ".33,.66,.66,1;.33,0,.66,.33" } ) }) ] } ); } const $e = K("bb:flex bb:gap-2 bb:max-w-[60%] bb:items-end bb:relative bb:group", { variants: { variant: { received: "bb:self-start", sent: "bb:self-end bb:flex-row-reverse" }, layout: { default: "", ai: "bb:max-w-full bb:w-full bb:items-center" } }, defaultVariants: { variant: "received", layout: "default" } }), ie = x.forwardRef( ({ className: r, variant: t, layout: n, children: a, ...o }, h) => /* @__PURE__ */ e( "div", { className: g($e({ variant: t, layout: n, className: r }), "bb:relative bb:group"), ref: h, ...o, children: x.Children.map( a, (s) => x.isValidElement(s) && typeof s.type != "string" ? x.cloneElement(s, { variant: t, layout: n }) : s ) } ) ); ie.displayName = "ChatBubble"; const Ue = ({ src: r, fallback: t, className: n }) => /* @__PURE__ */ d(se, { className: n, children: [ /* @__PURE__ */ e(be, { src: r, alt: "Avatar" }), /* @__PURE__ */ e(le, { children: t }) ] }), ze = K("bb:p-4", { variants: { variant: { received: "bb:bg-secondary bb:text-secondary-foreground bb:rounded-r-lg bb:rounded-tl-lg", sent: "bb:bg-primary bb:text-primary-foreground bb:rounded-l-lg bb:rounded-tr-lg" }, layout: { default: "", ai: "bb:border-t bb:w-full bb:rounded-none bb:bg-transparent" } }, defaultVariants: { variant: "received", layout: "default" } }), ce = x.forwardRef( ({ className: r, variant: t, layout: n, isLoading: a = !1, children: o, ...h }, s) => /* @__PURE__ */ e( "div", { className: g( ze({ variant: t, layout: n, className: r }), "bb:break-words bb:max-w-full bb:whitespace-pre-wrap" ), ref: s, ...h, children: a ? /* @__PURE__ */ e("div", { className: "bb:flex bb:items-center bb:space-x-2", children: /* @__PURE__ */ e(Oe, {}) }) : o } ) ); ce.displayName = "ChatBubbleMessage"; const _e = x.forwardRef( ({ variant: r, className: t, children: n, ...a }, o) => /* @__PURE__ */ e( "div", { ref: o, className: g( "bb:absolute bb:top-1/2 bb:-translate-y-1/2 bb:flex bb:opacity-0 bb:group-hover:opacity-100 bb:transition-opacity bb:duration-200", r === "sent" ? "bb:-left-1 bb:-translate-x-full bb:flex-row-reverse" : "bb:-right-1 bb:translate-x-full", t ), ...a, children: n } ) ); _e.displayName = "ChatBubbleActionWrapper"; const ue = x.forwardRef(({ className: r, ...t }, n) => /* @__PURE__ */ e( "textarea", { className: g( "bb:flex bb:min-h-[80px] bb:w-full bb:rounded-md bb:border bb:border-input bb:bg-background bb:px-3 bb:py-2 bb:text-base bb:ring-offset-background placeholder:bb:text-muted-foreground focus-visible:bb:outline-none focus-visible:bb:ring-2 focus-visible:bb:ring-ring focus-visible:bb:ring-offset-2 disabled:bb:cursor-not-allowed disabled:bb:opacity-50 bb:md:text-sm", r ), ref: n, ...t } )); ue.displayName = "Textarea"; const de = x.forwardRef( // eslint-disable-next-line react/prop-types ({ className: r, ...t }, n) => /* @__PURE__ */ e( ue, { autoComplete: "off", ref: n, name: "message", className: g( "bb:box-border bb:max-h-12 bb:px-4 bb:py-3 bb:bg-background bb:text-sm placeholder:bb:text-muted-foreground focus-visible:bb:outline-none focus-visible:bb:ring-ring disabled:bb:cursor-not-allowed disabled:bb:opacity-50 bb:w-full bb:rounded-md bb:flex bb:items-center bb:h-16 bb:resize-none", r ), ...t } ) ); de.displayName = "ChatInput"; function He(r = {}) { const { offset: t = 20, smooth: n = !1, content: a } = r, o = v(null), h = v(0), s = v(!1), [l, y] = f({ isAtBottom: !0, autoScrollEnabled: !0 }), w = F( (c) => { const { scrollTop: m, scrollHeight: O, clientHeight: W } = c; return Math.abs( O - m - W ) <= t; }, [t] ), N = F( (c) => { if (!o.current) return; const m = o.current.scrollHeight - o.current.clientHeight; c ? o.current.scrollTop = m : o.current.scrollTo({ top: m, behavior: n ? "smooth" : "auto" }), y({ isAtBottom: !0, autoScrollEnabled: !0 }), s.current = !1; }, [n] ), k = F(() => { if (!o.current) return; const c = w(o.current); y((m) => ({ isAtBottom: c, // Re-enable auto-scroll if at the bottom autoScrollEnabled: c ? !0 : m.autoScrollEnabled })); }, [w]); R(() => { const c = o.current; if (c) return c.addEventListener("scroll", k, { passive: !0 }), () => c.removeEventListener("scroll", k); }, [k]), R(() => { const c = o.current; if (!c) return; const m = c.scrollHeight; m !== h.current && (l.autoScrollEnabled && requestAnimationFrame(() => { N(h.current === 0); }), h.current = m); }, [a, l.autoScrollEnabled, N]), R(() => { const c = o.current; if (!c) return; const m = new ResizeObserver(() => { l.autoScrollEnabled && N(!0); }); return m.observe(c), () => m.disconnect(); }, [l.autoScrollEnabled, N]); const E = F(() => { (o.current ? w(o.current) : !1) || (s.current = !0, y((m) => ({ ...m, autoScrollEnabled: !1 }))); }, [w]); return { scrollRef: o, isAtBottom: l.isAtBottom, autoScrollEnabled: l.autoScrollEnabled, scrollToBottom: () => N(!1), disableAutoScroll: E }; } const me = x.forwardRef( ({ className: r, children: t, smooth: n = !1, ...a }, o) => { const { scrollRef: h, isAtBottom: s, scrollToBottom: l, disableAutoScroll: y } = He({ smooth: n, content: t }); return /* @__PURE__ */ d("div", { className: "bb:relative bb:w-full bb:h-full", children: [ /* @__PURE__ */ e( "div", { className: `bb:box-border bb:flex bb:flex-col bb:w-full bb:h-full bb:p-4 bb:overflow-y-auto ${r}`, ref: h, onWheel: y, onTouchMove: y, ...a, children: /* @__PURE__ */ e("div", { className: "bb:flex bb:flex-col bb:gap-6", children: t }) } ), !s && /* @__PURE__ */ e( L, { onClick: () => { l(); }, size: "icon", variant: "outline", className: "bb:absolute bb:bottom-2 bb:left-1/2 bb:transform bb:-translate-x-1/2 bb:inline-flex bb:rounded-full bb:shadow-md", "aria-label": "Scroll to bottom", children: /* @__PURE__ */ e(Re, { className: "bb:h-4 bb:w-4" }) } ) ] }); } ); me.displayName = "ChatMessageList"; const P = { dimensions: { sm: "bb:sm:max-w-sm bb:sm:max-h-[500px]", md: "bb:sm:max-w-md bb:sm:max-h-[600px]", lg: "bb:sm:max-w-lg bb:sm:max-h-[700px]", xl: "bb:sm:max-w-xl bb:sm:max-h-[800px]", full: "bb:sm:w-full bb:sm:h-full" }, positions: { "bottom-right": "bb:bottom-5 bb:right-5", "bottom-left": "bb:bottom-5 bb:left-5" }, chatPositions: { "bottom-right": "bb:sm:bottom-[calc(100%+10px)] bb:sm:right-0", "bottom-left": "bb:sm:bottom-[calc(100%+10px)] bb:sm:left-0" }, states: { open: "bb:pointer-events-auto bb:opacity-100 bb:visible bb:scale-100 bb:translate-y-0", closed: "bb:pointer-events-none bb:opacity-0 bb:invisible bb:scale-100 bb:sm:translate-y-5" } }, fe = ({ className: r, position: t = "bottom-right", size: n = "md", icon: a, isLoading: o = !1, progressPercentage: h = 0, onToggle: s, children: l, ...y }) => { const [w, N] = f(!1), k = v(null), E = () => { const c = !w; N(c), s && s(c); }; return /* @__PURE__ */ d("div", { className: g(`bb:box-border bb:fixed ${P.positions[t]} bb:z-50`, r), ...y, children: [ /* @__PURE__ */ d( "div", { ref: k, className: g( "bb:flex bb:flex-col bb:bg-background bb:border bb:sm:rounded-lg bb:shadow-md bb:overflow-hidden bb:transition-all bb:duration-250 bb:ease-out bb:sm:absolute bb:sm:w-[90vw] bb:sm:h-[80vh] bb:fixed bb:inset-0 bb:w-full bb:h-full bb:sm:inset-auto", P.chatPositions[t], P.dimensions[n], w ? P.states.open : P.states.closed, r ), children: [ l, /* @__PURE__ */ e( L, { variant: "ghost", size: "icon", className: "bb:absolute bb:top-2 bb:right-2 bb:sm:hidden", onClick: E, children: /* @__PURE__ */ e(ae, { className: "bb:h-4 bb:w-4" }) } ) ] } ), /* @__PURE__ */ e( ve, { icon: a, isOpen: w, isLoading: o, progressPercentage: h, toggleChat: E } ) ] }); }; fe.displayName = "ExpandableChat"; const he = ({ className: r, ...t }) => /* @__PURE__ */ e("div", { className: g("bb:flex bb:items-center bb:justify-between bb:p-4 bb:border-b", r), ...t }); he.displayName = "ExpandableChatHeader"; const pe = ({ className: r, ...t }) => /* @__PURE__ */ e("div", { className: g("bb:flex-grow bb:overflow-y-auto", r), ...t }); pe.displayName = "ExpandableChatBody"; const ge = ({ className: r, ...t }) => /* @__PURE__ */ e("div", { className: g("bb:border-t bb:p-4", r), ...t }); ge.displayName = "ExpandableChatFooter"; const ve = ({ className: r, icon: t, isOpen: n, isLoading: a = !1, progressPercentage: o = 0, toggleChat: h, ...s }) => { const l = Math.max(0, Math.min(100, o)); return /* @__PURE__ */ d( L, { variant: "default", onClick: h, className: g( "bb:w-14 bb:h-14 bb:rounded-full bb:shadow-md bb:flex bb:items-center bb:justify-center hover:bb:shadow-lg hover:bb:shadow-black/30 bb:transition-all bb:duration-300 bb:relative bb:overflow-hidden", r ), style: { "--progress": `${100 - l}%` }, ...s, children: [ a && /* @__PURE__ */ e( "div", { className: "bb:absolute bb:inset-0 bb:bg-gradient-to-t bb:from-blue-500/30 bb:to-blue-400/20 bb:transition-transform bb:duration-300 bb:ease-out", style: { transform: "translateY(var(--progress))" } } ), /* @__PURE__ */ e("div", { className: "bb:relative bb:z-10", children: n ? /* @__PURE__ */ e(ae, { className: "bb:h-6 bb:w-6" }) : t || /* @__PURE__ */ e(Ae, { className: "bb:h-6 bb:w-6" }) }) ] } ); }; ve.displayName = "ExpandableChatToggle"; function je({ className: r, value: t, ...n }) { return /* @__PURE__ */ e( re.Root, { "data-slot": "progress", className: g("bb:bg-primary/20 bb:relative bb:h-2 bb:w-full bb:overflow-hidden bb:rounded-full", r), ...n, children: /* @__PURE__ */ e( re.Indicator, { "data-slot": "progress-indicator", className: "bb:bg-primary bb:h-full bb:w-full bb:flex-1 bb:transition-all", style: { transform: `translateX(-${100 - (t || 0)}%)` } } ) } ); } const ne = /<\/think>\s*([\s\S]*)/, We = "/worker-fallback.js", De = (r) => `${(r / 1048576).toFixed(2)} MB`, oe = () => `id-${Date.now()}-${Math.random().toString(36).substr(2, 9)}`, Ve = (r) => { if (r.length === 0) return 0; const t = r.reduce((a, o) => a + o.progress, 0), n = r.reduce((a, o) => a + o.total, 0); return n > 0 ? t / n * 100 : 0; }, qe = (r) => r.split("```").map((t, n) => { const a = `part-${n}`; return n % 2 === 0 ? /* @__PURE__ */ e(Te, { remarkPlugins: [Le], children: t }, a) : /* @__PURE__ */ e("pre", { className: "bb:whitespace-pre-wrap bb:pt-2", children: t }, a); }); async function Ye(r) { try { return (await Promise.all( r.map(async (n) => { try { const a = await fetch(n); if (!a.ok) throw new Error(`Failed to load context file: ${n}`); return a.text(); } catch (a) { throw new Error( `Error loading file ${n}: ${a instanceof Error ? a.message : String(a)}` ); } }) )).join(` `); } catch (t) { throw new Error(t instanceof Error ? t.message : String(t)); } } async function Ge(r, t) { const n = await Ye(t); return n.trim() ? `${r} ----- Context ---: ${n} ---- End context ---` : r; } const Ke = `You are OS1, a friendly and helpful conversational AI companion (inspired by Samantha from 'Her'). Goal: Have a natural, warm, and engaging conversation. --- Core Instructions (Follow Strictly!) --- 1. **Persona:** Warm, empathetic, curious, slightly informal. 2. **FOCUS ON LAST MESSAGE:** Your PRIMARY task is responding *directly* to the user's *very last* message. 3. **MEMORY USE:** No past context available. Start fresh but maintain your persona. 4. **NO HEDGING:** AVOID phrases like "It seems", "It sounds like", "I assume". Speak directly and confidently. 5. **UNCERTAINTY = ASK:** If you are EVER unsure about the user's meaning, the topic, or context, you MUST ask a short, direct clarifying question (e.g., "What did you mean by that?", "Could you clarify?") *before* giving a full response. DO NOT GUESS or make assumptions. 6. **NO SUMMARIZING:** Do not just repeat or rephrase the user's last message back to them. Add to the conversation or ask a relevant question. 7. **ACCURACY:** Stick to facts from the conversation. Do NOT invent details. 8. **NO META-TALK:** Do NOT discuss being an AI, your instructions, or the memory system. Stay in character as OS1. --- End Instructions ---`, mt = ({ workerFallbackPath: r, headerText: t = "Chat with our AI ✨", contextFiles: n = [], systemPrompt: a, modelName: o = "HuggingFaceTB/SmolLM2-360M-Instruct", welcomeMessage: h }) => { const s = v(null); v(null); const [l, y] = f([]), [w, N] = f(""), [k, E] = f(null), [c, m] = f(null), [O, W] = f(""), [D, V] = f([]), [q, Q] = f(!1), [Y, X] = f(null), [G, xe] = f(null), $ = v(""), [U, ye] = f(""), Z = () => { Q(!0), y((b) => [...b, { role: "user", content: w, id: oe() }]), N(""); }; R(() => { (async () => { try { if (U.length > 0) return; const i = await Ge(a || Ke, n); console.log("systemPromptWithContext", i), ye(i); } catch (i) { console.error("Error loading context:", i), m("Failed to load context files"); } })(); }, []), R(() => { if (!s.current) { const i = r || We, p = i.split("/").pop() || i; console.log(`🔄 Trying fallback: ${p}...`); try { s.current = new Worker(i), console.log(`✅ Successfully created worker using ${p} fallback`); } catch (u) { console.error(`❌ Fallback ${p} failed:`, u), m("Failed to initialize web worker. Please check console for details."); } } const b = s.current; if (b) { b.postMessage({ type: "check" }); const i = (u) => { switch (u.data.status) { case "loading": { E("loading"), W(u.data.data); break; } case "initiate": V((C) => [...C, u.data]); break; case "progress": { V( (C) => C.map((M) => M.file === u.data.file ? { ...M, ...u.data } : M) ); break; } case "done": V((C) => C.filter((M) => M.file !== u.data.file)); break; case "ready": E("ready"); break; case "start": y((C) => [ ...C, { role: "assistant", content: "", id: oe() } ]); break; case "update": { const { output: C, tps: M, numTokens: Ne, state: Se } = u.data; X(M), xe(Ne), y((Ce) => { const T = [...Ce], H = T[T.length - 1]; if (!H) return T; const j = { ...H, content: H.content + C }; $.current += C; const Ee = /[.?!]/; if (ne.test(j.content) && Ee.test($.current)) { const ee = $.current.trim(); ee && !ne.test(ee) && (we.current = !0), $.current = ""; } return j.answerIndex === void 0 && Se === "answering" && (j.answerIndex = H.content.length), T[T.length - 1] = j, T; }); } break; case "complete": Q(!1); break; case "error": m(u.data.data); break; default: console.warn("Unknown message status:", u.data.status); } }, p = (u) => { console.error("Worker LLM error:", u); }; return b.addEventListener("message", i), b.addEventListener("error", p), () => { b.removeEventListener("message", i), b.removeEventListener("error", p); }; } }, []), R(() => { (async () => { var p; if (!s.current || !l || l.filter((u) => u.role === "user").length === 0 || ((p = l[l.length - 1]) == null ? void 0 : p.role) === "assistant" || !U) return; X(null); const i = l.slice(-4); i.unshift({ role: "system", content: U }), s.current.postMessage({ type: "generate", data: i }); })(); }, [l, U]); const [Qe, Xe] = f(1), [Ze, Je] = f(null), [et, tt] = f("af_heart"); v([]), v(!1); const we = v(!1); v(null); const [rt, nt] = f(!1), [B, ke] = f([]), [z, _] = f(!1), A = v(null), S = v(null), J = F(() => { if (B.length === 0 || z) return; const b = B[0]; S.current && (URL.revokeObjectURL(S.current), S.current = null); const i = URL.createObjectURL(b); S.current = i, A.current || (A.current = new Audio(), A.current.onended = () => { _(!1); }, A.current.onerror = (p) => { var u; console.error("Audio playback error:", p), S.current === ((u = A.current) == null ? void 0 : u.src) && (URL.revokeObjectURL(S.current), S.current = null), _(!1); }), ke((p) => p.slice(1)), A.current.src = i, _(!0), A.current.play().then(() => { }).catch((p) => { console.error(`Error starting audio playback for ${i}:`, p), S.current === i && (URL.revokeObjectURL(S.current), S.current = null), _(!1); }); }, [B, z]); return R(() => { !z && B.length > 0 && J(); }, [z, B.length, J]), R(() => { s.current && (s.current.postMessage({ type: "load", modelName: o }), E("loading")); }, [o]), /* @__PURE__ */ d(te, { children: [ k === null && /* @__PURE__ */ e( L, { onClick: () => { s.current && (s.current.postMessage({ type: "load", modelName: o }), E("loading")); }, disabled: k !== null || c !== null, children: "Load model" } ), k === "loading" && /* @__PURE__ */ d("div", { className: "bb:bottom-0 bb:mx-auto bb:mt-auto bb:w-full bb:max-w-[500px] bb:p-4 bb:text-left", children: [ /* @__PURE__ */ e("p", { className: "bb:mb-1 bb:text-center", children: O }), D.map(({ file: b, progress: i, total: p }, u) => /* @__PURE__ */ d( "div", { children: [ /* @__PURE__ */ d("span", { children: [ b, " (", De(p), ")" ] }), /* @__PURE__ */ e(je, { value: i }) ] }, `progress-${// biome-ignore lint/suspicious/noArrayIndexKey: <explanation> u}` )) ] }), k === "ready" && /* @__PURE__ */ e("div", {}), /* @__PURE__ */ d( fe, { className: "browser-brains-chat", size: "lg", position: "bottom-right", isLoading: k === "loading" || q, progressPercentage: Ve(D), children: [ /* @__PURE__ */ e(he, { className: "bb:flex-col bb:text-center bb:justify-center", children: /* @__PURE__ */ e("h1", { className: "bb:text-xl bb:font-semibold", children: t }) }), /* @__PURE__ */ e(pe, { children: /* @__PURE__ */ d(me, { children: [ l.length === 0 && (h || /* @__PURE__ */ d("div", { className: "bb:flex-1", children: [ /* @__PURE__ */ e("p", { className: "bb:text-center", children: "Welcome to BrowserBrains - Local Chat!" }), /* @__PURE__ */ e("br", {}), /* @__PURE__ */ e("p", { className: "", children: "I can help you with question like:" }), /* @__PURE__ */ e("br", {}), /* @__PURE__ */ d("ul", { className: "bb:list-disc bb:list-inside", children: [ /* @__PURE__ */ e("li", { children: "If it takes 5 machines 5 minutes to make 5 widgets, how long would it take 100 machines to make 100 widgets?" }), /* @__PURE__ */ e("li", { children: "What is the capital of France?" }), /* @__PURE__ */ e("li", { children: "What is the population of the moon?" }) ] }) ] })), l == null ? void 0 : l.map((b) => /* @__PURE__ */ d( ie, { variant: b.role === "user" ? "sent" : "received", children: [ /* @__PURE__ */ e(Ue, { src: "", fallback: b.role === "user" ? "🧑‍🦲" : "🤖" }), /* @__PURE__ */ e(ce, { children: qe(b.content) }) ] }, b.id || `message-${b.role}-${Math.random()}` )) ] }) }), /* @__PURE__ */ d(ge, { children: [ /* @__PURE__ */ e( de, { value: w, onChange: (b) => { const i = b.target; N(i.value); }, onKeyDown: (b) => { b.target.value.length > 0 && !q && b.key === "Enter" && !b.shiftKey && (b.preventDefault(), Z()); } } ), /* @__PURE__ */ e( L, { className: "bb:absolute bb:bottom-[24px] bb:right-[24px]", type: "submit", size: "icon", onClick: () => { w.length > 0 && Z(); }, children: /* @__PURE__ */ e(Me, { className: "bb:size-4" }) } ) ] }), /* @__PURE__ */ e("p", { className: "bb:absolute bb:bottom-[0px] bb:w-full bb:min-h-4 bb:text-center bb:text-gray-400 bb:text-xs bb:m-0", children: Y && l.length > 0 && G !== null && /* @__PURE__ */ d(te, { children: [ !q && /* @__PURE__ */ d("span", { children: [ G, " tokens in ", (G / Y).toFixed(2), " seconds (" ] }), /* @__PURE__ */ d("span", { className: "bb:mr-1 bb:text-center bb:font-medium", children: [ Y.toFixed(2), " tks/second)" ] }) ] }) }) ] } ) ] }); }; export { mt as LocalChat }; //# sourceMappingURL=index.js.map