@openedx/paragon 23.18.2 → 23.19.0

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.
@@ -16,7 +16,7 @@ interface BreadcrumbProps {
16
16
  spacer?: React.ReactElement;
17
17
  /** allows to add a custom function to be called `onClick` of a breadcrumb link.
18
18
  * The use case for this is for adding custom analytics to the component. */
19
- clickHandler?: (event: React.MouseEvent, link: any) => void;
19
+ clickHandler?: (event: React.MouseEvent<HTMLAnchorElement>, link: any) => void;
20
20
  /** The `Breadcrumbs` style variant to use. */
21
21
  variant?: 'light' | 'dark';
22
22
  /** The `Breadcrumbs` mobile variant view. */
@@ -25,6 +25,8 @@ interface BreadcrumbProps {
25
25
  * [react-router's Link](https://reactrouter.com/en/main/components/link).
26
26
  */
27
27
  linkAs?: React.ElementType;
28
+ /** Optional class name(s) to append to the base `<nav>` element. */
29
+ className?: string;
28
30
  }
29
- declare function Breadcrumb({ links, activeLabel, spacer, clickHandler, variant, isMobile, ariaLabel, linkAs, ...props }: BreadcrumbProps): import("react/jsx-runtime").JSX.Element;
31
+ declare function Breadcrumb({ links, activeLabel, spacer, clickHandler, className, variant, isMobile, ariaLabel, linkAs, }: BreadcrumbProps): import("react/jsx-runtime").JSX.Element;
30
32
  export default Breadcrumb;
@@ -8,18 +8,17 @@ function Breadcrumb({
8
8
  activeLabel,
9
9
  spacer,
10
10
  clickHandler,
11
+ className,
11
12
  variant = 'light',
12
13
  isMobile = false,
13
14
  ariaLabel = 'breadcrumb',
14
- linkAs = 'a',
15
- ...props
15
+ linkAs = 'a'
16
16
  }) {
17
17
  const linkCount = links.length;
18
18
  const displayLinks = isMobile ? [links[linkCount - 1]] : links;
19
19
  return /*#__PURE__*/React.createElement("nav", {
20
20
  "aria-label": ariaLabel,
21
- className: classNames('pgn__breadcrumb', `pgn__breadcrumb-${variant}`),
22
- ...props
21
+ className: classNames('pgn__breadcrumb', `pgn__breadcrumb-${variant}`, className)
23
22
  }, /*#__PURE__*/React.createElement("ol", {
24
23
  className: classNames('list-inline', {
25
24
  'is-mobile': isMobile
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","names":["React","classNames","BreadcrumbLink","ChevronRight","Icon","Breadcrumb","links","activeLabel","spacer","clickHandler","variant","isMobile","ariaLabel","linkAs","props","linkCount","length","displayLinks","createElement","className","map","link","i","Fragment","key","label","as","linkProps","role","src","id"],"sources":["../../src/Breadcrumb/index.tsx"],"sourcesContent":["import React from 'react';\nimport classNames from 'classnames';\n\nimport BreadcrumbLink from './BreadcrumbLink';\nimport { ChevronRight } from '../../icons';\nimport Icon from '../Icon';\n\ninterface BreadcrumbProps {\n /** An array of objects describing links to be rendered. The contents of an object depend on the value of `linkAs`\n * prop as these objects will get passed down as props to the underlying component defined by `linkAs` prop.\n */\n links: Array<{ label: string, [key: string]: any }>;\n /** allows to add a label that is not a link to the end of the breadcrumb. */\n activeLabel?: string;\n /** label of the element */\n ariaLabel?: string;\n /** allows to add a custom element between the breadcrumb items.\n * Defaults to `>` rendered using the `Icon` component. */\n spacer?: React.ReactElement;\n /** allows to add a custom function to be called `onClick` of a breadcrumb link.\n * The use case for this is for adding custom analytics to the component. */\n clickHandler?: (event: React.MouseEvent, link: any) => void;\n /** The `Breadcrumbs` style variant to use. */\n variant?: 'light' | 'dark';\n /** The `Breadcrumbs` mobile variant view. */\n isMobile?: boolean;\n /** Specifies the base element to use when rendering links, you should generally use either plain 'a' or\n * [react-router's Link](https://reactrouter.com/en/main/components/link).\n */\n linkAs?: React.ElementType;\n}\n\nfunction Breadcrumb({\n links, activeLabel, spacer, clickHandler,\n variant = 'light', isMobile = false, ariaLabel = 'breadcrumb', linkAs = 'a', ...props\n}: BreadcrumbProps) {\n const linkCount = links.length;\n const displayLinks = isMobile ? [links[linkCount - 1]] : links;\n\n return (\n <nav\n aria-label={ariaLabel}\n className={classNames('pgn__breadcrumb', `pgn__breadcrumb-${variant}`)}\n {...props}\n >\n <ol className={classNames('list-inline', { 'is-mobile': isMobile })}>\n {displayLinks.map((link, i) => (\n <React.Fragment key={link.label}>\n <li className={classNames('list-inline-item')}>\n <BreadcrumbLink as={linkAs} clickHandler={clickHandler} linkProps={link} />\n </li>\n {(activeLabel || ((i + 1) < linkCount))\n && (\n <li className=\"list-inline-item\" role=\"presentation\">\n {spacer || <Icon src={ChevronRight} id={`spacer-${i}`} />}\n </li>\n )}\n </React.Fragment>\n ))}\n {!isMobile && activeLabel && <li className=\"list-inline-item active\" key=\"active\" aria-current=\"page\">{activeLabel}</li>}\n </ol>\n </nav>\n );\n}\n\nexport default Breadcrumb;\n"],"mappings":"AAAA,OAAOA,KAAK,MAAM,OAAO;AACzB,OAAOC,UAAU,MAAM,YAAY;AAEnC,OAAOC,cAAc,MAAM,kBAAkB;AAC7C,SAASC,YAAY,QAAQ,aAAa;AAC1C,OAAOC,IAAI,MAAM,SAAS;AA2B1B,SAASC,UAAUA,CAAC;EAClBC,KAAK;EAAEC,WAAW;EAAEC,MAAM;EAAEC,YAAY;EACxCC,OAAO,GAAG,OAAO;EAAEC,QAAQ,GAAG,KAAK;EAAEC,SAAS,GAAG,YAAY;EAAEC,MAAM,GAAG,GAAG;EAAE,GAAGC;AACjE,CAAC,EAAE;EAClB,MAAMC,SAAS,GAAGT,KAAK,CAACU,MAAM;EAC9B,MAAMC,YAAY,GAAGN,QAAQ,GAAG,CAACL,KAAK,CAACS,SAAS,GAAG,CAAC,CAAC,CAAC,GAAGT,KAAK;EAE9D,oBACEN,KAAA,CAAAkB,aAAA;IACE,cAAYN,SAAU;IACtBO,SAAS,EAAElB,UAAU,CAAC,iBAAiB,EAAE,mBAAmBS,OAAO,EAAE,CAAE;IAAA,GACnEI;EAAK,gBAETd,KAAA,CAAAkB,aAAA;IAAIC,SAAS,EAAElB,UAAU,CAAC,aAAa,EAAE;MAAE,WAAW,EAAEU;IAAS,CAAC;EAAE,GACjEM,YAAY,CAACG,GAAG,CAAC,CAACC,IAAI,EAAEC,CAAC,kBACxBtB,KAAA,CAAAkB,aAAA,CAAClB,KAAK,CAACuB,QAAQ;IAACC,GAAG,EAAEH,IAAI,CAACI;EAAM,gBAC9BzB,KAAA,CAAAkB,aAAA;IAAIC,SAAS,EAAElB,UAAU,CAAC,kBAAkB;EAAE,gBAC5CD,KAAA,CAAAkB,aAAA,CAAChB,cAAc;IAACwB,EAAE,EAAEb,MAAO;IAACJ,YAAY,EAAEA,YAAa;IAACkB,SAAS,EAAEN;EAAK,CAAE,CACxE,CAAC,EACJ,CAACd,WAAW,IAAMe,CAAC,GAAG,CAAC,GAAIP,SAAU,kBAEpCf,KAAA,CAAAkB,aAAA;IAAIC,SAAS,EAAC,kBAAkB;IAACS,IAAI,EAAC;EAAc,GACjDpB,MAAM,iBAAIR,KAAA,CAAAkB,aAAA,CAACd,IAAI;IAACyB,GAAG,EAAE1B,YAAa;IAAC2B,EAAE,EAAE,UAAUR,CAAC;EAAG,CAAE,CACtD,CAEQ,CACjB,CAAC,EACD,CAACX,QAAQ,IAAIJ,WAAW,iBAAIP,KAAA,CAAAkB,aAAA;IAAIC,SAAS,EAAC,yBAAyB;IAACK,GAAG,EAAC,QAAQ;IAAC,gBAAa;EAAM,GAAEjB,WAAgB,CACrH,CACD,CAAC;AAEV;AAEA,eAAeF,UAAU","ignoreList":[]}
1
+ {"version":3,"file":"index.js","names":["React","classNames","BreadcrumbLink","ChevronRight","Icon","Breadcrumb","links","activeLabel","spacer","clickHandler","className","variant","isMobile","ariaLabel","linkAs","linkCount","length","displayLinks","createElement","map","link","i","Fragment","key","label","as","linkProps","role","src","id"],"sources":["../../src/Breadcrumb/index.tsx"],"sourcesContent":["import React from 'react';\nimport classNames from 'classnames';\n\nimport BreadcrumbLink from './BreadcrumbLink';\nimport { ChevronRight } from '../../icons';\nimport Icon from '../Icon';\n\ninterface BreadcrumbProps {\n /** An array of objects describing links to be rendered. The contents of an object depend on the value of `linkAs`\n * prop as these objects will get passed down as props to the underlying component defined by `linkAs` prop.\n */\n links: Array<{ label: string, [key: string]: any }>;\n /** allows to add a label that is not a link to the end of the breadcrumb. */\n activeLabel?: string;\n /** label of the element */\n ariaLabel?: string;\n /** allows to add a custom element between the breadcrumb items.\n * Defaults to `>` rendered using the `Icon` component. */\n spacer?: React.ReactElement;\n /** allows to add a custom function to be called `onClick` of a breadcrumb link.\n * The use case for this is for adding custom analytics to the component. */\n clickHandler?: (event: React.MouseEvent<HTMLAnchorElement>, link: any) => void;\n /** The `Breadcrumbs` style variant to use. */\n variant?: 'light' | 'dark';\n /** The `Breadcrumbs` mobile variant view. */\n isMobile?: boolean;\n /** Specifies the base element to use when rendering links, you should generally use either plain 'a' or\n * [react-router's Link](https://reactrouter.com/en/main/components/link).\n */\n linkAs?: React.ElementType;\n /** Optional class name(s) to append to the base `<nav>` element. */\n className?: string;\n}\n\nfunction Breadcrumb({\n links, activeLabel, spacer, clickHandler, className,\n variant = 'light', isMobile = false, ariaLabel = 'breadcrumb', linkAs = 'a',\n}: BreadcrumbProps) {\n const linkCount = links.length;\n const displayLinks = isMobile ? [links[linkCount - 1]] : links;\n\n return (\n <nav\n aria-label={ariaLabel}\n className={classNames('pgn__breadcrumb', `pgn__breadcrumb-${variant}`, className)}\n >\n <ol className={classNames('list-inline', { 'is-mobile': isMobile })}>\n {displayLinks.map((link, i) => (\n <React.Fragment key={link.label}>\n <li className={classNames('list-inline-item')}>\n <BreadcrumbLink as={linkAs} clickHandler={clickHandler} linkProps={link} />\n </li>\n {(activeLabel || ((i + 1) < linkCount))\n && (\n <li className=\"list-inline-item\" role=\"presentation\">\n {spacer || <Icon src={ChevronRight} id={`spacer-${i}`} />}\n </li>\n )}\n </React.Fragment>\n ))}\n {!isMobile && activeLabel && <li className=\"list-inline-item active\" key=\"active\" aria-current=\"page\">{activeLabel}</li>}\n </ol>\n </nav>\n );\n}\n\nexport default Breadcrumb;\n"],"mappings":"AAAA,OAAOA,KAAK,MAAM,OAAO;AACzB,OAAOC,UAAU,MAAM,YAAY;AAEnC,OAAOC,cAAc,MAAM,kBAAkB;AAC7C,SAASC,YAAY,QAAQ,aAAa;AAC1C,OAAOC,IAAI,MAAM,SAAS;AA6B1B,SAASC,UAAUA,CAAC;EAClBC,KAAK;EAAEC,WAAW;EAAEC,MAAM;EAAEC,YAAY;EAAEC,SAAS;EACnDC,OAAO,GAAG,OAAO;EAAEC,QAAQ,GAAG,KAAK;EAAEC,SAAS,GAAG,YAAY;EAAEC,MAAM,GAAG;AACzD,CAAC,EAAE;EAClB,MAAMC,SAAS,GAAGT,KAAK,CAACU,MAAM;EAC9B,MAAMC,YAAY,GAAGL,QAAQ,GAAG,CAACN,KAAK,CAACS,SAAS,GAAG,CAAC,CAAC,CAAC,GAAGT,KAAK;EAE9D,oBACEN,KAAA,CAAAkB,aAAA;IACE,cAAYL,SAAU;IACtBH,SAAS,EAAET,UAAU,CAAC,iBAAiB,EAAE,mBAAmBU,OAAO,EAAE,EAAED,SAAS;EAAE,gBAElFV,KAAA,CAAAkB,aAAA;IAAIR,SAAS,EAAET,UAAU,CAAC,aAAa,EAAE;MAAE,WAAW,EAAEW;IAAS,CAAC;EAAE,GACjEK,YAAY,CAACE,GAAG,CAAC,CAACC,IAAI,EAAEC,CAAC,kBACxBrB,KAAA,CAAAkB,aAAA,CAAClB,KAAK,CAACsB,QAAQ;IAACC,GAAG,EAAEH,IAAI,CAACI;EAAM,gBAC9BxB,KAAA,CAAAkB,aAAA;IAAIR,SAAS,EAAET,UAAU,CAAC,kBAAkB;EAAE,gBAC5CD,KAAA,CAAAkB,aAAA,CAAChB,cAAc;IAACuB,EAAE,EAAEX,MAAO;IAACL,YAAY,EAAEA,YAAa;IAACiB,SAAS,EAAEN;EAAK,CAAE,CACxE,CAAC,EACJ,CAACb,WAAW,IAAMc,CAAC,GAAG,CAAC,GAAIN,SAAU,kBAEpCf,KAAA,CAAAkB,aAAA;IAAIR,SAAS,EAAC,kBAAkB;IAACiB,IAAI,EAAC;EAAc,GACjDnB,MAAM,iBAAIR,KAAA,CAAAkB,aAAA,CAACd,IAAI;IAACwB,GAAG,EAAEzB,YAAa;IAAC0B,EAAE,EAAE,UAAUR,CAAC;EAAG,CAAE,CACtD,CAEQ,CACjB,CAAC,EACD,CAACT,QAAQ,IAAIL,WAAW,iBAAIP,KAAA,CAAAkB,aAAA;IAAIR,SAAS,EAAC,yBAAyB;IAACa,GAAG,EAAC,QAAQ;IAAC,gBAAa;EAAM,GAAEhB,WAAgB,CACrH,CACD,CAAC;AAEV;AAEA,eAAeF,UAAU","ignoreList":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@openedx/paragon",
3
- "version": "23.18.2",
3
+ "version": "23.19.0",
4
4
  "description": "Accessible, responsive UI component library based on Bootstrap.",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.js",
@@ -95,4 +95,29 @@ describe('<Breadcrumb />', () => {
95
95
  expect(links.getAttribute('target')).toBe('_blank');
96
96
  expect(links.getAttribute('href')).toBe('/link-1');
97
97
  });
98
+
99
+ it('renders with a custom CSS class', () => {
100
+ render(<Breadcrumb {...baseProps} ariaLabel="Breadcrumbs" className="foobar" />);
101
+ const nav = screen.getByLabelText('Breadcrumbs');
102
+ expect(nav.classList).toContain('foobar');
103
+ expect(nav.classList).toContain('pgn__breadcrumb');
104
+ expect(nav.classList).toContain('pgn__breadcrumb-light');
105
+ });
106
+
107
+ it('can access data-xxxxx attributes on the links in clickHandler', async () => {
108
+ const user = userEvent.setup();
109
+ const clickHandler = jest.fn();
110
+ render(
111
+ <Breadcrumb
112
+ ariaLabel="Location"
113
+ links={[
114
+ { label: 'Link1', href: '/link1', 'data-parent-index': 17 },
115
+ ]}
116
+ clickHandler={({ currentTarget }) => clickHandler(currentTarget.dataset.parentIndex)}
117
+ />,
118
+ );
119
+ const link = screen.getByRole('link', { name: 'Link1' });
120
+ await user.click(link);
121
+ expect(clickHandler).toHaveBeenCalledWith('17');
122
+ });
98
123
  });
@@ -19,7 +19,7 @@ interface BreadcrumbProps {
19
19
  spacer?: React.ReactElement;
20
20
  /** allows to add a custom function to be called `onClick` of a breadcrumb link.
21
21
  * The use case for this is for adding custom analytics to the component. */
22
- clickHandler?: (event: React.MouseEvent, link: any) => void;
22
+ clickHandler?: (event: React.MouseEvent<HTMLAnchorElement>, link: any) => void;
23
23
  /** The `Breadcrumbs` style variant to use. */
24
24
  variant?: 'light' | 'dark';
25
25
  /** The `Breadcrumbs` mobile variant view. */
@@ -28,11 +28,13 @@ interface BreadcrumbProps {
28
28
  * [react-router's Link](https://reactrouter.com/en/main/components/link).
29
29
  */
30
30
  linkAs?: React.ElementType;
31
+ /** Optional class name(s) to append to the base `<nav>` element. */
32
+ className?: string;
31
33
  }
32
34
 
33
35
  function Breadcrumb({
34
- links, activeLabel, spacer, clickHandler,
35
- variant = 'light', isMobile = false, ariaLabel = 'breadcrumb', linkAs = 'a', ...props
36
+ links, activeLabel, spacer, clickHandler, className,
37
+ variant = 'light', isMobile = false, ariaLabel = 'breadcrumb', linkAs = 'a',
36
38
  }: BreadcrumbProps) {
37
39
  const linkCount = links.length;
38
40
  const displayLinks = isMobile ? [links[linkCount - 1]] : links;
@@ -40,8 +42,7 @@ function Breadcrumb({
40
42
  return (
41
43
  <nav
42
44
  aria-label={ariaLabel}
43
- className={classNames('pgn__breadcrumb', `pgn__breadcrumb-${variant}`)}
44
- {...props}
45
+ className={classNames('pgn__breadcrumb', `pgn__breadcrumb-${variant}`, className)}
45
46
  >
46
47
  <ol className={classNames('list-inline', { 'is-mobile': isMobile })}>
47
48
  {displayLinks.map((link, i) => (