Skip to content

AssistedPanel renders inside AssistedProvider and picks where it shows with mode. Import the styles once, anywhere in the app:

import "@super-assist/react/styles.css";

Each branch below is from examples/app/app/assistant.tsx, which switches mode on a query parameter in development.

Floating: a window over the page that the user drags, resizes, minimizes and maximizes. While it is closed, a launcher button in the corner opens it.

return (
<>
<main className="min-h-dvh p-6">{children}</main>
<AssistedPanel mode="floating" />
</>
);

Sheet: a column beside the page that takes the page’s space, with no overlay. Closed, it is a slim rail with a button. Put it in a flex row with the page:

return (
<div className="flex h-dvh">
<main className="min-w-0 flex-1 overflow-y-auto p-6">{children}</main>
<AssistedPanel mode="sheet" />
</div>
);

Embedded: the conversation and the composer, placed where your layout puts them. It has no header and no launcher, and it is always shown. Give its container a height:

return (
<div className="flex h-dvh">
<main className="min-w-0 flex-1 overflow-y-auto p-6">{children}</main>
<div className="w-md shrink-0 border-s">
<AssistedPanel mode="embedded" />
</div>
</div>
);

title and icon replace “Assistant” and the logo in the header and on the launcher. description is the header’s line when no assisted page is open:

<AssistedPanel
mode="floating"
title="Shop assistant"
icon={<ShoppingBag />}
description="Ask about anything in the shop."
/>

The floating window opens 420 by 640 px in the bottom-right corner, 24 px in. defaultPosition and defaultSize change where and how big it first opens. The user’s moves and resizes persist across opens.

<AssistedPanel
mode="floating"
defaultPosition="bottom-left"
defaultSize={{ width: 480, height: 720 }}
/>

resizable={false}, draggable={false} and windowControls={false} turn off its edge handles, its dragging by the header, and its Minimize and Maximize buttons. Close stays.

AssistedPanel.Trigger is a small Assistant button for your own toolbar. It opens and closes the floating window or the sheet. From examples/app/app/shell.tsx:

<div className="ms-auto flex gap-2">
{mode !== "embedded" && <AssistedPanel.Trigger />}
<Button variant="outline" size="sm" onClick={() => shop.call("reset")}>
Reset shop
</Button>
</div>

With asChild, your own button becomes the trigger. Pass launcher={false} when the trigger is the only way in:

<AssistedPanel mode="floating" launcher={false} />
<AssistedPanel.Trigger asChild>
<Button>Help</Button>
</AssistedPanel.Trigger>

The trigger may sit anywhere inside AssistedProvider, outside the panel.

useAssisted opens and closes the panel. open with a message also sends it as the user’s:

export function AskAboutOrder({ id }: { id: string }) {
const { open } = useAssisted();
return (
<Button onClick={() => open(`Why hasn't order #${id} shipped?`)}>Ask the assistant</Button>
);
}

The floating panel sits at z-index 50, above the ring. A modal dialog’s backdrop still blocks it. Make assisted dialogs non-modal, see Make a dialog assisted.

Every prop is on Roots and window. To change what the panel holds, see Rearrange the panel’s parts.