@synerise/ds-color-picker 1.1.4 → 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.
package/CHANGELOG.md CHANGED
@@ -3,6 +3,25 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ ## [1.2.1](https://github.com/Synerise/synerise-design/compare/@synerise/ds-color-picker@1.2.0...@synerise/ds-color-picker@1.2.1) (2025-05-07)
7
+
8
+ **Note:** Version bump only for package @synerise/ds-color-picker
9
+
10
+
11
+
12
+
13
+
14
+ # [1.2.0](https://github.com/Synerise/synerise-design/compare/@synerise/ds-color-picker@1.1.4...@synerise/ds-color-picker@1.2.0) (2025-04-24)
15
+
16
+
17
+ ### Features
18
+
19
+ * **color-picker:** disabled / readonly / error props ([ac222a7](https://github.com/Synerise/synerise-design/commit/ac222a79aaf4ebb5af9908c8a898f019b1390488))
20
+
21
+
22
+
23
+
24
+
6
25
  ## [1.1.4](https://github.com/Synerise/synerise-design/compare/@synerise/ds-color-picker@1.1.3...@synerise/ds-color-picker@1.1.4) (2025-04-16)
7
26
 
8
27
  **Note:** Version bump only for package @synerise/ds-color-picker
package/README.md ADDED
@@ -0,0 +1,52 @@
1
+ ---
2
+ id: color-picker
3
+ title: ColorPicker
4
+ ---
5
+
6
+ ColorPicker UI Component
7
+
8
+ ## Installation
9
+
10
+ ```
11
+ npm i @synerise/ds-color-picker
12
+ or
13
+ yarn add @synerise/ds-color-picker
14
+ ```
15
+
16
+ ## Usage
17
+
18
+ ```
19
+ import ColorPicker from '@synerise/ds-color-picker'
20
+
21
+ <ColorPicker />
22
+
23
+ ```
24
+
25
+ ## Demo
26
+
27
+ <iframe src="/storybook-static/iframe.html?id=components-color-picker--default"></iframe>
28
+
29
+ ## API
30
+
31
+ #### ColorPicker
32
+
33
+ | Property | Description | Type | Default |
34
+ | ------------------ | --------------------------------------------------------------------------------------------------------------------------------- | ---------------------------------------------------- | ------- |
35
+ | maxWidth | Picker overlay max width | number | 228 |
36
+ | value | picker value | string | - |
37
+ | onChange | value change handler | (color: string) => void | - |
38
+ | colors | Array of color swatches to render | string[] | - |
39
+ | onSaveColors | change swatches handler | (colors: string[]) => void | - |
40
+ | infix | used for inlining implementation of other ways of selecting/showing color value (select with converting to other color notations) | (colorHooks?: Partial<ColorHookType>) => JSX.Element | - |
41
+ | maxSavedColors | max number of allowed swatches | number | - |
42
+ | tooltip | copy color tooltip text | { copy: string; copied: string; } | - |
43
+ | isShownSavedColors | controls rendering of swtches | boolean | - |
44
+ | size | different size overlay | 'S' / 'M' / 'L' | - |
45
+ | readOnly | renders readOnly styled input | boolean | - |
46
+ | disabled | renders disabled input | boolean | - |
47
+ | error | renders error styled input | boolean | - |
48
+ | errorText | renders error styled input and error message | string | - |
49
+ | description | renders description below trigger | string | - |
50
+ | placeholder | Input placeholder text | string | - |
51
+ | getPopupContainer | function to find DOM node in which the overlay should be rendered | (triggerNode: HTMLElement) => HTMLElement | - |
52
+ | inputProps | subset of InputProps - see ds-input | InputProps | - |
@@ -1,4 +1,4 @@
1
1
  import React from 'react';
2
2
  import { ColorPickerProps } from './ColorPicker.types';
3
- declare const ColorPicker: ({ maxWidth, value, onChange, colors, onSaveColors, infix, getPopupContainer, placeholder, inputProps, maxSavedColors, tooltip, isShownSavedColors, size, errorText, description, }: ColorPickerProps) => React.JSX.Element;
3
+ declare const ColorPicker: ({ maxWidth, value, onChange, colors, onSaveColors, infix, getPopupContainer, placeholder, inputProps, maxSavedColors, tooltip, isShownSavedColors, size, errorText, description, disabled, error, readOnly, }: ColorPickerProps) => React.JSX.Element;
4
4
  export default ColorPicker;
@@ -1,5 +1,5 @@
1
1
  function _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }
2
- import React from 'react';
2
+ import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react';
3
3
  import { HexColorPicker as ReactColorful } from 'react-colorful';
4
4
  import Divider from '@synerise/ds-divider';
5
5
  import Tags, { TagShape, Tag } from '@synerise/ds-tags';
@@ -9,7 +9,7 @@ import Tooltip from '@synerise/ds-tooltip';
9
9
  import Dropdown from '@synerise/ds-dropdown';
10
10
  import { useOnClickOutside, getPopupContainer as defaultGetPopupContainer } from '@synerise/ds-utils';
11
11
  import { isValidHexColor, isValidTextColor, convert3DigitHexTo6Digit, filterAlphanumeric, standardizeColor } from './utils';
12
- import ColorPickerStyles from './ColorPicker.styles';
12
+ import * as S from './ColorPicker.styles';
13
13
  var DEFAULT_MAX_WIDTH_PICKER = 228;
14
14
  var DEFAULT_COLOR = '#ffffff';
15
15
  var ColorPicker = function ColorPicker(_ref) {
@@ -34,29 +34,32 @@ var ColorPicker = function ColorPicker(_ref) {
34
34
  _ref$size = _ref.size,
35
35
  size = _ref$size === void 0 ? 'M' : _ref$size,
36
36
  errorText = _ref.errorText,
37
- description = _ref.description;
38
- var _React$useState = React.useState(value),
39
- colorTextInput = _React$useState[0],
40
- setColorTextInput = _React$useState[1];
41
- var _React$useState2 = React.useState(value),
42
- colorHexInput = _React$useState2[0],
43
- setColorHexInput = _React$useState2[1];
44
- var _React$useState3 = React.useState(value),
45
- lastValidHexColor = _React$useState3[0],
46
- setLastValidHexColor = _React$useState3[1];
47
- var _React$useState4 = React.useState(-1),
48
- pressed = _React$useState4[0],
49
- setPressed = _React$useState4[1];
50
- var _React$useState5 = React.useState(false),
51
- dropdownVisible = _React$useState5[0],
52
- setDropdownVisible = _React$useState5[1];
53
- var _React$useState6 = React.useState(colors),
54
- savedColors = _React$useState6[0],
55
- setSavedColors = _React$useState6[1];
56
- var _React$useState7 = React.useState(tooltip == null ? void 0 : tooltip.copy),
57
- tooltipText = _React$useState7[0],
58
- setTooltipText = _React$useState7[1];
59
- var onChangeTextColor = React.useCallback(function (colorValue) {
37
+ description = _ref.description,
38
+ disabled = _ref.disabled,
39
+ error = _ref.error,
40
+ readOnly = _ref.readOnly;
41
+ var _useState = useState(value),
42
+ colorTextInput = _useState[0],
43
+ setColorTextInput = _useState[1];
44
+ var _useState2 = useState(value),
45
+ colorHexInput = _useState2[0],
46
+ setColorHexInput = _useState2[1];
47
+ var _useState3 = useState(value),
48
+ lastValidHexColor = _useState3[0],
49
+ setLastValidHexColor = _useState3[1];
50
+ var _useState4 = useState(-1),
51
+ pressed = _useState4[0],
52
+ setPressed = _useState4[1];
53
+ var _useState5 = useState(false),
54
+ dropdownVisible = _useState5[0],
55
+ setDropdownVisible = _useState5[1];
56
+ var _useState6 = useState(colors),
57
+ savedColors = _useState6[0],
58
+ setSavedColors = _useState6[1];
59
+ var _useState7 = useState(tooltip == null ? void 0 : tooltip.copy),
60
+ tooltipText = _useState7[0],
61
+ setTooltipText = _useState7[1];
62
+ var onChangeTextColor = useCallback(function (colorValue) {
60
63
  setColorTextInput(colorValue);
61
64
  if (isValidTextColor(colorValue)) {
62
65
  var standardizedColor = standardizeColor(colorValue);
@@ -71,7 +74,7 @@ var ColorPicker = function ColorPicker(_ref) {
71
74
  }
72
75
  setPressed(-1);
73
76
  }, [onChange]);
74
- var onChangeHexColor = React.useCallback(function (colorValue) {
77
+ var onChangeHexColor = useCallback(function (colorValue) {
75
78
  setColorHexInput(colorValue);
76
79
  if (isValidHexColor(colorValue)) {
77
80
  var fullHexColor = convert3DigitHexTo6Digit(colorValue);
@@ -81,21 +84,21 @@ var ColorPicker = function ColorPicker(_ref) {
81
84
  }
82
85
  setPressed(-1);
83
86
  }, [onChange]);
84
- var onBlurHandler = React.useCallback(function () {
87
+ var onBlurHandler = useCallback(function () {
85
88
  setColorTextInput(lastValidHexColor);
86
89
  setColorHexInput(lastValidHexColor);
87
90
  }, [lastValidHexColor]);
88
- var onClickHandler = React.useCallback(function () {
91
+ var onClickHandler = useCallback(function () {
89
92
  setDropdownVisible(!dropdownVisible);
90
93
  }, [dropdownVisible]);
91
- var copyHandler = React.useCallback(function () {
94
+ var copyHandler = useCallback(function () {
92
95
  lastValidHexColor && copy(lastValidHexColor);
93
96
  setTooltipText(tooltip == null ? void 0 : tooltip.copied);
94
97
  setTimeout(function () {
95
98
  setTooltipText(tooltip == null ? void 0 : tooltip.copy);
96
99
  }, 3000);
97
100
  }, [lastValidHexColor, tooltip]);
98
- React.useEffect(function () {
101
+ useEffect(function () {
99
102
  if (value && (isValidHexColor(value) || isValidTextColor(value))) {
100
103
  onChangeTextColor(value);
101
104
  } else {
@@ -103,7 +106,7 @@ var ColorPicker = function ColorPicker(_ref) {
103
106
  }
104
107
  // eslint-disable-next-line react-hooks/exhaustive-deps
105
108
  }, []);
106
- var heightOfDropdown = React.useCallback(function () {
109
+ var heightOfDropdown = useCallback(function () {
107
110
  if (errorText || description) {
108
111
  if (errorText && description) {
109
112
  return -40;
@@ -112,7 +115,7 @@ var ColorPicker = function ColorPicker(_ref) {
112
115
  }
113
116
  return 4;
114
117
  }, [errorText, description]);
115
- var ref = React.useRef(null);
118
+ var ref = useRef(null);
116
119
  useOnClickOutside(ref, function () {
117
120
  setDropdownVisible(false);
118
121
  });
@@ -123,9 +126,12 @@ var ColorPicker = function ColorPicker(_ref) {
123
126
  return colorsArray;
124
127
  });
125
128
  };
126
- var swatchSection = /*#__PURE__*/React.createElement(ColorPickerStyles.SwatchSectionWrapper, null, /*#__PURE__*/React.createElement(Tooltip, {
129
+ var onChangeHandler = useCallback(function (event) {
130
+ onChangeTextColor(event.target.value);
131
+ }, [onChangeTextColor]);
132
+ var swatchSection = /*#__PURE__*/React.createElement(S.SwatchSectionWrapper, null, /*#__PURE__*/React.createElement(Tooltip, {
127
133
  title: "Save color swatch"
128
- }, /*#__PURE__*/React.createElement(ColorPickerStyles.AddColorButton, {
134
+ }, /*#__PURE__*/React.createElement(S.AddColorButton, {
129
135
  mode: "single-icon",
130
136
  type: "ghost",
131
137
  onClick: saveColor
@@ -145,7 +151,7 @@ var ColorPicker = function ColorPicker(_ref) {
145
151
  key: "color-" + i,
146
152
  name: /*#__PURE__*/React.createElement(Tooltip, {
147
153
  title: colorEntry
148
- }, /*#__PURE__*/React.createElement(ColorPickerStyles.TagDot, {
154
+ }, /*#__PURE__*/React.createElement(S.TagDot, {
149
155
  pressed: i === pressed
150
156
  })),
151
157
  color: colorEntry,
@@ -156,35 +162,58 @@ var ColorPicker = function ColorPicker(_ref) {
156
162
  };
157
163
  })
158
164
  }));
159
- var dropdown = /*#__PURE__*/React.createElement(ColorPickerStyles.Container, {
165
+ var dropdown = /*#__PURE__*/React.createElement(S.Container, {
160
166
  ref: ref,
161
167
  size: size
162
168
  }, /*#__PURE__*/React.createElement(ReactColorful, {
163
169
  color: lastValidHexColor,
164
170
  onChange: onChangeHexColor
165
- }), /*#__PURE__*/React.createElement(ColorPickerStyles.PrefixTag, {
171
+ }), /*#__PURE__*/React.createElement(S.PrefixTag, {
166
172
  height: isShownSavedColors,
167
173
  size: size
168
174
  }, /*#__PURE__*/React.createElement(Tag, {
169
175
  shape: TagShape.SINGLE_CHARACTER_SQUARE,
170
176
  color: lastValidHexColor
171
- })), /*#__PURE__*/React.createElement(ColorPickerStyles.SubContainer, {
177
+ })), /*#__PURE__*/React.createElement(S.SubContainer, {
172
178
  savedColors: isShownSavedColors
173
- }, /*#__PURE__*/React.createElement(ColorPickerStyles.ColorPickerInput, {
179
+ }, /*#__PURE__*/React.createElement(S.ColorPickerInput, {
174
180
  value: colorHexInput && filterAlphanumeric(colorHexInput),
175
- prefixel: /*#__PURE__*/React.createElement(ColorPickerStyles.PreffixWrapper, null, "#"),
181
+ prefixel: /*#__PURE__*/React.createElement(S.PreffixWrapper, null, "#"),
176
182
  onChange: function onChange(ev) {
177
183
  onChangeHexColor("#" + ev.target.value);
178
184
  },
179
185
  onBlur: onBlurHandler,
180
186
  placeholder: placeholder,
181
- icon1: tooltipText ? /*#__PURE__*/React.createElement(ColorPickerStyles.CopyIcon, {
187
+ icon1: tooltipText ? /*#__PURE__*/React.createElement(S.CopyIcon, {
182
188
  onClick: copyHandler,
183
189
  component: /*#__PURE__*/React.createElement(CopyClipboardM, null)
184
190
  }) : undefined,
185
191
  icon1Tooltip: tooltipText ? /*#__PURE__*/React.createElement("span", null, tooltipText) : undefined
186
192
  }), isShownSavedColors && /*#__PURE__*/React.createElement("div", null, /*#__PURE__*/React.createElement(Divider, null), swatchSection)));
187
- return /*#__PURE__*/React.createElement(React.Fragment, null, maxWidth && maxWidth >= DEFAULT_MAX_WIDTH_PICKER && /*#__PURE__*/React.createElement(ColorPickerStyles.ColorPickerModalStyle, {
193
+ var trigger = useMemo(function () {
194
+ var isClickable = !disabled && !readOnly;
195
+ return /*#__PURE__*/React.createElement(S.ColorPickerSelect, _extends({
196
+ "data-testid": "color-picker",
197
+ disabled: disabled,
198
+ readOnly: readOnly,
199
+ prefix: /*#__PURE__*/React.createElement(S.ColorTag, {
200
+ shape: TagShape.SINGLE_CHARACTER_ROUND,
201
+ color: lastValidHexColor,
202
+ disabled: false,
203
+ onClick: isClickable ? onClickHandler : undefined
204
+ }),
205
+ onClick: isClickable ? onClickHandler : undefined,
206
+ onChange: isClickable ? onChangeHandler : undefined,
207
+ onBlur: onBlurHandler,
208
+ placeholder: placeholder,
209
+ value: colorTextInput,
210
+ description: description,
211
+ errorText: errorText,
212
+ error: error
213
+ }, inputProps));
214
+ }, [disabled, error, readOnly, onClickHandler, onChangeHandler, onBlurHandler, lastValidHexColor, placeholder, colorTextInput, description, errorText, inputProps]);
215
+ if (readOnly || disabled) return trigger;
216
+ return /*#__PURE__*/React.createElement(React.Fragment, null, maxWidth && maxWidth >= DEFAULT_MAX_WIDTH_PICKER && /*#__PURE__*/React.createElement(S.ColorPickerModalStyle, {
188
217
  maxWidth: maxWidth
189
218
  }), /*#__PURE__*/React.createElement(Dropdown, {
190
219
  overlayClassName: "color-picker-overlay",
@@ -195,23 +224,6 @@ var ColorPicker = function ColorPicker(_ref) {
195
224
  overlay: dropdown,
196
225
  placement: "bottomLeft",
197
226
  getPopupContainer: getPopupContainer
198
- }, /*#__PURE__*/React.createElement(ColorPickerStyles.ColorPickerSelect, _extends({
199
- "data-testid": "color-picker",
200
- prefix: /*#__PURE__*/React.createElement(ColorPickerStyles.ColorTag, {
201
- shape: TagShape.SINGLE_CHARACTER_ROUND,
202
- color: lastValidHexColor,
203
- disabled: false,
204
- onClick: onClickHandler
205
- }),
206
- onClick: onClickHandler,
207
- onChange: function onChange(ev) {
208
- onChangeTextColor(ev.target.value);
209
- },
210
- onBlur: onBlurHandler,
211
- placeholder: placeholder,
212
- value: colorTextInput,
213
- description: description,
214
- errorText: errorText
215
- }, inputProps))));
227
+ }, trigger));
216
228
  };
217
229
  export default ColorPicker;
@@ -3,6 +3,12 @@ import Button from '@synerise/ds-button';
3
3
  export declare const TagDot: import("styled-components").StyledComponent<"div", any, {
4
4
  pressed?: boolean | undefined;
5
5
  }, never>;
6
+ export declare const Container: import("styled-components").StyledComponent<"div", any, {
7
+ size?: "S" | "M" | "L" | undefined;
8
+ }, never>;
9
+ export declare const SubContainer: import("styled-components").StyledComponent<"div", any, {
10
+ savedColors?: boolean | undefined;
11
+ }, never>;
6
12
  export declare const ColorTag: import("styled-components").StyledComponent<({ id, name, className, disabled, removable, image, shape, color, textColor, onRemove, onClick, prefixel, suffixel, texts, asPill, dashed, ...htmlAttributes }: import("@synerise/ds-tags").TagProps) => import("react").JSX.Element, any, {}, never>;
7
13
  export declare const AddColorButton: import("styled-components").StyledComponent<typeof Button, any, {}, never>;
8
14
  export declare const CopyIcon: import("styled-components").StyledComponent<({ name, component, className, ...rest }: import("@synerise/ds-icon").IconProps) => import("react").JSX.Element, any, {}, never>;
@@ -13,7 +13,7 @@ export var TagDot = styled.div.withConfig({
13
13
  return props.theme.palette.white;
14
14
  });
15
15
  var SIZE_DEFAULT = 168;
16
- var Container = styled.div.withConfig({
16
+ export var Container = styled.div.withConfig({
17
17
  displayName: "ColorPickerstyles__Container",
18
18
  componentId: "sc-1iu8b6j-1"
19
19
  })(["width:100%;@media (min-width:200px){min-width:200px;background-color:", ";}.react-colorful__last-control{margin:24px 56px 8px 17px;border-radius:4px;height:8px;}.react-colorful__saturation{border-bottom:0px;border-radius:4px 4px 0 0;height:96px;.react-colorful__interactive{width:100%;height:100%;}}&&& .ds-tag{width:16px;height:16px;border:1px solid ", ";margin:0 0 0 4px;&:hover{", "{display:flex;}}}.react-colorful__pointer{width:16px;height:16px;}.react-colorful{width:100%;height:", "px;}.react-colorful__hue-pointer{border:1px solid ", ";box-shadow:none !important;.react-colorful__pointer-fill{background-color:", " !important;}}.ant-divider-horizontal{margin:16px 0px;}", "{margin-bottom:-8px;}"], function (props) {
@@ -27,7 +27,7 @@ var Container = styled.div.withConfig({
27
27
  }, function (props) {
28
28
  return props.theme.palette.white;
29
29
  }, TagsStyles.Container);
30
- var SubContainer = styled.div.withConfig({
30
+ export var SubContainer = styled.div.withConfig({
31
31
  displayName: "ColorPickerstyles__SubContainer",
32
32
  componentId: "sc-1iu8b6j-2"
33
33
  })(["padding:8px 16px 16px;margin-bottom:", ";"], function (props) {
@@ -1,5 +1,6 @@
1
1
  /// <reference types="react" />
2
- import type { InputProps } from 'antd/lib/input';
2
+ import type { InputProps } from '@synerise/ds-input';
3
+ import type { FormFieldCommonProps } from '@synerise/ds-form-field';
3
4
  import { DropdownProps } from '@synerise/ds-dropdown';
4
5
  export type ColorHookType = {
5
6
  color: string;
@@ -22,13 +23,14 @@ export type ColorPickerProps = {
22
23
  */
23
24
  infix?: (colorHooks?: Partial<ColorHookType>) => JSX.Element;
24
25
  maxSavedColors?: number;
25
- inputProps?: Omit<InputProps, 'value' | 'onChange' | 'defaultValue'>;
26
+ inputProps?: Omit<InputProps, 'value' | 'onChange' | 'defaultValue' | 'placeholder' | 'disabled' | 'readOnly' | 'prefix' | keyof FormFieldCommonProps>;
26
27
  tooltip?: {
27
28
  copy: string;
28
29
  copied: string;
29
30
  };
30
31
  isShownSavedColors?: boolean;
31
32
  size?: 'S' | 'M' | 'L';
32
- errorText?: string;
33
- description?: string;
34
- } & Partial<Pick<HTMLInputElement, 'placeholder'>> & Partial<Pick<DropdownProps, 'getPopupContainer'>>;
33
+ error?: boolean;
34
+ disabled?: boolean;
35
+ readOnly?: boolean;
36
+ } & Pick<FormFieldCommonProps, 'description' | 'errorText'> & Partial<Pick<HTMLInputElement, 'placeholder'>> & Partial<Pick<DropdownProps, 'getPopupContainer'>>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@synerise/ds-color-picker",
3
- "version": "1.1.4",
3
+ "version": "1.2.1",
4
4
  "description": "Color-Picker Component for the Synerise Design System",
5
5
  "license": "ISC",
6
6
  "repository": "Synerise/synerise-design",
@@ -34,14 +34,14 @@
34
34
  ],
35
35
  "types": "dist/index.d.ts",
36
36
  "dependencies": {
37
- "@synerise/ds-button": "^1.1.4",
38
- "@synerise/ds-divider": "^1.0.5",
39
- "@synerise/ds-dropdown": "^1.0.5",
40
- "@synerise/ds-icon": "^1.4.0",
41
- "@synerise/ds-input": "^1.1.0",
42
- "@synerise/ds-tags": "^1.1.4",
43
- "@synerise/ds-tooltip": "^1.1.4",
44
- "@synerise/ds-utils": "^1.0.1",
37
+ "@synerise/ds-button": "^1.2.0",
38
+ "@synerise/ds-divider": "^1.0.7",
39
+ "@synerise/ds-dropdown": "^1.0.7",
40
+ "@synerise/ds-icon": "^1.4.2",
41
+ "@synerise/ds-input": "^1.1.2",
42
+ "@synerise/ds-tags": "^1.1.6",
43
+ "@synerise/ds-tooltip": "^1.1.6",
44
+ "@synerise/ds-utils": "^1.1.0",
45
45
  "copy-to-clipboard": "^3.3.1",
46
46
  "react-colorful": "^5.2.0"
47
47
  },
@@ -51,5 +51,5 @@
51
51
  "react": ">=16.9.0 <= 18.3.1",
52
52
  "styled-components": "^5.3.3"
53
53
  },
54
- "gitHead": "6735f9babfeef53122f54ca86cba5f581e8870d9"
54
+ "gitHead": "90af7549cf0f556340bdd0deec4bb59bacf3e95e"
55
55
  }