Skip to content

Commit 415b636

Browse files
authored
feat(ListGroup): add numbered prop (react-bootstrap#6072)
1 parent 3fa3b28 commit 415b636

File tree

5 files changed

+95
-17
lines changed

5 files changed

+95
-17
lines changed

src/ListGroup.tsx

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ export interface ListGroupProps extends BsPrefixProps, BaseNavProps {
1313
variant?: 'flush';
1414
horizontal?: boolean | 'sm' | 'md' | 'lg' | 'xl' | 'xxl';
1515
defaultActiveKey?: EventKey;
16+
numbered?: boolean;
1617
}
1718

1819
const propTypes = {
@@ -37,6 +38,11 @@ const propTypes = {
3738
*/
3839
horizontal: PropTypes.oneOf([true, 'sm', 'md', 'lg', 'xl', 'xxl']),
3940

41+
/**
42+
* Generate numbered list items.
43+
*/
44+
numbered: PropTypes.bool,
45+
4046
/**
4147
* You can use a custom element type for this component.
4248
*/
@@ -50,6 +56,7 @@ const ListGroup: BsPrefixRefForwardingComponent<'div', ListGroupProps> =
5056
bsPrefix: initialBsPrefix,
5157
variant,
5258
horizontal,
59+
numbered,
5360
// Need to define the default "as" during prop destructuring to be compatible with styled-components github.com/react-bootstrap/react-bootstrap/issues/3595
5461
as = 'div',
5562
...controlledProps
@@ -80,6 +87,7 @@ const ListGroup: BsPrefixRefForwardingComponent<'div', ListGroupProps> =
8087
bsPrefix,
8188
variant && `${bsPrefix}-${variant}`,
8289
horizontalVariant && `${bsPrefix}-${horizontalVariant}`,
90+
numbered && `${bsPrefix}-numbered`,
8391
)}
8492
/>
8593
);

test/ListGroupSpec.js

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,4 +64,15 @@ describe('<ListGroup>', () => {
6464

6565
getByTestId('list-item').classList.contains('active').should.be.true;
6666
});
67+
68+
it('should add numbered class', () => {
69+
const { getByTestId } = render(
70+
<ListGroup activeKey="1" numbered data-testid="list-group">
71+
<ListGroup.Item eventKey="1">test</ListGroup.Item>
72+
</ListGroup>,
73+
);
74+
75+
getByTestId('list-group').classList.contains('list-group-numbered').should
76+
.be.true;
77+
});
6778
});
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
<ListGroup as="ol" numbered>
2+
<ListGroup.Item as="li">Cras justo odio</ListGroup.Item>
3+
<ListGroup.Item as="li">Cras justo odio</ListGroup.Item>
4+
<ListGroup.Item as="li">Cras justo odio</ListGroup.Item>
5+
</ListGroup>;
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
<ListGroup as="ol" numbered>
2+
<ListGroup.Item
3+
as="li"
4+
className="d-flex justify-content-between align-items-start"
5+
>
6+
<div className="ms-2 me-auto">
7+
<div className="fw-bold">Subheading</div>
8+
Cras justo odio
9+
</div>
10+
<Badge variant="primary" pill>
11+
14
12+
</Badge>
13+
</ListGroup.Item>
14+
<ListGroup.Item
15+
as="li"
16+
className="d-flex justify-content-between align-items-start"
17+
>
18+
<div className="ms-2 me-auto">
19+
<div className="fw-bold">Subheading</div>
20+
Cras justo odio
21+
</div>
22+
<Badge variant="primary" pill>
23+
14
24+
</Badge>
25+
</ListGroup.Item>
26+
<ListGroup.Item
27+
as="li"
28+
className="d-flex justify-content-between align-items-start"
29+
>
30+
<div className="ms-2 me-auto">
31+
<div className="fw-bold">Subheading</div>
32+
Cras justo odio
33+
</div>
34+
<Badge variant="primary" pill>
35+
14
36+
</Badge>
37+
</ListGroup.Item>
38+
</ListGroup>;

www/src/pages/components/list-group.mdx

Lines changed: 33 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -12,19 +12,19 @@ import ListGroupDisabled from '../../examples/ListGroup/Disabled';
1212
import ListGroupStyle from '../../examples/ListGroup/Style';
1313
import ListGroupStyleActions from '../../examples/ListGroup/StyleActions';
1414
import ListGroupFlush from '../../examples/ListGroup/Flush';
15+
import ListGroupNumbered from '../../examples/ListGroup/Numbered';
16+
import ListGroupNumberedCustom from '../../examples/ListGroup/NumberedCustom';
1517
import ListGroupHorizontal from '../../examples/ListGroup/Horizontal';
1618
import ListGroupHorizontalResponsive from '../../examples/ListGroup/HorizontalResponsive';
1719
import ListGroupTabs from '../../examples/ListGroup/Tabs';
1820

1921
import styles from '../../css/examples.module.scss';
2022

21-
2223
# List groups
2324

2425
<p className="lead">
25-
List groups are a flexible and powerful component for displaying a
26-
series of content. Modify and extend them to support just about any
27-
content within.
26+
List groups are a flexible and powerful component for displaying a series of
27+
content. Modify and extend them to support just about any content within.
2828
</p>
2929

3030
## Basic Example
@@ -54,7 +54,6 @@ that call `preventDefault` to mimick disabled behavior.
5454
exampleClassName={styles.listGroup}
5555
/>
5656

57-
5857
### Actionable items
5958

6059
Toggle the `action` prop to create <em>actionable</em> list group
@@ -80,6 +79,24 @@ edge-to-edge in a parent container [such as a `Card`](/components/cards/#list-gr
8079
exampleClassName={styles.listGroup}
8180
/>
8281

82+
### Numbered
83+
84+
Add the `numbered` prop to opt into numbered list group items. Numbers are generated via CSS
85+
(as opposed to a `<ol>`s default browser styling) for better placement inside list group items
86+
and to allow for better customization.
87+
88+
<ReactPlayground
89+
codeText={ListGroupNumbered}
90+
exampleClassName={styles.listGroup}
91+
/>
92+
93+
These work great with custom content as well.
94+
95+
<ReactPlayground
96+
codeText={ListGroupNumberedCustom}
97+
exampleClassName={styles.listGroup}
98+
/>
99+
83100
### Horizontal
84101

85102
Use the `horizontal` prop to make the ListGroup render horizontally. Currently **horizontal list groups cannot be combined with flush list groups.**
@@ -113,11 +130,12 @@ When paired with `action`s, additional hover and active styles apply.
113130
/>
114131

115132
<Callout title="Conveying meaning to assistive technologies">
116-
Using color to add meaning only provides a visual indication,
117-
which will not be conveyed to users of assistive technologies – such as screen readers.
118-
Ensure that information denoted by the color is either obvious from the content itself
119-
(e.g. the visible text), or is included through alternative means,
120-
such as additional text hidden with the <code>.visually-hidden</code> class.
133+
Using color to add meaning only provides a visual indication, which will not
134+
be conveyed to users of assistive technologies – such as screen readers.
135+
Ensure that information denoted by the color is either obvious from the
136+
content itself (e.g. the visible text), or is included through alternative
137+
means, such as additional text hidden with the <code>.visually-hidden</code>{' '}
138+
class.
121139
</Callout>
122140

123141
## Tabbed Interfaces
@@ -126,17 +144,15 @@ You can also use the [Tab][tabs] components to create ARIA compliant tabbable
126144
interfaces with the `<ListGroup>` component. Swap out the `<Nav>` component
127145
for the list group and you are good to go.
128146

129-
<ReactPlayground
130-
codeText={ListGroupTabs}
131-
exampleClassName={styles.listGroup}
132-
/>
147+
<ReactPlayground codeText={ListGroupTabs} exampleClassName={styles.listGroup} />
133148

134149
## API
135150

136151
<ComponentApi metadata={props.data.ListGroup} />
137-
<ComponentApi metadata={props.data.ListGroupItem} exportedBy={props.data.ListGroup} />
138-
139-
152+
<ComponentApi
153+
metadata={props.data.ListGroupItem}
154+
exportedBy={props.data.ListGroup}
155+
/>
140156

141157
export const query = graphql`
142158
query ListGroupQuery {

0 commit comments

Comments
 (0)