@momo-kits/foundation 0.92.30 → 0.92.32

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.
@@ -65,7 +65,7 @@ const NavigationButton: React.FC<NavigationButtonProps> = ({
65
65
  }, [badgeType, badgeValue]);
66
66
 
67
67
  return (
68
- <View style={{width: scaleSize(28)}}>
68
+ <View style={{width: 28}}>
69
69
  <TouchableOpacity
70
70
  accessibilityLabel={accessibilityLabel}
71
71
  style={[styles.navigationButton, buttonStyle]}
@@ -113,7 +113,7 @@ const HeaderLeft: React.FC<HeaderBackProps> = ({
113
113
  useEffect(() => {
114
114
  const backHandler = BackHandler.addEventListener(
115
115
  'hardwareBackPress',
116
- goBackSafe,
116
+ goBackSafe
117
117
  );
118
118
 
119
119
  return () => backHandler.remove();
@@ -268,7 +268,7 @@ const HeaderRightAction: React.FC<any> = ({children, ...restProps}) => {
268
268
  const valid = child?.type === NavigationButton || child?.type === Fragment;
269
269
  if (__DEV__ && !valid) {
270
270
  console.warn(
271
- 'HeaderRightAction contains element type of NavigationButton, Please check again.',
271
+ 'HeaderRightAction contains element type of NavigationButton, Please check again.'
272
272
  );
273
273
  }
274
274
  return child;
@@ -327,7 +327,7 @@ const HeaderToolkitAction: React.FC<any> = ({
327
327
  (config: any) => {
328
328
  navigator.toolkitConfig = config;
329
329
  setToolConfig(navigator?.toolkitConfig);
330
- },
330
+ }
331
331
  );
332
332
  };
333
333
 
@@ -338,9 +338,9 @@ const HeaderToolkitAction: React.FC<any> = ({
338
338
  {runtimeTools},
339
339
  (res: {item: {action?: string; key: string}}) => {
340
340
  const {item} = res;
341
- navigator?.toolkitCallback?.(item);
341
+ navigator?.toolkitCallback?.(item.key);
342
342
  getToolkitConfig();
343
- },
343
+ }
344
344
  );
345
345
  };
346
346
 
@@ -357,7 +357,7 @@ const HeaderToolkitAction: React.FC<any> = ({
357
357
  navigator?.maxApi?.dispatchFunction?.(
358
358
  'dismiss',
359
359
  undefined,
360
- undefined,
360
+ undefined
361
361
  );
362
362
  },
363
363
  }}
@@ -388,7 +388,7 @@ const HeaderToolkitAction: React.FC<any> = ({
388
388
  [pinTool?.key],
389
389
  () => {
390
390
  getToolkitConfig();
391
- },
391
+ }
392
392
  );
393
393
  navigator?.toolkitCallback?.(pinTool.key);
394
394
  }}
@@ -12,7 +12,7 @@ class Navigator {
12
12
  toolkitConfig?: HeaderToolkitProps;
13
13
  maxApi?: any;
14
14
  dismissData?: any;
15
- toolkitCallback?: (item: any) => void;
15
+ toolkitCallback?: (key: string) => void;
16
16
 
17
17
  constructor(navigation: any, isReady: any) {
18
18
  this.ref = navigation;
@@ -78,7 +78,7 @@ class Navigator {
78
78
  StackActions.push('Modal', {
79
79
  ...params,
80
80
  isBottomSheet: true,
81
- }),
81
+ })
82
82
  );
83
83
  }
84
84
  };
@@ -103,7 +103,7 @@ class Navigator {
103
103
  CommonActions.navigate({
104
104
  name,
105
105
  params,
106
- }),
106
+ })
107
107
  );
108
108
  }
109
109
  };
@@ -124,7 +124,7 @@ class Navigator {
124
124
  params,
125
125
  },
126
126
  ],
127
- }),
127
+ })
128
128
  );
129
129
  }
130
130
  };
@@ -141,9 +141,7 @@ class Navigator {
141
141
  * set callback function for toolkit
142
142
  * @param callback
143
143
  */
144
- setToolkitCallback = (
145
- callback: (item: {key: string; action: string}) => void,
146
- ) => {
144
+ setToolkitCallback = (callback: (key: string) => void) => {
147
145
  this.toolkitCallback = callback;
148
146
  };
149
147
  }
@@ -1,6 +1,6 @@
1
1
  import React, {useContext, useEffect, useLayoutEffect, useRef} from 'react';
2
2
  import {useHeaderHeight} from '@react-navigation/stack';
3
- import {InteractionManager, Linking, View} from 'react-native';
3
+ import {Alert, InteractionManager, Linking, View} from 'react-native';
4
4
  import {ScreenParams} from './types';
5
5
  import Navigation from './Navigation';
6
6
  import {ApplicationContext, MiniAppContext, ScreenContext} from './index';
@@ -95,6 +95,8 @@ const StackScreen: React.FC<ScreenParams> = props => {
95
95
  const timeInteraction = useRef(0);
96
96
  const timeoutLoad = useRef<any>();
97
97
  const tracked = useRef<any>({
98
+ traceIdLoad: undefined,
99
+ traceIdInteraction: undefined,
98
100
  releaseLoad: undefined,
99
101
  releaseInteraction: undefined,
100
102
  timeoutLoad: undefined,
@@ -125,6 +127,15 @@ const StackScreen: React.FC<ScreenParams> = props => {
125
127
  if (options) {
126
128
  navigation.setOptions(options);
127
129
  }
130
+ navigator?.maxApi?.startTraceScreenLoad?.(screenName, (data: any) => {
131
+ tracked.current.traceIdLoad = data?.traceId;
132
+ });
133
+ navigator?.maxApi?.startTraceScreenInteraction?.(
134
+ screenName,
135
+ (data: any) => {
136
+ tracked.current.traceIdInteraction = data?.traceId;
137
+ }
138
+ );
128
139
  }, [options]);
129
140
 
130
141
  /**
@@ -146,6 +157,8 @@ const StackScreen: React.FC<ScreenParams> = props => {
146
157
  }, 5000);
147
158
 
148
159
  return () => {
160
+ clearTimeout(tracked.current.timeoutLoad);
161
+ clearTimeout(tracked.current.timeoutInteraction);
149
162
  onScreenLoad();
150
163
  onScreenInteraction();
151
164
  };
@@ -155,8 +168,10 @@ const StackScreen: React.FC<ScreenParams> = props => {
155
168
  * tracking for screen load
156
169
  */
157
170
  const onScreenLoad = () => {
158
- clearTimeout(tracked.current.timeoutLoad);
159
171
  if (!tracked.current?.releaseLoad) {
172
+ if (timeLoad.current === 0) {
173
+ timeLoad.current = endTime.current - startTime.current;
174
+ }
160
175
  context.autoTracking?.({
161
176
  appId: context.appId,
162
177
  code: context.code,
@@ -166,10 +181,18 @@ const StackScreen: React.FC<ScreenParams> = props => {
166
181
  state: 'load',
167
182
  duration: timeLoad.current,
168
183
  });
184
+ navigator?.maxApi?.stopTrace?.(
185
+ tracked.current.traceIdLoad,
186
+ {value: timeLoad.current},
187
+ null
188
+ );
169
189
  navigator?.maxApi?.showToastDebug?.({
170
190
  appId: `auto - ${context.appId}`,
171
191
  message: `${screenName} screen_load_time ${timeLoad.current}`,
172
192
  });
193
+ if (timeLoad.current === 0 && context.enableAutoId) {
194
+ Alert.alert(screenName, "Can't get screen load time");
195
+ }
173
196
  tracked.current.releaseLoad = true;
174
197
  }
175
198
  };
@@ -178,8 +201,17 @@ const StackScreen: React.FC<ScreenParams> = props => {
178
201
  * tracking for screen load
179
202
  */
180
203
  const onScreenInteraction = () => {
181
- clearTimeout(tracked.current.timeoutInteraction);
182
204
  if (!tracked.current?.releaseInteraction) {
205
+ if (timeLoad.current === 0) {
206
+ timeLoad.current = endTime.current - startTime.current;
207
+ }
208
+ if (timeInteraction.current === 0 && context.enableAutoId) {
209
+ if (context.enableAutoId) {
210
+ Alert.alert(screenName, "Can't get screen interaction time");
211
+ }
212
+ timeInteraction.current = timeLoad.current;
213
+ }
214
+
183
215
  context.autoTracking?.({
184
216
  appId: context.appId,
185
217
  code: context.code,
@@ -189,7 +221,11 @@ const StackScreen: React.FC<ScreenParams> = props => {
189
221
  state: 'interaction',
190
222
  duration: timeInteraction.current - timeLoad.current,
191
223
  });
192
-
224
+ navigator?.maxApi?.stopTrace?.(
225
+ tracked.current.traceIdInteraction,
226
+ {value: timeInteraction.current},
227
+ null
228
+ );
193
229
  navigator?.maxApi?.showToastDebug?.({
194
230
  appId: `auto - ${context.appId}`,
195
231
  message: `${screenName} screen_interaction_time ${timeInteraction.current}`,
@@ -203,12 +239,12 @@ const StackScreen: React.FC<ScreenParams> = props => {
203
239
  value={{
204
240
  screenName,
205
241
  onElementLoad: () => {
242
+ clearTimeout(timeoutLoad.current);
206
243
  endTime.current = Date.now();
207
244
  interaction.current?.cancel?.();
208
245
  interaction.current = InteractionManager.runAfterInteractions(() => {
209
246
  timeInteraction.current = Date.now() - startTime.current;
210
247
  });
211
- clearTimeout(timeoutLoad.current);
212
248
  timeoutLoad.current = setTimeout(() => {
213
249
  if (timeLoad.current === 0) {
214
250
  timeLoad.current = endTime.current - startTime.current;
package/Input/Input.tsx CHANGED
@@ -1,5 +1,6 @@
1
1
  import React, {
2
2
  forwardRef,
3
+ ReactNode,
3
4
  useContext,
4
5
  useImperativeHandle,
5
6
  useRef,
@@ -16,11 +17,15 @@ import {
16
17
  import {ApplicationContext, ComponentContext} from '../Application';
17
18
  import {Icon} from '../Icon';
18
19
  import {Loader} from '../Loader';
20
+ import {Text} from '../Text';
19
21
  import {ErrorView, FloatingView, getBorderColor, getSizeStyle} from './common';
20
22
  import {InputProps} from './index';
21
23
  import styles from './styles';
22
24
  import {checkTyping} from './utils';
23
25
 
26
+ /**
27
+ * Input default component
28
+ */
24
29
  const Input = forwardRef(
25
30
  (
26
31
  {
@@ -34,16 +39,19 @@ const Input = forwardRef(
34
39
  onFocus,
35
40
  errorMessage,
36
41
  icon,
42
+ iconColor,
43
+ onPressIcon,
44
+ trailing,
45
+ trailingColor,
46
+ onPressTrailing,
37
47
  disabled = false,
38
48
  floatingIconColor,
39
- iconColor,
40
49
  required = false,
41
50
  errorSpacing,
42
51
  loading = false,
43
52
  leadingIcon,
44
53
  leadingIconColor,
45
54
  fontWeight = 'Regular',
46
- onPressIcon,
47
55
  secureTextEntry,
48
56
  keyboardType,
49
57
  style,
@@ -51,9 +59,10 @@ const Input = forwardRef(
51
59
  hintText,
52
60
  accessibilityLabel,
53
61
  editable = true,
62
+ onPressFloatingIcon,
54
63
  ...props
55
64
  }: InputProps,
56
- ref,
65
+ ref
57
66
  ) => {
58
67
  const {theme} = useContext(ApplicationContext);
59
68
  const [focused, setFocused] = useState(false);
@@ -90,7 +99,11 @@ const Input = forwardRef(
90
99
  };
91
100
  });
92
101
 
93
- const renderIcon = (color: string | undefined) => {
102
+ /**
103
+ * Render trailing icon or text
104
+ * @param color
105
+ */
106
+ const renderTrailing = (color?: string) => {
94
107
  if (loading) {
95
108
  return <Loader type={'spinner'} color={color} style={styles.icon} />;
96
109
  }
@@ -109,24 +122,46 @@ const Input = forwardRef(
109
122
  </TouchableOpacity>
110
123
  );
111
124
  }
112
- if (icon) {
113
- return (
114
- <TouchableOpacity
115
- onPress={onPressIcon}
116
- disabled={!onPressIcon}
117
- style={styles.icon}>
118
- <Icon color={color} source={icon} size={24} />
119
- </TouchableOpacity>
125
+ if (icon || trailing) {
126
+ const renderIconTouchable = (icon: ReactNode) => {
127
+ return (
128
+ <TouchableOpacity
129
+ onPress={onPressTrailing ?? onPressIcon}
130
+ style={styles.icon}>
131
+ {icon}
132
+ </TouchableOpacity>
133
+ );
134
+ };
135
+ const trailingValue = icon || trailing;
136
+ if (trailingValue?.includes('_') || trailingValue?.includes('http')) {
137
+ return renderIconTouchable(
138
+ <Icon
139
+ color={color}
140
+ source={(icon || trailing) as string}
141
+ size={24}
142
+ />
143
+ );
144
+ }
145
+ return renderIconTouchable(
146
+ <Text
147
+ typography="action_xs_bold"
148
+ color={color ?? theme.colors.primary}
149
+ numberOfLines={1}>
150
+ {trailingValue!.substring(0, 15)}
151
+ </Text>
120
152
  );
121
153
  }
122
154
  };
123
155
 
156
+ /**
157
+ * Render input view
158
+ */
124
159
  const renderInputView = () => {
125
160
  const disabledColor = theme.colors.text.disable;
126
161
  const secure = secureTextInput && secureTextEntry;
127
162
  let textColor = theme.colors.text.default;
128
163
  let placeholderColor = theme.colors.text.hint;
129
- let iconTintColor = iconColor;
164
+ let iconTintColor = trailingColor ?? iconColor;
130
165
 
131
166
  if (disabled) {
132
167
  textColor = disabledColor;
@@ -155,6 +190,7 @@ const Input = forwardRef(
155
190
  disabled={disabled}
156
191
  required={required}
157
192
  floatingIcon={floatingIcon}
193
+ onPress={onPressFloatingIcon}
158
194
  />
159
195
  <View style={styles.inputView}>
160
196
  {!!leadingIcon && (
@@ -204,21 +240,19 @@ const Input = forwardRef(
204
240
  />
205
241
  </TouchableOpacity>
206
242
  )}
207
- {renderIcon(iconTintColor)}
243
+ {renderTrailing(iconTintColor)}
208
244
  </View>
209
245
  </View>
210
246
  );
211
247
  };
212
248
 
213
249
  let inputState = 'active';
214
-
215
250
  if (value && value?.length > 0) {
216
251
  inputState = 'filled';
217
252
  }
218
253
  if (errorMessage && errorMessage?.length > 0) {
219
254
  inputState = 'error';
220
255
  }
221
-
222
256
  if (disabled) {
223
257
  inputState = 'disabled';
224
258
  }
@@ -242,7 +276,7 @@ const Input = forwardRef(
242
276
  </View>
243
277
  </ComponentContext.Provider>
244
278
  );
245
- },
279
+ }
246
280
  );
247
281
 
248
282
  export default Input;
@@ -1,66 +1,55 @@
1
1
  import React, {useContext} from 'react';
2
- import {TextInput, TouchableOpacity, View} from 'react-native';
2
+ import {TouchableOpacity, View} from 'react-native';
3
3
  import {ApplicationContext, ComponentContext} from '../Application';
4
- import {Styles} from '../Consts';
5
4
  import {Icon} from '../Icon';
6
- import {Loader} from '../Loader';
7
5
  import {ErrorView, FloatingView, getBorderColor, getSizeStyle} from './common';
8
6
  import {InputDropDownProps} from './index';
7
+ import {Text} from '../Text';
9
8
  import styles from './styles';
9
+ import {Spacing} from '../Consts';
10
10
 
11
11
  const InputDropDown = ({
12
12
  value,
13
13
  floatingValue,
14
14
  floatingIcon,
15
+ onPressFloatingIcon,
15
16
  size = 'small',
16
17
  onPress,
17
18
  placeholder,
18
19
  errorMessage,
19
- icon = 'arrow_chevron_down_small',
20
20
  disabled = false,
21
21
  floatingIconColor,
22
- iconColor,
23
22
  required = false,
24
23
  errorSpacing,
25
- loading = false,
26
24
  leadingIcon,
27
25
  leadingIconColor,
28
26
  style,
29
27
  params,
30
28
  accessibilityLabel,
31
29
  hintText,
32
- ...props
30
+ multiline,
33
31
  }: InputDropDownProps) => {
34
32
  const {theme} = useContext(ApplicationContext);
35
- const full = !!value || !!placeholder;
36
-
37
- const renderIcon = (color: string | undefined) => {
38
- if (loading) {
39
- return <Loader type={'spinner'} color={color} />;
40
- }
41
- if (icon) {
42
- return <Icon color={color} source={icon} size={24} />;
43
- }
44
- };
45
33
 
34
+ /**
35
+ * Render the input view
36
+ */
46
37
  const renderInputView = () => {
47
38
  const disabledColor = theme.colors.text.disable;
48
39
  let textColor = theme.colors.text.default;
49
40
  let placeholderColor = theme.colors.text.hint;
50
- let iconTintColor = iconColor;
51
41
 
52
42
  if (disabled) {
53
43
  textColor = disabledColor;
54
44
  placeholderColor = disabledColor;
55
- iconTintColor = disabledColor;
56
45
  }
57
46
 
58
47
  return (
59
48
  <View
60
49
  style={[
61
- styles.inputWrapper,
50
+ styles.inputDropDownWrapper,
62
51
  {backgroundColor: theme.colors.background.surface},
63
- getSizeStyle(size),
52
+ getSizeStyle(size, multiline),
64
53
  getBorderColor(theme, false, errorMessage, disabled),
65
54
  ]}>
66
55
  <FloatingView
@@ -69,10 +58,18 @@ const InputDropDown = ({
69
58
  disabled={disabled}
70
59
  required={required}
71
60
  floatingIcon={floatingIcon}
61
+ onPress={onPressFloatingIcon}
72
62
  />
73
- <View style={full ? styles.inputView : Styles.row}>
63
+ <View style={styles.inputDropDownView}>
74
64
  {!!leadingIcon && (
75
- <View style={styles.leadingIconContainer}>
65
+ <View
66
+ style={[
67
+ styles.leadingIconContainerDropDown,
68
+ {
69
+ marginTop: Spacing.M,
70
+ marginRight: Spacing.S,
71
+ },
72
+ ]}>
76
73
  <Icon
77
74
  color={leadingIconColor}
78
75
  source={leadingIcon}
@@ -80,28 +77,27 @@ const InputDropDown = ({
80
77
  />
81
78
  </View>
82
79
  )}
83
- {full && (
84
- <TextInput
85
- {...props}
86
- accessibilityLabel={accessibilityLabel}
87
- onPressIn={onPress}
88
- editable={false}
89
- style={[
90
- styles.input,
91
- {
92
- color: textColor,
93
- fontFamily: `${theme.font}-Regular`,
94
- },
95
- ]}
96
- textBreakStrategy="highQuality"
97
- value={value}
98
- placeholder={placeholder}
99
- selectionColor={theme.colors.primary}
100
- placeholderTextColor={placeholderColor}
101
- />
102
- )}
80
+ <View
81
+ accessibilityLabel={accessibilityLabel}
82
+ style={styles.textViewDropDown}>
83
+ <Text
84
+ numberOfLines={multiline ? undefined : 1}
85
+ typography={'body_default_regular'}
86
+ color={value ? textColor : placeholderColor}>
87
+ {value || placeholder}
88
+ </Text>
89
+ </View>
90
+ </View>
91
+ <View
92
+ style={[
93
+ styles.iconViewDropDown,
94
+ {
95
+ alignItems: multiline ? 'flex-start' : 'center',
96
+ paddingTop: multiline ? Spacing.M : 0,
97
+ },
98
+ ]}>
99
+ <Icon source={'arrow_chevron_down_small'} />
103
100
  </View>
104
- <View style={styles.iconView}>{renderIcon(iconTintColor)}</View>
105
101
  </View>
106
102
  );
107
103
  };
@@ -116,8 +112,9 @@ const InputDropDown = ({
116
112
  componentId: accessibilityLabel,
117
113
  }}>
118
114
  <TouchableOpacity
115
+ activeOpacity={0.6}
119
116
  onPress={onPress}
120
- style={[style, full && styles.wrapper]}>
117
+ style={[style, styles.wrapper]}>
121
118
  {renderInputView()}
122
119
  <ErrorView
123
120
  errorMessage={errorMessage}
@@ -1,5 +1,6 @@
1
1
  import React, {
2
2
  forwardRef,
3
+ ReactNode,
3
4
  useContext,
4
5
  useEffect,
5
6
  useImperativeHandle,
@@ -19,6 +20,8 @@ import {ErrorView, FloatingView, getBorderColor, getSizeStyle} from './common';
19
20
  import {InputMoneyProps} from './index';
20
21
  import styles from './styles';
21
22
  import {formatMoneyToNumber, formatNumberToMoney} from './utils';
23
+ import {Text} from '../Text';
24
+ import {Loader} from '../Loader';
22
25
 
23
26
  const InputMoney = forwardRef(
24
27
  (
@@ -27,13 +30,18 @@ const InputMoney = forwardRef(
27
30
  floatingValue,
28
31
  floatingIcon,
29
32
  size = 'small',
33
+ loading,
30
34
  onBlur,
31
35
  onFocus,
32
36
  errorMessage,
33
37
  icon,
38
+ iconColor,
39
+ onPressIcon,
40
+ trailing,
41
+ trailingColor,
42
+ onPressTrailing,
34
43
  disabled = false,
35
44
  floatingIconColor,
36
- iconColor,
37
45
  required = false,
38
46
  errorSpacing,
39
47
  style,
@@ -42,9 +50,10 @@ const InputMoney = forwardRef(
42
50
  accessibilityLabel,
43
51
  hintText,
44
52
  value: _value,
53
+ onPressFloatingIcon,
45
54
  ...props
46
55
  }: InputMoneyProps,
47
- ref,
56
+ ref
48
57
  ) => {
49
58
  const {theme} = useContext(ApplicationContext);
50
59
  const [focused, setFocused] = useState(false);
@@ -63,7 +72,7 @@ const InputMoney = forwardRef(
63
72
  };
64
73
 
65
74
  const [value, setValue] = useState(
66
- defaultValue ? validateText(defaultValue) : '',
75
+ defaultValue ? validateText(defaultValue) : ''
67
76
  );
68
77
 
69
78
  const onClearText = () => {
@@ -99,11 +108,51 @@ const InputMoney = forwardRef(
99
108
  onBlur?.(e);
100
109
  };
101
110
 
111
+ /**
112
+ * Render trailing icon or text
113
+ * @param color
114
+ */
115
+ const renderTrailing = (color?: string) => {
116
+ if (loading) {
117
+ return <Loader type={'spinner'} color={color} style={styles.icon} />;
118
+ }
119
+
120
+ if (icon || trailing) {
121
+ const renderIconTouchable = (icon: ReactNode) => {
122
+ return (
123
+ <TouchableOpacity
124
+ onPress={onPressTrailing ?? onPressIcon}
125
+ style={styles.icon}>
126
+ {icon}
127
+ </TouchableOpacity>
128
+ );
129
+ };
130
+ const trailingValue = icon || trailing;
131
+ if (trailingValue?.includes('_') || trailingValue?.includes('http')) {
132
+ return renderIconTouchable(
133
+ <Icon
134
+ color={color}
135
+ source={(icon || trailing) as string}
136
+ size={24}
137
+ />
138
+ );
139
+ }
140
+ return renderIconTouchable(
141
+ <Text
142
+ typography="action_xs_bold"
143
+ color={color ?? theme.colors.primary}
144
+ numberOfLines={1}>
145
+ {trailingValue!.substring(0, 15)}
146
+ </Text>
147
+ );
148
+ }
149
+ };
150
+
102
151
  const renderInputView = () => {
103
152
  const disabledColor = theme.colors.text.disable;
104
153
  let textColor = theme.colors.text.default;
105
154
  let placeholderColor = theme.colors.text.hint;
106
- let iconTintColor = iconColor;
155
+ let iconTintColor = trailingColor ?? iconColor;
107
156
 
108
157
  if (disabled) {
109
158
  textColor = disabledColor;
@@ -125,6 +174,7 @@ const InputMoney = forwardRef(
125
174
  disabled={disabled}
126
175
  required={required}
127
176
  floatingIcon={floatingIcon}
177
+ onPress={onPressFloatingIcon}
128
178
  />
129
179
  <View style={styles.inputView}>
130
180
  <TextInput
@@ -160,7 +210,7 @@ const InputMoney = forwardRef(
160
210
  />
161
211
  </TouchableOpacity>
162
212
  )}
163
- {!!icon && <Icon color={iconTintColor} source={icon} />}
213
+ {renderTrailing(iconTintColor)}
164
214
  </View>
165
215
  </View>
166
216
  );
@@ -198,7 +248,7 @@ const InputMoney = forwardRef(
198
248
  </View>
199
249
  </ComponentContext.Provider>
200
250
  );
201
- },
251
+ }
202
252
  );
203
253
 
204
254
  export default InputMoney;
@@ -94,7 +94,10 @@ const InputOTP = forwardRef(
94
94
  onChangeText: (text: string) => {
95
95
  _onChangeText(text);
96
96
  },
97
- focus: () => inputRef.current?.focus(),
97
+ focus: () => {
98
+ setFocused(true);
99
+ inputRef.current?.focus()
100
+ },
98
101
  blur: () => inputRef.current?.blur(),
99
102
  setText: (text: string) => _onChangeText(text),
100
103
  }));