@patternfly/react-core 4.232.8 → 4.232.11
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +24 -0
- package/dist/esm/components/Page/PageBreadcrumb.d.ts +3 -1
- package/dist/esm/components/Page/PageBreadcrumb.d.ts.map +1 -1
- package/dist/esm/components/Page/PageBreadcrumb.js +8 -2
- package/dist/esm/components/Page/PageBreadcrumb.js.map +1 -1
- package/dist/esm/components/Page/PageGroup.d.ts +3 -1
- package/dist/esm/components/Page/PageGroup.d.ts.map +1 -1
- package/dist/esm/components/Page/PageGroup.js +8 -2
- package/dist/esm/components/Page/PageGroup.js.map +1 -1
- package/dist/esm/components/Page/PageNavigation.d.ts +3 -1
- package/dist/esm/components/Page/PageNavigation.d.ts.map +1 -1
- package/dist/esm/components/Page/PageNavigation.js +8 -2
- package/dist/esm/components/Page/PageNavigation.js.map +1 -1
- package/dist/esm/components/Page/PageSection.d.ts +4 -0
- package/dist/esm/components/Page/PageSection.d.ts.map +1 -1
- package/dist/esm/components/Page/PageSection.js +8 -2
- package/dist/esm/components/Page/PageSection.js.map +1 -1
- package/dist/js/components/Page/PageBreadcrumb.d.ts +3 -1
- package/dist/js/components/Page/PageBreadcrumb.d.ts.map +1 -1
- package/dist/js/components/Page/PageBreadcrumb.js +8 -2
- package/dist/js/components/Page/PageBreadcrumb.js.map +1 -1
- package/dist/js/components/Page/PageGroup.d.ts +3 -1
- package/dist/js/components/Page/PageGroup.d.ts.map +1 -1
- package/dist/js/components/Page/PageGroup.js +8 -2
- package/dist/js/components/Page/PageGroup.js.map +1 -1
- package/dist/js/components/Page/PageNavigation.d.ts +3 -1
- package/dist/js/components/Page/PageNavigation.d.ts.map +1 -1
- package/dist/js/components/Page/PageNavigation.js +8 -2
- package/dist/js/components/Page/PageNavigation.js.map +1 -1
- package/dist/js/components/Page/PageSection.d.ts +4 -0
- package/dist/js/components/Page/PageSection.d.ts.map +1 -1
- package/dist/js/components/Page/PageSection.js +8 -2
- package/dist/js/components/Page/PageSection.js.map +1 -1
- package/dist/umd/react-core.js +444 -515
- package/dist/umd/react-core.min.css +106 -106
- package/dist/umd/react-core.min.js +5 -5
- package/package.json +10 -10
- package/src/components/Page/PageBreadcrumb.tsx +11 -0
- package/src/components/Page/PageGroup.tsx +11 -0
- package/src/components/Page/PageNavigation.tsx +11 -0
- package/src/components/Page/PageSection.tsx +13 -0
- package/src/components/Page/__tests__/PageBreadcrumb.test.tsx +41 -1
- package/src/components/Page/__tests__/PageGroup.test.tsx +41 -1
- package/src/components/Page/__tests__/PageNavigation.test.tsx +41 -1
- package/src/components/Page/__tests__/PageSection.test.tsx +41 -1
- package/src/components/SearchInput/examples/SearchInput.md +6 -223
- package/src/components/SearchInput/examples/SearchInputAdvanced.tsx +56 -0
- package/src/components/SearchInput/examples/SearchInputBasic.tsx +12 -0
- package/src/components/SearchInput/examples/SearchInputFocusSearch.tsx +14 -0
- package/src/components/SearchInput/examples/SearchInputWithNavigableOptions.tsx +43 -0
- package/src/components/SearchInput/examples/SearchInputWithResultCount.tsx +27 -0
- package/src/components/SearchInput/examples/SearchInputWithSubmitButton.tsx +16 -0
- package/src/demos/JumpLinks.md +1 -0
- package/src/demos/examples/BackToTop/BackToTopNameDemo.tsx +6 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@patternfly/react-core",
|
|
3
|
-
"version": "4.232.
|
|
3
|
+
"version": "4.232.11",
|
|
4
4
|
"description": "This library provides a set of common React components for use with the PatternFly reference implementation.",
|
|
5
5
|
"main": "dist/js/index.js",
|
|
6
6
|
"module": "dist/esm/index.js",
|
|
@@ -50,9 +50,9 @@
|
|
|
50
50
|
"generate": "node scripts/copyStyles.js"
|
|
51
51
|
},
|
|
52
52
|
"dependencies": {
|
|
53
|
-
"@patternfly/react-icons": "^4.83.
|
|
54
|
-
"@patternfly/react-styles": "^4.82.
|
|
55
|
-
"@patternfly/react-tokens": "^4.84.
|
|
53
|
+
"@patternfly/react-icons": "^4.83.11",
|
|
54
|
+
"@patternfly/react-styles": "^4.82.11",
|
|
55
|
+
"@patternfly/react-tokens": "^4.84.11",
|
|
56
56
|
"focus-trap": "6.9.2",
|
|
57
57
|
"react-dropzone": "9.0.0",
|
|
58
58
|
"tippy.js": "5.1.2",
|
|
@@ -60,21 +60,21 @@
|
|
|
60
60
|
},
|
|
61
61
|
"devDependencies": {
|
|
62
62
|
"@patternfly/patternfly": "4.208.1",
|
|
63
|
-
"@rollup/plugin-commonjs": "^
|
|
64
|
-
"@rollup/plugin-node-resolve": "^13.
|
|
65
|
-
"@rollup/plugin-replace": "^
|
|
63
|
+
"@rollup/plugin-commonjs": "^22.0.2",
|
|
64
|
+
"@rollup/plugin-node-resolve": "^13.3.0",
|
|
65
|
+
"@rollup/plugin-replace": "^4.0.0",
|
|
66
66
|
"css": "^2.2.3",
|
|
67
67
|
"fs-extra": "^6.0.1",
|
|
68
68
|
"glob": "^7.1.2",
|
|
69
69
|
"rimraf": "^3.0.2",
|
|
70
|
-
"rollup": "^2.
|
|
70
|
+
"rollup": "^2.78.0",
|
|
71
71
|
"rollup-plugin-scss": "^3.0.0",
|
|
72
|
-
"rollup-plugin-terser": "^7.0.
|
|
72
|
+
"rollup-plugin-terser": "^7.0.2",
|
|
73
73
|
"typescript": "^4.7.4"
|
|
74
74
|
},
|
|
75
75
|
"peerDependencies": {
|
|
76
76
|
"react": "^16.8.0 || ^17.0.0",
|
|
77
77
|
"react-dom": "^16.8.0 || ^17.0.0"
|
|
78
78
|
},
|
|
79
|
-
"gitHead": "
|
|
79
|
+
"gitHead": "3b4fe0a85d88aa9616d7a6768d187d6fc87abb32"
|
|
80
80
|
}
|
|
@@ -28,6 +28,8 @@ export interface PageBreadcrumbProps extends React.HTMLProps<HTMLElement> {
|
|
|
28
28
|
hasShadowBottom?: boolean;
|
|
29
29
|
/** Flag indicating if the PageBreadcrumb has a scrolling overflow */
|
|
30
30
|
hasOverflowScroll?: boolean;
|
|
31
|
+
/** Adds an accessible name to the breadcrumb section. Required when the hasOverflowScroll prop is set to true. */
|
|
32
|
+
'aria-label'?: string;
|
|
31
33
|
}
|
|
32
34
|
|
|
33
35
|
export const PageBreadcrumb = ({
|
|
@@ -39,10 +41,18 @@ export const PageBreadcrumb = ({
|
|
|
39
41
|
hasShadowTop = false,
|
|
40
42
|
hasShadowBottom = false,
|
|
41
43
|
hasOverflowScroll = false,
|
|
44
|
+
'aria-label': ariaLabel,
|
|
42
45
|
...props
|
|
43
46
|
}: PageBreadcrumbProps) => {
|
|
44
47
|
const { height, getVerticalBreakpoint } = React.useContext(PageContext);
|
|
45
48
|
|
|
49
|
+
React.useEffect(() => {
|
|
50
|
+
if (hasOverflowScroll && !ariaLabel) {
|
|
51
|
+
/* eslint-disable no-console */
|
|
52
|
+
console.warn('PageBreadcrumb: An accessible aria-label is required when hasOverflowScroll is set to true.');
|
|
53
|
+
}
|
|
54
|
+
}, [hasOverflowScroll, ariaLabel]);
|
|
55
|
+
|
|
46
56
|
return (
|
|
47
57
|
<section
|
|
48
58
|
className={css(
|
|
@@ -57,6 +67,7 @@ export const PageBreadcrumb = ({
|
|
|
57
67
|
className
|
|
58
68
|
)}
|
|
59
69
|
{...(hasOverflowScroll && { tabIndex: 0 })}
|
|
70
|
+
aria-label={ariaLabel}
|
|
60
71
|
{...props}
|
|
61
72
|
>
|
|
62
73
|
{isWidthLimited && <div className={css(styles.pageMainBody)}>{children}</div>}
|
|
@@ -25,6 +25,8 @@ export interface PageGroupProps extends React.HTMLProps<HTMLDivElement> {
|
|
|
25
25
|
hasShadowBottom?: boolean;
|
|
26
26
|
/** Flag indicating if the PageGroup has a scrolling overflow */
|
|
27
27
|
hasOverflowScroll?: boolean;
|
|
28
|
+
/** Adds an accessible name to the page group. Required when the hasOverflowScroll prop is set to true. */
|
|
29
|
+
'aria-label'?: string;
|
|
28
30
|
}
|
|
29
31
|
|
|
30
32
|
export const PageGroup = ({
|
|
@@ -35,10 +37,18 @@ export const PageGroup = ({
|
|
|
35
37
|
hasShadowTop = false,
|
|
36
38
|
hasShadowBottom = false,
|
|
37
39
|
hasOverflowScroll = false,
|
|
40
|
+
'aria-label': ariaLabel,
|
|
38
41
|
...props
|
|
39
42
|
}: PageGroupProps) => {
|
|
40
43
|
const { height, getVerticalBreakpoint } = React.useContext(PageContext);
|
|
41
44
|
|
|
45
|
+
React.useEffect(() => {
|
|
46
|
+
if (hasOverflowScroll && !ariaLabel) {
|
|
47
|
+
/* eslint-disable no-console */
|
|
48
|
+
console.warn('PageGroup: An accessible aria-label is required when hasOverflowScroll is set to true.');
|
|
49
|
+
}
|
|
50
|
+
}, [hasOverflowScroll, ariaLabel]);
|
|
51
|
+
|
|
42
52
|
return (
|
|
43
53
|
<div
|
|
44
54
|
{...props}
|
|
@@ -53,6 +63,7 @@ export const PageGroup = ({
|
|
|
53
63
|
className
|
|
54
64
|
)}
|
|
55
65
|
{...(hasOverflowScroll && { tabIndex: 0 })}
|
|
66
|
+
aria-label={ariaLabel}
|
|
56
67
|
>
|
|
57
68
|
{children}
|
|
58
69
|
</div>
|
|
@@ -28,6 +28,8 @@ export interface PageNavigationProps extends React.HTMLProps<HTMLDivElement> {
|
|
|
28
28
|
hasShadowBottom?: boolean;
|
|
29
29
|
/** Flag indicating if the PageNavigation has a scrolling overflow */
|
|
30
30
|
hasOverflowScroll?: boolean;
|
|
31
|
+
/** Adds an accessible name to the page navigation. Required when the hasOverflowScroll prop is set to true. */
|
|
32
|
+
'aria-label'?: string;
|
|
31
33
|
}
|
|
32
34
|
|
|
33
35
|
export const PageNavigation = ({
|
|
@@ -39,10 +41,18 @@ export const PageNavigation = ({
|
|
|
39
41
|
hasShadowTop = false,
|
|
40
42
|
hasShadowBottom = false,
|
|
41
43
|
hasOverflowScroll = false,
|
|
44
|
+
'aria-label': ariaLabel,
|
|
42
45
|
...props
|
|
43
46
|
}: PageNavigationProps) => {
|
|
44
47
|
const { height, getVerticalBreakpoint } = React.useContext(PageContext);
|
|
45
48
|
|
|
49
|
+
React.useEffect(() => {
|
|
50
|
+
if (hasOverflowScroll && !ariaLabel) {
|
|
51
|
+
/* eslint-disable no-console */
|
|
52
|
+
console.warn('PageNavigation: An accessible aria-label is required when hasOverflowScroll is set to true.');
|
|
53
|
+
}
|
|
54
|
+
}, [hasOverflowScroll, ariaLabel]);
|
|
55
|
+
|
|
46
56
|
return (
|
|
47
57
|
<div
|
|
48
58
|
className={css(
|
|
@@ -57,6 +67,7 @@ export const PageNavigation = ({
|
|
|
57
67
|
className
|
|
58
68
|
)}
|
|
59
69
|
{...(hasOverflowScroll && { tabIndex: 0 })}
|
|
70
|
+
aria-label={ariaLabel}
|
|
60
71
|
{...props}
|
|
61
72
|
>
|
|
62
73
|
{isWidthLimited && <div className={css(styles.pageMainBody)}>{children}</div>}
|
|
@@ -61,6 +61,10 @@ export interface PageSectionProps extends React.HTMLProps<HTMLDivElement> {
|
|
|
61
61
|
hasShadowBottom?: boolean;
|
|
62
62
|
/** Flag indicating if the PageSection has a scrolling overflow */
|
|
63
63
|
hasOverflowScroll?: boolean;
|
|
64
|
+
/** Adds an accessible name to the page section. Required when the hasOverflowScroll prop is set to true.
|
|
65
|
+
* This prop should also be passed in if a heading is not being used to describe the content of the page section.
|
|
66
|
+
*/
|
|
67
|
+
'aria-label'?: string;
|
|
64
68
|
}
|
|
65
69
|
|
|
66
70
|
const variantType = {
|
|
@@ -93,10 +97,18 @@ export const PageSection: React.FunctionComponent<PageSectionProps> = ({
|
|
|
93
97
|
hasShadowTop = false,
|
|
94
98
|
hasShadowBottom = false,
|
|
95
99
|
hasOverflowScroll = false,
|
|
100
|
+
'aria-label': ariaLabel,
|
|
96
101
|
...props
|
|
97
102
|
}: PageSectionProps) => {
|
|
98
103
|
const { height, getVerticalBreakpoint } = React.useContext(PageContext);
|
|
99
104
|
|
|
105
|
+
React.useEffect(() => {
|
|
106
|
+
if (hasOverflowScroll && !ariaLabel) {
|
|
107
|
+
/* eslint-disable no-console */
|
|
108
|
+
console.warn('PageSection: An accessible aria-label is required when hasOverflowScroll is set to true.');
|
|
109
|
+
}
|
|
110
|
+
}, [hasOverflowScroll, ariaLabel]);
|
|
111
|
+
|
|
100
112
|
return (
|
|
101
113
|
<section
|
|
102
114
|
{...props}
|
|
@@ -117,6 +129,7 @@ export const PageSection: React.FunctionComponent<PageSectionProps> = ({
|
|
|
117
129
|
className
|
|
118
130
|
)}
|
|
119
131
|
{...(hasOverflowScroll && { tabIndex: 0 })}
|
|
132
|
+
aria-label={ariaLabel}
|
|
120
133
|
>
|
|
121
134
|
{isWidthLimited && <div className={css(styles.pageMainBody)}>{children}</div>}
|
|
122
135
|
{!isWidthLimited && children}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
-
import { render } from '@testing-library/react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
3
|
import { PageBreadcrumb } from '../PageBreadcrumb';
|
|
4
4
|
|
|
5
5
|
describe('page breadcrumb', () => {
|
|
@@ -31,4 +31,44 @@ describe('page breadcrumb', () => {
|
|
|
31
31
|
const { asFragment } = render(<PageBreadcrumb hasOverflowScroll>test</PageBreadcrumb>);
|
|
32
32
|
expect(asFragment()).toMatchSnapshot();
|
|
33
33
|
});
|
|
34
|
+
|
|
35
|
+
test('Renders without an aria-label by default', () => {
|
|
36
|
+
render(<PageBreadcrumb>test</PageBreadcrumb>);
|
|
37
|
+
|
|
38
|
+
expect(screen.getByText('test')).not.toHaveAccessibleName('Test label');
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
test('Renders with the passed aria-label applied', () => {
|
|
42
|
+
render(<PageBreadcrumb aria-label="Test label">test</PageBreadcrumb>);
|
|
43
|
+
|
|
44
|
+
expect(screen.getByText('test')).toHaveAccessibleName('Test label');
|
|
45
|
+
});
|
|
46
|
+
|
|
47
|
+
test('Does not log a warning in the console by default', () => {
|
|
48
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
49
|
+
|
|
50
|
+
render(<PageBreadcrumb>test</PageBreadcrumb>);
|
|
51
|
+
|
|
52
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
53
|
+
});
|
|
54
|
+
|
|
55
|
+
test('Does not log a warning in the console when an aria-label is included with hasOverflowScroll', () => {
|
|
56
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
57
|
+
|
|
58
|
+
render(
|
|
59
|
+
<PageBreadcrumb hasOverflowScroll aria-label="Test label">
|
|
60
|
+
test
|
|
61
|
+
</PageBreadcrumb>
|
|
62
|
+
);
|
|
63
|
+
|
|
64
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
65
|
+
});
|
|
66
|
+
|
|
67
|
+
test('Logs a warning in the console when an aria-label is not included with hasOverflowScroll', () => {
|
|
68
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
69
|
+
|
|
70
|
+
render(<PageBreadcrumb hasOverflowScroll>test</PageBreadcrumb>);
|
|
71
|
+
|
|
72
|
+
expect(consoleWarning).toHaveBeenCalled();
|
|
73
|
+
});
|
|
34
74
|
});
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
-
import { render } from '@testing-library/react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
3
|
import { PageGroup } from '../PageGroup';
|
|
4
4
|
|
|
5
5
|
describe('page group', () => {
|
|
@@ -27,4 +27,44 @@ describe('page group', () => {
|
|
|
27
27
|
const { asFragment } = render(<PageGroup hasOverflowScroll>test</PageGroup>);
|
|
28
28
|
expect(asFragment()).toMatchSnapshot();
|
|
29
29
|
});
|
|
30
|
+
|
|
31
|
+
test('Renders without an aria-label by default', () => {
|
|
32
|
+
render(<PageGroup>test</PageGroup>);
|
|
33
|
+
|
|
34
|
+
expect(screen.getByText('test')).not.toHaveAccessibleName('Test label');
|
|
35
|
+
});
|
|
36
|
+
|
|
37
|
+
test('Renders with the passed aria-label applied', () => {
|
|
38
|
+
render(<PageGroup aria-label="Test label">test</PageGroup>);
|
|
39
|
+
|
|
40
|
+
expect(screen.getByText('test')).toHaveAccessibleName('Test label');
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
test('Does not log a warning in the console by default', () => {
|
|
44
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
45
|
+
|
|
46
|
+
render(<PageGroup>test</PageGroup>);
|
|
47
|
+
|
|
48
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
test('Does not log a warning in the console when an aria-label is included with hasOverflowScroll', () => {
|
|
52
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
53
|
+
|
|
54
|
+
render(
|
|
55
|
+
<PageGroup hasOverflowScroll aria-label="Test label">
|
|
56
|
+
test
|
|
57
|
+
</PageGroup>
|
|
58
|
+
);
|
|
59
|
+
|
|
60
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
61
|
+
});
|
|
62
|
+
|
|
63
|
+
test('Logs a warning in the console when an aria-label is not included with hasOverflowScroll', () => {
|
|
64
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
65
|
+
|
|
66
|
+
render(<PageGroup hasOverflowScroll>test</PageGroup>);
|
|
67
|
+
|
|
68
|
+
expect(consoleWarning).toHaveBeenCalled();
|
|
69
|
+
});
|
|
30
70
|
});
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
-
import { render } from '@testing-library/react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
3
|
import { PageNavigation } from '../PageNavigation';
|
|
4
4
|
|
|
5
5
|
describe('page navigation', () => {
|
|
@@ -31,4 +31,44 @@ describe('page navigation', () => {
|
|
|
31
31
|
const { asFragment } = render(<PageNavigation hasOverflowScroll>test</PageNavigation>);
|
|
32
32
|
expect(asFragment()).toMatchSnapshot();
|
|
33
33
|
});
|
|
34
|
+
|
|
35
|
+
test('Renders without an aria-label by default', () => {
|
|
36
|
+
render(<PageNavigation>test</PageNavigation>);
|
|
37
|
+
|
|
38
|
+
expect(screen.getByText('test')).not.toHaveAccessibleName('Test label');
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
test('Renders with the passed aria-label applied', () => {
|
|
42
|
+
render(<PageNavigation aria-label="Test label">test</PageNavigation>);
|
|
43
|
+
|
|
44
|
+
expect(screen.getByText('test')).toHaveAccessibleName('Test label');
|
|
45
|
+
});
|
|
46
|
+
|
|
47
|
+
test('Does not log a warning in the console by default', () => {
|
|
48
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
49
|
+
|
|
50
|
+
render(<PageNavigation>test</PageNavigation>);
|
|
51
|
+
|
|
52
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
53
|
+
});
|
|
54
|
+
|
|
55
|
+
test('Does not log a warning in the console when an aria-label is included with hasOverflowScroll', () => {
|
|
56
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
57
|
+
|
|
58
|
+
render(
|
|
59
|
+
<PageNavigation hasOverflowScroll aria-label="Test label">
|
|
60
|
+
test
|
|
61
|
+
</PageNavigation>
|
|
62
|
+
);
|
|
63
|
+
|
|
64
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
65
|
+
});
|
|
66
|
+
|
|
67
|
+
test('Logs a warning in the console when an aria-label is not included with hasOverflowScroll', () => {
|
|
68
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
69
|
+
|
|
70
|
+
render(<PageNavigation hasOverflowScroll>test</PageNavigation>);
|
|
71
|
+
|
|
72
|
+
expect(consoleWarning).toHaveBeenCalled();
|
|
73
|
+
});
|
|
34
74
|
});
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
|
-
import { render } from '@testing-library/react';
|
|
2
|
+
import { render, screen } from '@testing-library/react';
|
|
3
3
|
import { PageSection, PageSectionTypes } from '../PageSection';
|
|
4
4
|
|
|
5
5
|
jest.mock('../Page');
|
|
@@ -88,3 +88,43 @@ test('Verify page section overflow scroll', () => {
|
|
|
88
88
|
const { asFragment } = render(<PageSection hasOverflowScroll>test</PageSection>);
|
|
89
89
|
expect(asFragment()).toMatchSnapshot();
|
|
90
90
|
});
|
|
91
|
+
|
|
92
|
+
test('Renders without an aria-label by default', () => {
|
|
93
|
+
render(<PageSection>test</PageSection>);
|
|
94
|
+
|
|
95
|
+
expect(screen.getByText('test')).not.toHaveAccessibleName('Test label');
|
|
96
|
+
});
|
|
97
|
+
|
|
98
|
+
test('Renders with the passed aria-label applied', () => {
|
|
99
|
+
render(<PageSection aria-label="Test label">test</PageSection>);
|
|
100
|
+
|
|
101
|
+
expect(screen.getByText('test')).toHaveAccessibleName('Test label');
|
|
102
|
+
});
|
|
103
|
+
|
|
104
|
+
test('Does not log a warning in the console by default', () => {
|
|
105
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
106
|
+
|
|
107
|
+
render(<PageSection>test</PageSection>);
|
|
108
|
+
|
|
109
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
110
|
+
});
|
|
111
|
+
|
|
112
|
+
test('Does not log a warning in the console when an aria-label is included with hasOverflowScroll', () => {
|
|
113
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
114
|
+
|
|
115
|
+
render(
|
|
116
|
+
<PageSection hasOverflowScroll aria-label="Test label">
|
|
117
|
+
test
|
|
118
|
+
</PageSection>
|
|
119
|
+
);
|
|
120
|
+
|
|
121
|
+
expect(consoleWarning).not.toHaveBeenCalled();
|
|
122
|
+
});
|
|
123
|
+
|
|
124
|
+
test('Logs a warning in the console when an aria-label is not included with hasOverflowScroll', () => {
|
|
125
|
+
const consoleWarning = jest.spyOn(console, 'warn').mockImplementation();
|
|
126
|
+
|
|
127
|
+
render(<PageSection hasOverflowScroll>test</PageSection>);
|
|
128
|
+
|
|
129
|
+
expect(consoleWarning).toHaveBeenCalled();
|
|
130
|
+
});
|
|
@@ -6,193 +6,33 @@ propComponents: ['SearchInput', 'SearchAttribute']
|
|
|
6
6
|
beta: true
|
|
7
7
|
---
|
|
8
8
|
|
|
9
|
-
import { SearchInput } from '@patternfly/react-core';
|
|
10
9
|
import { ExternalLinkSquareAltIcon } from '@patternfly/react-icons';
|
|
11
10
|
|
|
12
11
|
## Examples
|
|
13
12
|
|
|
14
13
|
### Basic
|
|
15
14
|
|
|
16
|
-
```
|
|
17
|
-
import React from 'react';
|
|
18
|
-
import { SearchInput } from '@patternfly/react-core';
|
|
19
|
-
|
|
20
|
-
class BasicSearchInput extends React.Component {
|
|
21
|
-
constructor(props) {
|
|
22
|
-
super(props);
|
|
23
|
-
this.state = {
|
|
24
|
-
value: ''
|
|
25
|
-
};
|
|
26
|
-
|
|
27
|
-
this.onChange = (value, event) => {
|
|
28
|
-
this.setState({
|
|
29
|
-
value: value
|
|
30
|
-
});
|
|
31
|
-
};
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
render() {
|
|
35
|
-
return (
|
|
36
|
-
<SearchInput
|
|
37
|
-
placeholder="Find by name"
|
|
38
|
-
value={this.state.value}
|
|
39
|
-
onChange={this.onChange}
|
|
40
|
-
onClear={evt => this.onChange('', evt)}
|
|
41
|
-
/>
|
|
42
|
-
);
|
|
43
|
-
}
|
|
44
|
-
}
|
|
15
|
+
```ts file='./SearchInputBasic.tsx'
|
|
45
16
|
```
|
|
46
17
|
|
|
47
18
|
### Match with result count
|
|
48
19
|
|
|
49
|
-
```
|
|
50
|
-
import React from 'react';
|
|
51
|
-
import { SearchInput } from '@patternfly/react-core';
|
|
52
|
-
|
|
53
|
-
class SearchInputWithResultCount extends React.Component {
|
|
54
|
-
constructor(props) {
|
|
55
|
-
super(props);
|
|
56
|
-
this.state = {
|
|
57
|
-
value: '',
|
|
58
|
-
resultsCount: 0
|
|
59
|
-
};
|
|
60
|
-
|
|
61
|
-
this.onChange = (value, event) => {
|
|
62
|
-
this.setState({
|
|
63
|
-
value: value,
|
|
64
|
-
resultsCount: 3
|
|
65
|
-
});
|
|
66
|
-
};
|
|
67
|
-
|
|
68
|
-
this.onClear = event => {
|
|
69
|
-
this.setState({
|
|
70
|
-
value: '',
|
|
71
|
-
resultsCount: 0
|
|
72
|
-
});
|
|
73
|
-
};
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
render() {
|
|
77
|
-
return (
|
|
78
|
-
<SearchInput
|
|
79
|
-
placeholder="Find by name"
|
|
80
|
-
value={this.state.value}
|
|
81
|
-
onChange={this.onChange}
|
|
82
|
-
onClear={this.onClear}
|
|
83
|
-
resultsCount={this.state.resultsCount}
|
|
84
|
-
/>
|
|
85
|
-
);
|
|
86
|
-
}
|
|
87
|
-
}
|
|
20
|
+
```ts file='./SearchInputWithResultCount.tsx'
|
|
88
21
|
```
|
|
89
22
|
|
|
90
23
|
### Match with navigable options
|
|
91
24
|
|
|
92
|
-
```
|
|
93
|
-
import React from 'react';
|
|
94
|
-
import { SearchInput } from '@patternfly/react-core';
|
|
95
|
-
|
|
96
|
-
class SearchInputWithNavigableOptions extends React.Component {
|
|
97
|
-
constructor(props) {
|
|
98
|
-
super(props);
|
|
99
|
-
this.state = {
|
|
100
|
-
value: '',
|
|
101
|
-
resultsCount: 0,
|
|
102
|
-
currentResult: 1,
|
|
103
|
-
isPreviousNavigationButtonDisabled: false,
|
|
104
|
-
isNextNavigationButtonDisabled: false
|
|
105
|
-
};
|
|
106
|
-
|
|
107
|
-
this.onChange = (value, event) => {
|
|
108
|
-
this.setState({
|
|
109
|
-
value: value,
|
|
110
|
-
resultsCount: 3
|
|
111
|
-
});
|
|
112
|
-
};
|
|
113
|
-
|
|
114
|
-
this.onClear = event => {
|
|
115
|
-
this.setState({
|
|
116
|
-
value: '',
|
|
117
|
-
resultsCount: 0,
|
|
118
|
-
currentResult: 1
|
|
119
|
-
});
|
|
120
|
-
};
|
|
121
|
-
|
|
122
|
-
this.onNext = event => {
|
|
123
|
-
this.setState(prevState => {
|
|
124
|
-
const newCurrentResult = prevState.currentResult + 1;
|
|
125
|
-
return {
|
|
126
|
-
currentResult: newCurrentResult <= prevState.resultsCount ? newCurrentResult : prevState.resultsCount
|
|
127
|
-
};
|
|
128
|
-
});
|
|
129
|
-
};
|
|
130
|
-
|
|
131
|
-
this.onPrevious = event => {
|
|
132
|
-
this.setState(prevState => {
|
|
133
|
-
const newCurrentResult = prevState.currentResult - 1;
|
|
134
|
-
return {
|
|
135
|
-
currentResult: newCurrentResult > 0 ? newCurrentResult : 1
|
|
136
|
-
};
|
|
137
|
-
});
|
|
138
|
-
};
|
|
139
|
-
}
|
|
140
|
-
render() {
|
|
141
|
-
return (
|
|
142
|
-
<SearchInput
|
|
143
|
-
placeholder="Find by name"
|
|
144
|
-
value={this.state.value}
|
|
145
|
-
onChange={this.onChange}
|
|
146
|
-
onClear={this.onClear}
|
|
147
|
-
isNextNavigationButtonDisabled={this.state.currentResult === 3}
|
|
148
|
-
isPreviousNavigationButtonDisabled={this.state.currentResult === 1}
|
|
149
|
-
resultsCount={`${this.state.currentResult} / ${this.state.resultsCount}`}
|
|
150
|
-
onNextClick={this.onNext}
|
|
151
|
-
onPreviousClick={this.onPrevious}
|
|
152
|
-
/>
|
|
153
|
-
);
|
|
154
|
-
}
|
|
155
|
-
}
|
|
25
|
+
```ts file='./SearchInputWithNavigableOptions.tsx'
|
|
156
26
|
```
|
|
157
27
|
|
|
158
28
|
### With submit button
|
|
159
29
|
|
|
160
|
-
```
|
|
161
|
-
import React from 'react';
|
|
162
|
-
import { SearchInput } from '@patternfly/react-core';
|
|
163
|
-
|
|
164
|
-
SubmitButtonSearchInput = () => {
|
|
165
|
-
const [value, setValue] = React.useState('');
|
|
166
|
-
|
|
167
|
-
return (
|
|
168
|
-
<SearchInput
|
|
169
|
-
placeholder='Find by name'
|
|
170
|
-
value={value}
|
|
171
|
-
onChange={setValue}
|
|
172
|
-
onSearch={setValue}
|
|
173
|
-
onClear={() => setValue('')}
|
|
174
|
-
/>
|
|
175
|
-
);
|
|
176
|
-
}
|
|
177
|
-
|
|
30
|
+
```ts file='./SearchInputWithSubmitButton.tsx'
|
|
178
31
|
```
|
|
179
32
|
|
|
180
33
|
### Focus search input using ref
|
|
181
34
|
|
|
182
|
-
```
|
|
183
|
-
import React from 'react';
|
|
184
|
-
import { SearchInput, Button } from '@patternfly/react-core';
|
|
185
|
-
|
|
186
|
-
TextInputSelectAll = () => {
|
|
187
|
-
const [value, setValue] = React.useState('');
|
|
188
|
-
const ref = React.useRef(null);
|
|
189
|
-
return (
|
|
190
|
-
<React.Fragment>
|
|
191
|
-
<SearchInput ref={ref} value={value} onChange={setValue} onClear={() => setValue('')} />
|
|
192
|
-
<Button onClick={() => ref.current && ref.current.focus()}>Focus on the search input</Button>
|
|
193
|
-
</React.Fragment>
|
|
194
|
-
);
|
|
195
|
-
};
|
|
35
|
+
```ts file='./SearchInputFocusSearch.tsx'
|
|
196
36
|
```
|
|
197
37
|
|
|
198
38
|
### Advanced
|
|
@@ -203,62 +43,5 @@ the following example. The search input component can also be used as a composab
|
|
|
203
43
|
or other elements to build a completely custom advanced search form. This feature is demonstrated
|
|
204
44
|
in the search input's <a href="/components/search-input/react-demos">react demos</a>.
|
|
205
45
|
|
|
206
|
-
```
|
|
207
|
-
import React from 'react';
|
|
208
|
-
import { Button, Checkbox, FormGroup, SearchInput } from '@patternfly/react-core';
|
|
209
|
-
import ExternalLinkSquareAltIcon from '@patternfly/react-icons/dist/esm/icons/external-link-square-alt-icon';
|
|
210
|
-
|
|
211
|
-
AdvancedSearchInput = () => {
|
|
212
|
-
const [value, setValue] = React.useState('username:player firstname:john');
|
|
213
|
-
const [useEqualsAsDelimiter, setUseEqualsAsDelimiter] = React.useState(false);
|
|
214
|
-
const [useCustomFooter, setUseCustomFooter] = React.useState(false);
|
|
215
|
-
|
|
216
|
-
const toggleDelimiter = checked => {
|
|
217
|
-
const newValue = value.replace(/:|=/g, checked ? '=' : ':');
|
|
218
|
-
setUseEqualsAsDelimiter(checked);
|
|
219
|
-
setValue(newValue);
|
|
220
|
-
};
|
|
221
|
-
|
|
222
|
-
return (
|
|
223
|
-
<>
|
|
224
|
-
<Checkbox
|
|
225
|
-
label="Use equal sign as search attribute delimiter"
|
|
226
|
-
isChecked={useEqualsAsDelimiter}
|
|
227
|
-
onChange={toggleDelimiter}
|
|
228
|
-
aria-label="change delimiter checkbox"
|
|
229
|
-
id="toggle-delimiter"
|
|
230
|
-
name="toggle-delimiter"
|
|
231
|
-
/>
|
|
232
|
-
<Checkbox
|
|
233
|
-
label="Add custom footer element after the attributes in the menu"
|
|
234
|
-
isChecked={useCustomFooter}
|
|
235
|
-
onChange={value => setUseCustomFooter(value)}
|
|
236
|
-
aria-label="change use custom footer checkbox"
|
|
237
|
-
id="toggle-custom-footer"
|
|
238
|
-
name="toggle-custom-footer"
|
|
239
|
-
/>
|
|
240
|
-
<br />
|
|
241
|
-
<SearchInput
|
|
242
|
-
attributes={[
|
|
243
|
-
{ attr: 'username', display: 'Username' },
|
|
244
|
-
{ attr: 'firstname', display: 'First name' }
|
|
245
|
-
]}
|
|
246
|
-
advancedSearchDelimiter={useEqualsAsDelimiter ? '=' : ':'}
|
|
247
|
-
value={value}
|
|
248
|
-
onChange={setValue}
|
|
249
|
-
onSearch={setValue}
|
|
250
|
-
onClear={() => setValue('')}
|
|
251
|
-
formAdditionalItems={
|
|
252
|
-
useCustomFooter ? (
|
|
253
|
-
<FormGroup>
|
|
254
|
-
<Button variant="link" isInline icon={<ExternalLinkSquareAltIcon />} iconPosition="right">
|
|
255
|
-
Link
|
|
256
|
-
</Button>
|
|
257
|
-
</FormGroup>
|
|
258
|
-
) : null
|
|
259
|
-
}
|
|
260
|
-
/>
|
|
261
|
-
</>
|
|
262
|
-
);
|
|
263
|
-
};
|
|
46
|
+
```ts file='./SearchInputAdvanced.tsx'
|
|
264
47
|
```
|