Skip to content

Commit 1f8a133

Browse files
authored
WIP
1 parent 17c6318 commit 1f8a133

File tree

5 files changed

+366
-13
lines changed

5 files changed

+366
-13
lines changed

packages/react/src/ButtonGroup/ButtonGroup.docs.json

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,12 @@
2525
{
2626
"name": "ref",
2727
"type": "React.RefObject<HTMLDivElement>"
28+
},
29+
{
30+
"name": "overflowAriaLabel",
31+
"type": "string",
32+
"defaultValue": "\"More actions\"",
33+
"description": "Accessible label announced for the overflow trigger button."
2834
}
2935
],
3036
"subcomponents": []

packages/react/src/ButtonGroup/ButtonGroup.module.css

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,12 @@
33
vertical-align: middle;
44
isolation: isolate;
55

6-
& > *:not([data-loading-wrapper]) {
6+
&[data-phase='measuring'] {
7+
visibility: hidden;
8+
pointer-events: none;
9+
}
10+
11+
& > [data-button-group-slot]:not([data-loading-wrapper]) {
712
/* stylelint-disable-next-line primer/spacing */
813
margin-inline-end: -1px;
914
position: relative;
@@ -46,7 +51,7 @@
4651
}
4752

4853
/* if child is loading button */
49-
& > *[data-loading-wrapper] {
54+
& > [data-button-group-slot][data-loading-wrapper] {
5055
/* stylelint-disable-next-line primer/spacing */
5156
margin-inline-end: -1px;
5257
position: relative;
@@ -80,3 +85,18 @@
8085
}
8186
}
8287
}
88+
89+
.MeasurementItem {
90+
display: inline-flex;
91+
}
92+
93+
.OverflowOverlay {
94+
display: flex;
95+
flex-direction: column;
96+
gap: var(--base-size-8);
97+
padding: var(--base-size-8);
98+
}
99+
100+
.OverflowItem {
101+
display: flex;
102+
}

packages/react/src/ButtonGroup/ButtonGroup.stories.tsx

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,17 @@ export const Default = () => (
2323
</ButtonGroup>
2424
)
2525

26+
export const Overflow = () => (
27+
<div style={{maxWidth: '220px'}}>
28+
<ButtonGroup>
29+
<Button>Button 1</Button>
30+
<Button>Button 2</Button>
31+
<Button>Button 3</Button>
32+
<Button>Button 4</Button>
33+
</ButtonGroup>
34+
</div>
35+
)
36+
2637
export const Playground: StoryFn<ButtonProps & {buttonCount: number}> = args => {
2738
const {buttonCount = 3, ...buttonProps} = args
2839
const buttons = Array.from({length: buttonCount}, (_, i) => (

packages/react/src/ButtonGroup/ButtonGroup.test.tsx

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import {render, screen} from '@testing-library/react'
2-
import ButtonGroup from './ButtonGroup'
2+
import ButtonGroup, {calculateVisibleCount} from './ButtonGroup'
33
import {describe, expect, it} from 'vitest'
44

55
describe('ButtonGroup', () => {
@@ -18,3 +18,35 @@ describe('ButtonGroup', () => {
1818
expect(screen.getByRole('toolbar')).toBeInTheDocument()
1919
})
2020
})
21+
22+
describe('calculateVisibleCount', () => {
23+
it('returns total items when container is wide enough', () => {
24+
const result = calculateVisibleCount({
25+
itemWidths: [80, 80, 80],
26+
containerWidth: 240,
27+
overflowWidth: 32,
28+
})
29+
30+
expect(result).toBe(3)
31+
})
32+
33+
it('returns zero when nothing fits', () => {
34+
const result = calculateVisibleCount({
35+
itemWidths: [120, 80],
36+
containerWidth: 60,
37+
overflowWidth: 32,
38+
})
39+
40+
expect(result).toBe(0)
41+
})
42+
43+
it('avoids leaving a single item in overflow', () => {
44+
const result = calculateVisibleCount({
45+
itemWidths: [120, 100, 100],
46+
containerWidth: 230,
47+
overflowWidth: 40,
48+
})
49+
50+
expect(result).toBe(1)
51+
})
52+
})

0 commit comments

Comments
 (0)