@transferwise/components 0.0.0-experimental-b2dc1ea → 0.0.0-experimental-4c86474

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.
Files changed (60) hide show
  1. package/build/divider/Divider.js +33 -0
  2. package/build/divider/Divider.js.map +1 -0
  3. package/build/divider/Divider.mjs +31 -0
  4. package/build/divider/Divider.mjs.map +1 -0
  5. package/build/header/Header.js +34 -89
  6. package/build/header/Header.js.map +1 -1
  7. package/build/header/Header.mjs +31 -85
  8. package/build/header/Header.mjs.map +1 -1
  9. package/build/index.js +3 -1
  10. package/build/index.js.map +1 -1
  11. package/build/index.mjs +2 -1
  12. package/build/index.mjs.map +1 -1
  13. package/build/link/Link.js +3 -5
  14. package/build/link/Link.js.map +1 -1
  15. package/build/link/Link.mjs +3 -5
  16. package/build/link/Link.mjs.map +1 -1
  17. package/build/main.css +24 -3
  18. package/build/selectOption/SelectOption.js +1 -1
  19. package/build/selectOption/SelectOption.js.map +1 -1
  20. package/build/selectOption/SelectOption.mjs +1 -1
  21. package/build/styles/divider/Divider.css +24 -0
  22. package/build/styles/header/Header.css +0 -3
  23. package/build/styles/main.css +24 -3
  24. package/build/title/Title.js +3 -6
  25. package/build/title/Title.js.map +1 -1
  26. package/build/title/Title.mjs +3 -6
  27. package/build/title/Title.mjs.map +1 -1
  28. package/build/types/divider/Divider.d.ts +42 -0
  29. package/build/types/divider/Divider.d.ts.map +1 -0
  30. package/build/types/divider/index.d.ts +3 -0
  31. package/build/types/divider/index.d.ts.map +1 -0
  32. package/build/types/header/Header.d.ts +10 -34
  33. package/build/types/header/Header.d.ts.map +1 -1
  34. package/build/types/header/index.d.ts +0 -1
  35. package/build/types/header/index.d.ts.map +1 -1
  36. package/build/types/index.d.ts +2 -1
  37. package/build/types/index.d.ts.map +1 -1
  38. package/build/types/link/Link.d.ts +1 -3
  39. package/build/types/link/Link.d.ts.map +1 -1
  40. package/build/types/title/Title.d.ts +4 -3
  41. package/build/types/title/Title.d.ts.map +1 -1
  42. package/package.json +3 -3
  43. package/src/divider/Divider.css +24 -0
  44. package/src/divider/Divider.less +31 -0
  45. package/src/divider/Divider.spec.tsx +85 -0
  46. package/src/divider/Divider.story.tsx +29 -0
  47. package/src/divider/Divider.tsx +72 -0
  48. package/src/divider/index.ts +2 -0
  49. package/src/header/Header.css +0 -3
  50. package/src/header/Header.less +0 -4
  51. package/src/header/Header.spec.tsx +0 -33
  52. package/src/header/Header.story.tsx +40 -54
  53. package/src/header/Header.tsx +60 -126
  54. package/src/header/index.ts +0 -1
  55. package/src/index.ts +2 -1
  56. package/src/link/Link.tsx +27 -29
  57. package/src/main.css +24 -3
  58. package/src/main.less +1 -0
  59. package/src/ssr.spec.js +1 -0
  60. package/src/title/Title.tsx +11 -25
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@transferwise/components",
3
- "version": "0.0.0-experimental-b2dc1ea",
3
+ "version": "0.0.0-experimental-4c86474",
4
4
  "description": "Neptune React components",
5
5
  "license": "Apache-2.0",
6
6
  "repository": {
@@ -92,9 +92,9 @@
92
92
  "rollup": "^4.18.1",
93
93
  "rollup-preserve-directives": "^1.1.1",
94
94
  "storybook": "^8.2.2",
95
+ "@transferwise/less-config": "3.1.0",
95
96
  "@transferwise/neptune-css": "14.18.0",
96
- "@wise/components-theming": "1.6.0",
97
- "@transferwise/less-config": "3.1.0"
97
+ "@wise/components-theming": "1.6.0"
98
98
  },
99
99
  "peerDependencies": {
100
100
  "@transferwise/icons": "^3.7.0",
@@ -0,0 +1,24 @@
1
+ .wds-Divider {
2
+ --Divider-border-width: var(--size-4);
3
+ --Divider-border-color: var(--color-border-neutral);
4
+ --Divider-border-style: solid;
5
+ --Divider-dash-length: var(--size-4);
6
+ --Divider-dash-spacing: var(--size-4);
7
+ border-top: 4px solid rgba(0,0,0,0.10196);
8
+ border-top: var(--Divider-border-width) var(--Divider-border-style) var(--Divider-border-color);
9
+ display: inline-block;
10
+ margin: 0;
11
+ padding: 0;
12
+ height: 4px;
13
+ height: var(--Divider-border-width);
14
+ width: 100%;
15
+ }
16
+ .wds-Divider--content {
17
+ border-top: none;
18
+ background: repeating-linear-gradient(to right, var(--Divider-border-color), var(--Divider-border-color) var(--Divider-dash-length), transparent var(--Divider-dash-length), transparent calc(var(--Divider-dash-length) + var(--Divider-dash-spacing)));
19
+ height: var(--Divider-border-width);
20
+ }
21
+ .wds-Divider--content,
22
+ .wds-Divider--subsection {
23
+ --Divider-border-width: 1px;
24
+ }
@@ -0,0 +1,31 @@
1
+ .wds-Divider {
2
+ --Divider-border-width: var(--size-4);
3
+ --Divider-border-color: var(--color-border-neutral);
4
+ --Divider-border-style: solid;
5
+ --Divider-dash-length: var(--size-4);
6
+ --Divider-dash-spacing: var(--size-4);
7
+
8
+ border-top: var(--Divider-border-width) var(--Divider-border-style) var(--Divider-border-color);
9
+ display: inline-block;
10
+ margin: 0;
11
+ padding: 0;
12
+ height: var(--Divider-border-width);
13
+ width: 100%;
14
+
15
+ &--content {
16
+ border-top: none;
17
+ background: repeating-linear-gradient(
18
+ to right,
19
+ var(--Divider-border-color),
20
+ var(--Divider-border-color) var(--Divider-dash-length),
21
+ transparent var(--Divider-dash-length),
22
+ transparent calc(var(--Divider-dash-length) + var(--Divider-dash-spacing))
23
+ );
24
+ height: var(--Divider-border-width);
25
+ }
26
+
27
+ &--content,
28
+ &--subsection {
29
+ --Divider-border-width: 1px;
30
+ }
31
+ }
@@ -0,0 +1,85 @@
1
+ import React from 'react';
2
+ import { render, screen } from '@testing-library/react';
3
+ import Divider, { DividerProps } from './Divider';
4
+
5
+ describe('Divider', () => {
6
+ const defaultProps: DividerProps = {
7
+ testId: 'test-divider',
8
+ };
9
+
10
+ let rerenderDivider: (props?: DividerProps) => void;
11
+
12
+ beforeEach(() => {
13
+ const { rerender } = render(<Divider {...defaultProps} />);
14
+
15
+ rerenderDivider = (props?: DividerProps) => {
16
+ rerender(<Divider {...defaultProps} {...props} />);
17
+ };
18
+ });
19
+
20
+ const renderDivider = (props: Partial<DividerProps> = {}) => {
21
+ return render(<Divider {...props} />);
22
+ };
23
+
24
+ it('renders', () => {
25
+ expect(screen.getByTestId('test-divider')).toBeInTheDocument();
26
+ expect(screen.getByTestId('test-divider')).toHaveClass('wds-Divider');
27
+ });
28
+
29
+ it('renders as an `div`', () => {
30
+ const props: DividerProps = {
31
+ as: 'div',
32
+ };
33
+
34
+ expect(screen.getByTestId('test-divider')).toBeInTheDocument();
35
+ expect(screen.getByTestId('test-divider')).not.toHaveAttribute('role', 'separator');
36
+ expect(screen.getByTestId('test-divider')).not.toHaveAttribute(
37
+ 'aria-orientation',
38
+ 'horizontal',
39
+ );
40
+
41
+ rerenderDivider(props);
42
+
43
+ expect(screen.getByTestId('test-divider')).toHaveAttribute('role', 'separator');
44
+ expect(screen.getByTestId('test-divider')).toHaveAttribute('aria-orientation', 'horizontal');
45
+ });
46
+
47
+ it('renders with a custom class', () => {
48
+ const props: DividerProps = {
49
+ className: 'custom-class',
50
+ };
51
+
52
+ expect(screen.getByTestId('test-divider')).not.toHaveClass('custom-class');
53
+
54
+ rerenderDivider(props);
55
+
56
+ expect(screen.getByTestId('test-divider')).toHaveClass('custom-class');
57
+ });
58
+
59
+ it('renders with content variant class', () => {
60
+ const props: DividerProps = {
61
+ variant: 'content',
62
+ };
63
+
64
+ expect(screen.getByTestId('test-divider')).not.toHaveClass('wds-Divider--content');
65
+
66
+ rerenderDivider(props);
67
+
68
+ expect(screen.getByTestId('test-divider')).toHaveClass('wds-Divider', 'wds-Divider--content');
69
+ });
70
+
71
+ it('renders with subsection variant class', () => {
72
+ const props: DividerProps = {
73
+ variant: 'subsection',
74
+ };
75
+
76
+ expect(screen.getByTestId('test-divider')).not.toHaveClass('wds-Divider--subsection');
77
+
78
+ rerenderDivider(props);
79
+
80
+ expect(screen.getByTestId('test-divider')).toHaveClass(
81
+ 'wds-Divider',
82
+ 'wds-Divider--subsection',
83
+ );
84
+ });
85
+ });
@@ -0,0 +1,29 @@
1
+ import type { Meta, StoryObj } from '@storybook/react';
2
+
3
+ import Divider from './Divider';
4
+
5
+ const meta: Meta<typeof Divider> = {
6
+ component: Divider,
7
+ title: 'Layouts/Divider',
8
+ tags: ['autodocs'],
9
+ parameters: {
10
+ actions: { argTypesRegex: null },
11
+ },
12
+ };
13
+
14
+ export default meta;
15
+ type Story = StoryObj<typeof Divider>;
16
+
17
+ export const Basic: Story = {};
18
+
19
+ export const Subsection: Story = {
20
+ args: {
21
+ variant: 'subsection',
22
+ },
23
+ };
24
+
25
+ export const Content: Story = {
26
+ args: {
27
+ variant: 'content',
28
+ },
29
+ };
@@ -0,0 +1,72 @@
1
+ import { clsx } from 'clsx';
2
+ import React, { FunctionComponent } from 'react';
3
+
4
+ export interface DividerProps {
5
+ /** Option prop to specify DOM render element */
6
+ as?: 'hr' | 'div';
7
+
8
+ /** Optional prop to specify classNames onto the Divider */
9
+ className?: string;
10
+
11
+ /** Optional prop to specify the ID used for testing */
12
+ testId?: string;
13
+
14
+ /** Optional prop to specify the variant of the Divider */
15
+ variant?: 'content' | 'subsection' | 'section';
16
+ }
17
+
18
+ /**
19
+ * Divider component
20
+ *
21
+ * The Divider component is used to visually separate different sections of content.
22
+ * It can be rendered as a horizontal line and supports various styles such as
23
+ * section, subsection, and content. Additionally, the Divider can include custom styles.
24
+ *
25
+ * @component
26
+ * @param {'hr' | 'div'} [as='hr'] - Option prop to specify DOM render element.
27
+ * @param {string} [className] - Optional prop to specify classNames onto the Divider.
28
+ * @param {string} [testId] - Optional prop to specify the ID used for testing.
29
+ * @param {'section' | 'subsection' | 'content'} [variant='section'] - Optional prop to specify the variant of the Divider.
30
+ *
31
+ * @example
32
+ * // Example usage:
33
+ * import Divider from './Divider';
34
+ *
35
+ * function App() {
36
+ * return (
37
+ * <div>
38
+ * <p>Content above the divider</p>
39
+ * <Divider variant="content" />
40
+ * <p>Content below the divider</p>
41
+ * <Divider variant="subsection" />
42
+ * </div>
43
+ * );
44
+ * }
45
+ */
46
+ const Divider: FunctionComponent<DividerProps> = ({
47
+ as = 'hr',
48
+ className,
49
+ testId,
50
+ variant = 'section',
51
+ ...props
52
+ }) => {
53
+ const Element = as;
54
+ const variantClass = variant && variant !== 'section' ? `wds-Divider--${variant}` : '';
55
+
56
+ const commonProps = {
57
+ className: clsx('wds-Divider', variantClass, className),
58
+ 'data-testid': testId,
59
+ };
60
+
61
+ const divProps = {
62
+ ...commonProps,
63
+ 'aria-orientation': 'horizontal',
64
+ role: 'separator',
65
+ };
66
+
67
+ const componentProps = Element === 'div' ? divProps : commonProps;
68
+
69
+ return <Element {...componentProps} {...props} />;
70
+ };
71
+
72
+ export default Divider;
@@ -0,0 +1,2 @@
1
+ export { default } from './Divider';
2
+ export type { DividerProps } from './Divider';
@@ -14,9 +14,6 @@
14
14
  -moz-column-gap: var(--size-24);
15
15
  column-gap: var(--size-24);
16
16
  }
17
- .np-header--section {
18
- border-bottom: none;
19
- }
20
17
  .np-header__title {
21
18
  color: #5d7079;
22
19
  color: var(--color-content-secondary);
@@ -7,10 +7,6 @@
7
7
  border-bottom: 1px solid var(--color-border-neutral);
8
8
  margin-bottom: var(--size-8);
9
9
 
10
- &--section {
11
- border-bottom: none;
12
- }
13
-
14
10
  &__title {
15
11
  color: var(--color-content-secondary);
16
12
  }
@@ -75,39 +75,6 @@ describe('Header', () => {
75
75
  expect(screen.getByRole('heading', { name: 'Header title', level: 3 })).toBeInTheDocument();
76
76
  });
77
77
 
78
- it('renders header with section variant', () => {
79
- render(<Header title="Header title" variant="section" />);
80
-
81
- const header = screen.getByRole('heading', { name: 'Header title' });
82
- expect(header).toHaveClass('np-header--section');
83
- });
84
-
85
- it('warns if Header as legend is not inside a fieldset', () => {
86
- const consoleWarnMock = jest.spyOn(console, 'warn').mockImplementation();
87
-
88
- render(<Header as="legend" title="Header title" />);
89
-
90
- expect(consoleWarnMock).toHaveBeenCalledWith(
91
- 'Legends should be the first child in a fieldset, and this is not possible when including an action',
92
- );
93
-
94
- consoleWarnMock.mockRestore();
95
- });
96
-
97
- it('does not warn if Header as legend is inside a fieldset', () => {
98
- const consoleWarnMock = jest.spyOn(console, 'warn').mockImplementation();
99
-
100
- render(
101
- <fieldset>
102
- <Header as="legend" title="Header title" />
103
- </fieldset>,
104
- );
105
-
106
- expect(consoleWarnMock).not.toHaveBeenCalled();
107
-
108
- consoleWarnMock.mockRestore();
109
- });
110
-
111
78
  it('runs onClick if specified even when it got href prop', async () => {
112
79
  const callback = jest.fn();
113
80
  render(
@@ -1,67 +1,53 @@
1
- import type { Meta, StoryObj } from '@storybook/react';
2
-
3
1
  import Header from './Header';
4
2
 
5
- const meta: Meta<typeof Header> = {
3
+ export default {
6
4
  component: Header,
7
5
  title: 'Typography/Header',
8
- tags: ['autodocs'],
9
- parameters: {
10
- actions: { argTypesRegex: null },
11
- },
12
- };
13
-
14
- export default meta;
15
- type Story = StoryObj<typeof Header>;
16
-
17
- export const Basic: Story = {
18
- args: {
19
- title: 'Group header',
20
- },
21
- };
22
-
23
- export const WithAction: Story = {
24
- args: {
25
- ...Basic.args,
26
- action: {
27
- 'aria-label': 'Magic',
28
- text: 'Action',
29
- onClick: () => alert('Action!'),
30
- },
31
- },
32
6
  };
33
7
 
34
- export const WithActionLink: Story = {
35
- args: {
36
- ...Basic.args,
37
- action: {
38
- text: 'Link',
39
- href: 'https://wise.com',
40
- },
41
- },
8
+ export const Basic = () => {
9
+ return <Header title="Header title" />;
42
10
  };
43
11
 
44
- export const WithCustomElement: Story = {
45
- args: {
46
- title: 'Legend header',
47
- as: 'legend',
48
- },
12
+ export const WithAction = () => {
13
+ return (
14
+ <Header
15
+ title="Header title"
16
+ action={{
17
+ 'aria-label': 'Magic',
18
+ text: 'Click me!',
19
+ onClick: () => alert('Action!'),
20
+ }}
21
+ />
22
+ );
49
23
  };
50
24
 
51
- export const WithSectionVariant: Story = {
52
- args: {
53
- title: 'Section header',
54
- variant: 'section',
55
- },
25
+ export const WithActionAsLink = () => {
26
+ return (
27
+ <Header
28
+ title="Header title"
29
+ action={{
30
+ text: 'This is a link',
31
+ href: 'https://wise.com',
32
+ }}
33
+ />
34
+ );
56
35
  };
57
36
 
58
- export const WithSectionVariantAndAction: Story = {
59
- args: {
60
- ...WithSectionVariant.args,
61
- action: {
62
- 'aria-label': 'Magic',
63
- text: 'Action',
64
- onClick: () => alert('Action!'),
65
- },
66
- },
37
+ export const WithActionAsLinkPreventingNavigationWithTracking = () => {
38
+ return (
39
+ <Header
40
+ title="Header title"
41
+ action={{
42
+ text: 'This is a link',
43
+ href: 'https://wise.com',
44
+ onClick: (event: React.MouseEvent<HTMLElement>) => {
45
+ alert('Running onClick handler');
46
+
47
+ // we can stop the navigation from happening as onClick will always run before href redirect
48
+ event.preventDefault();
49
+ },
50
+ }}
51
+ />
52
+ );
67
53
  };
@@ -1,158 +1,92 @@
1
1
  import { clsx } from 'clsx';
2
2
 
3
3
  import { ActionButtonProps } from '../actionButton/ActionButton';
4
+ import Button from '../button';
4
5
  import { AriaLabelProperty, CommonProps, Heading, LinkProps, Typography } from '../common';
5
6
  import Link from '../link';
6
- import Button from '../button';
7
7
  import Title from '../title';
8
- import React, { useEffect, useRef, FunctionComponent } from 'react';
9
8
 
10
9
  type ActionProps = AriaLabelProperty & {
11
10
  text: string;
12
11
  };
13
12
 
14
13
  type ButtonActionProps = ActionProps & ActionButtonProps;
14
+
15
15
  type LinkActionProps = ActionProps & LinkProps;
16
16
 
17
- export interface HeaderProps extends CommonProps {
17
+ export type HeaderProps = CommonProps & {
18
18
  /**
19
- * Optional prop to define the action for the header. If the `href` property
20
- * is provided, a `Link` will be rendered instead of an `ActionButton`.
19
+ * When the `href` property is provided to the `action`, we will render a `Link` instead of a `ActionButton`.
21
20
  */
22
21
  action?: ButtonActionProps | LinkActionProps;
23
-
24
- /** Option prop to specify DOM render element of the title */
22
+ /**
23
+ * Override the heading element rendered for the title, useful to specify the semantics of your header.
24
+ *
25
+ * @default "h5"
26
+ */
25
27
  as?: Heading | 'legend';
26
-
27
- /** Optional prop to specify classNames onto the Header */
28
- className?: string;
29
-
30
- /** Optional prop to specify the ID used for testing */
31
- testId?: string;
32
-
33
- /** Required prop to set the title of the Header. */
34
28
  title: string;
29
+ };
35
30
 
36
- /** Optional prop to specify the variant of the Header */
37
- variant?: 'section' | 'group';
38
- }
39
-
40
- /**
41
- * Renders a header action which can be either a button or a link.
42
- *
43
- * @param {Object} props - The properties object.
44
- * @param {ButtonActionProps | LinkActionProps} props.action - The action object which can be either a button or a link.
45
- * @returns {JSX.Element} The rendered header action component.
46
- */
47
- const HeaderAction = React.forwardRef(
48
- (
49
- { action }: { action: ButtonActionProps | LinkActionProps },
50
- ref: React.Ref<HTMLButtonElement | HTMLAnchorElement>,
51
- ) => {
52
- const { 'aria-label': ariaLabel, text, onClick } = action;
53
-
54
- if ('href' in action) {
55
- const { href, target, onClick: linkOnClick } = action;
56
- return (
57
- <Link
58
- ref={ref as React.Ref<HTMLAnchorElement>}
59
- href={href}
60
- target={target}
61
- aria-label={ariaLabel}
62
- onClick={linkOnClick}
63
- >
64
- {text}
65
- </Link>
66
- );
67
- }
31
+ const HeaderAction = ({ action }: { action: ButtonActionProps | LinkActionProps }) => {
32
+ const props = {
33
+ 'aria-label': action['aria-label'],
34
+ };
68
35
 
36
+ if ('href' in action) {
69
37
  return (
70
- <Button
71
- ref={ref as React.Ref<HTMLButtonElement>}
72
- className="np-header__button"
73
- priority="tertiary"
74
- size="sm"
75
- aria-label={ariaLabel}
76
- onClick={onClick}
77
- >
78
- {text}
79
- </Button>
38
+ <Link href={action.href} target={action.target} onClick={action.onClick} {...props}>
39
+ {action.text}
40
+ </Link>
80
41
  );
81
- },
82
- );
42
+ }
43
+
44
+ return (
45
+ <Button
46
+ className="np-header__button"
47
+ priority="tertiary"
48
+ size="sm"
49
+ onClick={action.onClick}
50
+ {...props}
51
+ >
52
+ {action.text}
53
+ </Button>
54
+ );
55
+ };
83
56
 
84
57
  /**
85
- * Header component
86
- *
87
- * The header component is used to render a section header with an optional action button or link.
88
- * The header component can be rendered as a `h1`, `h2`, `h3`, `h4`, `h5`, `h6`, or `legend` element.
89
58
  *
90
- * @component
91
- * @param {ButtonActionProps | LinkActionProps} [action] - Optional prop to specify the action button or link.
92
- * @param {Heading | 'legend'} [as='h5'] - Optional prop to override the heading element rendered for the title.
93
- * @param {string} title - Required prop to set the title of the section header.
94
- * @param {'group' | 'section'} [variant='group'] - Optional prop to specify the variant of the section header.
95
- * @param {string} [className] - Optional prop to specify classNames onto the Header.
96
- * @param {string} [testId] - Optional prop to specify the ID used for testing.
59
+ * Neptune Web: https://transferwise.github.io/neptune-web/components/content/Header
97
60
  *
98
- * @example
99
- * // Example usage:
100
- * import Header from './Header';
101
- *
102
- * function App() {
103
- * return (
104
- * <Header title="Header" />
105
- * );
106
- * }
107
61
  */
108
- const Header: FunctionComponent<HeaderProps> = React.forwardRef(
109
- (
110
- { as = 'h5', action, className, testId, title, variant = 'group', ...props },
111
- ref: React.Ref<HTMLDivElement | HTMLHeadingElement | HTMLLegendElement>,
112
- ) => {
113
- const internalRef = useRef<HTMLLegendElement>(null);
114
- const variantTypography =
115
- variant === 'section' ? Typography.TITLE_SUBSECTION : Typography.TITLE_GROUP;
116
- const headerClasses = clsx('np-header', className, {
117
- 'np-header--section': variant === 'section',
118
- 'np-header__title': !action || as === 'legend',
119
- });
120
-
121
- const commonProps = {
122
- className: headerClasses,
123
- 'data-testid': testId,
124
- };
125
-
126
- useEffect(() => {
127
- if (as === 'legend' && internalRef.current) {
128
- const { parentElement } = internalRef.current;
129
- if (!parentElement || parentElement.tagName.toLowerCase() !== 'fieldset') {
130
- console.warn(
131
- 'Legends should be the first child in a fieldset, and this is not possible when including an action',
132
- );
133
- }
134
- }
135
- }, [as]);
136
-
137
- if (!action || as === 'legend') {
138
- return (
139
- <Title ref={internalRef} as={as} type={variantTypography} {...commonProps} {...props}>
140
- {title}
141
- </Title>
142
- );
143
- }
144
-
145
- const actionRef = React.createRef<HTMLButtonElement | HTMLAnchorElement>();
146
-
62
+ export const Header = ({ action, as = 'h5', title, className }: HeaderProps) => {
63
+ if (!action) {
147
64
  return (
148
- <div {...commonProps} {...props} ref={ref as React.Ref<HTMLDivElement>}>
149
- <Title as={as} type={variantTypography} className="np-header__title">
150
- {title}
151
- </Title>
152
- <HeaderAction ref={actionRef} action={action} />
153
- </div>
65
+ <Title
66
+ as={as}
67
+ type={Typography.TITLE_GROUP}
68
+ className={clsx('np-header', 'np-header__title', className)}
69
+ >
70
+ {title}
71
+ </Title>
154
72
  );
155
- },
156
- );
73
+ }
74
+
75
+ if (as === 'legend') {
76
+ // eslint-disable-next-line no-console
77
+ console.warn(
78
+ 'Legends should be the first child in a fieldset, and this is not possible when including an action',
79
+ );
80
+ }
81
+
82
+ return (
83
+ <div className={clsx('np-header', className)}>
84
+ <Title as={as} type={Typography.TITLE_GROUP} className="np-header__title">
85
+ {title}
86
+ </Title>
87
+ <HeaderAction action={action} />
88
+ </div>
89
+ );
90
+ };
157
91
 
158
92
  export default Header;
@@ -1,2 +1 @@
1
1
  export { default } from './Header';
2
- export type { HeaderProps } from './Header';
package/src/index.ts CHANGED
@@ -28,7 +28,7 @@ export type { DecisionProps } from './decision/Decision';
28
28
  export type { DefinitionListProps, DefinitionListDefinition } from './definitionList';
29
29
  export type { DimmerProps } from './dimmer';
30
30
  export type { DrawerProps } from './drawer';
31
- export type { HeaderProps } from './header';
31
+ export type { DividerProps } from './divider';
32
32
  export type { EmphasisProps } from './emphasis';
33
33
  export type { FieldProps } from './field/Field';
34
34
  export type { InfoProps } from './info';
@@ -125,6 +125,7 @@ export { default as Decision } from './decision';
125
125
  export { default as DefinitionList } from './definitionList';
126
126
  export { default as Dimmer } from './dimmer';
127
127
  export { default as Display } from './display';
128
+ export { default as Divider } from './divider';
128
129
  export { default as Drawer } from './drawer';
129
130
  export { default as DropFade } from './dropFade';
130
131
  export { default as Emphasis } from './emphasis';