Message Bubble

The visible surface of a single chat message: six tones from solid to danger, start or end alignment inherited from its Message row, tight bubble groups, a line-clamped show-more toggle, and room for links or buttons inside.

Animated Surfaces

message-bubble.tsx

A live demo conversation: each message you send pops in once from its corner, while the assistant reply streams into a row that holds still.

Message Bubble Animated Surfaces preview width

With Avatars

message-bubble.tsx

Messages land one after another with sender avatars, header details, a delivery status, and follow-ups kept in line by an empty avatar slot.

Message Bubble With Avatars preview width

Show More

message-bubble.tsx

A long assistant answer clamped to a few lines, with a toggle under the text that opens it downward and folds it back up.

Message Bubble Show More preview width

API Reference

MessageBubble

variant?
"ghost" | "outline" | "solid" | "danger" | "soft" | "tint"
soft
align?
"end" | "start"

Defaults to the surrounding Message alignment when omitted.

—
animateIn?
boolean

Plays the bubble entrance once when this component mounts.

false
className?
string
—

MessageBubbleContent

render?
ReactElement<unknown, string | JSXElementConstructor<any>>

Replaces the content element while preserving bubble styling.

—
className?
string
—

MessageBubbleGroup

spacing?
"default" | "compact"
compact
className?
string
—

MessageBubbleCollapsible

open?
boolean
—
defaultOpen?
boolean
false
onOpenChange?
((open: boolean) => void)
—
collapsedLines?
2 | 3 | 4 | 5 | 6
4
moreLabel?
ReactNode
Show more
lessLabel?
ReactNode
Show less
contentClassName?
string
—
triggerClassName?
string
—
className?
string
—

Install

Add it with the shadcn CLI, or copy the source manually.

$ bunx --bun shadcn add @karaui/message-bubble
@karaui not found? Add it to components.json
{
  "registries": {
    "@karaui": "https://karaui.kamisama-v0.my.id/r/{name}.json"
  }
}

@karaui is in shadcn's public registry directory, so the latest CLI needs no setup. On an older CLI, merge this into the existing file once and every @karaui/… install resolves.

Composition

Nest MessageBubble within MessageContent, so the row keeps avatar and alignment while the bubble only styles what is said.

Message
├── MessageAvatar
└── MessageContent
    └── MessageBubble
        └── MessageBubbleContent

Note: Message supplies the row: sender side, header details and the avatar slot. Streaming Response handles the answer while it streams and after it finishes.

How it works

Think of the bubble as paint, not plumbing. It shapes how one message reads, while who sent it, whether it arrived and where the transcript scrolls are settled by the components around it.

Updated