Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
47 commits
Select commit Hold shift + click to select a range
cad3f82
Init tests
TylerJDev Feb 20, 2026
89c1fe9
Add back `fixed`
TylerJDev Feb 26, 2026
c6dd31c
Add feature flag
TylerJDev Feb 26, 2026
eea8dd5
Add `data-*`
TylerJDev Feb 26, 2026
b05fca7
Fix `data-*`
TylerJDev Feb 26, 2026
7ba9406
Add `outside` sides
TylerJDev Feb 26, 2026
794f280
Add as default `true` for test
TylerJDev Feb 26, 2026
8368f2b
chore: auto-fix lint and formatting issues
TylerJDev Feb 26, 2026
bafd606
Merge branch 'main' into tylerjdev/css-anchor-positioning
TylerJDev Feb 26, 2026
281f48b
Add scope
TylerJDev Feb 27, 2026
c8dbbff
chore: auto-fix lint and formatting issues
TylerJDev Feb 27, 2026
8c7d5e4
Fix scope
TylerJDev Feb 27, 2026
2250621
Adjust classname
TylerJDev Feb 27, 2026
a043626
Fix lint issues
TylerJDev Feb 27, 2026
bd1791d
Make FF `false` by default
TylerJDev Feb 27, 2026
809f5e2
Fix `ActionMenu` classname issue
TylerJDev Feb 27, 2026
54d9f84
Run format
TylerJDev Feb 27, 2026
97a2a35
Fix `ActionMenu` with anchor
TylerJDev Feb 27, 2026
3adb9d7
Make flag `true`
TylerJDev Feb 27, 2026
0a0b120
Revert to `false`
TylerJDev Feb 27, 2026
9c79821
Wrap `AnchoredOverlay` in conditional for FF
TylerJDev Feb 27, 2026
b09415c
Add polyfill
TylerJDev Mar 2, 2026
d79584d
Add changeset
TylerJDev Mar 3, 2026
cdf6b0a
Merge branch 'main' into tylerjdev/css-anchor-positioning
TylerJDev Mar 3, 2026
17108eb
Fix lint
TylerJDev Mar 3, 2026
c8b9b8b
Fix lint again
TylerJDev Mar 3, 2026
2958648
test(vrt): update snapshots
TylerJDev Mar 3, 2026
7f38b18
Fix CSS for fullscreen
TylerJDev Mar 3, 2026
46a28ce
test(vrt): update snapshots
TylerJDev Mar 3, 2026
f3eef6f
Fix CSS again
TylerJDev Mar 3, 2026
3ce628e
test(vrt): update snapshots
TylerJDev Mar 3, 2026
d310e7c
test(vrt): update snapshots
TylerJDev Mar 3, 2026
4b51d94
Merge branch 'main' into tylerjdev/css-anchor-positioning
TylerJDev Mar 3, 2026
d66c451
Merge branch 'main' into tylerjdev/css-anchor-positioning
TylerJDev Mar 4, 2026
64633ff
Reset .playwright snapshots to main
TylerJDev Mar 4, 2026
14d7efb
Address feedback
TylerJDev Mar 5, 2026
af4ebbb
Fix `ActionMenu` test
TylerJDev Mar 5, 2026
3b881eb
Adjust CSS selector
TylerJDev Mar 5, 2026
452d29e
Adjust `data` selector
TylerJDev Mar 5, 2026
9719114
Adjust CSS
TylerJDev Mar 6, 2026
71f82d4
Adjust CSS once more
TylerJDev Mar 6, 2026
8e85626
Run format
TylerJDev Mar 6, 2026
cc5e406
Apply one more condition
TylerJDev Mar 6, 2026
bd0e812
Another one
TylerJDev Mar 6, 2026
2b3f2ba
Run lint/format
TylerJDev Mar 6, 2026
592822e
Add important for now
TylerJDev Mar 6, 2026
7587a63
remove important
TylerJDev Mar 6, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/nine-buttons-lose.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@primer/react': minor
---

AnchoredOverlay: Add CSS Anchor Positioning to `AnchoredOverlay` (under a feature flag)
83 changes: 68 additions & 15 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions packages/react/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@
"@github/relative-time-element": "^4.5.0",
"@github/tab-container-element": "^4.8.2",
"@lit-labs/react": "1.2.1",
"@oddbird/css-anchor-positioning": "^0.9.0",
"@oddbird/popover-polyfill": "^0.5.2",
"@primer/behaviors": "^1.10.2",
"@primer/live-region-element": "^0.7.1",
Expand Down
92 changes: 92 additions & 0 deletions packages/react/src/ActionMenu/ActionMenu.examples.stories.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -759,3 +759,95 @@ export const InsideDialog = () => {
</FeatureFlags>
)
}

export const CenteredOnPage = () => {
const [open, setOpen] = React.useState(false)

return (
<div className={classes.CustomPositionMiddle}>
<ActionMenu open={open} onOpenChange={setOpen}>
<ActionMenu.Button>Open menu</ActionMenu.Button>
<ActionMenu.Overlay width="medium">
<ActionList>
<ActionList.Item onSelect={() => alert('Copy link clicked')}>
Copy link
<ActionList.TrailingVisual>⌘C</ActionList.TrailingVisual>
</ActionList.Item>
<ActionList.Item onSelect={() => alert('Quote reply clicked')}>
Quote reply
<ActionList.TrailingVisual>⌘Q</ActionList.TrailingVisual>
</ActionList.Item>
<ActionList.Item onSelect={() => alert('Edit comment clicked')}>
Edit comment
<ActionList.TrailingVisual>⌘E</ActionList.TrailingVisual>
</ActionList.Item>
<ActionList.Divider />
<ActionList.Item variant="danger" onSelect={() => alert('Delete file clicked')}>
Delete file
<ActionList.TrailingVisual>⌘D</ActionList.TrailingVisual>
</ActionList.Item>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>
</div>
)
}

export const TwoActionMenus = () => {
return (
<div style={{display: 'flex', gap: '1rem', padding: '1rem'}}>
<ActionMenu>
<ActionMenu.Button className="Testing">First menu</ActionMenu.Button>
<ActionMenu.Overlay width="medium">
<ActionList>
<ActionList.Item onSelect={() => alert('Copy clicked')}>
<ActionList.LeadingVisual>
<CopyIcon />
</ActionList.LeadingVisual>
Copy
<ActionList.TrailingVisual>⌘C</ActionList.TrailingVisual>
</ActionList.Item>
<ActionList.Item onSelect={() => alert('Archive clicked')}>
<ActionList.LeadingVisual>
<ArchiveIcon />
</ActionList.LeadingVisual>
Archive
</ActionList.Item>
<ActionList.Divider />
<ActionList.Item variant="danger" onSelect={() => alert('Delete clicked')}>
Delete
<ActionList.TrailingVisual>⌘D</ActionList.TrailingVisual>
</ActionList.Item>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>

<ActionMenu>
<ActionMenu.Button leadingVisual={GearIcon}>Second menu</ActionMenu.Button>
<ActionMenu.Overlay width="medium">
<ActionList>
<ActionList.Item onSelect={() => alert('Settings clicked')}>
<ActionList.LeadingVisual>
<GearIcon />
</ActionList.LeadingVisual>
Settings
</ActionList.Item>
<ActionList.Item onSelect={() => alert('Workflows clicked')}>
<ActionList.LeadingVisual>
<WorkflowIcon />
</ActionList.LeadingVisual>
Workflows
</ActionList.Item>
<ActionList.Divider />
<ActionList.LinkItem href="#">
<ActionList.LeadingVisual>
<BookIcon />
</ActionList.LeadingVisual>
Documentation
</ActionList.LinkItem>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>
</div>
)
}
87 changes: 47 additions & 40 deletions packages/react/src/ActionMenu/ActionMenu.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import {Tooltip as TooltipV2} from '../TooltipV2/Tooltip'
import {SingleSelect} from '../ActionMenu/ActionMenu.features.stories'
import {MixedSelection} from '../ActionMenu/ActionMenu.examples.stories'
import {SearchIcon, KebabHorizontalIcon} from '@primer/octicons-react'
import anchoredOverlayClasses from '../AnchoredOverlay/AnchoredOverlay.module.css'
import {getAnchoredPosition} from '@primer/behaviors'
import type {AnchorPosition} from '@primer/behaviors'

Expand Down Expand Up @@ -624,56 +625,62 @@ describe('ActionMenu', () => {

it('supports className prop on ActionMenu.Anchor', async () => {
const component = HTMLRender(
<BaseStyles>
<ActionMenu>
<ActionMenu.Anchor className="test-class">
<Button>Toggle Menu</Button>
</ActionMenu.Anchor>
<ActionMenu.Overlay>
<ActionList>
<ActionList.Item>New file</ActionList.Item>
<ActionList.Divider />
<ActionList.Item>Copy link</ActionList.Item>
<ActionList.Item>Edit file</ActionList.Item>
<ActionList.Item variant="danger" onSelect={event => event.preventDefault()}>
Delete file
</ActionList.Item>
<ActionList.LinkItem href="//github.com" title="anchor" aria-keyshortcuts="s">
Github
</ActionList.LinkItem>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>
</BaseStyles>,
<FeatureFlags flags={{primer_react_css_anchor_positioning: true}}>
<BaseStyles>
<ActionMenu>
<ActionMenu.Anchor className="test-class">
<Button>Toggle Menu</Button>
</ActionMenu.Anchor>
<ActionMenu.Overlay>
<ActionList>
<ActionList.Item>New file</ActionList.Item>
<ActionList.Divider />
<ActionList.Item>Copy link</ActionList.Item>
<ActionList.Item>Edit file</ActionList.Item>
<ActionList.Item variant="danger" onSelect={event => event.preventDefault()}>
Delete file
</ActionList.Item>
<ActionList.LinkItem href="//github.com" title="anchor" aria-keyshortcuts="s">
Github
</ActionList.LinkItem>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>
</BaseStyles>
</FeatureFlags>,
)
const anchor = component.getByRole('button', {name: 'Toggle Menu'})
expect(anchor).toHaveClass('test-class')
expect(anchor).toHaveClass(anchoredOverlayClasses.Anchor)
})

it('supports className prop on ActionMenu.Button', async () => {
const component = HTMLRender(
<BaseStyles>
<ActionMenu>
<ActionMenu.Button className="test-class">Toggle Menu</ActionMenu.Button>
<ActionMenu.Overlay>
<ActionList>
<ActionList.Item>New file</ActionList.Item>
<ActionList.Divider />
<ActionList.Item>Copy link</ActionList.Item>
<ActionList.Item>Edit file</ActionList.Item>
<ActionList.Item variant="danger" onSelect={event => event.preventDefault()}>
Delete file
</ActionList.Item>
<ActionList.LinkItem href="//github.com" title="anchor" aria-keyshortcuts="s">
Github
</ActionList.LinkItem>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>
</BaseStyles>,
<FeatureFlags flags={{primer_react_css_anchor_positioning: true}}>
<BaseStyles>
<ActionMenu>
<ActionMenu.Button className="test-class">Toggle Menu</ActionMenu.Button>
<ActionMenu.Overlay>
<ActionList>
<ActionList.Item>New file</ActionList.Item>
<ActionList.Divider />
<ActionList.Item>Copy link</ActionList.Item>
<ActionList.Item>Edit file</ActionList.Item>
<ActionList.Item variant="danger" onSelect={event => event.preventDefault()}>
Delete file
</ActionList.Item>
<ActionList.LinkItem href="//github.com" title="anchor" aria-keyshortcuts="s">
Github
</ActionList.LinkItem>
</ActionList>
</ActionMenu.Overlay>
</ActionMenu>
</BaseStyles>
</FeatureFlags>,
)
const button = component.getByRole('button', {name: 'Toggle Menu'})
expect(button).toHaveClass('test-class')
expect(button).toHaveClass(anchoredOverlayClasses.Anchor)
})
})

Expand Down
Loading