@codeleap/web 5.4.4 → 5.4.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.
Files changed (116) hide show
  1. package/dist/components/ActionIcon/types.d.ts +1 -1
  2. package/dist/components/Checkbox/index.js +14 -10
  3. package/dist/components/Checkbox/index.js.map +1 -1
  4. package/dist/components/Checkbox/types.d.ts +4 -2
  5. package/dist/components/DatePicker/components/DayContent.d.ts +11 -0
  6. package/dist/components/DatePicker/components/DayContent.js +43 -0
  7. package/dist/components/DatePicker/components/DayContent.js.map +1 -0
  8. package/dist/components/DatePicker/components/OuterInput.js +2 -2
  9. package/dist/components/DatePicker/components/OuterInput.js.map +1 -1
  10. package/dist/components/DatePicker/components/YearContent.d.ts +9 -0
  11. package/dist/components/DatePicker/components/YearContent.js +33 -0
  12. package/dist/components/DatePicker/components/YearContent.js.map +1 -0
  13. package/dist/components/DatePicker/components/index.d.ts +2 -0
  14. package/dist/components/DatePicker/components/index.js +2 -0
  15. package/dist/components/DatePicker/components/index.js.map +1 -1
  16. package/dist/components/DatePicker/index.js +10 -33
  17. package/dist/components/DatePicker/index.js.map +1 -1
  18. package/dist/components/DatePicker/types.d.ts +5 -6
  19. package/dist/components/InputBase/index.d.ts +2 -5
  20. package/dist/components/InputBase/index.js +19 -11
  21. package/dist/components/InputBase/index.js.map +1 -1
  22. package/dist/components/InputBase/types.d.ts +2 -1
  23. package/dist/components/InputBase/useInputBase.d.ts +60 -0
  24. package/dist/components/InputBase/useInputBase.js +55 -0
  25. package/dist/components/InputBase/useInputBase.js.map +1 -0
  26. package/dist/components/InputBase/useInputBasePartialStyles.d.ts +2 -0
  27. package/dist/components/InputBase/useInputBasePartialStyles.js +40 -0
  28. package/dist/components/InputBase/useInputBasePartialStyles.js.map +1 -0
  29. package/dist/components/Modal/index.d.ts +0 -3
  30. package/dist/components/Modal/index.js +35 -52
  31. package/dist/components/Modal/index.js.map +1 -1
  32. package/dist/components/Modal/types.d.ts +0 -4
  33. package/dist/components/NumberIncrement/index.js +18 -124
  34. package/dist/components/NumberIncrement/index.js.map +1 -1
  35. package/dist/components/NumberIncrement/types.d.ts +5 -6
  36. package/dist/components/NumberIncrement/useNumberIncrement.d.ts +60 -0
  37. package/dist/components/NumberIncrement/useNumberIncrement.js +115 -0
  38. package/dist/components/NumberIncrement/useNumberIncrement.js.map +1 -0
  39. package/dist/components/RadioInput/index.js +14 -14
  40. package/dist/components/RadioInput/index.js.map +1 -1
  41. package/dist/components/RadioInput/types.d.ts +9 -9
  42. package/dist/components/SearchInput/index.js +1 -1
  43. package/dist/components/SearchInput/index.js.map +1 -1
  44. package/dist/components/Select/index.js +5 -7
  45. package/dist/components/Select/index.js.map +1 -1
  46. package/dist/components/Select/styles.d.ts +2 -8
  47. package/dist/components/Select/styles.js.map +1 -1
  48. package/dist/components/Select/types.d.ts +10 -9
  49. package/dist/components/Slider/index.js +16 -46
  50. package/dist/components/Slider/index.js.map +1 -1
  51. package/dist/components/Slider/types.d.ts +4 -2
  52. package/dist/components/Switch/index.js +13 -11
  53. package/dist/components/Switch/index.js.map +1 -1
  54. package/dist/components/Switch/types.d.ts +4 -2
  55. package/dist/components/TextEditor/index.js +7 -14
  56. package/dist/components/TextEditor/index.js.map +1 -1
  57. package/dist/components/TextEditor/types.d.ts +2 -3
  58. package/dist/components/TextInput/index.js +31 -92
  59. package/dist/components/TextInput/index.js.map +1 -1
  60. package/dist/components/TextInput/types.d.ts +8 -7
  61. package/dist/components/TextInput/useTextInput.d.ts +90 -0
  62. package/dist/components/TextInput/useTextInput.js +74 -0
  63. package/dist/components/TextInput/useTextInput.js.map +1 -0
  64. package/dist/lib/tools/index.d.ts +0 -1
  65. package/dist/lib/tools/index.js +0 -1
  66. package/dist/lib/tools/index.js.map +1 -1
  67. package/dist/lib/tools/modal.d.ts +2 -2
  68. package/dist/lib/tools/modal.js +5 -4
  69. package/dist/lib/tools/modal.js.map +1 -1
  70. package/dist/types/utility.d.ts +1 -1
  71. package/package.json +17 -19
  72. package/package.json.bak +1 -3
  73. package/src/components/ActionIcon/types.ts +1 -1
  74. package/src/components/Checkbox/index.tsx +23 -9
  75. package/src/components/Checkbox/types.ts +4 -2
  76. package/src/components/DatePicker/components/DayContent.tsx +52 -0
  77. package/src/components/DatePicker/components/OuterInput.tsx +1 -2
  78. package/src/components/DatePicker/components/YearContent.tsx +39 -0
  79. package/src/components/DatePicker/components/index.tsx +2 -0
  80. package/src/components/DatePicker/index.tsx +33 -84
  81. package/src/components/DatePicker/types.ts +5 -6
  82. package/src/components/InputBase/index.tsx +9 -8
  83. package/src/components/InputBase/types.ts +2 -1
  84. package/src/components/InputBase/useInputBase.ts +56 -0
  85. package/src/components/InputBase/useInputBasePartialStyles.ts +37 -0
  86. package/src/components/Modal/index.tsx +64 -64
  87. package/src/components/Modal/types.ts +0 -4
  88. package/src/components/NumberIncrement/index.tsx +44 -141
  89. package/src/components/NumberIncrement/types.ts +5 -6
  90. package/src/components/NumberIncrement/useNumberIncrement.ts +149 -0
  91. package/src/components/RadioInput/index.tsx +32 -17
  92. package/src/components/RadioInput/types.ts +16 -15
  93. package/src/components/SearchInput/index.tsx +1 -1
  94. package/src/components/Select/index.tsx +6 -11
  95. package/src/components/Select/styles.ts +2 -2
  96. package/src/components/Select/types.ts +10 -9
  97. package/src/components/Slider/index.tsx +28 -52
  98. package/src/components/Slider/types.ts +4 -2
  99. package/src/components/Switch/index.tsx +19 -8
  100. package/src/components/Switch/types.ts +4 -2
  101. package/src/components/TextEditor/index.tsx +6 -14
  102. package/src/components/TextEditor/types.ts +2 -3
  103. package/src/components/TextInput/index.tsx +54 -103
  104. package/src/components/TextInput/types.ts +8 -7
  105. package/src/components/TextInput/useTextInput.ts +101 -0
  106. package/src/lib/tools/index.ts +0 -1
  107. package/src/lib/tools/modal.ts +3 -3
  108. package/src/types/utility.ts +1 -1
  109. package/dist/lib/tools/navigation/index.d.ts +0 -58
  110. package/dist/lib/tools/navigation/index.js +0 -235
  111. package/dist/lib/tools/navigation/index.js.map +0 -1
  112. package/dist/lib/tools/navigation/types.d.ts +0 -32
  113. package/dist/lib/tools/navigation/types.js +0 -3
  114. package/dist/lib/tools/navigation/types.js.map +0 -1
  115. package/src/lib/tools/navigation/index.tsx +0 -282
  116. package/src/lib/tools/navigation/types.ts +0 -53
@@ -1,4 +1,3 @@
1
- import { FormTypes, yup } from '@codeleap/deprecated'
2
1
  import { MutableRefObject } from 'react'
3
2
  import { GroupBase, NoticeProps, OptionProps, Props } from 'react-select'
4
3
  import { AsyncProps } from 'react-select/async'
@@ -7,6 +6,8 @@ import { ButtonProps } from '../Button'
7
6
  import { InputBaseProps } from '../InputBase'
8
7
  import { SelectComposition, OptionState } from './styles'
9
8
  import { ICSS, StyledProp } from '@codeleap/styles'
9
+ import { Label, Option, Options } from '@codeleap/types'
10
+ import { Validator } from '@codeleap/form'
10
11
 
11
12
  type SelectValue<T, Multi extends boolean> = Multi extends true ? T[] : T
12
13
 
@@ -14,23 +15,23 @@ type OmitWithValues<T> = Omit<T, 'options' | 'value' | 'isMulti' | 'loadOptions'
14
15
 
15
16
  type DynamicSelectProps<T, Multi extends boolean> =
16
17
  ({
17
- loadOptions?: (search: string) => Promise<FormTypes.Options<T>>
18
- defaultValues?: FormTypes.Options<T>
18
+ loadOptions?: (search: string) => Promise<Options<T>>
19
+ defaultValues?: Options<T>
19
20
  } & OmitWithValues<
20
- AsyncProps<FormTypes.Option<T>, Multi, GroupBase<FormTypes.Option<T>>>
21
+ AsyncProps<Option<T>, Multi, GroupBase<Option<T>>>
21
22
  >) |
22
23
  ({
23
24
  loadOptions?: never
24
25
  } & OmitWithValues<
25
- Props<FormTypes.Option<T>, Multi, GroupBase<FormTypes.Option<T>>>
26
+ Props<Option<T>, Multi, GroupBase<Option<T>>>
26
27
  >)
27
28
 
28
29
  export type ReactSelectProps<T, Multi extends boolean = false> = Omit<InputBaseProps, 'style'> & {
29
- options: FormTypes.Options<T> & { itemProps?: ButtonProps }
30
+ options: Options<T> & { itemProps?: ButtonProps }
30
31
  value: SelectValue<T, Multi>
31
32
  onValueChange?: (value: SelectValue<T, Multi>) => void
32
33
  multiple?: Multi
33
- validate?: FormTypes.ValidatorWithoutForm<SelectValue<T, Multi>> | yup.Schema<SelectValue<T, Multi>>
34
+ validate?: Validator<SelectValue<T, Multi>, any, any>
34
35
  } & DynamicSelectProps<T, Multi>
35
36
 
36
37
  export type ComponentPartProps = {
@@ -97,9 +98,9 @@ export type SelectProps<T = any, Multi extends boolean = false> = React.PropsWit
97
98
  limit?: number
98
99
  loadInitialValue?: boolean
99
100
  loadingMessage?: string
100
- selectedOption?: { label: FormTypes.Label; value: T } | SelectValue<T, Multi>
101
+ selectedOption?: { label: Label; value: T } | SelectValue<T, Multi>
101
102
  selectRef?: MutableRefObject<any>
102
- setSelectedOption?: (value: { label: FormTypes.Label; value: T } | SelectValue<T, Multi>) => void
103
+ setSelectedOption?: (value: { label: Label; value: T } | SelectValue<T, Multi>) => void
103
104
  style?: StyledProp<SelectComposition>
104
105
  } & Omit<
105
106
  ReactSelectProps<T, Multi>,
@@ -1,7 +1,6 @@
1
1
  import React from 'react'
2
2
  import { TypeGuards } from '@codeleap/types'
3
3
  import { onMount, useRef } from '@codeleap/hooks'
4
-
5
4
  import { View } from '../View'
6
5
  import { InputBase, selectInputBaseProps } from '../InputBase'
7
6
  import { Text } from '../Text'
@@ -16,6 +15,9 @@ import { SliderProps, TrackMarkProps } from './types'
16
15
  import { useStylesFor } from '../../lib/hooks/useStylesFor'
17
16
  import { AnyRecord, IJSX, mergeStyles, StyledComponentProps } from '@codeleap/styles'
18
17
  import { WebStyleRegistry } from '../../lib/WebStyleRegistry'
18
+ import { useInputBase } from '../InputBase/useInputBase'
19
+ import { fields } from '@codeleap/form'
20
+ import { useInputBasePartialStyles } from '../InputBase/useInputBasePartialStyles'
19
21
 
20
22
  export * from './styles'
21
23
  export * from './types'
@@ -45,6 +47,7 @@ export const Slider = (props: SliderProps) => {
45
47
  onValueChange,
46
48
  onValueCommit,
47
49
  value: _value,
50
+ field,
48
51
  label,
49
52
  debugName,
50
53
  style,
@@ -65,8 +68,14 @@ export const Slider = (props: SliderProps) => {
65
68
 
66
69
  const styles = useStylesFor(Slider.styleRegistryName, style)
67
70
 
68
- const isUniqueValue = !TypeGuards.isArray(_value)
69
- const value = isUniqueValue ? [_value] : _value
71
+ const {
72
+ wrapperRef,
73
+ inputValue,
74
+ onInputValueChange,
75
+ } = useInputBase(field, fields.number, { value: _value, onValueChange })
76
+
77
+ const isUniqueValue = !TypeGuards.isArray(inputValue)
78
+ const value = isUniqueValue ? [inputValue] : inputValue
70
79
 
71
80
  const _defaultValue = TypeGuards.isArray(defaultSliderValue) ? defaultSliderValue : [defaultSliderValue]
72
81
 
@@ -80,43 +89,13 @@ export const Slider = (props: SliderProps) => {
80
89
  })
81
90
 
82
91
  const handleChange: SliderProps['onValueChange'] = (newValue: Array<number>) => {
83
- onValueChange?.(isUniqueValue ? newValue?.[0] : newValue)
92
+ onInputValueChange?.(isUniqueValue ? newValue?.[0] : newValue)
84
93
  }
85
94
 
86
95
  const handleValueCommit = (newValue: Array<number>) => {
87
96
  onValueCommit?.(newValue)
88
97
  }
89
98
 
90
- const thumbStyle = React.useMemo(() => {
91
- return mergeStyles([
92
- styles.thumb,
93
- disabled && styles['thumb:disabled'],
94
- ])
95
- }, [])
96
-
97
- const trackStyle = React.useMemo(() => {
98
- return mergeStyles([
99
- styles.track,
100
- disabled && styles['track:disabled'],
101
- styles.unselectedTrack,
102
- disabled && styles['unselectedTrack:disabled'],
103
- ])
104
- }, [disabled])
105
-
106
- const selectedTrackStyle = React.useMemo(() => {
107
- return mergeStyles([
108
- styles.selectedTrack,
109
- disabled && styles['selectedTrack:disabled'],
110
- ])
111
- }, [disabled])
112
-
113
- const containerStyle = React.useMemo(() => {
114
- return mergeStyles([
115
- styles.sliderContainer,
116
- disabled && styles['sliderContainer:disabled'],
117
- ])
118
- }, [disabled])
119
-
120
99
  const trackMarksHaveContent = !(TypeGuards.isArray(trackMarks) || TypeGuards.isNil(trackMarks))
121
100
 
122
101
  const trackMarksProp = React.useMemo(() => {
@@ -126,19 +105,15 @@ export const Slider = (props: SliderProps) => {
126
105
  return Object.keys(trackMarks).map((key) => Number(key))
127
106
  }, [trackMarksHaveContent])
128
107
 
129
- const trackMarkStyle = React.useMemo(() => {
130
- return mergeStyles([
131
- styles.trackMark,
132
- disabled && styles['trackMark:disabled'],
133
- ])
134
- }, [disabled])
108
+ const partialStyles = useInputBasePartialStyles(
109
+ styles,
110
+ ['thumb', 'track', 'selectedTrack', 'unselectedTrack', 'sliderContainer', 'trackMark', 'trackMarkWrapper'],
111
+ { disabled }
112
+ )
135
113
 
136
- const trackMarkWrapperStyle = React.useMemo(() => {
137
- return mergeStyles([
138
- styles.trackMarkWrapper,
139
- disabled && styles['trackMarkWrapper:disabled'],
140
- ])
141
- }, [disabled])
114
+ const trackStyle = React.useMemo(() => {
115
+ return mergeStyles([partialStyles?.track, partialStyles.unselectedTrack])
116
+ }, [partialStyles?.track, partialStyles.unselectedTrack])
142
117
 
143
118
  const sliderLabel = React.useMemo(() => {
144
119
  if (TypeGuards.isNil(indicatorLabel) || !indicatorLabel?.order && !indicatorLabel?.transformer) {
@@ -168,6 +143,7 @@ export const Slider = (props: SliderProps) => {
168
143
  return (
169
144
  <InputBase
170
145
  {...inputBaseProps}
146
+ ref={wrapperRef}
171
147
  disabled={disabled}
172
148
  style={styles}
173
149
  labelAsRow
@@ -182,20 +158,20 @@ export const Slider = (props: SliderProps) => {
182
158
  defaultValue={defaultValue}
183
159
  onValueCommit={handleValueCommit}
184
160
  onValueChange={handleChange}
185
- style={containerStyle}
161
+ style={partialStyles?.sliderContainer}
186
162
  value={value}
187
163
  minStepsBetweenThumbs={minStepsBetweenThumbs}
188
164
  >
189
165
  <SliderTrack style={trackStyle}>
190
- <SliderRange style={selectedTrackStyle} />
166
+ <SliderRange style={partialStyles?.selectedTrack} />
191
167
  </SliderTrack>
192
168
 
193
169
  {defaultValue.map((_, i) => (
194
170
  <SliderThumb
195
171
  key={i}
196
- style={thumbStyle}
172
+ style={partialStyles?.thumb}
197
173
  onClick={() => {
198
- if (onPressThumbSetValue) onValueChange?.(value)
174
+ if (onPressThumbSetValue) onInputValueChange?.(value)
199
175
  if (TypeGuards.isFunction(onPressThumb)) onPressThumb?.(value, i)
200
176
  }}
201
177
  />
@@ -203,7 +179,7 @@ export const Slider = (props: SliderProps) => {
203
179
  </SliderContainer>
204
180
 
205
181
  {trackMarksProp ?
206
- <View style={trackMarkWrapperStyle}>
182
+ <View style={partialStyles?.trackMarkWrapper}>
207
183
  {
208
184
  trackMarksProp.map((_, idx) => {
209
185
  let idxStyle = {}
@@ -225,7 +201,7 @@ export const Slider = (props: SliderProps) => {
225
201
  }
226
202
  }
227
203
 
228
- const style = mergeStyles([trackMarkStyle, idxStyle])
204
+ const style = mergeStyles([partialStyles?.trackMark, idxStyle])
229
205
 
230
206
  if (!trackMarksHaveContent) {
231
207
  return <SliderTrackMark
@@ -3,6 +3,7 @@ import { InputBaseProps } from '../InputBase'
3
3
  import { SliderComposition } from './styles'
4
4
  import { SliderProps as PrimitiveSliderProps } from '@radix-ui/react-slider'
5
5
  import { CSSProperties } from 'react'
6
+ import { NumberField } from '@codeleap/form'
6
7
 
7
8
  export type SliderProps =
8
9
  Partial<Omit<PrimitiveSliderProps, 'value' | 'onValueChange' | 'style'>> &
@@ -13,8 +14,9 @@ export type SliderProps =
13
14
  separator?: string
14
15
  transformer?: (value: number[], defaultValue: PrimitiveSliderProps['defaultValue']) => string
15
16
  }
16
- value: number | number[]
17
- onValueChange: (val: number | number[]) => void
17
+ field?: NumberField<any>
18
+ value?: number | number[]
19
+ onValueChange?: (val: number | number[]) => void
18
20
  style?: StyledProp<SliderComposition>
19
21
  trackMarks?: Record<number, string>
20
22
  trackMarkComponent?: React.ComponentType<TrackMarkProps>
@@ -6,6 +6,8 @@ import { motion } from 'framer-motion'
6
6
  import { AnyRecord, IJSX, mergeStyles, StyledComponentProps } from '@codeleap/styles'
7
7
  import { useStylesFor } from '../../lib/hooks/useStylesFor'
8
8
  import { SwitchProps } from './types'
9
+ import { useInputBase } from '../InputBase/useInputBase'
10
+ import { fields } from '@codeleap/form'
9
11
 
10
12
  export * from './styles'
11
13
  export * from './types'
@@ -29,10 +31,18 @@ export const Switch = (props: SwitchProps) => {
29
31
  onValueChange,
30
32
  onChange,
31
33
  switchOnLeft,
34
+ field,
32
35
  } = switchProps
33
36
 
34
37
  const styles = useStylesFor(Switch.styleRegistryName, style)
35
38
 
39
+ const {
40
+ validation,
41
+ wrapperRef,
42
+ inputValue,
43
+ onInputValueChange,
44
+ } = useInputBase<boolean>(field, fields.boolean, { value, onValueChange })
45
+
36
46
  const trackAnimation = useAnimatedVariantStyles({
37
47
  variantStyles: styles,
38
48
  animatedProperties: ['track:off', 'track:disabled', 'track:on', 'track:disabled-on', 'track:disabled-off'],
@@ -40,16 +50,16 @@ export const Switch = (props: SwitchProps) => {
40
50
  'worklet'
41
51
  let disabledStyle = {}
42
52
  if (disabled) {
43
- disabledStyle = value ? styles['track:disabled-on'] : styles['track:disabled-off']
53
+ disabledStyle = inputValue ? styles['track:disabled-on'] : styles['track:disabled-off']
44
54
  }
45
- const style = value ? styles['track:on'] : styles['track:off']
55
+ const style = inputValue ? styles['track:on'] : styles['track:off']
46
56
 
47
57
  return {
48
58
  ...style,
49
59
  ...disabledStyle,
50
60
  }
51
61
  },
52
- dependencies: [value, disabled],
62
+ dependencies: [inputValue, disabled],
53
63
  })
54
64
 
55
65
  const thumbAnimation = useAnimatedVariantStyles({
@@ -59,15 +69,15 @@ export const Switch = (props: SwitchProps) => {
59
69
  'worklet'
60
70
  let disabledStyle = {}
61
71
  if (disabled) {
62
- disabledStyle = value ? styles['thumb:disabled-on'] : styles['thumb:disabled-off']
72
+ disabledStyle = inputValue ? styles['thumb:disabled-on'] : styles['thumb:disabled-off']
63
73
  }
64
- const style = value ? styles['thumb:on'] : styles['thumb:off']
74
+ const style = inputValue ? styles['thumb:on'] : styles['thumb:off']
65
75
  return {
66
76
  ...style,
67
77
  ...disabledStyle,
68
78
  }
69
79
  },
70
- dependencies: [value, disabled],
80
+ dependencies: [inputValue, disabled],
71
81
  })
72
82
 
73
83
  // @ts-expect-error icss type
@@ -79,14 +89,15 @@ export const Switch = (props: SwitchProps) => {
79
89
  const handleChange = (e) => {
80
90
  if (disabled) return
81
91
  if (e?.type === 'click' || e?.keyCode === 13 || e?.key === 'Enter') {
82
- if (onValueChange) onValueChange?.(!value)
83
- if (onChange) onChange?.(!value)
92
+ onInputValueChange?.(!inputValue)
93
+ if (onChange) onChange?.(!inputValue)
84
94
  }
85
95
  }
86
96
 
87
97
  return (
88
98
  <InputBase
89
99
  {...inputBaseProps}
100
+ ref={wrapperRef}
90
101
  debugName={debugName}
91
102
  style={styles}
92
103
  order={_switchOnLeft ? reversedOrder : InputBaseDefaultOrder}
@@ -1,13 +1,15 @@
1
1
  import { StyledProp } from '@codeleap/styles'
2
2
  import { InputBaseProps } from '../InputBase'
3
3
  import { SwitchComposition } from './styles'
4
+ import { BooleanField } from '@codeleap/form'
4
5
 
5
6
  export type SwitchProps =
6
7
  Pick<InputBaseProps, 'debugName' | 'disabled' | 'label'> &
7
8
  {
8
9
  style?: StyledProp<SwitchComposition>
9
- value: boolean
10
- onValueChange: (value: boolean) => void
11
10
  onChange?: (value: boolean) => void
12
11
  switchOnLeft?: boolean
12
+ field?: BooleanField<any>
13
+ value?: boolean
14
+ onValueChange?: (value: boolean) => void
13
15
  }
@@ -1,12 +1,12 @@
1
1
  import React from 'react'
2
- import { onUpdate, useCallback, useState } from '@codeleap/hooks'
3
- import { useValidate } from '@codeleap/deprecated'
2
+ import { onUpdate, useCallback } from '@codeleap/hooks'
4
3
  import { BubbleMenu, FloatingMenu, EditorContent } from '@tiptap/react'
5
4
  import { FileInput, Text, View } from '../components'
6
5
  import { TextEditorProps } from './types'
7
6
  import { useStylesFor } from '../../lib/hooks/useStylesFor'
8
7
  import { WebStyleRegistry } from '../../lib/WebStyleRegistry'
9
8
  import { AnyRecord, IJSX, StyledComponentProps } from '@codeleap/styles'
9
+ import { useValidate } from '@codeleap/form'
10
10
 
11
11
  export * from './styles'
12
12
  export * from './types'
@@ -20,7 +20,6 @@ export const TextEditor = (props: TextEditorProps) => {
20
20
  floatingMenuProps,
21
21
  toolbarComponent,
22
22
  fileInputRef,
23
- _error,
24
23
  validate,
25
24
  } = {
26
25
  ...TextEditor.defaultProps,
@@ -29,22 +28,15 @@ export const TextEditor = (props: TextEditorProps) => {
29
28
 
30
29
  const styles = useStylesFor(TextEditor.styleRegistryName, style)
31
30
 
32
- const [_isFocused, setIsFocused] = useState(false)
33
31
  const validation = useValidate(editor?.getText() ?? '', validate)
34
32
 
35
- const hasError = !validation.isValid || _error
36
- const errorMessage = validation.message || _error
37
33
  const isDisabled = !editor?.isEditable ?? null
38
34
 
39
35
  const handleBlur = React.useCallback(() => {
40
36
  validation?.onInputBlurred()
41
- setIsFocused(false)
42
37
  }, [validation?.onInputBlurred])
43
38
 
44
- const handleFocus = React.useCallback(() => {
45
- validation?.onInputFocused()
46
- setIsFocused(true)
47
- }, [validation?.onInputFocused])
39
+ const handleFocus = React.useCallback(() => {}, [])
48
40
 
49
41
  onUpdate(() => {
50
42
  editor?.on('blur', handleBlur)
@@ -80,7 +72,7 @@ export const TextEditor = (props: TextEditorProps) => {
80
72
 
81
73
  const editorStyles = [
82
74
  styles.editor,
83
- hasError && styles['editor:error'],
75
+ validation?.showError && styles['editor:error'],
84
76
  isDisabled && styles['editor:disabled'],
85
77
  ]
86
78
 
@@ -90,7 +82,7 @@ export const TextEditor = (props: TextEditorProps) => {
90
82
  <View
91
83
  style={[
92
84
  styles.wrapper,
93
- hasError && styles['wrapper:error'],
85
+ validation?.showError && styles['wrapper:error'],
94
86
  {
95
87
  '.tiptap': editorStyles,
96
88
  },
@@ -101,7 +93,7 @@ export const TextEditor = (props: TextEditorProps) => {
101
93
  <_BubbleMenu />
102
94
  <_FloatingMenu />
103
95
  <EditorContent editor={editor} />
104
- {hasError ? <Text text={errorMessage as string} style={styles['errorMessage:error']} /> : null}
96
+ {validation?.showError ? <Text text={validation?.message as string} style={styles['errorMessage:error']} /> : null}
105
97
  <FileInput ref={fileInputRef} />
106
98
  </View>
107
99
  )
@@ -1,10 +1,10 @@
1
1
  import { RefObject } from 'react'
2
2
  import { AnyFunction } from '@codeleap/types'
3
- import { FormTypes, yup } from '@codeleap/deprecated'
4
3
  import { StyledProp } from '@codeleap/styles'
5
4
  import { BubbleMenuProps, Editor, FloatingMenuProps } from '@tiptap/react'
6
5
  import { FileInputRef } from '../FileInput'
7
6
  import { TextEditorComposition } from './styles'
7
+ import { Validator } from '@codeleap/form'
8
8
 
9
9
  export type TextEditorProps = React.PropsWithChildren<{
10
10
  editor: Editor & {
@@ -18,6 +18,5 @@ export type TextEditorProps = React.PropsWithChildren<{
18
18
  floatingMenuProps?: FloatingMenuProps & { renderContent: React.ReactNode }
19
19
  toolbarComponent?: JSX.Element
20
20
  fileInputRef?: RefObject<FileInputRef>
21
- _error?: boolean
22
- validate?: FormTypes.ValidatorWithoutForm<string> | yup.Schema<string>
21
+ validate?: Validator<string, any, any>
23
22
  }>
@@ -1,121 +1,98 @@
1
- import { useBooleanToggle } from '@codeleap/hooks'
2
1
  import { TypeGuards } from '@codeleap/types'
3
- import { useValidate } from '@codeleap/deprecated'
4
- import React, {
5
- forwardRef,
6
- useImperativeHandle,
7
- useRef,
8
- useState,
9
- } from 'react'
2
+ import React, { forwardRef, useImperativeHandle } from 'react'
10
3
  import TextareaAutosize from 'react-autosize-textarea'
11
4
  import InputMask from 'react-input-mask'
12
5
  import { Touchable } from '../Touchable'
13
6
  import { InputBase, selectInputBaseProps } from '../InputBase'
14
- import { getMaskInputProps } from './mask'
15
7
  import { getTestId } from '../../lib/utils/test'
16
8
  import { InputRef, TextInputProps } from './types'
17
- import { FileInputRef } from '../FileInput'
18
9
  import { AnyRecord, AppIcon, IJSX, StyledComponentProps, StyledComponentWithProps } from '@codeleap/styles'
19
10
  import { useStylesFor } from '../../lib/hooks/useStylesFor'
20
11
  import { WebStyleRegistry } from '../../lib/WebStyleRegistry'
12
+ import { useTextInput } from './useTextInput'
13
+ import { useInputBasePartialStyles } from '../InputBase/useInputBasePartialStyles'
21
14
 
22
15
  export * from './types'
23
16
  export * from './styles'
24
17
  export * from './mask'
25
18
 
26
- export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputRef) => {
19
+ export const TextInput = forwardRef<InputRef, TextInputProps>((props, inputRef) => {
20
+ const allProps = {
21
+ ...TextInput.defaultProps,
22
+ ...props,
23
+ }
24
+
27
25
  const {
28
26
  inputBaseProps,
29
27
  others,
30
- } = selectInputBaseProps({
31
- ...TextInput.defaultProps,
32
- ...props,
33
- })
28
+ } = selectInputBaseProps(allProps)
34
29
 
35
30
  const {
36
31
  style,
37
- value,
38
- validate,
39
32
  debugName,
40
33
  visibilityToggle,
41
34
  password,
42
35
  onPress,
43
- multiline,
44
36
  caretColor,
45
- focused,
46
- _error,
47
- masking,
48
37
  visibleIcon,
49
38
  hiddenIcon,
39
+ focused,
50
40
  ...textInputProps
51
41
  } = others as TextInputProps
52
42
 
53
- const innerInputRef = useRef<InputRef>(null)
54
-
55
43
  const styles = useStylesFor(TextInput.styleRegistryName, style)
56
44
 
57
- const [_isFocused, setIsFocused] = useState(false)
45
+ const {
46
+ isMultiline,
47
+ isMasked,
48
+ isFocused: isInputFocused,
49
+ secureTextEntry,
50
+ handleBlur,
51
+ handleFocus,
52
+ handleChange,
53
+ maskProps,
54
+ innerInputRef,
55
+ wrapperRef,
56
+ errorMessage,
57
+ toggleSecureTextEntry,
58
+ hasMultipleLines,
59
+ hasError,
60
+ inputValue,
61
+ } = useTextInput(allProps)
62
+
63
+ const isFocused = isInputFocused || focused
58
64
 
59
- const isFocused = _isFocused || focused
65
+ const isDisabled = !!inputBaseProps.disabled
60
66
 
61
- const [secureTextEntry, toggleSecureTextEntry] = useBooleanToggle(true)
67
+ const partialStyles = useInputBasePartialStyles(styles, ['placeholder', 'selection'], {
68
+ disabled: isDisabled,
69
+ error: !!hasError,
70
+ focus: isFocused,
71
+ })
62
72
 
63
- const isMultiline = multiline
73
+ const InputElement = isMasked ? InputMask : isMultiline ? TextareaAutosize : 'input'
64
74
 
65
- const isMasked = !TypeGuards.isNil(masking)
66
- const maskProps = isMasked ? getMaskInputProps({ masking }) : null
75
+ const isPressable = TypeGuards.isFunction(onPress)
67
76
 
68
- const InputElement = isMasked ? InputMask : isMultiline ? TextareaAutosize : 'input'
77
+ const focus = () => {
78
+ if (isMasked) {
79
+ // @ts-expect-error
80
+ innerInputRef.current?.getInputDOMNode()?.focus()
81
+ }
82
+
83
+ innerInputRef.current?.focus?.()
84
+ }
69
85
 
70
- // @ts-ignore
71
86
  useImperativeHandle(inputRef, () => {
72
87
  return {
73
- focus: () => {
74
- if (isMasked) {
75
- // @ts-expect-error
76
- innerInputRef.current?.getInputDOMNode()?.focus()
77
- }
78
- innerInputRef.current?.focus?.()
79
- },
88
+ focus: () => focus(),
80
89
  isTextInput: true,
81
90
  getInputRef: () => {
82
- return innerInputRef.current
91
+ return innerInputRef.current as unknown as HTMLInputElement
83
92
  },
84
93
  }
85
94
  }, [!!innerInputRef?.current?.focus])
86
95
 
87
- const isPressable = TypeGuards.isFunction(onPress)
88
-
89
- const validation = useValidate(
90
- value,
91
- TypeGuards.isFunction(maskProps?.validator) ? maskProps?.validator : validate,
92
- )
93
-
94
- const handleBlur = React.useCallback((e: React.FocusEvent<HTMLInputElement, Element>) => {
95
- validation?.onInputBlurred()
96
- setIsFocused(false)
97
- props?.onBlur?.(e)
98
- }, [validation?.onInputBlurred, props?.onBlur])
99
-
100
- const handleFocus = React.useCallback((e: React.FocusEvent<HTMLInputElement, Element>) => {
101
- validation?.onInputFocused()
102
- setIsFocused(true)
103
- props?.onFocus?.(e)
104
- }, [validation?.onInputFocused, props?.onFocus])
105
-
106
- const handleChange = (event: React.ChangeEvent<HTMLInputElement>) => {
107
- const _text = event?.target?.value
108
-
109
- const _value = isMasked && maskProps?.notSaveFormatted
110
- ? maskProps?.getRawValue(_text)
111
- : _text
112
-
113
- if (props?.onChange) props?.onChange(event)
114
- if (props?.onChangeText) props?.onChangeText(_value)
115
- }
116
-
117
- const isDisabled = !!inputBaseProps.disabled
118
-
119
96
  const visibilityToggleProps = visibilityToggle ? {
120
97
  onPress: toggleSecureTextEntry,
121
98
  icon: (secureTextEntry ? hiddenIcon : visibleIcon) as AppIcon,
@@ -128,27 +105,6 @@ export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputR
128
105
  editable: false,
129
106
  caretHidden: true,
130
107
  } : {}
131
- const rows = textInputProps?.rows ?? (
132
- isMultiline ? 2 : undefined
133
- )
134
- const hasMultipleLines = isMultiline && (String(value)?.includes('\n') || !!rows)
135
-
136
- const hasError = !validation.isValid || _error
137
- const errorMessage = validation.message || _error
138
-
139
- const placeholderStyles = [
140
- styles.placeholder,
141
- isFocused && styles['placeholder:focus'],
142
- hasError && styles['placeholder:error'],
143
- isDisabled && styles['placeholder:disabled'],
144
- ]
145
-
146
- const selectionStyles = [
147
- styles.selection,
148
- isFocused && styles['selection:focus'],
149
- hasError && styles['selection:error'],
150
- isDisabled && styles['selection:disabled'],
151
- ]
152
108
 
153
109
  const secureTextProps = (password && secureTextEntry) && {
154
110
  type: 'password',
@@ -166,6 +122,7 @@ export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputR
166
122
  <InputBase
167
123
  innerWrapper={isPressable ? Touchable : undefined}
168
124
  {...inputBaseProps}
125
+ ref={wrapperRef}
169
126
  debugName={debugName}
170
127
  error={hasError ? errorMessage : null}
171
128
  style={{
@@ -179,11 +136,7 @@ export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputR
179
136
  innerWrapperProps={{
180
137
  ...(inputBaseProps.innerWrapperProps || {}),
181
138
  [inputBaseAction]: () => {
182
- if (isMasked) {
183
- // @ts-expect-error
184
- innerInputRef.current?.getInputDOMNode()?.focus()
185
- }
186
- innerInputRef.current?.focus?.()
139
+ focus()
187
140
  if (isPressable) onPress?.()
188
141
  },
189
142
  debugName,
@@ -196,11 +149,7 @@ export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputR
196
149
  {...buttonModeProps}
197
150
  {...secureTextProps}
198
151
  {...textInputProps}
199
- value={value}
200
- onChange={(e) => handleChange(e)}
201
- // @ts-ignore
202
152
  onBlur={handleBlur}
203
- // @ts-ignore
204
153
  onFocus={handleFocus}
205
154
  css={[
206
155
  styles.input,
@@ -210,10 +159,10 @@ export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputR
210
159
  isDisabled && styles['input:disabled'],
211
160
  hasMultipleLines && styles['input:hasMultipleLines'],
212
161
  {
213
- '&::placeholder': placeholderStyles,
162
+ '&::placeholder': partialStyles?.placeholder,
214
163
  },
215
164
  {
216
- '&::selection': selectionStyles,
165
+ '&::selection': partialStyles?.selection,
217
166
  },
218
167
  {
219
168
  '&:focus': [
@@ -224,6 +173,8 @@ export const TextInput = forwardRef<FileInputRef, TextInputProps>((props, inputR
224
173
  },
225
174
  ]}
226
175
  {...maskProps}
176
+ value={inputValue}
177
+ onChange={handleChange}
227
178
  ref={innerInputRef}
228
179
  data-testid={testId}
229
180
  />