Skip to content
  1. Keyline UI
  2. Tooltip
Keyline UIComponents
  • Get started
    • Installation
    • Theming
    • Modes
    • Configuration
    • Composition
  • Actions
    • Button
    • Button group
    • Split button
    • Toggle
    • Toggle group
    • Toolbar
    • Menu
    • Menubar
    • Context menu
  • Inputs
    • Field and form
    • Checkbox
    • Checkbox group
    • Radio group
    • Switch
    • Slider
    • Segmented
    • Select
    • Native select
    • Combobox
    • Multiselect
    • Number field
    • OTP field
    • Time field
    • Date picker and calendar
    • Date range
  • Data
    • Table
    • Chart
    • Stat and meter
    • Status and badge
    • Progress
    • Skeleton
    • Empty
    • Avatar
    • Kbd
    • Marker
  • Navigation
    • Tabs
    • Breadcrumb
    • Pagination
    • Nav
    • Navigation menu
    • Command menu
  • Overlays
    • Dialog
    • Alert dialog
    • Drawer
    • Sheet
    • Popover
    • Hover card
    • Tooltip
    • Toast
    • Notice
  • Layout
    • App shell
    • Sidebar
    • Panel
    • Resizable
    • Scroll area
    • Accordion
    • Collapsible
    • Carousel
    • Inspector
    • Item
    • Direction
  • Conversation
    • Message
    • Bubble
    • Message scroller
    • Attachment
    • Questionnaire
  • Blocks
    • Shipments

Tooltip

An ink label that names what a control does, with its shortcut in a cell of its own. It docks to the focus ring, not the box, so keyboard and pointer see the same thing. It opens on hover and focus and never holds the only copy of something a reader needs.

Loading the live example…

"use client"

import { Archive, Copy, Mail, Printer } from "lucide-react"
import { useState } from "react"
import { Button } from "@/components/keyline/ui/button"
import { Tooltip } from "@/components/keyline/ui/tooltip"

const TOOLS = [
  { name: "Print", key: "⌘P", Icon: Printer, done: "Sent to the printer by Kevin's desk." },
  { name: "Email to client", key: "⌘E", Icon: Mail, done: "Emailed to Lackawanna County." },
  { name: "Duplicate", key: "⌘D", Icon: Copy, done: "Duplicated as DM-4142." },
  { name: "Archive", key: "⌘⌫", Icon: Archive, done: "Archived. It stays in reports." },
]

export function InvoiceTools() {
  const [last, setLast] = useState("")
  return (
    <div className="grid gap-3">
      <div role="toolbar" aria-label="Invoice DM-4107" className="flex gap-2">
        {TOOLS.map((t) => (
          <Tooltip key={t.name} content={t.name} shortcut={t.key}>
            <Button size="icon" aria-label={t.name} onClick={() => setLast(t.done)}>
              <t.Icon size={16} aria-hidden="true" />
            </Button>
          </Tooltip>
        ))}
      </div>
      <p role="status" className="m-0 min-h-5 text-[14px] text-kl-ink-2">
        {last}
      </p>
    </div>
  )
}

Installation

npx shadcn@latest add @keyline-ui/tooltip

Run it where your components.json is. The first time, map the @keyline-ui registry: one command, in Installation.

Usage

import { Tooltip } from "@/components/keyline/ui/tooltip"
<Tooltip content="Print" shortcut="⌘P">
  <Button size="icon" aria-label="Print">…</Button>
</Tooltip>

Props

PropTypeDefaultDescription
childrenReactElementDefault —The trigger: a focusable element that takes a ref, such as a Button.
contentReactNodeDefault —The label. Keep it to a few words.
shortcutReactNodeDefault —A keyboard shortcut, shown in its own cell.
side"top" | "bottom" | "left" | "right" | "inline-start" | "inline-end"Default "top"Where it sits. It flips when there&apos;s no room.
delaynumberDefault 500Milliseconds of hover before it opens. Focus opens it at once.

An icon button still needs its own aria-label; the tooltip is for sighted readers. Wrap a group in TooltipProvider so moving between buttons skips the delay. Built on Base UI Tooltip.

Sheet 54 of 73PreviousHover cardNextToast
On this page