@momo-kits/foundation 0.77.8 → 0.78.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 (52) hide show
  1. package/Application/BottomTab.tsx +13 -3
  2. package/Application/Components.tsx +51 -4
  3. package/Application/ModalScreen.tsx +17 -16
  4. package/Application/Navigation.ts +4 -2
  5. package/Application/NavigationContainer.tsx +22 -1
  6. package/Application/index.ts +8 -2
  7. package/Application/types.ts +19 -15
  8. package/Application/utils.tsx +13 -0
  9. package/Assets/DotAnimation.json +256 -0
  10. package/Assets/SpinnerAnimation.json +1027 -0
  11. package/Button/index.tsx +25 -14
  12. package/CheckBox/index.tsx +29 -24
  13. package/CheckBox/styles.ts +1 -1
  14. package/CheckBox/types.ts +1 -1
  15. package/Consts/styles.ts +0 -26
  16. package/Divider/index.tsx +2 -0
  17. package/Input/Input.tsx +126 -106
  18. package/Input/InputMoney.tsx +118 -110
  19. package/Input/InputSearch.tsx +129 -134
  20. package/Input/InputTextArea.tsx +126 -118
  21. package/Input/common.tsx +11 -5
  22. package/Input/index.tsx +12 -0
  23. package/Layout/Card.tsx +9 -2
  24. package/Layout/GridSystem.tsx +1 -1
  25. package/Layout/Item.tsx +15 -2
  26. package/Layout/Screen.tsx +76 -8
  27. package/Layout/Section.tsx +36 -3
  28. package/Layout/index.ts +1 -1
  29. package/Layout/types.ts +0 -37
  30. package/Layout/utils.ts +6 -9
  31. package/Loader/DotLoader.tsx +37 -0
  32. package/Loader/Loader.tsx +13 -0
  33. package/Loader/ProgressBar.tsx +44 -0
  34. package/Loader/Spinner.tsx +29 -0
  35. package/Loader/index.tsx +4 -0
  36. package/Loader/styles.ts +10 -0
  37. package/Loader/types.ts +35 -0
  38. package/Loader/utils.ts +25 -0
  39. package/Pagination/PaginationNumber.tsx +1 -2
  40. package/Pagination/PaginationWhiteDot.tsx +1 -3
  41. package/Popup/PopupNotify.tsx +11 -17
  42. package/Popup/PopupPromotion.tsx +19 -13
  43. package/Popup/types.ts +9 -1
  44. package/Radio/index.tsx +1 -1
  45. package/Skeleton/types.ts +3 -0
  46. package/Text/index.tsx +1 -16
  47. package/Text/utils.ts +1 -1
  48. package/code-scanner.js +51 -0
  49. package/index.ts +2 -0
  50. package/package.json +8 -4
  51. package/tsconfig.json +25 -0
  52. package/Application/NavigationButton.tsx +0 -54
package/Button/index.tsx CHANGED
@@ -11,6 +11,7 @@ import {Typography} from '../Text/types';
11
11
  import {Colors} from '../Consts';
12
12
  import styles from './styles';
13
13
  import {Icon} from '../Icon';
14
+ import {Loader} from '../Loader';
14
15
 
15
16
  export interface ButtonProps extends TouchableOpacityProps {
16
17
  /**
@@ -55,6 +56,11 @@ export interface ButtonProps extends TouchableOpacityProps {
55
56
  */
56
57
  useTintColor?: boolean;
57
58
 
59
+ /**
60
+ * If true, the icon of button will use be show indicator loading.
61
+ */
62
+ loading?: boolean;
63
+
58
64
  /**
59
65
  * A callback function that is called when the button is pressed.
60
66
  */
@@ -62,13 +68,14 @@ export interface ButtonProps extends TouchableOpacityProps {
62
68
  }
63
69
 
64
70
  const Button: FC<ButtonProps> = ({
65
- type,
66
- size,
67
- useTintColor,
68
- full,
71
+ type = 'primary',
72
+ size = 'large',
73
+ useTintColor = true,
74
+ full = true,
69
75
  iconRight,
70
76
  iconLeft,
71
- title,
77
+ loading = false,
78
+ title = 'Button',
72
79
  onPress,
73
80
  ...rest
74
81
  }) => {
@@ -223,6 +230,19 @@ const Button: FC<ButtonProps> = ({
223
230
  const renderTrailing = () => {
224
231
  const marginLeft = getIconSpace();
225
232
  const color = useTintColor ? getTextColor() : undefined;
233
+ if (loading) {
234
+ const iconSize = getIconSize();
235
+ const color = getTextColor();
236
+ return (
237
+ <View
238
+ style={[
239
+ styles.trailing,
240
+ {width: iconSize, height: iconSize, marginLeft},
241
+ ]}>
242
+ <Loader type="spinner" color={color} />
243
+ </View>
244
+ );
245
+ }
226
246
  if (iconRight) {
227
247
  const iconSize = getIconSize();
228
248
  return (
@@ -266,13 +286,4 @@ const Button: FC<ButtonProps> = ({
266
286
  );
267
287
  };
268
288
 
269
- Button.defaultProps = {
270
- type: 'primary',
271
- size: 'large',
272
- full: true,
273
- disabled: false,
274
- title: 'Button',
275
- useTintColor: true,
276
- };
277
-
278
289
  export {Button};
@@ -6,41 +6,46 @@ import {ApplicationContext} from '../Application';
6
6
  import {Text} from '../Text';
7
7
  import {Icon} from '../Icon';
8
8
 
9
- const CheckBox: FC<CheckBoxProps> = props => {
9
+ const CheckBox: FC<CheckBoxProps> = ({
10
+ value,
11
+ disabled,
12
+ onChange,
13
+ style,
14
+ label,
15
+ indeterminate,
16
+ }) => {
10
17
  const {theme} = useContext(ApplicationContext);
11
- const {value, disabled, onChange, style, label, indeterminated} = props;
18
+ const haveValue = value || indeterminate;
19
+ const iconSource = indeterminate ? 'ic_minus' : 'ic_checked';
20
+ let borderColor = theme.colors.text.default;
21
+ let backgroundColor = theme.colors.background.surface;
12
22
 
13
- const haveValue = value || indeterminated;
14
- let borderColor = haveValue
15
- ? theme.colors.primary
16
- : theme.colors.text.default;
17
- let backgroundColor = haveValue
18
- ? theme.colors.primary
19
- : theme.colors.background.surface;
20
-
21
- let iconSource = indeterminated ? 'ic_minus' : 'ic_checked';
23
+ if (haveValue) {
24
+ borderColor = theme.colors.primary;
25
+ backgroundColor = theme.colors.primary;
26
+ }
22
27
 
23
28
  if (disabled) {
24
- borderColor = haveValue
25
- ? theme.colors.background.tonal
26
- : theme.colors.border.disable;
27
- backgroundColor = haveValue
28
- ? theme.colors.background.tonal
29
- : theme.colors.background.surface;
29
+ borderColor = theme.colors.border.disable;
30
+ backgroundColor = theme.colors.background.surface;
31
+ if (haveValue) {
32
+ borderColor = theme.colors.background.tonal;
33
+ backgroundColor = theme.colors.background.tonal;
34
+ }
30
35
  }
31
- const checkboxStyle = {borderColor, backgroundColor, borderWidth: 1};
32
36
 
33
- const onChangeValue = () => {
34
- onChange?.(!value);
35
- };
36
37
  return (
37
38
  <TouchableOpacity
38
- accessibilityLabel={`CheckBox/${label}`}
39
+ accessibilityLabel={`CheckBox/${label}/${value}`}
39
40
  activeOpacity={0.8}
40
- onPress={onChangeValue}
41
+ onPress={() => onChange?.(!value)}
41
42
  disabled={disabled}
42
43
  style={[style, styles.container]}>
43
- <View style={[checkboxStyle, styles.checkbox]}>
44
+ <View
45
+ style={[
46
+ {borderColor, backgroundColor, borderWidth: 1},
47
+ styles.checkbox,
48
+ ]}>
44
49
  {haveValue && (
45
50
  <Icon
46
51
  color={theme.colors.background.surface}
@@ -11,5 +11,5 @@ export default StyleSheet.create({
11
11
  justifyContent: 'center',
12
12
  alignItems: 'center',
13
13
  },
14
- container: {flexDirection: 'row'},
14
+ container: {flexDirection: 'row', alignItems: 'center'},
15
15
  });
package/CheckBox/types.ts CHANGED
@@ -28,7 +28,7 @@ export type CheckBoxProps = {
28
28
  * which is typically used to represent a "mixed" or "partial" selection state.
29
29
  * Defaults to `false` if not provided.
30
30
  */
31
- indeterminated?: boolean;
31
+ indeterminate?: boolean;
32
32
 
33
33
  /**
34
34
  * Optional. Used to apply custom styling to the CheckBox component.
package/Consts/styles.ts CHANGED
@@ -47,32 +47,6 @@ const Styles = StyleSheet.create({
47
47
  alignItems: 'flex-end',
48
48
  justifyContent: 'center',
49
49
  },
50
- //paddingHorizontal
51
- paddingHorizontal4: {
52
- paddingHorizontal: 4,
53
- },
54
- paddingHorizontal8: {
55
- paddingHorizontal: 8,
56
- },
57
- paddingHorizontal16: {
58
- paddingHorizontal: 16,
59
- },
60
- paddingHorizontal24: {
61
- paddingHorizontal: 24,
62
- },
63
- //paddingVertical
64
- paddingVertical4: {
65
- paddingVertical: 4,
66
- },
67
- paddingVertical8: {
68
- paddingVertical: 8,
69
- },
70
- paddingVertical16: {
71
- paddingVertical: 16,
72
- },
73
- paddingVertical24: {
74
- paddingVertical: 24,
75
- },
76
50
  });
77
51
 
78
52
  export {Styles};
package/Divider/index.tsx CHANGED
@@ -1,6 +1,7 @@
1
1
  import React, {useContext} from 'react';
2
2
  import {View} from 'react-native';
3
3
  import {ApplicationContext} from '../Application';
4
+ import {Spacing} from '../Consts';
4
5
 
5
6
  const Divider = () => {
6
7
  const {theme} = useContext(ApplicationContext);
@@ -11,6 +12,7 @@ const Divider = () => {
11
12
  height: 1,
12
13
  width: '100%',
13
14
  backgroundColor: theme.colors.border.default,
15
+ marginVertical: Spacing.XS,
14
16
  }}
15
17
  />
16
18
  );
package/Input/Input.tsx CHANGED
@@ -1,4 +1,4 @@
1
- import React, {FC, useContext, useEffect, useRef, useState} from 'react';
1
+ import React, {FC, forwardRef, useContext, useRef, useState} from 'react';
2
2
  import {
3
3
  NativeSyntheticEvent,
4
4
  TextInput,
@@ -12,124 +12,144 @@ import {ErrorView, FloatingView, getBorderColor, getSizeStyle} from './common';
12
12
  import {InputProps} from './index';
13
13
  import {Icon} from '../Icon';
14
14
  import {checkTyping} from './utils';
15
+ import {Loader} from '../Loader';
15
16
 
16
- const Input: FC<InputProps> = ({
17
- value,
18
- onChangeText,
19
- floatingValue,
20
- floatingIcon,
21
- size,
22
- placeholder,
23
- onBlur,
24
- onFocus,
25
- errorMessage,
26
- icon,
27
- disabled,
28
- floatingIconColor,
29
- iconColor,
30
- required,
31
- ...props
32
- }) => {
33
- const {theme} = useContext(ApplicationContext);
34
- const [focused, setFocused] = useState(false);
35
- const [haveValue, setHaveValue] = useState(!!value || !!props.defaultValue);
17
+ const Input: FC<InputProps> = forwardRef(
18
+ (
19
+ {
20
+ value,
21
+ onChangeText,
22
+ floatingValue,
23
+ floatingIcon,
24
+ size,
25
+ placeholder,
26
+ onBlur,
27
+ onFocus,
28
+ errorMessage,
29
+ icon,
30
+ disabled,
31
+ floatingIconColor,
32
+ iconColor,
33
+ required,
34
+ errorSpacing,
35
+ loading,
36
+ ...props
37
+ },
38
+ ref,
39
+ ) => {
40
+ const {theme} = useContext(ApplicationContext);
41
+ const [focused, setFocused] = useState(false);
42
+ const [haveValue, setHaveValue] = useState(!!value || !!props.defaultValue);
43
+ const inputRef = (ref as React.RefObject<TextInput>) ?? useRef<TextInput>();
36
44
 
37
- const inputRef = useRef<any>(null);
45
+ const onClearText = () => {
46
+ inputRef?.current?.clear();
47
+ _onChangeText('');
48
+ };
38
49
 
39
- const onClearText = () => {
40
- inputRef?.current?.clear();
41
- _onChangeText('');
42
- };
50
+ const _onChangeText = (text: string) => {
51
+ checkTyping(text, haveValue, setHaveValue);
52
+ onChangeText?.(text);
53
+ };
43
54
 
44
- const _onChangeText = (text: string) => {
45
- checkTyping(text, haveValue, setHaveValue);
46
- onChangeText?.(text);
47
- };
55
+ const _onFocus = (e: NativeSyntheticEvent<TextInputFocusEventData>) => {
56
+ setFocused(true);
57
+ onFocus?.(e);
58
+ };
48
59
 
49
- const _onFocus = (e: NativeSyntheticEvent<TextInputFocusEventData>) => {
50
- setFocused(true);
51
- onFocus?.(e);
52
- };
60
+ const _onBlur = (e: NativeSyntheticEvent<TextInputFocusEventData>) => {
61
+ setFocused(false);
62
+ onBlur?.(e);
63
+ };
53
64
 
54
- const _onBlur = (e: NativeSyntheticEvent<TextInputFocusEventData>) => {
55
- setFocused(false);
56
- onBlur?.(e);
57
- };
65
+ const renderIcon = (color: string | undefined) => {
66
+ if (loading) {
67
+ return <Loader type={'spinner'} color={color} />;
68
+ }
69
+ if (icon) {
70
+ return <Icon color={color} source={icon} size={24} />;
71
+ }
72
+ };
58
73
 
59
- const renderInputView = () => {
60
- const disabledColor = theme.colors.text.disable;
61
- let textColor = theme.colors.text.default;
62
- let placeholderColor = theme.colors.text.hint;
63
- let iconTintColor = iconColor;
74
+ const renderInputView = () => {
75
+ const disabledColor = theme.colors.text.disable;
76
+ let textColor = theme.colors.text.default;
77
+ let placeholderColor = theme.colors.text.hint;
78
+ let iconTintColor = iconColor;
64
79
 
65
- if (disabled) {
66
- textColor = disabledColor;
67
- placeholderColor = disabledColor;
68
- iconTintColor = disabledColor;
69
- }
80
+ if (disabled) {
81
+ textColor = disabledColor;
82
+ placeholderColor = disabledColor;
83
+ iconTintColor = disabledColor;
84
+ }
70
85
 
71
- return (
72
- <View
73
- style={[
74
- getSizeStyle(size),
75
- getBorderColor(focused, errorMessage, disabled),
76
- styles.inputWrapper,
77
- {backgroundColor: theme.colors.background.surface},
78
- ]}>
79
- <FloatingView
80
- floatingValue={floatingValue}
81
- floatingIconColor={floatingIconColor}
82
- disabled={disabled}
83
- required={required}
84
- floatingIcon={floatingIcon}
85
- />
86
- <View style={styles.inputView}>
87
- <TextInput
88
- {...props}
89
- accessibilityLabel={`TextInput`}
90
- editable={!disabled}
91
- textAlignVertical="top"
92
- ref={inputRef}
93
- style={[
94
- styles.input,
95
- {
96
- color: textColor,
97
- fontFamily: `${theme.font}-Regular`,
98
- },
99
- ]}
100
- textBreakStrategy="highQuality"
101
- value={value}
102
- onChangeText={_onChangeText}
103
- onFocus={_onFocus}
104
- onBlur={_onBlur}
105
- placeholder={placeholder}
106
- selectionColor={theme.colors.primary}
107
- placeholderTextColor={placeholderColor}
86
+ return (
87
+ <View
88
+ style={[
89
+ styles.inputWrapper,
90
+ {backgroundColor: theme.colors.background.surface},
91
+ getSizeStyle(size),
92
+ getBorderColor(theme, focused, errorMessage, disabled),
93
+ ]}>
94
+ <FloatingView
95
+ floatingValue={floatingValue}
96
+ floatingIconColor={floatingIconColor}
97
+ disabled={disabled}
98
+ required={required}
99
+ floatingIcon={floatingIcon}
108
100
  />
101
+ <View style={styles.inputView}>
102
+ <TextInput
103
+ {...props}
104
+ accessibilityLabel={`TextInput`}
105
+ editable={!disabled}
106
+ textAlignVertical="top"
107
+ ref={inputRef}
108
+ style={[
109
+ styles.input,
110
+ {
111
+ color: textColor,
112
+ fontFamily: `${theme.font}-Regular`,
113
+ },
114
+ ]}
115
+ textBreakStrategy="highQuality"
116
+ value={value}
117
+ onChangeText={_onChangeText}
118
+ onFocus={_onFocus}
119
+ onBlur={_onBlur}
120
+ placeholder={placeholder}
121
+ selectionColor={theme.colors.primary}
122
+ placeholderTextColor={placeholderColor}
123
+ />
124
+ </View>
125
+ <View style={styles.iconView}>
126
+ {focused && haveValue && (
127
+ <TouchableOpacity
128
+ style={styles.iconWrapper}
129
+ onPress={onClearText}>
130
+ <Icon
131
+ source="24_navigation_close_circle_full"
132
+ size={16}
133
+ color={theme.colors.text.hint}
134
+ />
135
+ </TouchableOpacity>
136
+ )}
137
+ {renderIcon(iconTintColor)}
138
+ </View>
109
139
  </View>
110
- <View style={styles.iconView}>
111
- {focused && haveValue && (
112
- <TouchableOpacity style={styles.iconWrapper} onPress={onClearText}>
113
- <Icon
114
- source="24_navigation_close_circle_full"
115
- size={16}
116
- color={theme.colors.text.hint}
117
- />
118
- </TouchableOpacity>
119
- )}
120
- {!!icon && <Icon color={iconTintColor} source={icon} size={24} />}
121
- </View>
140
+ );
141
+ };
142
+
143
+ return (
144
+ <View
145
+ style={styles.wrapper}
146
+ accessibilityLabel={`Input/${floatingValue}`}>
147
+ {renderInputView()}
148
+ <ErrorView errorMessage={errorMessage} errorSpacing={errorSpacing} />
122
149
  </View>
123
150
  );
124
- };
125
-
126
- return (
127
- <View style={styles.wrapper} accessibilityLabel={`Input/${floatingValue}`}>
128
- {renderInputView()}
129
- <ErrorView errorMessage={errorMessage} />
130
- </View>
131
- );
132
- };
151
+ },
152
+ );
133
153
 
134
154
  Input.defaultProps = {
135
155
  size: 'small',