@antscorp/antsomi-ui 1.3.6-beta.4 → 1.3.6-beta.5
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/es/components/molecules/CodeStructure/CodeStructure.d.ts +21 -0
- package/es/components/molecules/CodeStructure/CodeStructure.js +39 -13
- package/es/components/molecules/CodeStructure/constants.js +4 -4
- package/es/components/molecules/CodeStructure/styled.d.ts +3 -0
- package/es/components/molecules/CodeStructure/styled.js +6 -0
- package/es/components/molecules/CodeStructure/type.d.ts +1 -2
- package/es/components/molecules/CodeStructure/type.js +0 -1
- package/es/components/molecules/CodeStructure/utils.js +3 -3
- package/package.json +1 -1
|
@@ -7,5 +7,26 @@ interface CodeStructureProps {
|
|
|
7
7
|
isError: boolean;
|
|
8
8
|
}) => void;
|
|
9
9
|
}
|
|
10
|
+
/**
|
|
11
|
+
* Component to configure the code structure for a pool rule.
|
|
12
|
+
*
|
|
13
|
+
* The component contains a form with fields for:
|
|
14
|
+
* - Prefix
|
|
15
|
+
* - Infix (character type, number of digits, number of letters, capitalization, character order)
|
|
16
|
+
* - Suffix
|
|
17
|
+
* - Separator
|
|
18
|
+
* - Quantity (number of codes per time)
|
|
19
|
+
* - Refill interval (manual or automatic)
|
|
20
|
+
* - Refill threshold (number of codes remaining)
|
|
21
|
+
* - Refill unit (codes or percent)
|
|
22
|
+
*
|
|
23
|
+
* The form also displays a preview of the generated code sample.
|
|
24
|
+
*
|
|
25
|
+
* The component calls the `onChange` callback with the updated form values and an `isError` flag
|
|
26
|
+
* indicating whether the form is valid or not.
|
|
27
|
+
*
|
|
28
|
+
* @param {CodeStructureProps} props The component props.
|
|
29
|
+
* @returns {React.ReactElement} The rendered component.
|
|
30
|
+
*/
|
|
10
31
|
export declare const CodeStructure: React.FC<CodeStructureProps>;
|
|
11
32
|
export {};
|
|
@@ -4,17 +4,39 @@ import { useEffect } from 'react';
|
|
|
4
4
|
import { Form, InputNumber, Radio, Select, Typography, Flex, Input, Row, Col } from 'antd';
|
|
5
5
|
import { useImmer } from 'use-immer';
|
|
6
6
|
import { translate, translations } from '@antscorp/antsomi-locales';
|
|
7
|
+
import { isEmpty } from 'lodash';
|
|
7
8
|
// Utils
|
|
8
9
|
import { calculateTotalCodes, generateCodeWithPrefixAndSuffix, generateRandomCodeWithConfig, } from './utils';
|
|
9
10
|
// Types
|
|
10
11
|
import { CapitalizationType, CharacterOrderType, CharacterType, RefillType, RefillUnitType, SeparatorType, } from './type';
|
|
11
12
|
// Constants
|
|
12
13
|
import { CAPITALIZATION_OPTIONS, CHARACTER_ORDER_OPTIONS, CHARACTER_TYPE_OPTIONS, REFILL_UNIT_OPTIONS, SEPARATOR_OPTIONS, } from './constants';
|
|
13
|
-
import { CodeStructureWrapper } from './styled';
|
|
14
|
+
import { BlockAbsolute, CodeStructureWrapper } from './styled';
|
|
14
15
|
import { useDebouncedCallbackV2 } from '@antscorp/antsomi-ui/es/hooks';
|
|
15
16
|
const { Title } = Typography;
|
|
17
|
+
/**
|
|
18
|
+
* Component to configure the code structure for a pool rule.
|
|
19
|
+
*
|
|
20
|
+
* The component contains a form with fields for:
|
|
21
|
+
* - Prefix
|
|
22
|
+
* - Infix (character type, number of digits, number of letters, capitalization, character order)
|
|
23
|
+
* - Suffix
|
|
24
|
+
* - Separator
|
|
25
|
+
* - Quantity (number of codes per time)
|
|
26
|
+
* - Refill interval (manual or automatic)
|
|
27
|
+
* - Refill threshold (number of codes remaining)
|
|
28
|
+
* - Refill unit (codes or percent)
|
|
29
|
+
*
|
|
30
|
+
* The form also displays a preview of the generated code sample.
|
|
31
|
+
*
|
|
32
|
+
* The component calls the `onChange` callback with the updated form values and an `isError` flag
|
|
33
|
+
* indicating whether the form is valid or not.
|
|
34
|
+
*
|
|
35
|
+
* @param {CodeStructureProps} props The component props.
|
|
36
|
+
* @returns {React.ReactElement} The rendered component.
|
|
37
|
+
*/
|
|
16
38
|
export const CodeStructure = ({ initialData, onChange }) => {
|
|
17
|
-
const { characterType = CharacterType.DIGIT_AND_LETTERS, digitalNumbers = 2, alphabetLetters = 3, capitalization = CapitalizationType.UPPERCASE, characterOrder = CharacterOrderType.RANDOM, separator = SeparatorType.UNDERSCORE, quantity =
|
|
39
|
+
const { characterType = CharacterType.DIGIT_AND_LETTERS, digitalNumbers = 2, alphabetLetters = 3, capitalization = CapitalizationType.UPPERCASE, characterOrder = CharacterOrderType.RANDOM, separator = SeparatorType.UNDERSCORE, quantity = 50, suffix = '', refillInterval = RefillType.MANUAL, prefix = '', refillThreshold = 10, refillUnit = RefillUnitType.CODES, } = initialData;
|
|
18
40
|
const [form] = Form.useForm();
|
|
19
41
|
const [state, setState] = useImmer({
|
|
20
42
|
codeSample: '',
|
|
@@ -42,7 +64,7 @@ export const CodeStructure = ({ initialData, onChange }) => {
|
|
|
42
64
|
draft.codeWithPrefixAndSuffix = value;
|
|
43
65
|
});
|
|
44
66
|
};
|
|
45
|
-
const debouncedOnChange = useDebouncedCallbackV2(onChange,
|
|
67
|
+
const debouncedOnChange = useDebouncedCallbackV2(onChange, 700);
|
|
46
68
|
const updateFormValues = async (fieldKeyChange, isError) => {
|
|
47
69
|
// Get all values from the form
|
|
48
70
|
const allValues = form.getFieldsValue();
|
|
@@ -110,28 +132,32 @@ export const CodeStructure = ({ initialData, onChange }) => {
|
|
|
110
132
|
updateFormValues(fieldKeyChange, isValidate);
|
|
111
133
|
}, children: [_jsx(Title, { level: 5, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE, 'Code Structure') }), _jsx(Form.Item, { label: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_PREFIX, 'Prefix'), name: "prefix", children: _jsx(Input, { placeholder: "", style: {
|
|
112
134
|
maxWidth: 465,
|
|
113
|
-
} }) }), _jsxs(Row, { children: [_jsx(Col, { span: 6, offset: 0, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_INFIX, 'Infix') }), _jsx(Col, { span: 16, offset: 0, children: _jsxs(Flex, { vertical: true, gap: 10, children: [_jsx(Row, { children: _jsx(Col, { offset: 0, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CHAC_TYPE, 'Character Type') }) }), _jsx(Form.Item, { name: "characterType", children: _jsx(Radio.Group, { options: CHARACTER_TYPE_OPTIONS }) })] }) })] }), _jsx(Row, { children: _jsx(Col, { offset: 6, children: _jsxs(Flex, { gap: 10, align: "center",
|
|
135
|
+
} }) }), _jsxs(Row, { children: [_jsx(Col, { span: 6, offset: 0, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_INFIX, 'Infix') }), _jsx(Col, { span: 16, offset: 0, children: _jsxs(Flex, { vertical: true, gap: 10, children: [_jsx(Row, { children: _jsx(Col, { offset: 0, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CHAC_TYPE, 'Character Type') }) }), _jsx(Form.Item, { name: "characterType", children: _jsx(Radio.Group, { options: CHARACTER_TYPE_OPTIONS }) })] }) })] }), _jsx(Row, { children: _jsx(Col, { offset: 6, children: _jsxs(Flex, { gap: 10, align: "center", style: {
|
|
136
|
+
position: 'relative',
|
|
137
|
+
}, children: [_jsx(Form.Item, { name: "digitalNumbers", rules: [{ required: true, message: `This field can't be empty` }], children: _jsx(InputNumber, { min: 1, max: 50, style: { width: '40px' } }) }), _jsx(BlockAbsolute, { children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CHAC_TYPE_DIG_NO, 'digital numbers') })] }) }) }), _jsx(Row, { children: _jsx(Col, { offset: 6, children: _jsxs(Flex, { gap: 10, align: "center", style: {
|
|
138
|
+
position: 'relative',
|
|
139
|
+
}, children: [_jsx(Form.Item, { name: "alphabetLetters", rules: [{ required: true, message: `This field can't be empty` }], children: _jsx(InputNumber, { min: 1, max: 50, style: { width: '40px' } }) }), _jsx(BlockAbsolute, { children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CHAC_TYPE_LET_NO, 'alphabet letters') })] }) }) }), _jsxs(Flex, { vertical: true, gap: 10, children: [_jsx(Row, { children: _jsx(Col, { offset: 6, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CAP, 'Letters Capitalization') }) }), _jsx(Form.Item, { label: _jsx("span", { children: "\u00A0" }), name: "capitalization", children: _jsx(Radio.Group, { options: CAPITALIZATION_OPTIONS }) })] }), _jsxs(Flex, { vertical: true, gap: 10, children: [_jsx(Row, { children: _jsx(Col, { offset: 6, children: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CHAC_ORDER, 'Character Order') }) }), _jsx(Form.Item, { label: _jsx("span", { children: "\u00A0" }), name: "characterOrder", children: _jsx(Radio.Group, { options: CHARACTER_ORDER_OPTIONS }) })] }), _jsx(Form.Item, { label: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_SUFFIX, 'Suffix'), name: "suffix", children: _jsx(Input, { placeholder: "", style: {
|
|
114
140
|
maxWidth: 465,
|
|
115
|
-
} }) }), _jsx(Form.Item, { label: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_SEPARATOR, 'Separator'), name: "separator", children: _jsx(Select, { options: SEPARATOR_OPTIONS, style: { width: '180px' } }) }), _jsxs(Row, { children: [_jsx(Col, { span: 6, children: _jsxs(Flex, { justify: "start", align: "center", gap: 5, children: [translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_QUANTITY, 'Quantity'), ' ', _jsx("span", { style: { color: 'red' }, children: "*" })] }) }), _jsx(Col, { children: _jsxs(Flex, { gap: 10, align: "center", children: [_jsx(Form.Item, { required: true, name: "quantity", rules: [{ required: true }], children: _jsx(InputNumber, { min: 1, max: 10000 }) }), _jsx(
|
|
141
|
+
} }) }), _jsx(Form.Item, { label: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_SEPARATOR, 'Separator'), name: "separator", children: _jsx(Select, { options: SEPARATOR_OPTIONS, style: { width: '180px' } }) }), _jsxs(Row, { children: [_jsx(Col, { span: 6, children: _jsxs(Flex, { justify: "start", align: "center", gap: 5, children: [translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_QUANTITY, 'Quantity'), ' ', _jsx("span", { style: { color: 'red' }, children: "*" })] }) }), _jsx(Col, { children: _jsxs(Flex, { gap: 10, align: "center", style: { position: 'relative' }, children: [_jsx(Form.Item, { required: true, name: "quantity", rules: [{ required: true, message: `This field can't be empty` }], children: _jsx(InputNumber, { min: 1, max: 10000 }) }), _jsx(BlockAbsolute, { left: 100, children: "code(s) per time" })] }) })] }), _jsxs(Form.Item, { label: translate(translations._ACT_PREVIEW, 'Preview'), children: ["Maximum of ", _jsx("b", { children: maxCodes.toLocaleString() }), " codes (sample", ' ', generateCodeWithPrefixAndSuffix(codeSample, form.getFieldValue('prefix'), form.getFieldValue('suffix'), form.getFieldValue('separator')), ") to be generated"] }), _jsx(Title, { level: 5, children: "Code Refill" }), _jsx(Form.Item, { label: "Refill Interval", name: "refillInterval", children: _jsxs(Radio.Group, { style: { display: 'flex', flexDirection: 'column', gap: '10px' }, onChange: e => {
|
|
142
|
+
if (e.target.value === 'manual' && isEmpty(form.getFieldValue('refillThreshold'))) {
|
|
143
|
+
form.setFieldsValue({ refillThreshold: 10 });
|
|
144
|
+
form.validateFields(['refillThreshold']);
|
|
145
|
+
}
|
|
146
|
+
}, children: [_jsx(Radio, { value: "manual", children: "Manual refill only" }), _jsx(Radio, { value: "auto", children: _jsxs(Flex, { gap: 10, align: "center", children: [_jsx(Typography.Text, { style: { whiteSpace: 'nowrap' }, children: "Add codes when less than" }), _jsx(Form.Item, { noStyle: true, shouldUpdate: true, children: ({ getFieldValue }) => {
|
|
116
147
|
const refillUnit = getFieldValue('refillUnit');
|
|
117
148
|
return (_jsx(Form.Item, { name: "refillThreshold", noStyle: true, rules: [
|
|
118
149
|
{ required: true, message: '' },
|
|
119
150
|
{
|
|
120
151
|
validator: (_, value) => {
|
|
121
152
|
if (refillUnit === RefillUnitType.PERCENT) {
|
|
122
|
-
if (value
|
|
123
|
-
|
|
124
|
-
}
|
|
125
|
-
}
|
|
126
|
-
else if (refillUnit === RefillUnitType.CODES) {
|
|
127
|
-
if (value < 0) {
|
|
128
|
-
return Promise.reject(new Error(''));
|
|
153
|
+
if (value > 100) {
|
|
154
|
+
form.setFieldsValue({ refillThreshold: 100 });
|
|
129
155
|
}
|
|
130
156
|
}
|
|
131
157
|
return Promise.resolve();
|
|
132
158
|
},
|
|
133
159
|
},
|
|
134
|
-
], children: _jsx(InputNumber, { min:
|
|
160
|
+
], children: _jsx(InputNumber, { min: 1, max: refillUnit === RefillUnitType.PERCENT ? 100 : undefined, style: { width: '63px' } }) }));
|
|
135
161
|
} }), _jsx(Form.Item, { noStyle: true, shouldUpdate: true, children: () => (_jsx(Form.Item, { name: "refillUnit", noStyle: true, rules: [
|
|
136
162
|
{ required: true, message: '' },
|
|
137
163
|
{
|
|
@@ -29,10 +29,10 @@ export const CAPITALIZATION_OPTIONS = [
|
|
|
29
29
|
value: CapitalizationType.LOWERCASE,
|
|
30
30
|
label: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CAP_LOW, 'lowercase'),
|
|
31
31
|
},
|
|
32
|
-
{
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
},
|
|
32
|
+
// {
|
|
33
|
+
// value: CapitalizationType.TITLE_CASE,
|
|
34
|
+
// label: translate(translations._POOL_RULE_SETTING_CODE_STRUCTURE_CAP_TITL, 'Title case'),
|
|
35
|
+
// },
|
|
36
36
|
];
|
|
37
37
|
export const CHARACTER_ORDER_OPTIONS = [
|
|
38
38
|
{
|
|
@@ -14,7 +14,6 @@ export var CapitalizationType;
|
|
|
14
14
|
(function (CapitalizationType) {
|
|
15
15
|
CapitalizationType["UPPERCASE"] = "upper";
|
|
16
16
|
CapitalizationType["LOWERCASE"] = "lower";
|
|
17
|
-
CapitalizationType["TITLE_CASE"] = "title";
|
|
18
17
|
})(CapitalizationType || (CapitalizationType = {}));
|
|
19
18
|
export var SeparatorType;
|
|
20
19
|
(function (SeparatorType) {
|
|
@@ -18,9 +18,9 @@ export const generateRandomCodeWithConfig = ({ characterType, digitalNumbers, al
|
|
|
18
18
|
else if (capitalization === CapitalizationType.LOWERCASE) {
|
|
19
19
|
letterPart = letterPart.toLowerCase();
|
|
20
20
|
}
|
|
21
|
-
else if (capitalization === CapitalizationType.TITLE_CASE && letterPart.length > 0) {
|
|
22
|
-
|
|
23
|
-
}
|
|
21
|
+
// } else if (capitalization === CapitalizationType.TITLE_CASE && letterPart.length > 0) {
|
|
22
|
+
// letterPart = letterPart.charAt(0).toUpperCase() + letterPart.slice(1).toLowerCase();
|
|
23
|
+
// }
|
|
24
24
|
// Order characters
|
|
25
25
|
let finalCode = '';
|
|
26
26
|
if (characterOrder === CharacterOrderType.RANDOM) {
|