Popover
Popovers reveal richer, interactive content anchored to a trigger, and stay open until dismissed.
Components · Messaging
A popover is an anchored panel with a title, a divider, and body content — richer than a tooltip and interactive rather than transient. Namirial popovers are built from --nm-popover-* tokens defined in namirial-theme.css, share the same position and pointer system as tooltip, and default to the primary intent.
Narrow results by status, owner, or date.
Overview
A popover opens on click (not hover) and stays open until the user dismisses it — by clicking its trigger again, clicking outside, or pressing Escape. That persistence is what separates it from a tooltip: a popover can hold interactive content because the user has time to engage with it.
When to use
Use a popover when:
- The content needs to stay visible while the user reads it or interacts with something inside it (a filter panel, a small form, a list of actions).
- The trigger should toggle the panel open and closed on click, not just on hover.
Consider another component when:
Anatomy
A popover is a title, a divider, and a content region, plus the same directional pointer used by tooltip.
Tokens and values that drive each part
| Part | Role | Source |
|---|---|---|
| Container | Fill | --nm-popover-bg |
| Container | Border | --nm-popover-border |
| Container | Radius / padding / gap | border-radius: 8px · padding: 8px · gap: 6px |
| Container | Size bounds | min-width: 160px · max-width: 320px |
| Title | Color / weight | --nm-popover-fg, font-weight: 700 |
| Divider | Color | --nm-popover-fg at opacity: 0.6 |
| Content | Color | --nm-popover-fg, font-weight: 400 |
| Pointer | Fill | --nm-popover-border (8px triangle, via ::before) |
Positions
Popover shares tooltip's 12-position system — four sides, each with a centered default plus -start/-end alignment.
Centered above the trigger.
Centered below the trigger.
To the left of the trigger.
To the right of the trigger.
Intent variants
Popover ships seven intents, defaulting to primary.
Default appearance.
Neutral, explanatory content.
Flags a caveat before an action.
Confirms a destructive choice.
Content types
Title + content
Narrow results by status, owner, or date.
Content only
Drop the title and divider when the popover doesn't need a heading — a short action list or a single line of text stands on its own.
Light & dark theme
Popover tokens read from the shared --palette-callout-* scale, so no per-component dark override is needed.
Narrow by status or owner.
Narrow by status or owner.
Both previews are locked — they don't follow the page theme switcher.
Do & don't
Anyone with the link can view.
A full multi-step settings form doesn't fit a 320px-wide anchored panel — use a dialog or a dedicated page instead.
Are you sure you want to delete this? This can't be undone.
Accessibility
Semantics
- Give the trigger
aria-haspopup="true"andaria-expanded, toggled with the panel's open state. - Connect trigger and panel with
aria-controlspointing at the panel'sid.
Keyboard
- The trigger must open/close the popover on
Enter/Space, not only on click. Escapecloses the popover and returns focus to the trigger.- Tab must be able to reach every interactive element inside the popover before it can reach anything behind it.
Focus
- On open, move focus into the popover only if it contains interactive content the user is expected to use immediately; otherwise leave focus on the trigger.
- On close, always return focus to the trigger.
Token reference
| Token | Role |
|---|---|
| --nm-popover-bg | Container fill — recolored per intent |
| --nm-popover-border | Container border and pointer fill — recolored per intent |
| --nm-popover-fg | Title, divider, and content color — recolored per intent |
Implementation
Positioning and open/close state need JavaScript; the markup and visuals are pure CSS.
<link rel="stylesheet" href="namirial-theme.css">
<div class="nm-popover nm-popover--bottom" role="dialog" id="pop-1">
<span class="nm-popover__title">Filters</span>
<hr class="nm-popover__divider">
<span class="nm-popover__content">Narrow results by status, owner, or date.</span>
</div>CSS classes
| Class | Values | Default |
|---|---|---|
nm-popover--{position} | top · top-start · top-end · bottom · bottom-start · bottom-end · left · left-start · left-end · right · right-start · right-end | — |
nm-popover--{intent} | primary · secondary · accent · info · positive · negative · warning — omit for primary | — (primary) |
nm-popover__title | Bold heading row | — |
nm-popover__divider | <hr>-style rule between title and content | — |
nm-popover__content | Body content | — |