pixel-react 1.1.9 → 1.2.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (62) hide show
  1. package/lib/components/AppHeader/types.d.ts +7 -7
  2. package/lib/components/Drawer/Drawer.stories.d.ts +2 -0
  3. package/lib/components/Drawer/Types.d.ts +11 -0
  4. package/lib/components/Icon/Icon.stories.d.ts +1 -0
  5. package/lib/components/Icon/types.d.ts +1 -0
  6. package/lib/components/InputWithDropdown/types.d.ts +1 -1
  7. package/lib/components/LabelEditTextField/LabelEditTextField.d.ts +5 -0
  8. package/lib/components/LabelEditTextField/LabelEditTextField.stories.d.ts +11 -0
  9. package/lib/components/LabelEditTextField/index.d.ts +1 -0
  10. package/lib/components/LabelEditTextField/types.d.ts +38 -0
  11. package/lib/components/Select/Select.d.ts +1 -1
  12. package/lib/components/Select/components/Dropdown/Dropdown.d.ts +1 -1
  13. package/lib/components/Select/components/Dropdown/dropdownTypes.d.ts +2 -0
  14. package/lib/components/Select/types.d.ts +11 -4
  15. package/lib/components/Table/Table.d.ts +1 -1
  16. package/lib/components/Table/Table.stories.d.ts +2 -0
  17. package/lib/components/Table/Types.d.ts +16 -0
  18. package/lib/index.d.ts +92 -16
  19. package/lib/index.esm.js +399 -152
  20. package/lib/index.esm.js.map +1 -1
  21. package/lib/index.js +399 -151
  22. package/lib/index.js.map +1 -1
  23. package/lib/tsconfig.tsbuildinfo +1 -1
  24. package/lib/utils/getSelectOptionValue/getSelectOptionValue.d.ts +8 -0
  25. package/package.json +1 -1
  26. package/src/assets/Themes/BaseTheme.scss +10 -0
  27. package/src/assets/Themes/DarkTheme.scss +19 -7
  28. package/src/assets/icons/eye_closed.svg +3 -0
  29. package/src/components/AppHeader/AppHeader.scss +14 -3
  30. package/src/components/AppHeader/AppHeader.stories.tsx +28 -28
  31. package/src/components/AppHeader/AppHeader.tsx +11 -11
  32. package/src/components/AppHeader/types.ts +7 -7
  33. package/src/components/Button/Button.scss +1 -0
  34. package/src/components/Checkbox/Checkbox.tsx +1 -1
  35. package/src/components/Drawer/Drawer.scss +13 -10
  36. package/src/components/Drawer/Drawer.stories.tsx +28 -0
  37. package/src/components/Drawer/Drawer.tsx +30 -7
  38. package/src/components/Drawer/Types.ts +11 -0
  39. package/src/components/Icon/Icon.stories.tsx +27 -0
  40. package/src/components/Icon/Icon.tsx +5 -1
  41. package/src/components/Icon/Icons.scss +14 -2
  42. package/src/components/Icon/iconList.ts +2 -0
  43. package/src/components/Icon/types.ts +1 -0
  44. package/src/components/InputWithDropdown/types.ts +1 -1
  45. package/src/components/LabelEditTextField/LabelEditTextField.scss +85 -0
  46. package/src/components/LabelEditTextField/LabelEditTextField.stories.tsx +136 -0
  47. package/src/components/LabelEditTextField/LabelEditTextField.tsx +207 -0
  48. package/src/components/LabelEditTextField/index.ts +1 -0
  49. package/src/components/LabelEditTextField/types.ts +38 -0
  50. package/src/components/Modal/Modal.tsx +8 -1
  51. package/src/components/Modal/modal.scss +10 -2
  52. package/src/components/Select/Select.stories.tsx +5 -3
  53. package/src/components/Select/Select.tsx +13 -5
  54. package/src/components/Select/components/Dropdown/Dropdown.tsx +3 -1
  55. package/src/components/Select/components/Dropdown/dropdownTypes.ts +3 -0
  56. package/src/components/Select/types.ts +12 -5
  57. package/src/components/Table/Table.scss +16 -4
  58. package/src/components/Table/Table.stories.tsx +36 -12
  59. package/src/components/Table/Table.tsx +33 -16
  60. package/src/components/Table/Types.ts +121 -105
  61. package/src/index.ts +2 -0
  62. package/src/utils/getSelectOptionValue/getSelectOptionValue.ts +31 -0
@@ -30,6 +30,8 @@ const Drawer: FC<DrawerProps> = ({
30
30
  onCloseIconClick,
31
31
  customHeader,
32
32
  customFooter,
33
+ tertiaryButtonProps = { left: {}, right: {} },
34
+ zIndex = 999,
33
35
  }: DrawerProps) => {
34
36
  const [isExpanded, setIsExpanded] = useState(_isExpanded);
35
37
 
@@ -72,11 +74,16 @@ const Drawer: FC<DrawerProps> = ({
72
74
  className={classNames('ff-drawer', `ff-drawer--${drawerSize}`, {
73
75
  'ff-drawer--open': isOpen,
74
76
  })}
77
+ style={{ zIndex }}
75
78
  >
76
79
  {showHeader && (
77
- <div className="ff-drawer-header">
80
+ <div
81
+ className={classNames('ff-drawer-header', {
82
+ 'ff-custom-header': customHeader,
83
+ })}
84
+ >
78
85
  {customHeader ? (
79
- customHeader
86
+ <div className="ff-custom-header">{customHeader}</div>
80
87
  ) : (
81
88
  <div className="ff-drawer-action-section">
82
89
  <div className="ff-action-button">
@@ -106,9 +113,7 @@ const Drawer: FC<DrawerProps> = ({
106
113
  className="ff-expand-collapse-button"
107
114
  onClick={onClose}
108
115
  >
109
- {backButtonIcon ? (
110
- backButtonIcon
111
- ) : (
116
+ {backButtonIcon || (
112
117
  <Icon
113
118
  name="error"
114
119
  height={16}
@@ -124,7 +129,7 @@ const Drawer: FC<DrawerProps> = ({
124
129
  <div className="ff-close-icon">
125
130
  <Icon
126
131
  name="close"
127
- hoverEffect={false}
132
+ hoverEffect={true}
128
133
  onClick={onCloseIconClick || onClose}
129
134
  height={6}
130
135
  width={6}
@@ -146,7 +151,11 @@ const Drawer: FC<DrawerProps> = ({
146
151
  </div>
147
152
 
148
153
  {isFooterRequired && (
149
- <div className="ff-drawer-footer">
154
+ <div
155
+ className={classNames('ff-drawer-footer', {
156
+ 'ff-custom-footer': customFooter,
157
+ })}
158
+ >
150
159
  {customFooter || footerContent || (
151
160
  <>
152
161
  <div className="button-container">
@@ -166,8 +175,22 @@ const Drawer: FC<DrawerProps> = ({
166
175
  transparentBackground={true}
167
176
  />
168
177
  )}
178
+ {tertiaryButtonProps.left?.label && (
179
+ <Button
180
+ {...tertiaryButtonProps.left}
181
+ variant="tertiary"
182
+ transparentBackground={true}
183
+ />
184
+ )}
169
185
  </div>
170
186
  <div className="button-container">
187
+ {tertiaryButtonProps.right?.label && (
188
+ <Button
189
+ {...tertiaryButtonProps.right}
190
+ variant="tertiary"
191
+ transparentBackground={true}
192
+ />
193
+ )}
171
194
  {secondaryButtonProps.label && (
172
195
  <Button
173
196
  {...secondaryButtonProps}
@@ -109,4 +109,15 @@ export interface DrawerProps {
109
109
  * If provided, this will render in place of the default footer.
110
110
  */
111
111
  customFooter?: ReactNode;
112
+ /**
113
+ * Tertiary button properties (optional)
114
+ */
115
+ tertiaryButtonProps?: {
116
+ left?: BtnPropsCommon;
117
+ right?: BtnPropsCommon;
118
+ };
119
+ /**
120
+ * Custom z-index for the drawer
121
+ */
122
+ zIndex?: number;
112
123
  }
@@ -6,6 +6,12 @@ const meta: Meta<typeof Icon> = {
6
6
  title: 'Components/Icon',
7
7
  component: Icon,
8
8
  tags: ['autodocs'],
9
+ argTypes: {
10
+ variant: {
11
+ control: { type: 'select' },
12
+ options: ['light', 'dark'],
13
+ },
14
+ },
9
15
  };
10
16
 
11
17
  type Story = StoryObj<typeof Icon>;
@@ -34,4 +40,25 @@ export const AllIcons: Story = {
34
40
  },
35
41
  };
36
42
 
43
+ export const DarkVariantIcons: Story = {
44
+ args: {
45
+ name: 'hamburger_menu',
46
+ color: 'var(--ff-icon-color-dark-variant)',
47
+ variant: 'dark',
48
+ hoverEffect: true,
49
+ },
50
+ render: (args) => {
51
+ const backgroundColor = args.variant === 'dark' ? '#000' : '#fff';
52
+ const iconColor = args.variant === 'dark' ? 'var(--ff-icon-color-dark-variant)' : 'var(--brand-color)';
53
+
54
+ return (
55
+ <div style={{ backgroundColor, padding: '20px' }}>
56
+ <Icon {...args} color={iconColor} height={16} width={16} />
57
+ </div>
58
+ );
59
+ },
60
+ };
61
+
62
+
63
+
37
64
  export default meta;
@@ -15,6 +15,7 @@ const Icon = forwardRef<HTMLSpanElement, IconProps>(
15
15
  hoverEffect = false,
16
16
  className = '',
17
17
  disabled = false,
18
+ variant = "light",
18
19
  ...props
19
20
  },
20
21
  ref
@@ -28,6 +29,8 @@ const Icon = forwardRef<HTMLSpanElement, IconProps>(
28
29
  return null;
29
30
  }
30
31
 
32
+ const iconColor = variant === "dark" ? 'var(--ff-icon-color-dark-variant)' : color;
33
+
31
34
  return (
32
35
  <span
33
36
  ref={ref}
@@ -36,11 +39,12 @@ const Icon = forwardRef<HTMLSpanElement, IconProps>(
36
39
  className={classNames('ff-icon-container', {
37
40
  'ff-icon-click': !!hoverEffect,
38
41
  'ff-icon-disabled': disabled,
42
+ 'ff-icon-dark': variant === "dark",
39
43
  [className]: !!className,
40
44
  })}
41
45
  {...props}
42
46
  >
43
- <IconComponent height="100%" width="100%" style={{ color: color }} />
47
+ <IconComponent height="100%" width="100%" style={{ color: iconColor }} />
44
48
  </span>
45
49
  );
46
50
  }
@@ -1,13 +1,25 @@
1
-
2
1
  .ff-icon-container {
3
2
  display: flex;
4
3
  justify-content: center;
5
4
  align-items: center;
5
+ padding: 4px;
6
+ box-sizing: content-box;
7
+ &.ff-icon-dark {
8
+ background-color: var(--brand-color);
9
+ &.ff-icon-click {
10
+ &:hover {
11
+ border-radius: 4px;
12
+ background-color: white;
13
+ svg path {
14
+ fill: var(--brand-color);
15
+ }
16
+ }
17
+ }
18
+ }
6
19
  }
7
20
 
8
21
  .ff-icon-click {
9
22
  cursor: pointer;
10
- padding: 4px;
11
23
  box-sizing: content-box;
12
24
  &:hover {
13
25
  border-radius: 4px;
@@ -113,6 +113,7 @@ import NotificationIcon from '../../assets/icons/notification_icon.svg?react';
113
113
  import NLPHelpIcon from '../../assets/icons/nlp_help_icon.svg?react';
114
114
  import UpdateIcon from '../../assets/icons/update_icon.svg?react';
115
115
  import AddFile from '../../assets/icons/add_file.svg?react';
116
+ import EyeClosed from '../../assets/icons/eye_closed.svg?react';
116
117
 
117
118
  import CloneIcon from '../../assets/icons/clone_icon.svg?react';
118
119
  import MoveIcon from '../../assets/icons/move_icon.svg?react';
@@ -236,5 +237,6 @@ Components['linked_defects'] = LinkedDefects;
236
237
  Components['no_access_icon'] = NoAccessIcon;
237
238
  Components['full_access_icon'] = FullAccessIcon;
238
239
  Components['view_access_icon'] = ViewAccessIcon;
240
+ Components['eye_closed'] = EyeClosed;
239
241
 
240
242
  export default Components;
@@ -7,4 +7,5 @@ export interface IconProps {
7
7
  onClick?: (data?: any) => void;
8
8
  hoverEffect?: boolean;
9
9
  disabled?: boolean;
10
+ variant?: "dark" | "light";
10
11
  }
@@ -74,7 +74,7 @@ export interface InputWithDropdownProps {
74
74
  /**
75
75
  * onChange handler for dropdown changes
76
76
  */
77
- onDropdownChangeHandler?: (option: Option) => void;
77
+ onDropdownChangeHandler?: (option: any) => void;
78
78
 
79
79
  /**
80
80
  * onInputBlurHandler action for input field
@@ -0,0 +1,85 @@
1
+ @use '../../assets/styles/fonts' as *;
2
+
3
+ .ff-label-edit-text-field {
4
+ display: flex;
5
+ flex-direction: column;
6
+ position: relative;
7
+ width: 100%;
8
+ .ff-label-text-field {
9
+ display: flex;
10
+ gap: 10px;
11
+ }
12
+ .ff-label-text-field-with-dropdown,
13
+ .ff-label-text-field-without-dropdown {
14
+ position: relative;
15
+ display: flex;
16
+ align-items: center;
17
+ }
18
+ .ff-label {
19
+ position: absolute;
20
+ top: 0;
21
+ left: 10px;
22
+ transform: translateY(-50%);
23
+ transition: all 0.2s ease;
24
+ color: var(--label-edit-text-label-color);
25
+ background: var(--label-edit-text-background-color);
26
+ padding: 0 4px;
27
+ @extend .font-size-8;
28
+ }
29
+ .ff-textfield-label {
30
+ @extend .ff-label;
31
+ top: 5px;
32
+ }
33
+
34
+ .display-text {
35
+ padding: 4px;
36
+ border-radius: 4px;
37
+ cursor: pointer;
38
+ display: flex;
39
+ align-items: center;
40
+ }
41
+
42
+ .ff-text-field,
43
+ .dropdown {
44
+ border: 1px solid var(--label-edit-text-label-color);
45
+ outline: none;
46
+ width: fit-content;
47
+ @extend .fontSm;
48
+ }
49
+ .ff-text-field {
50
+ padding: 0 4px;
51
+ border-radius: 4px;
52
+ }
53
+ .ff-text-dropdown-field {
54
+ flex: 2;
55
+ border: 1px solid var(--label-edit-text-label-color);
56
+ border-radius: 4px 0 0 4px;
57
+ border-right: none;
58
+ border-width: thin;
59
+ padding-left: 5px;
60
+ @extend .fontSm;
61
+ &:focus-visible {
62
+ outline: none;
63
+ }
64
+ }
65
+ .dropdown {
66
+ border-radius: 0 4px 4px 0;
67
+ flex: 1;
68
+ height: inherit;
69
+ }
70
+
71
+ .ff-icon-container {
72
+ display: flex;
73
+ gap: 8px;
74
+ align-items: center;
75
+ .confirm-icon,
76
+ .cancel-icon {
77
+ cursor: pointer;
78
+ }
79
+ }
80
+
81
+ .error-text {
82
+ margin: 0;
83
+ color: var(--label-edit-error-text);
84
+ }
85
+ }
@@ -0,0 +1,136 @@
1
+ import type { Meta, StoryObj } from '@storybook/react';
2
+ import LabelEditTextField from './LabelEditTextField';
3
+ import '../../assets/styles/_colors.scss';
4
+ import './LabelEditTextField.scss';
5
+
6
+ const meta: Meta<typeof LabelEditTextField> = {
7
+ title: 'Components/LabelEditTextField',
8
+ component: LabelEditTextField,
9
+ parameters: {
10
+ layout: 'centered',
11
+ },
12
+ tags: ['autodocs'],
13
+ };
14
+
15
+ type Story = StoryObj<typeof LabelEditTextField>;
16
+ export const textField: Story = {
17
+ render: () => {
18
+ const handleConfirmAction = (inputValue: string) => {
19
+ //DEMO: we are getting that value from LabelEditTextField
20
+ console.log('Confirmed input value:', inputValue);
21
+ };
22
+ return (
23
+ <LabelEditTextField
24
+ label="Add Module"
25
+ text="Verify The Function Of Categories For" //it might be state
26
+ confirmIcon={{
27
+ name: 'update_icon',
28
+ onClick: () => {},
29
+ }}
30
+ cancelIcon={{
31
+ name: 'close',
32
+ onClick: () => {},
33
+ }}
34
+ width="300px"
35
+ height="22px"
36
+ confirmAction={handleConfirmAction}
37
+ />
38
+ );
39
+ },
40
+ };
41
+ export const textFieldWithOutLabel: Story = {
42
+ render: () => {
43
+ const handleConfirmAction = (inputValue: string) => {
44
+ //DEMO: we are getting that value from LabelEditTextField
45
+ console.log('Confirmed input value:', inputValue);
46
+ };
47
+ return (
48
+ <LabelEditTextField
49
+ text="Verify The Function Of Categories For" //it might be state
50
+ confirmIcon={{
51
+ name: 'update_icon',
52
+ onClick: () => {},
53
+ }}
54
+ cancelIcon={{
55
+ name: 'close',
56
+ onClick: () => {},
57
+ }}
58
+ width="300px"
59
+ height="22px"
60
+ confirmAction={handleConfirmAction}
61
+ />
62
+ );
63
+ },
64
+ };
65
+ export const textFieldWithDropdown: Story = {
66
+ render: () => {
67
+ const handleConfirmAction = (inputValue: string, dropdownValue: string) => {
68
+ //DEMO: we are getting that value from LabelEditTextField
69
+ console.log(
70
+ 'Confirmed input value and dropdown value:',
71
+ inputValue,
72
+ dropdownValue
73
+ );
74
+ };
75
+ return (
76
+ <LabelEditTextField
77
+ label="Add Module"
78
+ text="Verify The Function Of Categories For"
79
+ confirmIcon={{
80
+ name: 'update_icon',
81
+ onClick: () => {},
82
+ }}
83
+ cancelIcon={{
84
+ name: 'close',
85
+ onClick: () => {},
86
+ }}
87
+ variant="textFieldWithDropdown"
88
+ dropdownData={[
89
+ { id: 1, value: 'web', label: 'Web & Mobile' },
90
+ { id: 2, value: 'desktop', label: 'Desktop' },
91
+ ]}
92
+ width="300px"
93
+ height="22px"
94
+ confirmAction={handleConfirmAction}
95
+ />
96
+ );
97
+ },
98
+ };
99
+ export const textFieldWithHighlight: Story = {
100
+ render: () => {
101
+ const handleConfirmAction = (inputValue: string, dropdownValue: string) => {
102
+ //DEMO: we are getting that value from LabelEditTextField
103
+
104
+ console.log(
105
+ 'Confirmed input value and dropdown value:',
106
+ inputValue,
107
+ dropdownValue
108
+ );
109
+ };
110
+ return (
111
+ <LabelEditTextField
112
+ label="Add Module"
113
+ text="Verify The Function Of Categories For"
114
+ highlightText="The Function"
115
+ confirmIcon={{
116
+ name: 'update_icon',
117
+ onClick: () => {},
118
+ }}
119
+ cancelIcon={{
120
+ name: 'close',
121
+ onClick: () => {},
122
+ }}
123
+ variant="textFieldWithDropdown"
124
+ dropdownData={[
125
+ { id: 1, value: 'web', label: 'Web & Mobile' },
126
+ { id: 2, value: 'desktop', label: 'Desktop' },
127
+ ]}
128
+ width="400px"
129
+ height="22px"
130
+ confirmAction={handleConfirmAction}
131
+ />
132
+ );
133
+ },
134
+ };
135
+
136
+ export default meta;
@@ -0,0 +1,207 @@
1
+ import React, { useState, useRef, useEffect, FC } from 'react';
2
+ import './LabelEditTextField.scss';
3
+ import { LabelEditTextFieldTypes } from './types';
4
+ import Typography from '../Typography';
5
+ import HighlightText from '../HighlightText';
6
+ import Icon from '../Icon';
7
+
8
+ const getErrorMessage = (
9
+ inputValue: string,
10
+ text: string,
11
+ customError?: string
12
+ ): string => {
13
+ if (inputValue === text) {
14
+ return 'No changes were made.';
15
+ } else if (!inputValue) {
16
+ return 'Text is required';
17
+ } else if (inputValue.length < 3) {
18
+ return 'Please enter at least 3 characters.';
19
+ } else if (customError) {
20
+ return customError;
21
+ }
22
+ return '';
23
+ };
24
+ const LabelEditTextField: FC<LabelEditTextFieldTypes> = ({
25
+ label,
26
+ text,
27
+ highlightText,
28
+ customError,
29
+ confirmIcon,
30
+ cancelIcon,
31
+ variant = 'textField',
32
+ dropdownData = [],
33
+ width = '300px',
34
+ height = '22px',
35
+ confirmAction,
36
+ }) => {
37
+ const [isEditing, setIsEditing] = useState(false);
38
+ const [inputValue, setInputValue] = useState(text);
39
+ const [dropdownValue, setDropdownValue] = useState(
40
+ dropdownData[0]?.value ?? ''
41
+ );
42
+ const [showError, setShowError] = useState('');
43
+ const [isTextFieldModified, setIsTextFieldModified] = useState(false);
44
+ const [isDropdownModified, setIsDropdownModified] = useState(false);
45
+ const containerRef = useRef<HTMLDivElement | null>(null);
46
+ const cancelRef = useRef<HTMLDivElement | null>(null); // New ref for cancel icon
47
+
48
+ const handleDoubleClick = () => {
49
+ setIsEditing(true);
50
+ setShowError('');
51
+ };
52
+
53
+ const handleConfirm = () => {
54
+ const errorMessage = getErrorMessage(inputValue, text, customError);
55
+
56
+ if (errorMessage && isEditing) {
57
+ setShowError(errorMessage);
58
+ } else {
59
+ setIsEditing(false);
60
+ setShowError('');
61
+ if (confirmAction) confirmAction(inputValue, dropdownValue);
62
+ }
63
+ };
64
+
65
+ const handleCancel = () => {
66
+ setInputValue(text);
67
+ setDropdownValue(dropdownData[0]?.value ?? '');
68
+ setIsEditing(false);
69
+ setShowError('');
70
+ setIsTextFieldModified(false);
71
+ setIsDropdownModified(false);
72
+ };
73
+
74
+ const handleTextFieldChange = (e: React.ChangeEvent<HTMLInputElement>) => {
75
+ setInputValue(e.target.value);
76
+ setIsTextFieldModified(true);
77
+ setShowError('');
78
+ };
79
+
80
+ const handleDropdownChange = (e: React.ChangeEvent<HTMLSelectElement>) => {
81
+ setDropdownValue(e.target.value);
82
+ setIsDropdownModified(true);
83
+ setShowError('');
84
+ };
85
+
86
+ const handleBlur = (e: MouseEvent) => {
87
+ if (
88
+ containerRef.current &&
89
+ !containerRef.current.contains(e.target as Node) &&
90
+ cancelRef.current !== e.target // Exclude clicks on cancel icon
91
+ ) {
92
+ const errorMessage = getErrorMessage(inputValue, text, customError);
93
+
94
+ if (errorMessage && isEditing) {
95
+ setShowError(errorMessage);
96
+ } else {
97
+ setIsEditing(false);
98
+ setShowError('');
99
+ }
100
+ }
101
+ };
102
+
103
+ useEffect(() => {
104
+ document.addEventListener('click', handleBlur);
105
+ return () => {
106
+ document.removeEventListener('click', handleBlur);
107
+ };
108
+ }, [inputValue]);
109
+
110
+ return (
111
+ <div
112
+ className="ff-label-edit-text-field"
113
+ ref={containerRef}
114
+ style={{ width }}
115
+ >
116
+ {isEditing ? (
117
+ <div className="ff-label-text-field">
118
+ {variant === 'textFieldWithDropdown' ? (
119
+ <div
120
+ className={`ff-label-text-field-with-dropdown ${
121
+ isEditing ? 'open' : ''
122
+ }`}
123
+ style={{ height }}
124
+ >
125
+ <input
126
+ type="text"
127
+ value={inputValue}
128
+ onChange={handleTextFieldChange}
129
+ className={`ff-text-dropdown-field ${
130
+ isTextFieldModified ? 'modified' : ''
131
+ }`}
132
+ placeholder=" "
133
+ style={{
134
+ width,
135
+ }}
136
+ />
137
+ {label && <label className="ff-label">{label}</label>}
138
+ <select
139
+ value={dropdownValue}
140
+ onChange={handleDropdownChange}
141
+ className={`dropdown ${isDropdownModified ? 'modified' : ''}`}
142
+ >
143
+ {dropdownData.map((item) => (
144
+ <option key={item.id} value={item.value}>
145
+ {item.label}
146
+ </option>
147
+ ))}
148
+ </select>
149
+ </div>
150
+ ) : (
151
+ <div className="ff-label-text-field-without-dropdown">
152
+ <input
153
+ type="text"
154
+ value={inputValue}
155
+ onChange={handleTextFieldChange}
156
+ className={`ff-text-field ${
157
+ isTextFieldModified ? 'modified' : ''
158
+ }`}
159
+ placeholder=" "
160
+ style={{ width, height }}
161
+ />
162
+ <label className="ff-textfield-label">{label}</label>
163
+ </div>
164
+ )}
165
+ <div className="ff-icon-container">
166
+ {confirmIcon && (
167
+ <Icon
168
+ color="var(--label-edit-confirm-icon)"
169
+ height={20}
170
+ width={20}
171
+ name={confirmIcon.name}
172
+ className="confirm-icon"
173
+ onClick={handleConfirm}
174
+ />
175
+ )}
176
+ {cancelIcon && (
177
+ <Icon
178
+ color="var(--label-edit-cancel-icon)"
179
+ height={12}
180
+ width={20}
181
+ name={cancelIcon.name}
182
+ className="cancel-icon"
183
+ onClick={handleCancel}
184
+ ref={cancelRef}
185
+ />
186
+ )}
187
+ </div>
188
+ </div>
189
+ ) : (
190
+ <span
191
+ className="display-text"
192
+ onDoubleClick={handleDoubleClick}
193
+ role="button"
194
+ >
195
+ <HighlightText text={inputValue} highlight={highlightText} />
196
+ </span>
197
+ )}
198
+ {showError && isEditing && (
199
+ <Typography as="p" fontSize={8} className="error-text">
200
+ {showError}
201
+ </Typography>
202
+ )}
203
+ </div>
204
+ );
205
+ };
206
+
207
+ export default LabelEditTextField;
@@ -0,0 +1 @@
1
+ export { default } from './LabelEditTextField';
@@ -0,0 +1,38 @@
1
+ export interface IconProps {
2
+ /** Name of the icon to be displayed. */
3
+ name: string;
4
+ /** Optional click handler function for the icon. */
5
+ onClick?: () => void;
6
+ }
7
+ export interface DropdownOption {
8
+ /** Unique identifier for the dropdown option. */
9
+ id: number;
10
+ /** Value associated with the dropdown option. */
11
+ value: string;
12
+ /** Label displayed for the dropdown option. */
13
+ label: string;
14
+ }
15
+ export interface LabelEditTextFieldTypes {
16
+ /** Label text displayed above the input field. */
17
+ label?: string;
18
+ /** Initial text displayed in the input field. */
19
+ text: string;
20
+ /** Text to be highlighted within the displayed text, if provided. */
21
+ highlightText?: string;
22
+ /** Custom error message to be displayed, if applicable. */
23
+ customError?: string;
24
+ /** Confirm icon properties including icon name and click handler. */
25
+ confirmIcon?: IconProps;
26
+ /** Cancel icon properties including icon name and click handler. */
27
+ cancelIcon?: IconProps;
28
+ /** Type of input field - standard text field or text field with a dropdown. */
29
+ variant?: 'textFieldWithDropdown' | 'textField';
30
+ /** Array of dropdown options used if the dropdown variant is selected. */
31
+ dropdownData?: DropdownOption[];
32
+ /** Width of the input field component. */
33
+ width?: string;
34
+ /** Height of the input field component. */
35
+ height?: string;
36
+ /** Function called when confirming input changes, with input and dropdown values as arguments. */
37
+ confirmAction?: (inputValue: string, dropdownValue: string) => void;
38
+ }