VisorVisor
ComponentsFeedback

Tooltip

Small text label that appears on hover or focus to describe an element.

Default

Wrap your trigger element with Tooltip and TooltipTrigger, then place the label text in TooltipContent. A TooltipProvider must wrap all tooltips in your app.

Side Offset

Use the sideOffset prop on TooltipContent to control the distance between the trigger and the tooltip.

Portal Container

TooltipContent portals into document.body by default. A theme scoped to a class on a wrapper never reaches the body, so the tooltip would read the page's theme instead. Pass the wrapper as container and the tooltip mounts inside it, under the scoped theme.

const [themeRoot, setThemeRoot] = React.useState<HTMLDivElement | null>(null);

<div ref={setThemeRoot} className="my-scoped-theme">
  <Tooltip>
    <TooltipTrigger asChild>
      <Button variant="ghost">Edit</Button>
    </TooltipTrigger>
    <TooltipContent container={themeRoot}>Edit section</TooltipContent>
  </Tooltip>
</div>

Theme Tokens

The tooltip reads its own ground and ink. Each falls back to the pair it has always used, so a theme that sets neither renders exactly as before.

TokenPropertyFalls back to
--tooltip-bgbackground-colorvar(--surface-overlay, #111827)
--tooltip-textcolorvar(--text-inverse, #ffffff)

In a dark theme --surface-overlay and --text-inverse can both resolve dark, which leaves the label unreadable. Do not retune --text-inverse to fix it: Calendar, Badge and Chip read it as their dark ink on light and accent fills. Bind the tooltip pair instead, as a component token or a flat override:

components:
  tooltip:
    bg:
      dark: "rgba(0, 0, 0, 0.8)"
    text:
      dark: "#fafafa"

# or, equivalently
overrides:
  dark:
    tooltip-bg: "rgba(0, 0, 0, 0.8)"
    tooltip-text: "#fafafa"

See Component tokens for the full contract.

Installation

npx visor add tooltip

This copies two files into your project:

  • components/ui/tooltip/tooltip.tsx — the component
  • components/ui/tooltip/tooltip.module.css — the styles

Usage

import {
  Tooltip, TooltipContent, TooltipProvider, TooltipTrigger
} from '@/components/ui/tooltip/tooltip';

// Wrap your app with TooltipProvider once
<TooltipProvider>
  <Tooltip>
    <TooltipTrigger asChild>
      <button>?</button>
    </TooltipTrigger>
    <TooltipContent>Help text</TooltipContent>
  </Tooltip>
</TooltipProvider>

API Reference

TooltipProps

No props data available for “tooltip”.

Sub-components

ComponentPurpose
TooltipProviderWraps the app to set global tooltip delay and behavior
TooltipRoot component managing open/close state for a single tooltip
TooltipTriggerElement that activates the tooltip on hover/focus
TooltipContentThe floating label rendered in a portal (document.body unless container is set)

Accessibility

  • Built on @radix-ui/react-tooltip with automatic aria-describedby associations.
  • Tooltips appear on both hover and keyboard focus, ensuring full keyboard accessibility.
  • Use tooltips for supplementary labels only — they should not contain essential information or interactive elements.