Skip to content
Blog

Tooltip Widget in Flutter: Small Hints With Big UX Value

When to use Tooltip for hover and long-press hints, richText and decoration options, keyboard/semantics behavior, and why Tooltips are not for essential information.

Published on • November 4, 2026

AI Assistant

An icon button with no label is a guessing game — until a small dark bubble appears on hover. Tooltip wraps any widget and reveals a short hint on long-press (touch) or hover (desktop/web), and it’s one of the cheapest accessibility wins in Material (docs.flutter.dev).

The Basic Wrap

Tooltip(
  message: 'Archive conversation',
  child: IconButton(
    icon: const Icon(Icons.archive_outlined),
    onPressed: _archive,
  ),
)

That’s the whole contract: Tooltip provides the gesture detection (a GestureDetector for long-press, a MouseRegion for hover) and paints the bubble above the child.

Rich Tooltips

message takes a plain string, but richMessage accepts inline TextSpan styling when a hint needs emphasis:

Tooltip(
  richMessage: TextSpan(
    children: [
      const Text(text: 'Shortcut: '),
      TextSpan(
        text: 'Ctrl + K',
        style: TextStyle(
          fontWeight: FontWeight.bold,
          color: Theme.of(context).colorScheme.primary,
        ),
      ),
      const Text(text: ' to search'),
    ],
  ),
  child: const SearchButton(),
)

For genuinely complex content — images, buttons, multi-line cards — skip Tooltip and use a MenuAnchor or custom OverlayEntry; Tooltips are deliberately text-shaped and dismiss on any tap.

Shaping and Placement

Defaults are fine, but the tooltip inherits nothing from your theme — style it explicitly when it must match:

Tooltip(
  message: 'Delete permanently',
  decoration: BoxDecoration(
    color: const Color(0xFFB42318),
    borderRadius: BorderRadius.circular(8),
  ),
  textStyle: const TextStyle(color: Colors.white, fontSize: 12),
  padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 8),
  preferBelow: false,     // prefer showing above the child
  verticalOffset: 24,     // distance from the child
  showDuration: const Duration(seconds: 3),
  child: const Icon(Icons.delete_outline),
)

preferBelow/verticalOffset control placement; waitDuration delays appearance so tooltips don’t flash during pointer pass-through.

Accessibility: The Semantics Layer

This is where Tooltip earns its keep. On touch, TalkBack and VoiceOver users get the hint as the widget’s semantic label; on desktop, hover reveals it visually. But two rules matter:

  1. Never put essential information only in a tooltip — touch users must long-press to see it, and screen readers announce it only on focus.
  2. Icon buttons still need accessible names. A Tooltip message doubles as the semantics label, which is why pairing it with IconButton is the standard Material pattern — but if the icon is self-evident, semanticsLabel on the icon is enough.

When Not to Use Tooltips

Tooltips are hints, not documentation: no links, no interactive elements, no long paragraphs. They also don’t fire while a modal route is open or during rapid pointer movement across many icons — hover a toolbar and you’ll see Tooltip intentionally throttles. For persistent help, prefer an info icon opening a dialog or a HelpBadge-style inline marker.

Wrap the ambiguous icon, keep the message short, and never hide anything critical inside a hint — and Tooltip turns guesswork into guidance.