Reaction Bar
Preview: Default
Message reactions: toggle chips with live counts, plus an emoji picker to add new ones.
Import
import { ReactionBar } from '@marbleui/ui'Props
<ReactionBar>
| Prop | Type | Default | Description |
|---|---|---|---|
| onChange *required | (next: Reaction[]) => void | — | |
| reactions *required | Reaction[] | — | |
| className | string | — |
Accessibility
Keyboard interaction, focus management and ARIA semantics come from the underlying primitive: React Aria ToggleButton. Follow the primitive's docs for the full keyboard map.
Usage notes
Emoji reaction chips with counts, plus an “Add reaction” picker, for messages and comments between people. To rate an AI reply use the thumbs in MessageActions.
// comment.reactions: [{ emoji: '🎉', label: 'tada', count: 4, mine: true }, { emoji: '👀', label: 'eyes', count: 2 }]
<ReactionBar reactions={comment.reactions} onChange={(next) => saveReactions(comment.id, next)} />
- Controlled only:
onChangehands back the whole next array and nothing is saved for you.minemarks the current user’s reactions and drives the selected state. - Pressing a chip toggles your reaction, and a chip whose count reaches 0 disappears. Picking an emoji you already reacted with from the picker keeps it.
- Each chip is read as “tada, 4 reactions, including you”, built from
label. Reactions added from the picker take theirlabelfrom the picker’s emoji name (“tada”), falling back to the character. - Put it in the message body, not in
ChatMessage’sactions, which hide until hover.
Example source · show· hide
import { useState } from 'react'
import { Avatar } from '../avatar'
import { ReactionBar, type Reaction } from './reaction-bar'
function Demo() {
const [r, setR] = useState<Reaction[]>([{ emoji: '🎉', label: 'tada', count: 4, mine: true }, { emoji: '👀', label: 'eyes', count: 2 }, { emoji: '🚀', label: 'rocket', count: 1 }])
return (
<div className="flex w-96 gap-3 rounded-xl border border-border bg-surface p-4">
<Avatar size="sm" name="Ada Park" />
<div className="flex flex-col gap-2"><p className="text-sm text-fg"><span className="font-medium">Ada Park</span> · Shipped the new data grid 🎉</p><ReactionBar reactions={r} onChange={setR} /></div>
</div>
)
}
export const styles = { Default: Demo }Source: packages/ui/src/reaction-bar/reaction-bar.tsx
Catalog
- Category
- ai-agents
- Priority
- Extra
- Primitive
- composed
- React Aria
- ToggleButtonGroup
- Base UI
- Toggle Group