|$ curl https://forge-ai.dev/api/markdown?path=docs/css/anchor-positioning
$cat docs/css-anchor-positioning.md
updated Last week·13 min read·published

CSS Anchor Positioning

CSSAnchor PositioningTooltipsAdvanced🎯Free Tools
Introduction

CSS Anchor Positioning lets you position elements relative to an anchor element— any element you designate as a positioning reference. This eliminates the need for JavaScript-based tooltip and popover libraries by giving CSS a native way to say "position this element relative to that one."

The feature introduces the anchor-name property on anchor elements and the position-anchor / anchor() function on positioned elements. Combined with position-area, it provides a complete system for building tooltips, popovers, dropdown menus, and floating UI — all in CSS.

anchor-basics.css
CSS
1/* Define an anchor */
2.tooltip-trigger {
3 anchor-name: --my-trigger;
4}
5
6/* Position a tooltip relative to that anchor */
7.tooltip {
8 position: fixed;
9 position-anchor: --my-trigger;
10 top: anchor(bottom);
11 left: anchor(center);
12 transform: translateX(-50%);
13 margin-top: 8px;
14}
Anchor Elements

An anchor element is any element that has the anchor-name property set. This name is a dashed identifier (similar to CSS custom properties) that referenced elements use to find their anchor.

anchor-elements.css
CSS
1/* Any element can be an anchor */
2.button {
3 anchor-name: --submit-btn;
4}
5
6.card {
7 anchor-name: --product-card;
8}
9
10.nav-item {
11 anchor-name: --nav-home;
12}
13
14/* Multiple anchors on the same element */
15.input-wrapper {
16 anchor-name: --email-field --name-field;
17}

Anchor names are scoped to the document. An element with position: absolute, fixed, or sticky can reference any anchor by name. The anchor element must exist in the DOM at render time.

📝

note

Anchor names must start with -- (double dash), following the CSS custom property naming convention. This avoids conflicts with future CSS specifications.
position-anchor

The position-anchor property establishes the default anchor reference for an element. Once set, you can use the anchor() function and position-area to position relative to it.

position-anchor.css
CSS
1/* Simple tooltip pattern */
2.trigger {
3 anchor-name: --trigger;
4}
5
6.tooltip {
7 position: fixed;
8 position-anchor: --trigger;
9
10 /* Position below the trigger, centered */
11 position-area: bottom center;
12
13 /* Or use anchor() for precise placement */
14 top: anchor(bottom);
15 left: anchor(center);
16 transform: translateX(-50%);
17}
18
19/* Implicit anchor — when a positioned element is a descendant
20 of an anchor, you can skip position-anchor */
21.parent {
22 anchor-name: --parent;
23}
24
25.child {
26 position: absolute;
27 /* Automatically finds --parent as its anchor */
28 position-area: top right;
29}
Positioning Functions

Two functions provide precise control: anchor() for positioning and anchor-size() for sizing. They let you reference any edge or the center of the anchor element.

anchor() Function

anchor-function.css
CSS
1/* Reference anchor edges */
2.tooltip {
3 position: fixed;
4 position-anchor: --trigger;
5
6 /* Top edge of tooltip at bottom edge of anchor */
7 top: anchor(bottom);
8
9 /* Left edge at the anchor's left edge */
10 left: anchor(left);
11
12 /* Center of tooltip at center of anchor */
13 top: anchor(center);
14 left: anchor(center);
15 transform: translate(-50%, -50%);
16
17 /* With offset distance */
18 top: anchor(bottom 8px); /* 8px below the bottom edge */
19 left: anchor(right 12px); /* 12px to the right of right edge */
20}
21
22/* Different edge names */
23.left-tooltip {
24 position-anchor: --trigger;
25 right: anchor(left 8px); /* 8px to the left */
26 top: anchor(top);
27}
28
29.right-tooltip {
30 position-anchor: --trigger;
31 left: anchor(right 8px); /* 8px to the right */
32 top: anchor(top);
33}

anchor-size() Function

anchor-size.css
CSS
1/* Match the width of the anchor */
2.trigger {
3 anchor-name: --trigger;
4}
5
6.dropdown {
7 position: fixed;
8 position-anchor: --trigger;
9
10 /* Match anchor width */
11 width: anchor-size(width);
12
13 /* Match anchor height */
14 height: anchor-size(height);
15
16 /* Fraction of anchor size */
17 min-width: anchor-size(width) * 0.8;
18 max-height: anchor-size(height) * 3;
19
20 /* Position below */
21 top: anchor(bottom);
22 left: anchor(left);
23}
position-area

The position-area shorthand is a grid-based system for placing elements relative to their anchor. It uses a 3×3 grid notation where you specify which cells the positioned element should occupy.

position-area.css
CSS
1/* position-area grid layout:
2
3 top left | top center | top right
4 left | center | right
5 bottom left | bottom center | bottom right
6
7*/
8
9/* Below and centered */
10.tooltip {
11 position-anchor: --trigger;
12 position-area: bottom center;
13}
14
15/* Above and centered */
16.tooltip-above {
17 position-anchor: --trigger;
18 position-area: top center;
19}
20
21/* To the right, full height */
22.sidebar-tooltip {
23 position-anchor: --trigger;
24 position-area: right;
25}
26
27/* Bottom-right corner */
28.floating-widget {
29 position-anchor: --container;
30 position-area: bottom right;
31}

info

position-area is the most ergonomic way to position tooltips and popovers. Use the anchor() function when you need precise offset control that position-area cannot express.
Fallback Positioning

One of the most powerful features is automatic fallback positioning. When the preferred position would cause the element to overflow the viewport, the browser shifts it to a fallback position. You specify fallbacks using the position-try-fallbacks property.

fallbacks.css
CSS
1.tooltip {
2 position: fixed;
3 position-anchor: --trigger;
4
5 /* Preferred position */
6 top: anchor(bottom 8px);
7 left: anchor(center);
8 transform: translateX(-50%);
9
10 /* Fallbacks — browser tries each in order */
11 position-try-fallbacks:
12 --above, /* Custom try tactics */
13 --left-side,
14 flip-block, /* Built-in: flip vertically */
15 flip-inline; /* Built-in: flip horizontally */
16}
17
18/* Define custom try tactics */
19@position-try --above {
20 top: anchor(top 8px);
21 bottom: auto;
22 transform: translateX(-50%);
23}
24
25@position-try --left-side {
26 right: anchor(left 8px);
27 left: auto;
28 top: anchor(center);
29 transform: translateY(-50%);
30}

Built-in fallback keywords simplify common patterns. flip-block mirrors the element along the block axis, and flip-inline mirrors along the inline axis. These are shorthand for common @position-try definitions.

fallback-try.css
CSS
1/* Built-in flip fallbacks */
2.tooltip {
3 position-anchor: --trigger;
4 top: anchor(bottom 8px);
5 left: anchor(center);
6 transform: translateX(-50%);
7
8 /* If it would overflow bottom, flip to top */
9 position-try-fallbacks: flip-block;
10}
11
12/* Custom @position-try block */
13@position-try --compact {
14 width: 200px;
15 padding: 8px;
16 font-size: 12px;
17}
18
19.tooltip {
20 position-anchor: --trigger;
21 top: anchor(bottom 8px);
22 left: anchor(left);
23 position-try-fallbacks: flip-block, --compact;
24}
Tooltip Pattern

Here is a complete, production-ready tooltip pattern using CSS Anchor Positioning. No JavaScript required.

tooltip.html
HTML
1<button class="tooltip-trigger" aria-describedby="tooltip-1">
2 Hover me
3</button>
4
5<div id="tooltip-1" class="tooltip" role="tooltip">
6 This is a CSS-only tooltip
7</div>
tooltip.css
CSS
1.tooltip-trigger {
2 anchor-name: --tooltip-trigger;
3}
4
5.tooltip {
6 position: fixed;
7 position-anchor: --tooltip-trigger;
8 top: anchor(bottom 8px);
9 left: anchor(center);
10 transform: translateX(-50%);
11
12 /* Visual styling */
13 background: #1A1A2E;
14 color: #E0E0E0;
15 font-size: 12px;
16 padding: 8px 12px;
17 border-radius: 6px;
18 border: 1px solid #333;
19 white-space: nowrap;
20 pointer-events: none;
21
22 /* Show/hide with opacity */
23 opacity: 0;
24 transition: opacity 0.15s;
25}
26
27.tooltip-trigger:hover + .tooltip,
28.tooltip-trigger:focus + .tooltip {
29 opacity: 1;
30}
31
32/* Fallback: flip above if near viewport bottom */
33.tooltip {
34 position-try-fallbacks: flip-block;
35}
Popover Pattern

Combine CSS Anchor Positioning with the HTML popover attribute for a powerful, accessible popover system. The popover API handles open/close state while CSS handles positioning.

popover.html
HTML
1<button popovertarget="menu-1">Open Menu</button>
2
3<div id="menu-1" popover anchor="anchor-menu">
4 <nav>
5 <a href="/profile">Profile</a>
6 <a href="/settings">Settings</a>
7 <a href="/logout">Log Out</a>
8 </nav>
9</div>
popover.css
CSS
1/* Anchor element */
2button[popovertarget] {
3 anchor-name: --menu-anchor;
4}
5
6/* Popover styling */
7[popover] {
8 position: fixed;
9 position-anchor: --menu-anchor;
10 top: anchor(bottom 4px);
11 left: anchor(left);
12
13 /* Size relative to anchor */
14 min-width: anchor-size(width);
15
16 /* Visual styling */
17 background: #1A1A2E;
18 border: 1px solid #333;
19 border-radius: 8px;
20 padding: 8px;
21 box-shadow: 0 8px 24px rgba(0,0,0,0.3);
22
23 /* Animation */
24 opacity: 0;
25 transform: translateY(-4px);
26 transition: opacity 0.15s, transform 0.15s;
27}
28
29[popover]:popover-open {
30 opacity: 1;
31 transform: translateY(0);
32}
33
34/* Fallback for overflow */
35[popover] {
36 position-try-fallbacks: flip-block;
37}
preview
Browser Support

CSS Anchor Positioning is a newer feature with growing browser support. Check current status before using in production.

BrowserSupportVersion
Chrome125+
Edge125+
FirefoxIn development
SafariIn development

warning

Use a JavaScript fallback (like Floating UI or Popper.js) for production tooltips until Firefox and Safari have full support. Feature detection: @supports(anchor-name: --a).
$Blueprint — Engineering Documentation·Section ID: CSS-49·Revision: 1.0