appCN
← All components

Stream Bubble

AI
new

An assistant message that animates through thinking, token streaming, and a settled final state. The AI-native flagship.

Preview

Scan with Expo Go to run it live

Install Expo Goon Android or iPhone, scan, and the entire appCN gallery loads — real native motion & gestures, not a web shim.

Open in Expo Go Play Store — coming soon
https://expo.dev/preview/update?message=v1.0.0+initial&updateRuntimeVersion=1.0.0&createdAt=2026-05-28T20%3A07%3A21.247Z&slug=exp&projectId=a2d02caa-be26-436a-acd6-f3007862ba0a&group=3ca7e750-9506-4146-8394-1a16c3a917a8

Install

npx @app-cn/cli@latest add stream-bubble

Recommended. Configures NativeWind + Reanimated and registers @app-cn on first run.

Anatomy

A self-bounded chat bubble that owns three phases — `thinking` (staggered dots), `streaming` (token reveal + blinking caret), `done` (settled). Optional tool chips fade in above the message once thinking ends. Pair it with PromptInput and ReasoningTrace for a complete AI screen.

The delight detail

The phase transitions are physical — dots stagger by 150ms each, the caret blinks on its own rhythm, and a `replayKey` re-runs the whole sequence so the bubble can come back to life on demand.

Props

NameTypeDefaultDescription
content*stringFull assistant message that streams in token-by-token.
toolsstring[]Optional "tool used" chips rendered above the message (e.g. "Searched the web").
thinkingDurationnumber900How long the thinking dots show before streaming begins (ms).
chunkSizenumber2Characters revealed per tick.
speednumber28Tick interval in ms — lower is faster.
replayKeystring | numberChange this value to replay the animation from the start.
classNamestringExtra NativeWind classes merged onto the bubble container.

Examples

Basic

Content-only — thinks, streams, settles.

<StreamBubble content="Hey! I'm appCN's streaming assistant bubble — watch me think, then stream, then settle." />

With tool chips

Chips fade in once thinking ends, before the tokens start.

<StreamBubble
  tools={["Searched the web", "Read 3 sources"]}
  content="Based on what I found, the short answer is yes — and here's why."
/>

Replayable

Bump replayKey to re-run the full thinking→stream→done cycle.

const [run, setRun] = React.useState(0);
return (
  <View className="gap-4">
    <StreamBubble replayKey={run} content="Tap replay to watch me do it again." />
    <Button variant="outline" onPress={() => setRun((r) => r + 1)}>Replay</Button>
  </View>
);

Accessibility

  • The bubble has `accessibilityRole="text"` so screen readers announce it as a single message.
  • Honors `useReducedMotion()` — when set, the bubble snaps straight to the settled state instead of animating.
  • The caret is decorative (no role); it's announced as part of the streaming text.
  • Tool chips inherit their text as accessible content — no extra label needed.