How to Design Tooltips and Popovers That Work on Touch and Keyboard

Hand holding a smartphone showing a signup screen up close

A designer adds a small question-mark icon next to a confusing field, wires up a tooltip that appears on hover, and moves on. In the design review on a laptop it looks perfect. Then the first customer opens the page on a phone, taps the icon, and nothing happens. A keyboard user tabs right past it. A screen reader announces an unlabeled button. The help text exists, but a large share of the audience can never reach it.

This is one of the most common small failures in interface work, and it is cheap to avoid once you know where it comes from. This guide covers when to use a tooltip versus a popover, how to trigger each one for every input type, how to position them, and how to test the result.

whiteboard sketches of a user flow
Photo by Shuki Harel on Pexels

Why Hover-Only Tooltips Fail

The hover state is a mouse feature. A finger has no hover, so on a touch device the pointer either never fires or fires as a side effect of a tap, which is unreliable and differs between browsers. A keyboard has no pointer at all, so anything that depends on mouseenter is invisible to someone who navigates with the Tab key. Switch devices, voice control, and many screen magnifier setups behave the same way.

The accessibility guidance published by the W3C Web Accessibility Initiative frames this as content on hover or focus. If the information appears when a pointer rests on something, it must also appear when keyboard focus lands there, and the user must be able to dismiss it without moving the pointer. A tooltip that satisfies only the first half fails real people and fails audits.

The practical lesson is to stop thinking of the tooltip as a hover effect. It is a small piece of content with a trigger, and the trigger has to exist for every way a person can interact with the page.

Decide Whether You Need a Tooltip or a Popover

The two patterns get mixed up constantly, and mixing them produces most of the bugs. A tooltip is a short, non-interactive label that describes the element it is attached to. It holds plain text, usually a few words, and nothing inside it can be clicked. A popover is a small floating panel that can hold richer content, such as a paragraph, a link, a button, or a short form.

Use a tooltip when the element needs a name or a one-line hint and the information is supplementary. An icon-only toolbar button that shows its label is the classic case. Use a popover when the content is longer than a sentence, when it contains a link, or when the user needs to act on it. Help text that includes a "learn more" link is a popover, not a tooltip, no matter what the design file calls it.

A useful test is to ask whether the user could do their task without ever seeing the text. If the answer is no, the text does not belong in a tooltip at all. It belongs on the page, visible by default, because anything required should never hide behind an interaction.

Build Triggers for Every Input Type

A robust tooltip opens on four events. It opens on pointer hover, with a short delay so it does not flicker as the mouse crosses the page. It opens on keyboard focus, immediately, so Tab navigation reveals it. It closes on blur and on pointer leave. And it closes when the user presses Escape, which is the dismissal rule from the accessibility guidance above.

Touch is the case that needs a decision. For a true tooltip on a touch device, the simplest honest answer is that the label should already be visible or reachable another way, because a tap on a button should perform the button's action, not show a hint. For a popover, the trigger is a real button that toggles the panel on tap, click, Enter, and Space alike. That single design choice, using a button element instead of a decorated span, gives you keyboard activation, focus handling, and screen reader support for free.

smartphone held in hand showing an app screen
Photo by freestocks.org on Pexels

Wire Up the Accessibility Attributes

The markup carries more of the work than the styling does. For a tooltip, the element that owns the hint should reference it with aria-describedby, pointing at the tooltip's id, and the tooltip itself should have role="tooltip". This tells assistive technology that the text describes the control without replacing its accessible name. The MDN Web Docs reference for ARIA roles documents the exact behavior and the edge cases.

For a popover, the trigger button should expose aria-expanded set to true or false and aria-controls pointing at the panel. When the panel opens, focus should move into it if it contains interactive content, and when it closes, focus must return to the trigger. Losing focus to the top of the document after closing is the single most disorienting behavior in keyboard use.

Icon-only triggers need an accessible name. A question-mark glyph inside a button needs an aria-label such as "More information about billing address", written to say what the help is about, not just "help". Five identical "Help" buttons on one form are indistinguishable to a screen reader user who lists the controls on the page.

Position and Size the Content Sensibly

A tooltip that gets clipped by the edge of the screen or hidden under a sticky header is as broken as one that never opens. Positioning logic has more edge cases than it looks like: scrolling containers, transformed ancestors, right-to-left layouts, and small viewports all change where the content should go.

Rather than hand-rolling it, use a library built for the problem. Floating UI handles flipping to the opposite side when there is no room, shifting along the edge to stay on screen, and tracking the anchor as the page scrolls. It also gives you collision padding so the bubble never touches the viewport edge.

Keep the content itself small. A tooltip should rarely exceed around eighty characters, and a popover should rarely exceed a short paragraph. Set a maximum width so lines stay readable, and make sure the text contrast meets the same ratio as the rest of the page. Pale gray text on a white bubble is a surprisingly common contrast failure.

Handle the Hard Cases: Hover Bridges, Persistence, and Motion

Two behaviors cause the most complaints in testing. The first is the disappearing popover. If a panel opens on hover and the user moves the pointer toward it, any gap between the trigger and the panel closes it before they arrive. The fix is to treat the trigger and the panel as one hover region, or to add a short close delay so the pointer can cross the gap. The accessibility guidance calls this being hoverable: the content must stay visible while the pointer is over it.

The second is persistence. A tooltip should stay open until the user moves focus, moves the pointer away, or presses Escape. Auto-hiding after three seconds is a failure for anyone who reads slowly, uses a magnifier, or simply got distracted. Never put a timer on information the user may still be reading.

Then there is motion. A subtle fade of around one hundred and fifty milliseconds feels polished, but a sliding or bouncing entrance is a problem for people who have asked their system to reduce motion. Respect the prefers-reduced-motion media query and drop the animation entirely in that case. The text appearing instantly is perfectly fine.

designer sketches pinned across a studio wall
Photo by Anna Shvets on Pexels

Know When Not to Use Either One

The strongest design move is often to delete the tooltip. If a label is needed to understand a control, write the label on the control. If a field needs a format hint, put it under the field where everyone sees it. Hidden help makes sense for secondary detail, not for the main instruction, and every hiding place you add is a place a user can fail to look.

On mobile screens in particular, consider replacing popovers with an inline expandable section or a bottom sheet. A small floating bubble anchored to a tiny icon is awkward to tap and easy to cover with a thumb. Research and guidance from the Nielsen Norman Group on contextual help consistently points toward visible, persistent instructions over hover-revealed ones for exactly this reason.

"The test for a tooltip is brutally simple. If a customer on a phone would be stuck without it, it was never a tooltip. It was missing content that someone hid." - Dennis Traina, founder of 137Foundry

Test the Behavior, Not Just the Look

tablet and stylus resting on a desk
Photo by cottonbro studio on Pexels

Static screenshots will never reveal these bugs. The checks that find them take only a few minutes. Put the mouse away and tab through the page: every trigger should receive visible focus, and the content should appear and disappear predictably. Press Escape while one is open and confirm it closes with focus staying where it should.

Next, run the page with a screen reader on at least one platform and listen to what the trigger announces. You should hear a meaningful name and an expanded or collapsed state for popovers. Then open the page on a real phone, not just a resized browser window, and tap every trigger. Emulated touch in desktop tools does not reproduce every browser quirk.

Finally, automate what you can. Linting rules and automated checkers from groups like WebAIM can flag missing labels and contrast failures, though they cannot judge whether the interaction feels right. Treat the automated pass as a floor and the manual keyboard and phone pass as the real test.

Putting It Into Practice on a Real Product

If your product already has dozens of hover tooltips scattered across screens, do not rewrite them all at once. Start with an inventory: list each one, mark whether its content is required or supplementary, and note what triggers it today. The required ones move into visible text. The supplementary ones get rebuilt on a single shared component that implements the triggers, attributes, positioning, and dismissal rules once.

A shared component is the real payoff. When the pattern lives in one place, every new use inherits correct behavior, and a future fix lands everywhere at once. That is far cheaper than auditing fifty bespoke implementations after a complaint arrives.

Our team at 137Foundry builds and repairs interface components like this as part of broader front-end work, and the web development service page explains how we approach it. For a wider look at how we think about accessible, maintainable interfaces, the about page is a good place to start, and our services hub lists the other kinds of projects we take on.

A Short Checklist to Keep Nearby

Before shipping any tooltip or popover, run through the same list. Decide whether it is a tooltip or a popover, and confirm the content is not required to complete the task. Use a real button as the trigger with a descriptive accessible name. Open on hover and on focus, close on blur, pointer leave, and Escape, and keep the content visible while the pointer is over it. Link the pieces with aria-describedby or aria-expanded and aria-controls, return focus to the trigger on close, and position with a tested library instead of custom math.

Hover is a convenience for some users, not a foundation for everyone. Build the trigger for the keyboard and the thumb first, and the mouse version takes care of itself.

Need help with Web Development?

137Foundry builds custom software, AI integrations, and automation systems for businesses that need real solutions.

Book a Free Consultation View Services