@carbon/react 1.54.0-rc.0 → 1.55.0-rc.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.
Files changed (82) hide show
  1. package/.playwright/INTERNAL_AVT_REPORT_DO_NOT_USE.json +994 -1023
  2. package/es/components/Button/Button.d.ts +1 -1
  3. package/es/components/Button/Button.js +13 -89
  4. package/es/components/Button/ButtonBase.d.ts +10 -0
  5. package/es/components/Button/ButtonBase.js +110 -0
  6. package/es/components/CodeSnippet/CodeSnippet.Skeleton.d.ts +37 -0
  7. package/es/components/CodeSnippet/CodeSnippet.d.ts +196 -0
  8. package/es/components/CodeSnippet/CodeSnippet.js +20 -18
  9. package/es/components/CodeSnippet/index.d.ts +10 -0
  10. package/es/components/ComboBox/ComboBox.d.ts +2 -2
  11. package/es/components/ComboBox/ComboBox.js +13 -5
  12. package/es/components/ComboButton/index.d.ts +51 -0
  13. package/es/components/ComboButton/index.js +9 -7
  14. package/es/components/ComposedModal/ComposedModal.js +2 -2
  15. package/es/components/DataTable/TableBatchAction.d.ts +1 -5
  16. package/es/components/Dropdown/Dropdown.js +3 -1
  17. package/es/components/IconButton/index.js +2 -3
  18. package/es/components/Menu/Menu.js +2 -0
  19. package/es/components/Modal/Modal.js +2 -2
  20. package/es/components/ModalWrapper/ModalWrapper.d.ts +1 -1
  21. package/es/components/MultiSelect/FilterableMultiSelect.js +31 -0
  22. package/es/components/MultiSelect/MultiSelect.js +37 -7
  23. package/es/components/Slider/Slider.Skeleton.js +6 -2
  24. package/es/components/Slug/index.js +8 -13
  25. package/es/components/StructuredList/StructuredList.d.ts +8 -0
  26. package/es/components/StructuredList/StructuredList.js +28 -10
  27. package/es/components/Tag/DismissibleTag.js +119 -0
  28. package/es/components/Tag/OperationalTag.js +99 -0
  29. package/es/components/Tag/SelectableTag.js +98 -0
  30. package/es/components/Tag/index.d.ts +4 -1
  31. package/es/components/TreeView/TreeNode.js +1 -1
  32. package/es/components/UIShell/SideNavMenu.js +11 -1
  33. package/es/components/UIShell/SideNavMenuItem.d.ts +4 -0
  34. package/es/components/UIShell/SideNavMenuItem.js +8 -1
  35. package/es/components/UIShell/SwitcherItem.d.ts +4 -0
  36. package/es/components/UIShell/SwitcherItem.js +6 -0
  37. package/es/feature-flags.js +2 -1
  38. package/es/index.js +5 -2
  39. package/es/internal/environment.js +5 -1
  40. package/es/internal/keyboard/navigation.js +6 -2
  41. package/es/internal/useOutsideClick.js +31 -0
  42. package/lib/components/Button/Button.d.ts +1 -1
  43. package/lib/components/Button/Button.js +13 -90
  44. package/lib/components/Button/ButtonBase.d.ts +10 -0
  45. package/lib/components/Button/ButtonBase.js +119 -0
  46. package/lib/components/CodeSnippet/CodeSnippet.Skeleton.d.ts +37 -0
  47. package/lib/components/CodeSnippet/CodeSnippet.d.ts +196 -0
  48. package/lib/components/CodeSnippet/CodeSnippet.js +20 -18
  49. package/lib/components/CodeSnippet/index.d.ts +10 -0
  50. package/lib/components/ComboBox/ComboBox.d.ts +2 -2
  51. package/lib/components/ComboBox/ComboBox.js +13 -5
  52. package/lib/components/ComboButton/index.d.ts +51 -0
  53. package/lib/components/ComboButton/index.js +9 -7
  54. package/lib/components/ComposedModal/ComposedModal.js +2 -2
  55. package/lib/components/DataTable/TableBatchAction.d.ts +1 -5
  56. package/lib/components/Dropdown/Dropdown.js +3 -1
  57. package/lib/components/IconButton/index.js +2 -3
  58. package/lib/components/Menu/Menu.js +2 -0
  59. package/lib/components/Modal/Modal.js +2 -2
  60. package/lib/components/ModalWrapper/ModalWrapper.d.ts +1 -1
  61. package/lib/components/MultiSelect/FilterableMultiSelect.js +31 -0
  62. package/lib/components/MultiSelect/MultiSelect.js +37 -7
  63. package/lib/components/Slider/Slider.Skeleton.js +5 -1
  64. package/lib/components/Slug/index.js +8 -13
  65. package/lib/components/StructuredList/StructuredList.d.ts +8 -0
  66. package/lib/components/StructuredList/StructuredList.js +27 -9
  67. package/lib/components/Tag/DismissibleTag.js +129 -0
  68. package/lib/components/Tag/OperationalTag.js +109 -0
  69. package/lib/components/Tag/SelectableTag.js +108 -0
  70. package/lib/components/Tag/index.d.ts +4 -1
  71. package/lib/components/TreeView/TreeNode.js +1 -1
  72. package/lib/components/UIShell/SideNavMenu.js +11 -1
  73. package/lib/components/UIShell/SideNavMenuItem.d.ts +4 -0
  74. package/lib/components/UIShell/SideNavMenuItem.js +8 -1
  75. package/lib/components/UIShell/SwitcherItem.d.ts +4 -0
  76. package/lib/components/UIShell/SwitcherItem.js +6 -0
  77. package/lib/feature-flags.js +2 -1
  78. package/lib/index.js +10 -4
  79. package/lib/internal/environment.js +5 -1
  80. package/lib/internal/keyboard/navigation.js +6 -2
  81. package/lib/internal/useOutsideClick.js +35 -0
  82. package/package.json +6 -6
@@ -14,7 +14,7 @@ export declare const ButtonTooltipAlignments: readonly ["start", "center", "end"
14
14
  export type ButtonTooltipAlignment = (typeof ButtonTooltipAlignments)[number];
15
15
  export declare const ButtonTooltipPositions: string[];
16
16
  export type ButtonTooltipPosition = (typeof ButtonTooltipPositions)[number];
17
- interface ButtonBaseProps extends React.ButtonHTMLAttributes<HTMLButtonElement> {
17
+ export interface ButtonBaseProps extends React.ButtonHTMLAttributes<HTMLButtonElement> {
18
18
  /**
19
19
  * Specify the message read by screen readers for the danger button variant
20
20
  */
@@ -8,11 +8,9 @@
8
8
  import { extends as _extends } from '../../_virtual/_rollupPluginBabelHelpers.js';
9
9
  import PropTypes from 'prop-types';
10
10
  import React__default, { useRef } from 'react';
11
- import cx from 'classnames';
12
11
  import { IconButton } from '../IconButton/index.js';
13
12
  import { composeEventHandlers } from '../../tools/events.js';
14
- import { usePrefix } from '../../internal/usePrefix.js';
15
- import { useId } from '../../internal/useId.js';
13
+ import ButtonBase from './ButtonBase.js';
16
14
 
17
15
  const ButtonKinds = ['primary', 'secondary', 'danger', 'ghost', 'danger--primary', 'danger--ghost', 'danger--tertiary', 'tertiary'];
18
16
  const ButtonSizes = ['sm', 'md', 'lg', 'xl', '2xl'];
@@ -24,18 +22,13 @@ function isIconOnlyButton(hasIconOnly, _kind) {
24
22
  }
25
23
  return false;
26
24
  }
27
- const Button = /*#__PURE__*/React__default.forwardRef(function Button(_ref, ref) {
28
- let {
25
+ const Button = /*#__PURE__*/React__default.forwardRef(function Button(props, ref) {
26
+ const tooltipRef = useRef(null);
27
+ const {
29
28
  as,
30
29
  children,
31
- className,
32
- dangerDescription = 'danger',
33
- disabled = false,
34
30
  hasIconOnly = false,
35
- href,
36
31
  iconDescription,
37
- isExpressive = false,
38
- isSelected,
39
32
  kind = 'primary',
40
33
  onBlur,
41
34
  onClick,
@@ -44,92 +37,21 @@ const Button = /*#__PURE__*/React__default.forwardRef(function Button(_ref, ref)
44
37
  onMouseLeave,
45
38
  renderIcon: ButtonImageElement,
46
39
  size,
47
- tabIndex,
48
40
  tooltipAlignment = 'center',
49
41
  tooltipPosition = 'top',
50
- type = 'button',
51
42
  ...rest
52
- } = _ref;
53
- const tooltipRef = useRef(null);
54
- const prefix = usePrefix();
43
+ } = props;
55
44
  const handleClick = evt => {
56
45
  // Prevent clicks on the tooltip from triggering the button click event
57
46
  if (evt.target === tooltipRef.current) {
58
47
  evt.preventDefault();
59
48
  }
60
49
  };
61
- const buttonClasses = cx(className, {
62
- [`${prefix}--btn`]: true,
63
- [`${prefix}--btn--sm`]: size === 'sm' && !isExpressive,
64
- // TODO: V12 - Remove this class
65
- [`${prefix}--btn--md`]: size === 'md' && !isExpressive,
66
- // TODO: V12 - Remove this class
67
- [`${prefix}--btn--xl`]: size === 'xl',
68
- // TODO: V12 - Remove this class
69
- [`${prefix}--btn--2xl`]: size === '2xl',
70
- // TODO: V12 - Remove this class
71
- [`${prefix}--layout--size-${size}`]: size,
72
- [`${prefix}--btn--${kind}`]: kind,
73
- [`${prefix}--btn--disabled`]: disabled,
74
- [`${prefix}--btn--expressive`]: isExpressive,
75
- [`${prefix}--btn--icon-only`]: hasIconOnly,
76
- [`${prefix}--btn--selected`]: hasIconOnly && isSelected && kind === 'ghost'
77
- });
78
- const commonProps = {
79
- tabIndex,
80
- className: buttonClasses,
81
- ref
82
- };
83
- const buttonImage = !ButtonImageElement ? null : /*#__PURE__*/React__default.createElement(ButtonImageElement, {
84
- "aria-label": iconDescription,
85
- className: `${prefix}--btn__icon`,
86
- "aria-hidden": "true"
87
- });
88
50
  const iconOnlyImage = !ButtonImageElement ? null : /*#__PURE__*/React__default.createElement(ButtonImageElement, null);
89
- const dangerButtonVariants = ['danger', 'danger--tertiary', 'danger--ghost'];
90
- let component = 'button';
91
- const assistiveId = useId('danger-description');
92
- const {
93
- 'aria-pressed': ariaPressed,
94
- 'aria-describedby': ariaDescribedBy
95
- } = rest;
96
- let otherProps = {
97
- disabled,
98
- type,
99
- 'aria-describedby': dangerButtonVariants.includes(kind) ? assistiveId : ariaDescribedBy || undefined,
100
- 'aria-pressed': ariaPressed ?? (hasIconOnly && kind === 'ghost' ? isSelected : undefined)
101
- };
102
- const anchorProps = {
103
- href
104
- };
105
- let assistiveText = null;
106
- if (dangerButtonVariants.includes(kind)) {
107
- assistiveText = /*#__PURE__*/React__default.createElement("span", {
108
- id: assistiveId,
109
- className: `${prefix}--visually-hidden`
110
- }, dangerDescription);
111
- }
112
- if (as) {
113
- component = as;
114
- otherProps = {
115
- ...otherProps,
116
- ...anchorProps
117
- };
118
- } else if (href && !disabled) {
119
- component = 'a';
120
- otherProps = anchorProps;
121
- }
122
51
  if (!isIconOnlyButton(hasIconOnly)) {
123
- return /*#__PURE__*/React__default.createElement(component, {
124
- onMouseEnter,
125
- onMouseLeave,
126
- onFocus,
127
- onBlur,
128
- onClick,
129
- ...rest,
130
- ...commonProps,
131
- ...otherProps
132
- }, assistiveText, children, buttonImage);
52
+ return /*#__PURE__*/React__default.createElement(ButtonBase, _extends({
53
+ ref: ref
54
+ }, props));
133
55
  } else {
134
56
  let align = undefined;
135
57
  if (tooltipPosition === 'top' || tooltipPosition === 'bottom') {
@@ -146,7 +68,8 @@ const Button = /*#__PURE__*/React__default.forwardRef(function Button(_ref, ref)
146
68
  if (tooltipPosition === 'right' || tooltipPosition === 'left') {
147
69
  align = tooltipPosition;
148
70
  }
149
- return /*#__PURE__*/React__default.createElement(IconButton, _extends({
71
+ return /*#__PURE__*/React__default.createElement(IconButton, _extends({}, rest, {
72
+ ref: ref,
150
73
  as: as,
151
74
  align: align,
152
75
  label: iconDescription,
@@ -156,8 +79,9 @@ const Button = /*#__PURE__*/React__default.forwardRef(function Button(_ref, ref)
156
79
  onMouseLeave: onMouseLeave,
157
80
  onFocus: onFocus,
158
81
  onBlur: onBlur,
159
- onClick: composeEventHandlers([onClick, handleClick])
160
- }, rest, commonProps, otherProps), iconOnlyImage ?? children);
82
+ onClick: composeEventHandlers([onClick, handleClick]),
83
+ renderIcon: iconOnlyImage ? null : ButtonImageElement // avoid doubling the icon.
84
+ }), iconOnlyImage ?? children);
161
85
  }
162
86
  });
163
87
  Button.displayName = 'Button';
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Copyright IBM Corp. 2016, 2023
3
+ *
4
+ * This source code is licensed under the Apache-2.0 license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+ import React from 'react';
8
+ import { ButtonProps } from './Button';
9
+ declare const ButtonBase: React.ForwardRefExoticComponent<Omit<ButtonProps<React.ElementType<any>>, "ref"> & React.RefAttributes<unknown>>;
10
+ export default ButtonBase;
@@ -0,0 +1,110 @@
1
+ /**
2
+ * Copyright IBM Corp. 2016, 2023
3
+ *
4
+ * This source code is licensed under the Apache-2.0 license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import React__default from 'react';
9
+ import cx from 'classnames';
10
+ import { usePrefix } from '../../internal/usePrefix.js';
11
+ import { useId } from '../../internal/useId.js';
12
+
13
+ const ButtonBase = /*#__PURE__*/React__default.forwardRef(function ButtonBase(_ref, ref) {
14
+ let {
15
+ as,
16
+ children,
17
+ className,
18
+ dangerDescription = 'danger',
19
+ disabled = false,
20
+ hasIconOnly = false,
21
+ href,
22
+ iconDescription,
23
+ isExpressive = false,
24
+ isSelected,
25
+ kind = 'primary',
26
+ onBlur,
27
+ onClick,
28
+ onFocus,
29
+ onMouseEnter,
30
+ onMouseLeave,
31
+ renderIcon: ButtonImageElement,
32
+ size,
33
+ tabIndex,
34
+ type = 'button',
35
+ ...rest
36
+ } = _ref;
37
+ const prefix = usePrefix();
38
+ const buttonClasses = cx(className, {
39
+ [`${prefix}--btn`]: true,
40
+ [`${prefix}--btn--sm`]: size === 'sm' && !isExpressive,
41
+ // TODO: V12 - Remove this class
42
+ [`${prefix}--btn--md`]: size === 'md' && !isExpressive,
43
+ // TODO: V12 - Remove this class
44
+ [`${prefix}--btn--xl`]: size === 'xl',
45
+ // TODO: V12 - Remove this class
46
+ [`${prefix}--btn--2xl`]: size === '2xl',
47
+ // TODO: V12 - Remove this class
48
+ [`${prefix}--layout--size-${size}`]: size,
49
+ [`${prefix}--btn--${kind}`]: kind,
50
+ [`${prefix}--btn--disabled`]: disabled,
51
+ [`${prefix}--btn--expressive`]: isExpressive,
52
+ [`${prefix}--btn--icon-only`]: hasIconOnly && !className?.includes(`${prefix}--btn--icon-only`),
53
+ [`${prefix}--btn--selected`]: hasIconOnly && isSelected && kind === 'ghost'
54
+ });
55
+ const commonProps = {
56
+ tabIndex,
57
+ className: buttonClasses,
58
+ ref
59
+ };
60
+ const buttonImage = !ButtonImageElement ? null : /*#__PURE__*/React__default.createElement(ButtonImageElement, {
61
+ "aria-label": iconDescription,
62
+ className: `${prefix}--btn__icon`,
63
+ "aria-hidden": "true"
64
+ });
65
+ const dangerButtonVariants = ['danger', 'danger--tertiary', 'danger--ghost'];
66
+ let component = 'button';
67
+ const assistiveId = useId('danger-description');
68
+ const {
69
+ 'aria-pressed': ariaPressed,
70
+ 'aria-describedby': ariaDescribedBy
71
+ } = rest;
72
+ let otherProps = {
73
+ disabled,
74
+ type,
75
+ 'aria-describedby': dangerButtonVariants.includes(kind) ? assistiveId : ariaDescribedBy || undefined,
76
+ 'aria-pressed': ariaPressed ?? (hasIconOnly && kind === 'ghost' ? isSelected : undefined)
77
+ };
78
+ const anchorProps = {
79
+ href
80
+ };
81
+ let assistiveText = null;
82
+ if (dangerButtonVariants.includes(kind)) {
83
+ assistiveText = /*#__PURE__*/React__default.createElement("span", {
84
+ id: assistiveId,
85
+ className: `${prefix}--visually-hidden`
86
+ }, dangerDescription);
87
+ }
88
+ if (as) {
89
+ component = as;
90
+ otherProps = {
91
+ ...otherProps,
92
+ ...anchorProps
93
+ };
94
+ } else if (href && !disabled) {
95
+ component = 'a';
96
+ otherProps = anchorProps;
97
+ }
98
+ return /*#__PURE__*/React__default.createElement(component, {
99
+ onMouseEnter,
100
+ onMouseLeave,
101
+ onFocus,
102
+ onBlur,
103
+ onClick,
104
+ ...rest,
105
+ ...commonProps,
106
+ ...otherProps
107
+ }, assistiveText, children, buttonImage);
108
+ });
109
+
110
+ export { ButtonBase as default };
@@ -0,0 +1,37 @@
1
+ /**
2
+ * Copyright IBM Corp. 2016, 2023
3
+ *
4
+ * This source code is licensed under the Apache-2.0 license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+ import PropTypes from 'prop-types';
8
+ import React from 'react';
9
+ export interface CodeSnippetSkeletonProps extends React.HTMLAttributes<Omit<HTMLDivElement, 'children'>> {
10
+ /**
11
+ * Specify an optional className to be applied to the container node
12
+ */
13
+ className?: string;
14
+ /**
15
+ * The type of the code snippet, including single or multi
16
+ */
17
+ type?: 'single' | 'multi' | undefined;
18
+ }
19
+ declare function CodeSnippetSkeleton({ className: containerClassName, type, ...rest }: {
20
+ [x: string]: any;
21
+ className: any;
22
+ type?: string | undefined;
23
+ }): import("react/jsx-runtime").JSX.Element | undefined;
24
+ declare namespace CodeSnippetSkeleton {
25
+ var propTypes: {
26
+ /**
27
+ * Specify an optional className to be applied to the container node
28
+ */
29
+ className: PropTypes.Requireable<string>;
30
+ /**
31
+ * The type of the code snippet, including single or multi
32
+ */
33
+ type: PropTypes.Requireable<string>;
34
+ };
35
+ }
36
+ export default CodeSnippetSkeleton;
37
+ export { CodeSnippetSkeleton };
@@ -0,0 +1,196 @@
1
+ /**
2
+ * Copyright IBM Corp. 2016, 2023
3
+ *
4
+ * This source code is licensed under the Apache-2.0 license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+ import PropTypes from 'prop-types';
8
+ import { PropsWithChildren } from 'react';
9
+ export interface CodeSnippetProps {
10
+ /**
11
+ * Specify how the trigger should align with the tooltip
12
+ */
13
+ align?: 'top' | 'top-left' | 'top-right' | 'bottom' | 'bottom-left' | 'bottom-right' | 'left' | 'right';
14
+ /**
15
+ * Specify a label to be read by screen readers on the containing textbox
16
+ * node
17
+ */
18
+ ['aria-label']?: string;
19
+ /**
20
+ * Deprecated, please use `aria-label` instead.
21
+ * Specify a label to be read by screen readers on the containing textbox
22
+ * node
23
+ */
24
+ ariaLabel?: string;
25
+ /**
26
+ * Specify an optional className to be applied to the container node
27
+ */
28
+ className?: string;
29
+ /**
30
+ * Specify the description for the Copy Button
31
+ */
32
+ copyButtonDescription?: string;
33
+ /**
34
+ * Optional text to copy. If not specified, the `children` node's `innerText`
35
+ * will be used as the copy value.
36
+ */
37
+ copyText?: string;
38
+ /**
39
+ * Specify whether or not the CodeSnippet should be disabled
40
+ */
41
+ disabled?: boolean;
42
+ /**
43
+ * Specify the string displayed when the snippet is copied
44
+ */
45
+ feedback?: string;
46
+ /**
47
+ * Specify the time it takes for the feedback message to timeout
48
+ */
49
+ feedbackTimeout?: number;
50
+ /**
51
+ * Specify whether or not a copy button should be used/rendered.
52
+ */
53
+ hideCopyButton?: boolean;
54
+ /**
55
+ * Specify whether you are using the light variant of the Code Snippet,
56
+ * typically used for inline snippet to display an alternate color
57
+ */
58
+ light?: boolean;
59
+ /**
60
+ * Specify the maximum number of rows to be shown when in collapsed view
61
+ */
62
+ maxCollapsedNumberOfRows?: number;
63
+ /**
64
+ * Specify the maximum number of rows to be shown when in expanded view
65
+ */
66
+ maxExpandedNumberOfRows?: number;
67
+ /**
68
+ * Specify the minimum number of rows to be shown when in collapsed view
69
+ */
70
+ minCollapsedNumberOfRows?: number;
71
+ /**
72
+ * Specify the minimum number of rows to be shown when in expanded view
73
+ */
74
+ minExpandedNumberOfRows?: number;
75
+ /**
76
+ * An optional handler to listen to the `onClick` even fired by the Copy
77
+ * Button
78
+ */
79
+ onClick?: (e: MouseEvent) => void;
80
+ /**
81
+ * Specify a string that is displayed when the Code Snippet has been
82
+ * interacted with to show more lines
83
+ */
84
+ showLessText?: string;
85
+ /**
86
+ * Specify a string that is displayed when the Code Snippet text is more
87
+ * than 15 lines
88
+ */
89
+ showMoreText?: string;
90
+ /**
91
+ * Provide the type of Code Snippet
92
+ */
93
+ type?: 'single' | 'inline' | 'multi';
94
+ /**
95
+ * Specify whether or not to wrap the text.
96
+ */
97
+ wrapText?: boolean;
98
+ }
99
+ declare function CodeSnippet({ align, className, type, children, disabled, feedback, feedbackTimeout, onClick, ['aria-label']: ariaLabel, ariaLabel: deprecatedAriaLabel, copyText, copyButtonDescription, light, showMoreText, showLessText, hideCopyButton, wrapText, maxCollapsedNumberOfRows, maxExpandedNumberOfRows, minCollapsedNumberOfRows, minExpandedNumberOfRows, ...rest }: PropsWithChildren<CodeSnippetProps>): import("react/jsx-runtime").JSX.Element;
100
+ declare namespace CodeSnippet {
101
+ var propTypes: {
102
+ /**
103
+ * Specify how the trigger should align with the tooltip
104
+ */
105
+ align: PropTypes.Requireable<string>;
106
+ /**
107
+ * Specify a label to be read by screen readers on the containing textbox
108
+ * node
109
+ */
110
+ "aria-label": PropTypes.Requireable<string>;
111
+ /**
112
+ * Deprecated, please use `aria-label` instead.
113
+ * Specify a label to be read by screen readers on the containing textbox
114
+ * node
115
+ */
116
+ ariaLabel: (props: any, propName: any, componentName: any, ...rest: any[]) => any;
117
+ /**
118
+ * Provide the content of your CodeSnippet as a node or string
119
+ */
120
+ children: PropTypes.Requireable<PropTypes.ReactNodeLike>;
121
+ /**
122
+ * Specify an optional className to be applied to the container node
123
+ */
124
+ className: PropTypes.Requireable<string>;
125
+ /**
126
+ * Specify the description for the Copy Button
127
+ */
128
+ copyButtonDescription: PropTypes.Requireable<string>;
129
+ /**
130
+ * Optional text to copy. If not specified, the `children` node's `innerText`
131
+ * will be used as the copy value.
132
+ */
133
+ copyText: PropTypes.Requireable<string>;
134
+ /**
135
+ * Specify whether or not the CodeSnippet should be disabled
136
+ */
137
+ disabled: PropTypes.Requireable<boolean>;
138
+ /**
139
+ * Specify the string displayed when the snippet is copied
140
+ */
141
+ feedback: PropTypes.Requireable<string>;
142
+ /**
143
+ * Specify the time it takes for the feedback message to timeout
144
+ */
145
+ feedbackTimeout: PropTypes.Requireable<number>;
146
+ /**
147
+ * Specify whether or not a copy button should be used/rendered.
148
+ */
149
+ hideCopyButton: PropTypes.Requireable<boolean>;
150
+ /**
151
+ * Specify whether you are using the light variant of the Code Snippet,
152
+ * typically used for inline snippet to display an alternate color
153
+ */
154
+ light: (props: any, propName: any, componentName: any, ...rest: any[]) => any;
155
+ /**
156
+ * Specify the maximum number of rows to be shown when in collapsed view
157
+ */
158
+ maxCollapsedNumberOfRows: PropTypes.Requireable<number>;
159
+ /**
160
+ * Specify the maximum number of rows to be shown when in expanded view
161
+ */
162
+ maxExpandedNumberOfRows: PropTypes.Requireable<number>;
163
+ /**
164
+ * Specify the minimum number of rows to be shown when in collapsed view
165
+ */
166
+ minCollapsedNumberOfRows: PropTypes.Requireable<number>;
167
+ /**
168
+ * Specify the minimum number of rows to be shown when in expanded view
169
+ */
170
+ minExpandedNumberOfRows: PropTypes.Requireable<number>;
171
+ /**
172
+ * An optional handler to listen to the `onClick` even fired by the Copy
173
+ * Button
174
+ */
175
+ onClick: PropTypes.Requireable<(...args: any[]) => any>;
176
+ /**
177
+ * Specify a string that is displayed when the Code Snippet has been
178
+ * interacted with to show more lines
179
+ */
180
+ showLessText: PropTypes.Requireable<string>;
181
+ /**
182
+ * Specify a string that is displayed when the Code Snippet text is more
183
+ * than 15 lines
184
+ */
185
+ showMoreText: PropTypes.Requireable<string>;
186
+ /**
187
+ * Provide the type of Code Snippet
188
+ */
189
+ type: PropTypes.Requireable<string>;
190
+ /**
191
+ * Specify whether or not to wrap the text.
192
+ */
193
+ wrapText: PropTypes.Requireable<boolean>;
194
+ };
195
+ }
196
+ export default CodeSnippet;
@@ -24,7 +24,7 @@ const rowHeightInPixels = 16;
24
24
  const defaultMaxCollapsedNumberOfRows = 15;
25
25
  const defaultMaxExpandedNumberOfRows = 0;
26
26
  const defaultMinCollapsedNumberOfRows = 3;
27
- const defaultMinExpandedNumberOfRows = 0;
27
+ const defaultMinExpandedNumberOfRows = 16;
28
28
  function CodeSnippet(_ref) {
29
29
  let {
30
30
  align = 'bottom',
@@ -55,9 +55,9 @@ function CodeSnippet(_ref) {
55
55
  const {
56
56
  current: uid
57
57
  } = useRef(uniqueId());
58
- const codeContentRef = useRef();
59
- const codeContainerRef = useRef();
60
- const innerCodeRef = useRef();
58
+ const codeContentRef = useRef(null);
59
+ const codeContainerRef = useRef(null);
60
+ const innerCodeRef = useRef(null);
61
61
  const [hasLeftOverflow, setHasLeftOverflow] = useState(false);
62
62
  const [hasRightOverflow, setHasRightOverflow] = useState(false);
63
63
  const getCodeRef = useCallback(() => {
@@ -66,15 +66,17 @@ function CodeSnippet(_ref) {
66
66
  }
67
67
  if (type === 'multi') {
68
68
  return codeContentRef;
69
+ } else {
70
+ return innerCodeRef;
69
71
  }
70
72
  }, [type]);
71
73
  const prefix = usePrefix();
72
74
  const getCodeRefDimensions = useCallback(() => {
73
75
  const {
74
- clientWidth: codeClientWidth,
75
- scrollLeft: codeScrollLeft,
76
- scrollWidth: codeScrollWidth
77
- } = getCodeRef().current;
76
+ clientWidth: codeClientWidth = 0,
77
+ scrollLeft: codeScrollLeft = 0,
78
+ scrollWidth: codeScrollWidth = 0
79
+ } = getCodeRef().current || {};
78
80
  return {
79
81
  horizontalOverflow: codeScrollWidth > codeClientWidth,
80
82
  codeClientWidth,
@@ -101,7 +103,7 @@ function CodeSnippet(_ref) {
101
103
  if (codeContentRef?.current && type === 'multi') {
102
104
  const {
103
105
  height
104
- } = innerCodeRef.current.getBoundingClientRect();
106
+ } = codeContentRef.current.getBoundingClientRect();
105
107
  if (maxCollapsedNumberOfRows > 0 && (maxExpandedNumberOfRows <= 0 || maxExpandedNumberOfRows > maxCollapsedNumberOfRows) && height > maxCollapsedNumberOfRows * rowHeightInPixels) {
106
108
  setShouldShowMoreLessBtn(true);
107
109
  } else {
@@ -115,13 +117,13 @@ function CodeSnippet(_ref) {
115
117
  handleScroll();
116
118
  }
117
119
  }
118
- }, [type, maxCollapsedNumberOfRows, maxExpandedNumberOfRows, minExpandedNumberOfRows, rowHeightInPixels]);
120
+ });
119
121
  useEffect(() => {
120
122
  handleScroll();
121
123
  }, [handleScroll]);
122
124
  const handleCopyClick = evt => {
123
125
  if (copyText || innerCodeRef?.current) {
124
- copy(copyText ?? innerCodeRef?.current?.innerText);
126
+ copy(copyText ?? innerCodeRef?.current?.innerText ?? '');
125
127
  }
126
128
  if (onClick) {
127
129
  onClick(evt);
@@ -159,7 +161,7 @@ function CodeSnippet(_ref) {
159
161
  ref: innerCodeRef
160
162
  }, children));
161
163
  }
162
- let containerStyle = {};
164
+ const containerStyle = {};
163
165
  if (type === 'multi') {
164
166
  const styles = {};
165
167
  if (expandedCode) {
@@ -185,16 +187,16 @@ function CodeSnippet(_ref) {
185
187
  className: codeSnippetClasses
186
188
  }), /*#__PURE__*/React__default.createElement("div", _extends({
187
189
  ref: codeContainerRef,
188
- role: type === 'single' || type === 'multi' ? 'textbox' : null,
189
- tabIndex: (type === 'single' || type === 'multi') && !disabled ? 0 : null,
190
+ role: type === 'single' || type === 'multi' ? 'textbox' : undefined,
191
+ tabIndex: (type === 'single' || type === 'multi') && !disabled ? 0 : undefined,
190
192
  className: `${prefix}--snippet-container`,
191
193
  "aria-label": deprecatedAriaLabel || ariaLabel || 'code-snippet',
192
- "aria-readonly": type === 'single' || type === 'multi' ? true : null,
193
- "aria-multiline": type === 'multi' ? true : null,
194
- onScroll: type === 'single' && handleScroll || null
194
+ "aria-readonly": type === 'single' || type === 'multi' ? true : undefined,
195
+ "aria-multiline": type === 'multi' ? true : undefined,
196
+ onScroll: type === 'single' && handleScroll || undefined
195
197
  }, containerStyle), /*#__PURE__*/React__default.createElement("pre", {
196
198
  ref: codeContentRef,
197
- onScroll: type === 'multi' && handleScroll || null
199
+ onScroll: type === 'multi' && handleScroll || undefined
198
200
  }, /*#__PURE__*/React__default.createElement("code", {
199
201
  ref: innerCodeRef
200
202
  }, children))), hasLeftOverflow && /*#__PURE__*/React__default.createElement("div", {
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Copyright IBM Corp. 2016, 2023
3
+ *
4
+ * This source code is licensed under the Apache-2.0 license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+ import CodeSnippet from './CodeSnippet';
8
+ export default CodeSnippet;
9
+ export { CodeSnippet };
10
+ export { default as CodeSnippetSkeleton } from './CodeSnippet.Skeleton';
@@ -6,7 +6,7 @@
6
6
  */
7
7
  import Downshift from 'downshift';
8
8
  import { ReactNodeLike } from 'prop-types';
9
- import { type ComponentProps, type ReactNode, type ComponentType, type ReactElement, type RefAttributes, type PropsWithChildren, type PropsWithoutRef, type InputHTMLAttributes, type MouseEvent } from 'react';
9
+ import { type ComponentProps, type ReactNode, type ComponentType, type ReactElement, type RefAttributes, type PropsWithChildren, type PropsWithRef, type InputHTMLAttributes, type MouseEvent } from 'react';
10
10
  import { ListBoxSize } from '../ListBox';
11
11
  type ExcludedAttributes = 'id' | 'onChange' | 'onClick' | 'type' | 'size';
12
12
  interface OnChangeData<ItemType> {
@@ -159,7 +159,7 @@ export interface ComboBoxProps<ItemType> extends Omit<InputHTMLAttributes<HTMLIn
159
159
  */
160
160
  warnText?: ReactNode;
161
161
  }
162
- type ComboboxComponentProps<ItemType> = PropsWithoutRef<PropsWithChildren<ComboBoxProps<ItemType>> & RefAttributes<HTMLInputElement>>;
162
+ type ComboboxComponentProps<ItemType> = PropsWithRef<PropsWithChildren<ComboBoxProps<ItemType>> & RefAttributes<HTMLInputElement>>;
163
163
  interface ComboBoxComponent {
164
164
  <ItemType>(props: ComboboxComponentProps<ItemType>): ReactElement | null;
165
165
  }