@momo-kits/foundation 0.89.4-rc.1 → 0.89.4-rc.2
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/Application/StackScreen.tsx +13 -2
- package/Application/utils.tsx +36 -1
- package/Button/index.tsx +40 -14
- package/CheckBox/index.tsx +44 -20
- package/CheckBox/types.ts +4 -0
- package/IconButton/index.tsx +33 -7
- package/Input/Input.tsx +39 -4
- package/Input/InputDropDown.tsx +28 -4
- package/Input/InputMoney.tsx +38 -4
- package/Input/InputOTP.tsx +28 -7
- package/Input/InputSearch.tsx +55 -26
- package/Input/index.tsx +11 -0
- package/Radio/index.tsx +41 -18
- package/Radio/types.ts +5 -0
- package/Switch/index.tsx +31 -14
- package/Switch/types.ts +4 -0
- package/package.json +1 -1
|
@@ -5,6 +5,10 @@ import {ApplicationContext, MiniAppContext} from './index';
|
|
|
5
5
|
import {GridSystem} from '../Layout';
|
|
6
6
|
import {useHeaderHeight} from '@react-navigation/stack';
|
|
7
7
|
|
|
8
|
+
const {
|
|
9
|
+
ScreenContext,
|
|
10
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
11
|
+
|
|
8
12
|
const StackScreen: React.FC<ScreenParams> = props => {
|
|
9
13
|
const {theme, showGrid, navigator} = useContext(ApplicationContext);
|
|
10
14
|
const context = useContext(MiniAppContext);
|
|
@@ -61,10 +65,17 @@ const StackScreen: React.FC<ScreenParams> = props => {
|
|
|
61
65
|
}, []);
|
|
62
66
|
|
|
63
67
|
return (
|
|
64
|
-
|
|
68
|
+
<ScreenContext.Provider
|
|
69
|
+
value={{
|
|
70
|
+
...context,
|
|
71
|
+
screenName: Component.name,
|
|
72
|
+
autoTracking: (data: any) => {
|
|
73
|
+
navigator?.maxApi?.dispatchFunction?.('autoTracking', data);
|
|
74
|
+
},
|
|
75
|
+
}}>
|
|
65
76
|
<Component heightHeader={heightHeader} {...params} />
|
|
66
77
|
{showGrid && <GridSystem />}
|
|
67
|
-
|
|
78
|
+
</ScreenContext.Provider>
|
|
68
79
|
);
|
|
69
80
|
};
|
|
70
81
|
|
package/Application/utils.tsx
CHANGED
|
@@ -148,4 +148,39 @@ const getOptions = (params: NavigationOptions, theme: Theme) => {
|
|
|
148
148
|
};
|
|
149
149
|
};
|
|
150
150
|
|
|
151
|
-
|
|
151
|
+
const formatComponentName= (word: string) =>{
|
|
152
|
+
const accentsMap = {
|
|
153
|
+
'a': 'á|à|ả|ã|ạ|â|ấ|ầ|ẩ|ẫ|ậ|ă|ắ|ằ|ẳ|ẵ|ặ',
|
|
154
|
+
'A': 'Á|À|Ả|Ã|Ạ|Â|Ấ|Ầ|Ẩ|Ẫ|Ậ|Ă|Ắ|Ằ|Ẳ|Ẵ|Ặ',
|
|
155
|
+
'e': 'é|è|ẻ|ẽ|ẹ|ê|ế|ề|ể|ễ|ệ',
|
|
156
|
+
'E': 'É|È|Ẻ|Ẽ|Ẹ|Ê|Ế|Ề|Ể|Ễ|Ệ',
|
|
157
|
+
'i': 'í|ì|ỉ|ĩ|ị',
|
|
158
|
+
'I': 'Í|Ì|Ỉ|Ĩ|Ị',
|
|
159
|
+
'o': 'ó|ò|ỏ|õ|ọ|ô|ố|ồ|ổ|ỗ|ộ|ơ|ớ|ờ|ở|ỡ|ợ',
|
|
160
|
+
'O': 'Ó|Ò|Ỏ|Õ|Ọ|Ô|Ố|Ồ|Ổ|Ỗ|Ộ|Ơ|Ớ|Ờ|Ở|Ỡ|Ợ',
|
|
161
|
+
'u': 'ú|ù|ủ|ũ|ụ|ư|ứ|ừ|ử|ữ|ự',
|
|
162
|
+
'U': 'Ú|Ù|Ủ|Ũ|Ụ|Ư|Ứ|Ừ|Ử|Ữ|Ự',
|
|
163
|
+
'y': 'ý|ỳ|ỷ|ỹ|ỵ',
|
|
164
|
+
'Y': 'Ý|Ỳ|Ỷ|Ỹ|Ỵ',
|
|
165
|
+
'd': 'đ',
|
|
166
|
+
'D': 'Đ'
|
|
167
|
+
};
|
|
168
|
+
|
|
169
|
+
for (const [nonAccent, accentGroup] of Object.entries(accentsMap)) {
|
|
170
|
+
const accents = new RegExp(accentGroup, 'g');
|
|
171
|
+
word = word.replace(accents, nonAccent);
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
word = word.replace(/\s+/g, '_').toLowerCase();
|
|
175
|
+
|
|
176
|
+
return word;
|
|
177
|
+
}
|
|
178
|
+
|
|
179
|
+
const formatNameLength = (name: string) =>{
|
|
180
|
+
let formattedName = name
|
|
181
|
+
if (formattedName.length > 100) {
|
|
182
|
+
formattedName = formattedName.substring(0, 100);
|
|
183
|
+
}
|
|
184
|
+
return formattedName
|
|
185
|
+
}
|
|
186
|
+
export {getStackOptions, getDialogOptions, getModalOptions, getOptions, formatComponentName, formatNameLength};
|
package/Button/index.tsx
CHANGED
|
@@ -6,7 +6,6 @@ import {
|
|
|
6
6
|
TouchableOpacityProps,
|
|
7
7
|
View,
|
|
8
8
|
} from 'react-native';
|
|
9
|
-
|
|
10
9
|
import LinearGradient from 'react-native-linear-gradient';
|
|
11
10
|
import {ApplicationContext} from '../Application';
|
|
12
11
|
import {Text} from '../Text';
|
|
@@ -15,6 +14,11 @@ import {Colors, Spacing} from '../Consts';
|
|
|
15
14
|
import styles from './styles';
|
|
16
15
|
import {Icon} from '../Icon';
|
|
17
16
|
import {Loader} from '../Loader';
|
|
17
|
+
import {formatComponentName} from "../Application/utils";
|
|
18
|
+
|
|
19
|
+
const {
|
|
20
|
+
ScreenContext,
|
|
21
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
18
22
|
|
|
19
23
|
const AnimationLinear = Animated.createAnimatedComponent(LinearGradient);
|
|
20
24
|
|
|
@@ -70,6 +74,10 @@ export interface ButtonProps extends TouchableOpacityProps {
|
|
|
70
74
|
* A callback function that is called when the button is pressed.
|
|
71
75
|
*/
|
|
72
76
|
onPress: () => void;
|
|
77
|
+
|
|
78
|
+
params?: any;
|
|
79
|
+
|
|
80
|
+
componentId?: string;
|
|
73
81
|
}
|
|
74
82
|
|
|
75
83
|
const Button: FC<ButtonProps> = ({
|
|
@@ -82,6 +90,8 @@ const Button: FC<ButtonProps> = ({
|
|
|
82
90
|
loading = false,
|
|
83
91
|
title = 'Button',
|
|
84
92
|
onPress,
|
|
93
|
+
params,
|
|
94
|
+
componentId,
|
|
85
95
|
...rest
|
|
86
96
|
}) => {
|
|
87
97
|
const {theme, config} = useContext(ApplicationContext);
|
|
@@ -94,6 +104,8 @@ const Button: FC<ButtonProps> = ({
|
|
|
94
104
|
end: {x: 0, y: 0.5},
|
|
95
105
|
};
|
|
96
106
|
}
|
|
107
|
+
|
|
108
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
97
109
|
const getSizeStyle = () => {
|
|
98
110
|
const styleSheet: {[key: string]: any} = styles;
|
|
99
111
|
return styleSheet[size ?? 'small'];
|
|
@@ -289,21 +301,35 @@ const Button: FC<ButtonProps> = ({
|
|
|
289
301
|
};
|
|
290
302
|
|
|
291
303
|
const activeOpacity = type === 'disabled' ? 0.75 : 0.5;
|
|
304
|
+
const button_name = formatComponentName(title)
|
|
292
305
|
|
|
293
306
|
return (
|
|
294
|
-
<
|
|
295
|
-
{
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
+
<ScreenContext.Provider
|
|
308
|
+
value={{
|
|
309
|
+
...screenInfo,
|
|
310
|
+
componentName: 'Button',
|
|
311
|
+
params: {
|
|
312
|
+
...params,
|
|
313
|
+
button_name
|
|
314
|
+
},
|
|
315
|
+
state: loading ? "loading" : type === 'disabled' ? 'disabled' : 'enabled',
|
|
316
|
+
componentId,
|
|
317
|
+
action: 'click',
|
|
318
|
+
}}>
|
|
319
|
+
<TouchableOpacity
|
|
320
|
+
{...rest}
|
|
321
|
+
activeOpacity={activeOpacity}
|
|
322
|
+
onPress={onPressButton}
|
|
323
|
+
style={buttonStyle}>
|
|
324
|
+
{renderLeading()}
|
|
325
|
+
{renderTitle()}
|
|
326
|
+
{renderTrailing()}
|
|
327
|
+
{gradientPros && (
|
|
328
|
+
<AnimationLinear {...gradientPros} style={styles.gradientView} />
|
|
329
|
+
)}
|
|
330
|
+
{gradientPros && <View style={styles.strokeView} />}
|
|
331
|
+
</TouchableOpacity>
|
|
332
|
+
</ScreenContext.Provider>
|
|
307
333
|
);
|
|
308
334
|
};
|
|
309
335
|
|
package/CheckBox/index.tsx
CHANGED
|
@@ -5,6 +5,11 @@ import styles from './styles';
|
|
|
5
5
|
import {ApplicationContext} from '../Application';
|
|
6
6
|
import {Text} from '../Text';
|
|
7
7
|
import {Icon} from '../Icon';
|
|
8
|
+
import {formatNameLength} from '../Application/utils';
|
|
9
|
+
|
|
10
|
+
const {
|
|
11
|
+
ScreenContext,
|
|
12
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
8
13
|
|
|
9
14
|
const CheckBox: FC<CheckBoxProps> = ({
|
|
10
15
|
value,
|
|
@@ -13,8 +18,11 @@ const CheckBox: FC<CheckBoxProps> = ({
|
|
|
13
18
|
style,
|
|
14
19
|
label,
|
|
15
20
|
indeterminate,
|
|
21
|
+
params,
|
|
22
|
+
componentId,
|
|
16
23
|
}) => {
|
|
17
24
|
const {theme} = useContext(ApplicationContext);
|
|
25
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
18
26
|
const haveValue = value || indeterminate;
|
|
19
27
|
const iconSource = indeterminate ? 'ic_minus' : 'ic_checked';
|
|
20
28
|
let borderColor = theme.colors.text.default;
|
|
@@ -34,27 +42,43 @@ const CheckBox: FC<CheckBoxProps> = ({
|
|
|
34
42
|
}
|
|
35
43
|
}
|
|
36
44
|
|
|
45
|
+
const component_name = formatNameLength(label || '');
|
|
46
|
+
|
|
37
47
|
return (
|
|
38
|
-
<
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
48
|
+
<ScreenContext.Provider
|
|
49
|
+
value={{
|
|
50
|
+
...screenInfo,
|
|
51
|
+
componentName: 'Button',
|
|
52
|
+
params: {
|
|
53
|
+
...params,
|
|
54
|
+
component_name,
|
|
55
|
+
},
|
|
56
|
+
state: disabled ? 'disabled' : 'filled',
|
|
57
|
+
componentId,
|
|
58
|
+
componentValue: indeterminate ? 'indetermine' : value,
|
|
59
|
+
action: 'click',
|
|
60
|
+
}}>
|
|
61
|
+
<TouchableOpacity
|
|
62
|
+
activeOpacity={0.8}
|
|
63
|
+
onPress={() => onChange?.(!value)}
|
|
64
|
+
disabled={disabled}
|
|
65
|
+
style={[style, styles.container]}>
|
|
66
|
+
<View
|
|
67
|
+
style={[
|
|
68
|
+
{borderColor, backgroundColor, borderWidth: 1},
|
|
69
|
+
styles.checkbox,
|
|
70
|
+
]}>
|
|
71
|
+
{haveValue && (
|
|
72
|
+
<Icon
|
|
73
|
+
color={theme.colors.background.surface}
|
|
74
|
+
size={20}
|
|
75
|
+
source={iconSource}
|
|
76
|
+
/>
|
|
77
|
+
)}
|
|
78
|
+
</View>
|
|
79
|
+
{!!label && <Text typography={'body_default_regular'}>{label}</Text>}
|
|
80
|
+
</TouchableOpacity>
|
|
81
|
+
</ScreenContext.Provider>
|
|
58
82
|
);
|
|
59
83
|
};
|
|
60
84
|
|
package/CheckBox/types.ts
CHANGED
package/IconButton/index.tsx
CHANGED
|
@@ -9,6 +9,11 @@ import {ApplicationContext} from '../Application';
|
|
|
9
9
|
import {Colors} from '../Consts';
|
|
10
10
|
import {Icon} from '../Icon';
|
|
11
11
|
import styles from './styles';
|
|
12
|
+
import {formatComponentName} from "../Application/utils";
|
|
13
|
+
|
|
14
|
+
const {
|
|
15
|
+
ScreenContext,
|
|
16
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
12
17
|
|
|
13
18
|
export interface IconButtonProps extends TouchableOpacityProps {
|
|
14
19
|
/**
|
|
@@ -26,6 +31,10 @@ export interface IconButtonProps extends TouchableOpacityProps {
|
|
|
26
31
|
* Optional. Defines the size of the IconButton.
|
|
27
32
|
*/
|
|
28
33
|
size?: 'large' | 'small';
|
|
34
|
+
|
|
35
|
+
params?: any;
|
|
36
|
+
|
|
37
|
+
componentId?: string;
|
|
29
38
|
}
|
|
30
39
|
|
|
31
40
|
const IconButton: React.FC<IconButtonProps> = ({
|
|
@@ -33,9 +42,12 @@ const IconButton: React.FC<IconButtonProps> = ({
|
|
|
33
42
|
icon,
|
|
34
43
|
size,
|
|
35
44
|
onPress,
|
|
45
|
+
params,
|
|
46
|
+
componentId,
|
|
36
47
|
...rest
|
|
37
48
|
}) => {
|
|
38
49
|
const {theme} = useContext(ApplicationContext);
|
|
50
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
39
51
|
|
|
40
52
|
/**
|
|
41
53
|
* get size icon button
|
|
@@ -119,15 +131,29 @@ const IconButton: React.FC<IconButtonProps> = ({
|
|
|
119
131
|
const activeOpacity = type === 'disabled' ? 0.75 : 0.5;
|
|
120
132
|
const buttonStyle = StyleSheet.flatten([getTypeStyle(), getSizeStyle()]);
|
|
121
133
|
const iconSize = size === 'small' ? 16 : 24;
|
|
134
|
+
const icon_name = formatComponentName(icon)
|
|
122
135
|
|
|
123
136
|
return (
|
|
124
|
-
<
|
|
125
|
-
{
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
137
|
+
<ScreenContext.Provider
|
|
138
|
+
value={{
|
|
139
|
+
...screenInfo,
|
|
140
|
+
componentName: 'IconButton',
|
|
141
|
+
params: {
|
|
142
|
+
...params,
|
|
143
|
+
icon_name
|
|
144
|
+
},
|
|
145
|
+
state: type === 'disabled' ? 'disabled' : 'enabled',
|
|
146
|
+
componentId,
|
|
147
|
+
action: 'click',
|
|
148
|
+
}}>
|
|
149
|
+
<TouchableOpacity
|
|
150
|
+
{...rest}
|
|
151
|
+
activeOpacity={activeOpacity}
|
|
152
|
+
onPress={onPressButton}
|
|
153
|
+
style={buttonStyle}>
|
|
154
|
+
<Icon size={iconSize} source={icon} color={getIconColor()} />
|
|
155
|
+
</TouchableOpacity>
|
|
156
|
+
</ScreenContext.Provider>
|
|
131
157
|
);
|
|
132
158
|
};
|
|
133
159
|
|
package/Input/Input.tsx
CHANGED
|
@@ -13,6 +13,11 @@ import {InputProps} from './index';
|
|
|
13
13
|
import {Icon} from '../Icon';
|
|
14
14
|
import {checkTyping} from './utils';
|
|
15
15
|
import {Loader} from '../Loader';
|
|
16
|
+
import {formatComponentName} from '../Application/utils';
|
|
17
|
+
|
|
18
|
+
const {
|
|
19
|
+
ScreenContext,
|
|
20
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
16
21
|
|
|
17
22
|
const Input = forwardRef(
|
|
18
23
|
(
|
|
@@ -39,6 +44,8 @@ const Input = forwardRef(
|
|
|
39
44
|
onPressIcon,
|
|
40
45
|
secureTextEntry,
|
|
41
46
|
style,
|
|
47
|
+
params,
|
|
48
|
+
componentId,
|
|
42
49
|
...props
|
|
43
50
|
}: InputProps,
|
|
44
51
|
ref,
|
|
@@ -48,6 +55,7 @@ const Input = forwardRef(
|
|
|
48
55
|
const [haveValue, setHaveValue] = useState(!!value || !!props.defaultValue);
|
|
49
56
|
const [secureTextInput, setSecureTextInput] = useState(secureTextEntry);
|
|
50
57
|
const inputRef = (ref as React.RefObject<TextInput>) ?? useRef<TextInput>();
|
|
58
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
51
59
|
|
|
52
60
|
const onClearText = () => {
|
|
53
61
|
inputRef?.current?.clear();
|
|
@@ -180,11 +188,38 @@ const Input = forwardRef(
|
|
|
180
188
|
);
|
|
181
189
|
};
|
|
182
190
|
|
|
191
|
+
let inputState = 'active';
|
|
192
|
+
|
|
193
|
+
if (value && value?.length > 0) {
|
|
194
|
+
inputState = 'filled';
|
|
195
|
+
}
|
|
196
|
+
if (errorMessage && errorMessage?.length > 0) {
|
|
197
|
+
inputState = 'error';
|
|
198
|
+
}
|
|
199
|
+
|
|
200
|
+
if (disabled) {
|
|
201
|
+
inputState = 'disabled';
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
const component_name = formatComponentName(floatingValue || '');
|
|
205
|
+
|
|
183
206
|
return (
|
|
184
|
-
<
|
|
185
|
-
{
|
|
186
|
-
|
|
187
|
-
|
|
207
|
+
<ScreenContext.Provider
|
|
208
|
+
value={{
|
|
209
|
+
...screenInfo,
|
|
210
|
+
componentName: 'Input',
|
|
211
|
+
params: {
|
|
212
|
+
...params,
|
|
213
|
+
component_name,
|
|
214
|
+
},
|
|
215
|
+
state: inputState,
|
|
216
|
+
componentId,
|
|
217
|
+
}}>
|
|
218
|
+
<View style={[style, styles.wrapper]}>
|
|
219
|
+
{renderInputView()}
|
|
220
|
+
<ErrorView errorMessage={errorMessage} errorSpacing={errorSpacing} />
|
|
221
|
+
</View>
|
|
222
|
+
</ScreenContext.Provider>
|
|
188
223
|
);
|
|
189
224
|
},
|
|
190
225
|
);
|
package/Input/InputDropDown.tsx
CHANGED
|
@@ -7,6 +7,11 @@ import {InputDropDownProps} from './index';
|
|
|
7
7
|
import {Icon} from '../Icon';
|
|
8
8
|
import {Loader} from '../Loader';
|
|
9
9
|
import {Styles} from '../Consts';
|
|
10
|
+
import {formatComponentName} from '../Application/utils';
|
|
11
|
+
|
|
12
|
+
const {
|
|
13
|
+
ScreenContext,
|
|
14
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
10
15
|
|
|
11
16
|
const InputDropDown = ({
|
|
12
17
|
value,
|
|
@@ -26,10 +31,13 @@ const InputDropDown = ({
|
|
|
26
31
|
leadingIcon,
|
|
27
32
|
leadingIconColor,
|
|
28
33
|
style,
|
|
34
|
+
params,
|
|
35
|
+
componentId,
|
|
29
36
|
...props
|
|
30
37
|
}: InputDropDownProps) => {
|
|
31
38
|
const {theme} = useContext(ApplicationContext);
|
|
32
39
|
const full = !!value || !!placeholder;
|
|
40
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
33
41
|
|
|
34
42
|
const renderIcon = (color: string | undefined) => {
|
|
35
43
|
if (loading) {
|
|
@@ -103,11 +111,27 @@ const InputDropDown = ({
|
|
|
103
111
|
);
|
|
104
112
|
};
|
|
105
113
|
|
|
114
|
+
const button_name = formatComponentName(floatingValue || '');
|
|
115
|
+
|
|
106
116
|
return (
|
|
107
|
-
<
|
|
108
|
-
{
|
|
109
|
-
|
|
110
|
-
|
|
117
|
+
<ScreenContext.Provider
|
|
118
|
+
value={{
|
|
119
|
+
...screenInfo,
|
|
120
|
+
componentName: 'InputOTP',
|
|
121
|
+
params: {
|
|
122
|
+
...params,
|
|
123
|
+
button_name,
|
|
124
|
+
},
|
|
125
|
+
state: 'enabled',
|
|
126
|
+
componentId,
|
|
127
|
+
}}>
|
|
128
|
+
<TouchableOpacity
|
|
129
|
+
onPress={onPress}
|
|
130
|
+
style={[style, full && styles.wrapper]}>
|
|
131
|
+
{renderInputView()}
|
|
132
|
+
<ErrorView errorMessage={errorMessage} errorSpacing={errorSpacing} />
|
|
133
|
+
</TouchableOpacity>
|
|
134
|
+
</ScreenContext.Provider>
|
|
111
135
|
);
|
|
112
136
|
};
|
|
113
137
|
|
package/Input/InputMoney.tsx
CHANGED
|
@@ -18,6 +18,11 @@ import {ErrorView, FloatingView, getBorderColor, getSizeStyle} from './common';
|
|
|
18
18
|
import {InputMoneyProps} from './index';
|
|
19
19
|
import {Icon} from '../Icon';
|
|
20
20
|
import {formatMoneyToNumber, formatNumberToMoney} from './utils';
|
|
21
|
+
import {formatComponentName} from '../Application/utils';
|
|
22
|
+
|
|
23
|
+
const {
|
|
24
|
+
ScreenContext,
|
|
25
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
21
26
|
|
|
22
27
|
const InputMoney = forwardRef(
|
|
23
28
|
(
|
|
@@ -36,7 +41,9 @@ const InputMoney = forwardRef(
|
|
|
36
41
|
required = false,
|
|
37
42
|
errorSpacing,
|
|
38
43
|
style,
|
|
44
|
+
params,
|
|
39
45
|
defaultValue = '',
|
|
46
|
+
componentId,
|
|
40
47
|
...props
|
|
41
48
|
}: InputMoneyProps,
|
|
42
49
|
ref,
|
|
@@ -44,6 +51,7 @@ const InputMoney = forwardRef(
|
|
|
44
51
|
const {theme} = useContext(ApplicationContext);
|
|
45
52
|
const [focused, setFocused] = useState(false);
|
|
46
53
|
const inputRef = (ref as React.RefObject<TextInput>) ?? useRef<TextInput>();
|
|
54
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
47
55
|
|
|
48
56
|
const validateText = (text: string) => {
|
|
49
57
|
const valueFormat = formatMoneyToNumber(text, 'đ');
|
|
@@ -151,11 +159,37 @@ const InputMoney = forwardRef(
|
|
|
151
159
|
);
|
|
152
160
|
};
|
|
153
161
|
|
|
162
|
+
let inputState = 'active';
|
|
163
|
+
|
|
164
|
+
if (value && value?.length > 0) {
|
|
165
|
+
inputState = 'filled';
|
|
166
|
+
}
|
|
167
|
+
if (errorMessage && errorMessage?.length > 0) {
|
|
168
|
+
inputState = 'error';
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
if (disabled) {
|
|
172
|
+
inputState = 'disabled';
|
|
173
|
+
}
|
|
174
|
+
const component_name = formatComponentName(floatingValue || '');
|
|
175
|
+
|
|
154
176
|
return (
|
|
155
|
-
<
|
|
156
|
-
{
|
|
157
|
-
|
|
158
|
-
|
|
177
|
+
<ScreenContext.Provider
|
|
178
|
+
value={{
|
|
179
|
+
...screenInfo,
|
|
180
|
+
componentName: 'InputMoney',
|
|
181
|
+
params: {
|
|
182
|
+
...params,
|
|
183
|
+
component_name,
|
|
184
|
+
},
|
|
185
|
+
state: inputState,
|
|
186
|
+
componentId,
|
|
187
|
+
}}>
|
|
188
|
+
<View style={[style, styles.wrapper]}>
|
|
189
|
+
{renderInputView()}
|
|
190
|
+
<ErrorView errorMessage={errorMessage} errorSpacing={errorSpacing} />
|
|
191
|
+
</View>
|
|
192
|
+
</ScreenContext.Provider>
|
|
159
193
|
);
|
|
160
194
|
},
|
|
161
195
|
);
|
package/Input/InputOTP.tsx
CHANGED
|
@@ -21,6 +21,11 @@ import styles from './styles';
|
|
|
21
21
|
import {ErrorView, getBorderColor} from './common';
|
|
22
22
|
import {ApplicationContext} from '../Application';
|
|
23
23
|
import {Spacing} from '../Consts';
|
|
24
|
+
import {formatComponentName} from '../Application/utils';
|
|
25
|
+
|
|
26
|
+
const {
|
|
27
|
+
ScreenContext,
|
|
28
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
24
29
|
|
|
25
30
|
const OTPCaret: FC<CaretProps> = ({index, length}) => {
|
|
26
31
|
const DURATION = 300;
|
|
@@ -78,7 +83,9 @@ const InputOTP = forwardRef(
|
|
|
78
83
|
onFocus,
|
|
79
84
|
onBlur,
|
|
80
85
|
dataType = 'number',
|
|
86
|
+
params,
|
|
81
87
|
style,
|
|
88
|
+
componentId,
|
|
82
89
|
...props
|
|
83
90
|
}: InputOTPProps,
|
|
84
91
|
ref,
|
|
@@ -88,6 +95,7 @@ const InputOTP = forwardRef(
|
|
|
88
95
|
const [focused, setFocused] = useState(false);
|
|
89
96
|
const inputRef = useRef<TextInput>(null);
|
|
90
97
|
const {theme} = useContext(ApplicationContext);
|
|
98
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
91
99
|
|
|
92
100
|
useImperativeHandle(ref, () => ({
|
|
93
101
|
onChangeText: (text: string) => {
|
|
@@ -219,15 +227,28 @@ const InputOTP = forwardRef(
|
|
|
219
227
|
</View>
|
|
220
228
|
);
|
|
221
229
|
};
|
|
230
|
+
const component_name = formatComponentName(floatingValue || '');
|
|
222
231
|
|
|
223
232
|
return (
|
|
224
|
-
<
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
233
|
+
<ScreenContext.Provider
|
|
234
|
+
value={{
|
|
235
|
+
...screenInfo,
|
|
236
|
+
componentName: 'InputOTP',
|
|
237
|
+
params: {
|
|
238
|
+
...params,
|
|
239
|
+
component_name,
|
|
240
|
+
},
|
|
241
|
+
state: 'enabled',
|
|
242
|
+
componentId,
|
|
243
|
+
}}>
|
|
244
|
+
<TouchableOpacity
|
|
245
|
+
activeOpacity={1}
|
|
246
|
+
onPress={onFocusInput}
|
|
247
|
+
style={[style, styles.otpWrapper]}>
|
|
248
|
+
{renderInputView()}
|
|
249
|
+
<ErrorView errorMessage={errorMessage} errorSpacing={errorSpacing} />
|
|
250
|
+
</TouchableOpacity>
|
|
251
|
+
</ScreenContext.Provider>
|
|
231
252
|
);
|
|
232
253
|
},
|
|
233
254
|
);
|
package/Input/InputSearch.tsx
CHANGED
|
@@ -13,6 +13,10 @@ import {Icon} from '../Icon';
|
|
|
13
13
|
import {Text} from '../Text';
|
|
14
14
|
import {checkTyping} from './utils';
|
|
15
15
|
|
|
16
|
+
const {
|
|
17
|
+
ScreenContext,
|
|
18
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
19
|
+
|
|
16
20
|
const InputSearch = forwardRef(
|
|
17
21
|
(
|
|
18
22
|
{
|
|
@@ -29,6 +33,8 @@ const InputSearch = forwardRef(
|
|
|
29
33
|
style,
|
|
30
34
|
defaultValue,
|
|
31
35
|
onPressButtonText,
|
|
36
|
+
params,
|
|
37
|
+
componentId,
|
|
32
38
|
...props
|
|
33
39
|
}: InputSearchProps,
|
|
34
40
|
ref,
|
|
@@ -37,6 +43,7 @@ const InputSearch = forwardRef(
|
|
|
37
43
|
const [focused, setFocused] = useState(false);
|
|
38
44
|
const [haveValue, setHaveValue] = useState(!!value || !!defaultValue);
|
|
39
45
|
const inputRef = (ref as React.RefObject<TextInput>) ?? useRef<TextInput>();
|
|
46
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
40
47
|
|
|
41
48
|
const _onFocus = (e: NativeSyntheticEvent<TextInputFocusEventData>) => {
|
|
42
49
|
setFocused(true);
|
|
@@ -116,34 +123,56 @@ const InputSearch = forwardRef(
|
|
|
116
123
|
</View>
|
|
117
124
|
);
|
|
118
125
|
};
|
|
126
|
+
|
|
127
|
+
let inputState = 'empty';
|
|
128
|
+
|
|
129
|
+
if (focused) {
|
|
130
|
+
inputState = 'focus';
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
if (value && value?.length > 0) {
|
|
134
|
+
inputState = 'filled';
|
|
135
|
+
}
|
|
136
|
+
|
|
119
137
|
return (
|
|
120
|
-
<
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
+
<ScreenContext.Provider
|
|
139
|
+
value={{
|
|
140
|
+
...screenInfo,
|
|
141
|
+
componentName: 'InputSearch',
|
|
142
|
+
params,
|
|
143
|
+
state: inputState,
|
|
144
|
+
componentId,
|
|
145
|
+
}}>
|
|
146
|
+
<View style={[style, styles.searchInputContainer]}>
|
|
147
|
+
<View
|
|
148
|
+
style={[
|
|
149
|
+
styles.searchInputWrapper,
|
|
150
|
+
{
|
|
151
|
+
backgroundColor: theme.colors.background.surface,
|
|
152
|
+
borderColor: theme.colors.background.surface,
|
|
153
|
+
},
|
|
154
|
+
showBorder && {borderColor: theme.colors.border.default},
|
|
155
|
+
focused && {borderColor: theme.colors.primary},
|
|
156
|
+
]}>
|
|
157
|
+
<Icon
|
|
158
|
+
source={'navigation_search'}
|
|
159
|
+
size={24}
|
|
160
|
+
color={theme.colors.text.hint}
|
|
161
|
+
/>
|
|
162
|
+
{renderInputView()}
|
|
163
|
+
{renderIconView()}
|
|
164
|
+
</View>
|
|
165
|
+
{showButtonText && (
|
|
166
|
+
<TouchableOpacity onPress={onPressButtonText}>
|
|
167
|
+
<Text
|
|
168
|
+
typography={'action_default_bold'}
|
|
169
|
+
style={styles.textButton}>
|
|
170
|
+
{buttonText}
|
|
171
|
+
</Text>
|
|
172
|
+
</TouchableOpacity>
|
|
173
|
+
)}
|
|
138
174
|
</View>
|
|
139
|
-
|
|
140
|
-
<TouchableOpacity onPress={onPressButtonText}>
|
|
141
|
-
<Text typography={'action_default_bold'} style={styles.textButton}>
|
|
142
|
-
{buttonText}
|
|
143
|
-
</Text>
|
|
144
|
-
</TouchableOpacity>
|
|
145
|
-
)}
|
|
146
|
-
</View>
|
|
175
|
+
</ScreenContext.Provider>
|
|
147
176
|
);
|
|
148
177
|
},
|
|
149
178
|
);
|
package/Input/index.tsx
CHANGED
|
@@ -80,6 +80,9 @@ export interface InputProps extends TextInputProps {
|
|
|
80
80
|
fontWeight?: 'Regular' | 'Bold';
|
|
81
81
|
|
|
82
82
|
onPressIcon?: () => void;
|
|
83
|
+
|
|
84
|
+
params?: any;
|
|
85
|
+
componentId?: string;
|
|
83
86
|
}
|
|
84
87
|
|
|
85
88
|
type InputPropsWithoutSizeAndIcon = Omit<
|
|
@@ -126,6 +129,10 @@ export interface InputSearchProps extends TextInputProps {
|
|
|
126
129
|
* Optional. Represents the name or key of the icon to be displayed in the Input component.
|
|
127
130
|
*/
|
|
128
131
|
icon?: string;
|
|
132
|
+
|
|
133
|
+
params?: any;
|
|
134
|
+
|
|
135
|
+
componentId?: string;
|
|
129
136
|
}
|
|
130
137
|
|
|
131
138
|
export interface InputMoneyProps extends InputPropsWithoutPlaceholder {}
|
|
@@ -250,6 +257,10 @@ export interface InputDropDownProps {
|
|
|
250
257
|
leadingIconColor?: string;
|
|
251
258
|
|
|
252
259
|
style: ViewStyle | ViewStyle[];
|
|
260
|
+
|
|
261
|
+
params?: any
|
|
262
|
+
componentId?: string;
|
|
263
|
+
|
|
253
264
|
}
|
|
254
265
|
|
|
255
266
|
export {Input, InputTextArea, InputSearch, InputMoney, InputOTP, InputDropDown};
|
package/Radio/index.tsx
CHANGED
|
@@ -6,6 +6,10 @@ import {Text} from '../Text';
|
|
|
6
6
|
import styles from './styles';
|
|
7
7
|
import {ApplicationContext} from '../Application';
|
|
8
8
|
import {Spacing} from '../Consts';
|
|
9
|
+
import {formatNameLength} from '../Application/utils';
|
|
10
|
+
const {
|
|
11
|
+
ScreenContext,
|
|
12
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
9
13
|
|
|
10
14
|
const Radio: FC<RadioProps> = ({
|
|
11
15
|
value,
|
|
@@ -14,8 +18,11 @@ const Radio: FC<RadioProps> = ({
|
|
|
14
18
|
onChange,
|
|
15
19
|
label,
|
|
16
20
|
style,
|
|
21
|
+
params,
|
|
22
|
+
componentId,
|
|
17
23
|
}) => {
|
|
18
24
|
const {theme} = useContext(ApplicationContext);
|
|
25
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
19
26
|
const selected = value === groupValue;
|
|
20
27
|
let disabledStyle = {};
|
|
21
28
|
let checkBoxStyle = {
|
|
@@ -37,27 +44,43 @@ const Radio: FC<RadioProps> = ({
|
|
|
37
44
|
};
|
|
38
45
|
}
|
|
39
46
|
|
|
47
|
+
const component_name = formatNameLength(label || '');
|
|
48
|
+
|
|
40
49
|
return (
|
|
41
|
-
<
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
alignItems: 'center',
|
|
50
|
+
<ScreenContext.Provider
|
|
51
|
+
value={{
|
|
52
|
+
...screenInfo,
|
|
53
|
+
componentName: 'Button',
|
|
54
|
+
params: {
|
|
55
|
+
...params,
|
|
56
|
+
component_name,
|
|
49
57
|
},
|
|
50
|
-
|
|
51
|
-
|
|
58
|
+
state: disabled ? 'disabled' : 'enabled',
|
|
59
|
+
componentId,
|
|
60
|
+
componentValue: value,
|
|
61
|
+
action: 'click',
|
|
62
|
+
}}>
|
|
63
|
+
<TouchableOpacity
|
|
64
|
+
onPress={onChange}
|
|
65
|
+
disabled={disabled}
|
|
52
66
|
style={[
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
67
|
+
style,
|
|
68
|
+
{
|
|
69
|
+
flexDirection: 'row',
|
|
70
|
+
alignItems: 'center',
|
|
71
|
+
},
|
|
72
|
+
]}>
|
|
73
|
+
<View
|
|
74
|
+
style={[
|
|
75
|
+
styles.radio,
|
|
76
|
+
checkBoxStyle,
|
|
77
|
+
disabledStyle,
|
|
78
|
+
{marginRight: label ? Spacing.XS : 0},
|
|
79
|
+
]}
|
|
80
|
+
/>
|
|
81
|
+
{!!label && <Text typography={'body_default_regular'}>{label}</Text>}
|
|
82
|
+
</TouchableOpacity>
|
|
83
|
+
</ScreenContext.Provider>
|
|
61
84
|
);
|
|
62
85
|
};
|
|
63
86
|
|
package/Radio/types.ts
CHANGED
package/Switch/index.tsx
CHANGED
|
@@ -1,11 +1,17 @@
|
|
|
1
|
-
import React, {FC} from 'react';
|
|
1
|
+
import React, {FC, useContext} from 'react';
|
|
2
2
|
import {TouchableOpacity, View} from 'react-native';
|
|
3
3
|
import {SwitchProps} from './types';
|
|
4
4
|
import styles from './styles';
|
|
5
5
|
import {Colors} from '../Consts';
|
|
6
6
|
|
|
7
|
+
const {
|
|
8
|
+
ScreenContext,
|
|
9
|
+
} = require('react-native/Libraries/Components/ScreenContext');
|
|
10
|
+
|
|
7
11
|
const Switch: FC<SwitchProps> = props => {
|
|
8
|
-
const {value, onChange, disabled, style} = props;
|
|
12
|
+
const {value, onChange, disabled, style, params, componentId} = props;
|
|
13
|
+
const screenInfo = useContext<any>(ScreenContext);
|
|
14
|
+
|
|
9
15
|
const circleBackgroundColor = value ? Colors.black_01 : Colors.black_03;
|
|
10
16
|
const circleAlign = value ? 'flex-end' : 'flex-start';
|
|
11
17
|
|
|
@@ -15,18 +21,29 @@ const Switch: FC<SwitchProps> = props => {
|
|
|
15
21
|
}
|
|
16
22
|
|
|
17
23
|
return (
|
|
18
|
-
<
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
24
|
+
<ScreenContext.Provider
|
|
25
|
+
value={{
|
|
26
|
+
...screenInfo,
|
|
27
|
+
componentName: 'Button',
|
|
28
|
+
params,
|
|
29
|
+
state: disabled ? 'disabled' : 'enabled',
|
|
30
|
+
componentId,
|
|
31
|
+
componentValue: value,
|
|
32
|
+
action: 'click',
|
|
33
|
+
}}>
|
|
34
|
+
<TouchableOpacity
|
|
35
|
+
disabled={disabled}
|
|
36
|
+
onPress={() => onChange?.(!value)}
|
|
37
|
+
style={[
|
|
38
|
+
style,
|
|
39
|
+
styles.container,
|
|
40
|
+
{backgroundColor, alignItems: circleAlign},
|
|
41
|
+
]}>
|
|
42
|
+
<View style={[styles.circle, {backgroundColor: circleBackgroundColor}]}>
|
|
43
|
+
<View style={[styles.circleSmall, {backgroundColor}]} />
|
|
44
|
+
</View>
|
|
45
|
+
</TouchableOpacity>
|
|
46
|
+
</ScreenContext.Provider>
|
|
30
47
|
);
|
|
31
48
|
};
|
|
32
49
|
|
package/Switch/types.ts
CHANGED