pixel-react 1.1.9 → 1.2.1

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 (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
+ }