Meet Frontfriend.Your brand. Your rules. Your agents, connected.Explore what’s new

Bubble

Interactive preview

Rendered from the shared Frontfriend stories with React Base, the same preview Studio shows. Styling comes from your Design System; the code below is native to Reka UI.

Installation

Complete project setup first. Your configuration must select vue/reka and include your Design System ID.

pnpm exec frontfriend download bubble -f vue --primitive reka

Review dependencies reported by the downloader and keep your source changes in version control.

Usage

<script setup lang="ts">
import { Bubble } from "@/components/ui/bubble";
import { BubbleContent } from "@/components/ui/bubble";

const args = {
  "variant": "default",
  "align": "start",
  "text": "Hello! How can I help?",
} satisfies Partial<
  InstanceType<typeof Bubble> extends { $props: infer Props } ? Props : {}
> &
  Record<string, unknown> & {
    variant?: "default" | "muted";
    align?: "start" | "end";
  };
</script>

<template>
  <Bubble :variant="args.variant" :align="args.align"
    ><BubbleContent>{{ args.text }}</BubbleContent></Bubble
  >
</template>

Examples

Default

<script setup lang="ts">
import { Bubble } from "@/components/ui/bubble";
import { BubbleContent } from "@/components/ui/bubble";
import { BubbleGroup } from "@/components/ui/bubble";
import { BubbleReactions } from "@/components/ui/bubble";

const args = {

} satisfies Partial<
  InstanceType<typeof Bubble> extends { $props: infer Props } ? Props : {}
> &
  Record<string, unknown>;
</script>

<template>
  <div class="flex w-full max-w-sm flex-col gap-8 py-12">
    <Bubble align="end">
      <BubbleContent>Hey there! what&apos;s up?</BubbleContent>
    </Bubble>
    <BubbleGroup>
      <Bubble variant="muted">
        <BubbleContent>Hey! Want to see chat bubbles?</BubbleContent>
      </Bubble>
      <Bubble variant="muted">
        <BubbleContent>
          I can group messages, switch sides, and keep the whole thread easy to
          scan.
        </BubbleContent>
        <BubbleReactions role="img" aria-label="Reaction: thumbs up">
          <span>👍</span>
        </BubbleReactions>
      </Bubble>
    </BubbleGroup>
    <Bubble align="end">
      <BubbleContent>Sure. Hit me with your best demo.</BubbleContent>
    </Bubble>
    <Bubble variant="muted">
      <BubbleContent>
        Yes. You are reading a demo that is demoing itself. Very meta. Very
        on-brand.
      </BubbleContent>
      <BubbleReactions
        role="img"
        aria-label="Reactions: thumbs up, fire, eyes, and 2 more"
      >
        <span>👍</span>
        <span>🔥</span>
        <span>👀</span>
        <span>+2</span>
      </BubbleReactions>
    </Bubble>
  </div>
</template>

Variants

<script setup lang="ts">
import { Bubble } from "@/components/ui/bubble";
import { BubbleContent } from "@/components/ui/bubble";

const args = {

} satisfies Partial<
  InstanceType<typeof Bubble> extends { $props: infer Props } ? Props : {}
> &
  Record<string, unknown>;
const variants = [
  "default",
  "secondary",
  "muted",
  "tinted",
  "outline",
  "ghost",
  "destructive",
];
</script>

<template>
  <div class="flex w-full max-w-sm flex-col gap-3 py-12">
    <Bubble v-for="variant in variants" :key="variant" :variant="variant">
      <BubbleContent>{{ variant }}</BubbleContent>
    </Bubble>
  </div>
</template>

Reactions

<script setup lang="ts">
import { Bubble } from "@/components/ui/bubble";
import { BubbleContent } from "@/components/ui/bubble";
import { BubbleReactions } from "@/components/ui/bubble";

const args = {

} satisfies Partial<
  InstanceType<typeof Bubble> extends { $props: infer Props } ? Props : {}
> &
  Record<string, unknown>;
const placements = [
  { side: "bottom", align: "end" },
  { side: "bottom", align: "start" },
  { side: "top", align: "end" },
  { side: "top", align: "start" },
];
</script>

<template>
  <div class="flex w-full max-w-sm flex-col gap-10 py-12">
    <Bubble v-for="p in placements" :key="p.side + p.align" variant="muted">
      <BubbleContent>side={{ p.side }} · align={{ p.align }}</BubbleContent>
      <BubbleReactions
        :side="p.side"
        :align="p.align"
        role="img"
        aria-label="Reaction: thumbs up"
      >
        <span>👍</span>
      </BubbleReactions>
    </Bubble>
  </div>
</template>

API reference

Frontfriend-owned props. Native HTML and inherited primitive props remain documented by Reka UI.

Bubble

Prop Type Default Description
align "start" | "end" —
class HTMLAttributes["class"] —
variant BubbleVariants["variant"] —

BubbleContent

Prop Type Default Description
class HTMLAttributes["class"] —

BubbleGroup

Prop Type Default Description
class HTMLAttributes["class"] —

BubbleReactions

Prop Type Default Description
align BubbleReactionsVariants["align"] —
class HTMLAttributes["class"] —
side BubbleReactionsVariants["side"] —

Configuration determines the actual classes and available styling hooks. See Theming & component configuration before introducing a repeated local override.