LevelChatLevelChatDocs
ReactionBar

Components

ReactionBar

The send half of the reaction surface — a row of emoji buttons.

ReactionBar is the picker a participant taps to send a reaction. ReactionOverlay renders reactions coming the other way — together they are the full round-trip. The bar auto-wires to the active room; pass onReact to use it without one.

Install

pnpm add @levelchat/react-components @levelchat/web

Requirements

  • Reactreact and react-dom ^18 || ^19 (peer dependency).
  • LevelChat Web SDK@levelchat/web ^0.2.4 (peer dependency, wires hook-driven mode to the live Room).
  • Provider — wrap the tree in <LevelChatProvider> from @levelchat/web-react so hook-driven mode can subscribe to room events. Prop-driven demos work without it.
  • Styles — import the brand tokens + kit stylesheet exactly once at the app entry, before any kit component renders.

In Next.js (App Router), import the stylesheets at the top of your root layout:

TypeScript (TSX)
// app/layout.tsx
import '@levelchat/brand/tokens.css';
import '@levelchat/react-components/styles.css';

In Vite (or any plain React app), import them at the top of your entry module:

TypeScript (TSX)
// src/main.tsx
import '@levelchat/brand/tokens.css';
import '@levelchat/react-components/styles.css';

Basic usage

Drop it inside a <LevelChatProvider> and every tap calls room.reactions.send(). The glass surface floats over the video stage; plain sits on a light card.

Pairing with ReactionOverlay

The two reaction components share one hook (useReactions), so wiring both gives you the complete loop — picker in, floating emoji out:

<div className="relative">
  <ParticipantGrid />
  <ReactionOverlay />            {/* incoming reactions */}
  <div className="absolute bottom-4 inset-x-0 flex justify-center">
    <ReactionBar surface="glass" /> {/* outgoing reactions */}
  </div>
</div>

Custom reaction set

The default set is six reactions. Pass reactions to curate your own — each entry needs an emoji and a human-readable label (the label drives the button's accessible name).

<ReactionBar
  reactions={[
    { emoji: '👍', label: 'Agree' },
    { emoji: '🙌', label: 'Celebrate' },
    { emoji: '🤔', label: 'Thinking' },
  ]}
/>

Headless hook

useReactions is the headless layer — build a wholly custom picker against its send action.

import { useReactions } from '@levelchat/react-components';

function MyPicker() {
  const { send, supported } = useReactions();
  if (!supported) return null;
  return <button onClick={() => send('🎉')}>Celebrate</button>;
}

Accessibility

  • The bar is a role="group" labelled "Send a reaction".
  • Each button has a real aria-label ("React with Applause") so the reaction is announced by name, never as a bare emoji glyph.
  • The tap-pop animation is suppressed under `prefers-reduced-motion`.

Props

PropTypeDefaultNotes
reactionsReactionChoice[]DEFAULT_REACTIONSThe emoji + label pairs to render.
surface'glass' | 'plain'glassTranslucent over-video bar, or opaque on-surface card.
disabledbooleanfalseDisable every button.
onReact(emoji: string) => voidCalled on every tap, alongside the room send.
ReactionBar — LevelChat Docs