@utilitywarehouse/hearth-react-native 0.24.0 → 0.26.0

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 (90) hide show
  1. package/.turbo/turbo-build.log +1 -1
  2. package/.turbo/turbo-lint.log +13 -13
  3. package/CHANGELOG.md +72 -0
  4. package/build/components/DatePicker/DatePickerCalendar.js +4 -9
  5. package/build/components/Modal/Modal.d.ts +1 -1
  6. package/build/components/Modal/Modal.js +30 -7
  7. package/build/components/Modal/Modal.props.d.ts +4 -2
  8. package/build/components/TimePicker/TimePicker.d.ts +6 -0
  9. package/build/components/TimePicker/TimePicker.js +78 -0
  10. package/build/components/TimePicker/TimePicker.props.d.ts +45 -0
  11. package/build/components/TimePicker/TimePicker.props.js +1 -0
  12. package/build/components/TimePicker/TimePickerView.d.ts +12 -0
  13. package/build/components/TimePicker/TimePickerView.js +130 -0
  14. package/build/components/TimePicker/TimePickerWheel.d.ts +8 -0
  15. package/build/components/TimePicker/TimePickerWheel.js +78 -0
  16. package/build/components/{DatePicker/time-picker/wheel-web.d.ts → TimePicker/TimePickerWheel.web.d.ts} +4 -4
  17. package/build/components/TimePicker/TimePickerWheel.web.js +122 -0
  18. package/build/components/TimePicker/index.d.ts +6 -0
  19. package/build/components/TimePicker/index.js +3 -0
  20. package/build/components/TimePickerInput/TimePickerInput.d.ts +6 -0
  21. package/build/components/TimePickerInput/TimePickerInput.js +127 -0
  22. package/build/components/TimePickerInput/TimePickerInput.props.d.ts +52 -0
  23. package/build/components/TimePickerInput/TimePickerInput.props.js +1 -0
  24. package/build/components/TimePickerInput/TimePickerInputDoneButton.d.ts +8 -0
  25. package/build/components/TimePickerInput/TimePickerInputDoneButton.js +19 -0
  26. package/build/components/TimePickerInput/TimePickerInputDoneButton.web.d.ts +5 -0
  27. package/build/components/TimePickerInput/TimePickerInputDoneButton.web.js +5 -0
  28. package/build/components/TimePickerInput/index.d.ts +2 -0
  29. package/build/components/TimePickerInput/index.js +1 -0
  30. package/build/components/index.d.ts +2 -0
  31. package/build/components/index.js +2 -0
  32. package/docs/components/AllComponents.web.tsx +30 -0
  33. package/package.json +3 -2
  34. package/src/components/DatePicker/DatePickerCalendar.tsx +30 -13
  35. package/src/components/Modal/Modal.docs.mdx +9 -3
  36. package/src/components/Modal/Modal.props.ts +4 -2
  37. package/src/components/Modal/Modal.tsx +44 -7
  38. package/src/components/TimePicker/TimePicker.docs.mdx +84 -0
  39. package/src/components/TimePicker/TimePicker.figma.tsx +29 -0
  40. package/src/components/TimePicker/TimePicker.props.ts +45 -0
  41. package/src/components/TimePicker/TimePicker.stories.tsx +85 -0
  42. package/src/components/TimePicker/TimePicker.tsx +150 -0
  43. package/src/components/TimePicker/TimePickerView.tsx +216 -0
  44. package/src/components/TimePicker/TimePickerWheel.tsx +154 -0
  45. package/src/components/TimePicker/TimePickerWheel.web.tsx +217 -0
  46. package/src/components/TimePicker/index.ts +8 -0
  47. package/src/components/TimePickerInput/TimePickerInput.docs.mdx +135 -0
  48. package/src/components/TimePickerInput/TimePickerInput.figma.tsx +34 -0
  49. package/src/components/TimePickerInput/TimePickerInput.props.ts +55 -0
  50. package/src/components/TimePickerInput/TimePickerInput.stories.tsx +175 -0
  51. package/src/components/TimePickerInput/TimePickerInput.tsx +283 -0
  52. package/src/components/TimePickerInput/TimePickerInputDoneButton.tsx +42 -0
  53. package/src/components/TimePickerInput/TimePickerInputDoneButton.web.tsx +7 -0
  54. package/src/components/TimePickerInput/index.ts +2 -0
  55. package/src/components/index.ts +2 -0
  56. package/build/components/DatePicker/TimePicker.d.ts +0 -3
  57. package/build/components/DatePicker/TimePicker.js +0 -84
  58. package/build/components/DatePicker/time-picker/animated-math.d.ts +0 -4
  59. package/build/components/DatePicker/time-picker/animated-math.js +0 -19
  60. package/build/components/DatePicker/time-picker/period-native.d.ts +0 -6
  61. package/build/components/DatePicker/time-picker/period-native.js +0 -17
  62. package/build/components/DatePicker/time-picker/period-picker.d.ts +0 -6
  63. package/build/components/DatePicker/time-picker/period-picker.js +0 -10
  64. package/build/components/DatePicker/time-picker/period-web.d.ts +0 -6
  65. package/build/components/DatePicker/time-picker/period-web.js +0 -21
  66. package/build/components/DatePicker/time-picker/wheel-native.d.ts +0 -8
  67. package/build/components/DatePicker/time-picker/wheel-native.js +0 -19
  68. package/build/components/DatePicker/time-picker/wheel-picker/index.d.ts +0 -2
  69. package/build/components/DatePicker/time-picker/wheel-picker/index.js +0 -2
  70. package/build/components/DatePicker/time-picker/wheel-picker/wheel-picker-item.d.ts +0 -16
  71. package/build/components/DatePicker/time-picker/wheel-picker/wheel-picker-item.js +0 -97
  72. package/build/components/DatePicker/time-picker/wheel-picker/wheel-picker.d.ts +0 -21
  73. package/build/components/DatePicker/time-picker/wheel-picker/wheel-picker.js +0 -88
  74. package/build/components/DatePicker/time-picker/wheel-picker/wheel-picker.style.d.ts +0 -23
  75. package/build/components/DatePicker/time-picker/wheel-picker/wheel-picker.style.js +0 -21
  76. package/build/components/DatePicker/time-picker/wheel-web.js +0 -146
  77. package/build/components/DatePicker/time-picker/wheel.d.ts +0 -8
  78. package/build/components/DatePicker/time-picker/wheel.js +0 -10
  79. package/src/components/DatePicker/TimePicker.tsx +0 -141
  80. package/src/components/DatePicker/time-picker/animated-math.ts +0 -33
  81. package/src/components/DatePicker/time-picker/period-native.tsx +0 -34
  82. package/src/components/DatePicker/time-picker/period-picker.tsx +0 -16
  83. package/src/components/DatePicker/time-picker/period-web.tsx +0 -36
  84. package/src/components/DatePicker/time-picker/wheel-native.tsx +0 -37
  85. package/src/components/DatePicker/time-picker/wheel-picker/index.ts +0 -3
  86. package/src/components/DatePicker/time-picker/wheel-picker/wheel-picker-item.tsx +0 -132
  87. package/src/components/DatePicker/time-picker/wheel-picker/wheel-picker.style.ts +0 -22
  88. package/src/components/DatePicker/time-picker/wheel-picker/wheel-picker.tsx +0 -200
  89. package/src/components/DatePicker/time-picker/wheel-web.tsx +0 -180
  90. package/src/components/DatePicker/time-picker/wheel.tsx +0 -18
@@ -1,146 +0,0 @@
1
- import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
- import { memo, useMemo, useRef } from 'react';
3
- import { Animated, PanResponder, Platform, View } from 'react-native';
4
- import { StyleSheet } from 'react-native-unistyles';
5
- import { isEqual } from '../../../utils';
6
- import { BodyText } from '../../BodyText';
7
- import { CONTAINER_HEIGHT } from '../enums';
8
- import { sin } from './animated-math';
9
- const ITEM_HEIGHT = 44;
10
- const WheelWeb = ({ value, setValue = () => { }, items }) => {
11
- const displayCount = 5;
12
- const translateY = useRef(new Animated.Value(0)).current;
13
- const renderCount = displayCount * 2 < items.length ? displayCount * 8 : displayCount * 2 - 1;
14
- const circular = items.length >= displayCount;
15
- const height = 140;
16
- const radius = height / 2;
17
- const valueIndex = useMemo(() => {
18
- return Math.max(0, items.findIndex(item => item.value === value));
19
- }, [items, value]);
20
- const panResponder = useMemo(() => {
21
- return PanResponder.create({
22
- onMoveShouldSetPanResponder: () => true,
23
- onStartShouldSetPanResponderCapture: () => true,
24
- onPanResponderGrant: () => {
25
- translateY.setValue(0);
26
- },
27
- onPanResponderMove: (evt, gestureState) => {
28
- translateY.setValue(gestureState.dy);
29
- evt.stopPropagation();
30
- },
31
- onPanResponderRelease: (_, gestureState) => {
32
- translateY.extractOffset();
33
- let newValueIndex = valueIndex - Math.round(gestureState.dy / ((radius * 2) / displayCount));
34
- if (circular) {
35
- newValueIndex = (newValueIndex + items.length) % items.length;
36
- }
37
- else {
38
- if (newValueIndex < 0) {
39
- newValueIndex = 0;
40
- }
41
- else if (newValueIndex >= items.length) {
42
- newValueIndex = items.length - 1;
43
- }
44
- }
45
- const newValue = items[newValueIndex];
46
- if (newValue?.value === value) {
47
- translateY.setOffset(0);
48
- translateY.setValue(0);
49
- }
50
- else if (newValue?.value) {
51
- setValue(newValue.value);
52
- }
53
- else if (items[0]?.value) {
54
- setValue(items[0].value);
55
- }
56
- },
57
- });
58
- }, [circular, displayCount, radius, setValue, value, valueIndex, items, translateY]);
59
- const displayValues = useMemo(() => {
60
- const centerIndex = Math.floor(renderCount / 2);
61
- return Array.from({ length: renderCount }, (_, index) => {
62
- let targetIndex = valueIndex + index - centerIndex;
63
- if (circular) {
64
- targetIndex = ((targetIndex % items.length) + items.length) % items.length;
65
- }
66
- else {
67
- targetIndex = Math.max(0, Math.min(targetIndex, items.length - 1));
68
- }
69
- return items[targetIndex] || items[0];
70
- });
71
- }, [renderCount, valueIndex, items, circular]);
72
- const animatedAngles = useMemo(() => {
73
- //translateY.setValue(0);
74
- translateY.setOffset(0);
75
- const currentIndex = displayValues.findIndex(item => item?.value === value);
76
- return displayValues && displayValues.length > 0
77
- ? displayValues.map((_, index) => translateY
78
- .interpolate({
79
- inputRange: [-radius, radius],
80
- outputRange: [
81
- -radius + ((radius * 2) / displayCount) * (index - currentIndex),
82
- radius + ((radius * 2) / displayCount) * (index - currentIndex),
83
- ],
84
- extrapolate: 'extend',
85
- })
86
- .interpolate({
87
- inputRange: [-radius, radius],
88
- outputRange: [-Math.PI / 2, Math.PI / 2],
89
- extrapolate: 'clamp',
90
- }))
91
- : [];
92
- }, [displayValues, radius, value, displayCount, translateY]);
93
- return (_jsxs(View, { style: [styles.container], ...panResponder.panHandlers, children: [_jsx(View, { style: [
94
- styles.selectedIndicator,
95
- {
96
- transform: [{ translateY: -ITEM_HEIGHT / 2 }],
97
- height: ITEM_HEIGHT,
98
- },
99
- ] }), displayValues?.map((displayValue, index) => {
100
- const animatedAngle = animatedAngles[index];
101
- return (_jsx(Animated.View, { style: {
102
- position: 'absolute',
103
- height: ITEM_HEIGHT - 10,
104
- transform: animatedAngle
105
- ? [
106
- {
107
- translateY: Animated.multiply(radius, sin(animatedAngle)),
108
- },
109
- {
110
- rotateX: animatedAngle.interpolate({
111
- inputRange: [-Math.PI / 2, Math.PI / 2],
112
- outputRange: ['-89deg', '89deg'],
113
- extrapolate: 'clamp',
114
- }),
115
- },
116
- ]
117
- : [],
118
- opacity: displayValue?.value !== value ? 0.3 : 1,
119
- }, children: _jsx(BodyText, { children: displayValue?.text }) }, `${displayValue?.text}-${index}`));
120
- })] }));
121
- };
122
- const styles = StyleSheet.create({
123
- container: {
124
- minWidth: 30,
125
- overflow: 'hidden',
126
- alignItems: 'center',
127
- justifyContent: 'center',
128
- height: CONTAINER_HEIGHT / 2,
129
- ...Platform.select({
130
- web: {
131
- cursor: 'pointer',
132
- userSelect: 'none',
133
- },
134
- }),
135
- },
136
- selectedIndicator: {
137
- position: 'absolute',
138
- width: '100%',
139
- top: '50%',
140
- },
141
- });
142
- const customComparator = (prev, next) => {
143
- const areEqual = prev.value === next.value && prev.setValue === next.setValue && isEqual(prev.items, next.items);
144
- return areEqual;
145
- };
146
- export default memo(WheelWeb, customComparator);
@@ -1,8 +0,0 @@
1
- import { PickerOption } from '../DatePicker.props';
2
- type WheelProps = {
3
- value: number | string;
4
- setValue?: (value: any) => void;
5
- items: PickerOption[];
6
- };
7
- declare const _default: import("react").MemoExoticComponent<(props: WheelProps) => import("react/jsx-runtime").JSX.Element>;
8
- export default _default;
@@ -1,10 +0,0 @@
1
- import { jsx as _jsx } from "react/jsx-runtime";
2
- import { memo } from 'react';
3
- import { Platform } from 'react-native';
4
- import WheelNative from './wheel-native';
5
- import WheelWeb from './wheel-web';
6
- const Wheel = (props) => {
7
- const Component = Platform.OS === 'web' ? WheelWeb : WheelNative;
8
- return _jsx(Component, { ...props });
9
- };
10
- export default memo(Wheel);
@@ -1,141 +0,0 @@
1
- import dayjs from 'dayjs';
2
- import { useCallback, useMemo } from 'react';
3
- import { ScrollView, View } from 'react-native';
4
- import { StyleSheet } from 'react-native-unistyles';
5
- import { BodyText } from '../BodyText';
6
- import { useDatePickerContext } from './DatePicker.context';
7
- import { Numerals, PickerOption } from './DatePicker.props';
8
- import { CONTAINER_HEIGHT } from './enums';
9
- import PeriodPicker from './time-picker/period-picker';
10
- import Wheel from './time-picker/wheel';
11
- import { formatNumber, getParsedDate } from './utils';
12
-
13
- export type Period = 'AM' | 'PM';
14
-
15
- const createNumberList = (
16
- num: number,
17
- numerals: Numerals,
18
- startFrom: number = 0
19
- ): PickerOption[] => {
20
- return Array.from({ length: num }, (_, i) => ({
21
- value: i + startFrom,
22
- text:
23
- i + startFrom < 10
24
- ? `${formatNumber(0, numerals)}${formatNumber(i + startFrom, numerals)}`
25
- : `${formatNumber(i + startFrom, numerals)}`,
26
- }));
27
- };
28
-
29
- const TimePicker = () => {
30
- const {
31
- currentDate,
32
- date,
33
- onSelectDate,
34
- timeZone,
35
- numerals = 'latn',
36
- use12Hours,
37
- } = useDatePickerContext();
38
-
39
- const hours = useMemo(
40
- () => createNumberList(use12Hours ? 12 : 24, numerals, use12Hours ? 1 : 0),
41
- [numerals, use12Hours]
42
- );
43
-
44
- const minutes = useMemo(() => createNumberList(60, numerals), [numerals]);
45
-
46
- const { hour, hour12, minute, period } = getParsedDate(date || currentDate);
47
-
48
- const handleChangeHour = useCallback(
49
- (value: number) => {
50
- let hour24 = value;
51
-
52
- if (use12Hours) {
53
- if (period === 'AM' && value === 12) {
54
- hour24 = 0;
55
- } else if (period === 'PM' && value < 12) {
56
- hour24 = value + 12;
57
- } else {
58
- hour24 = value;
59
- }
60
- }
61
- const newDate = dayjs.tz(date, timeZone).hour(hour24).minute(minute);
62
- onSelectDate(newDate);
63
- },
64
- [date, onSelectDate, timeZone, use12Hours, period, minute]
65
- );
66
-
67
- const handleChangeMinute = useCallback(
68
- (value: number) => {
69
- const newDate = dayjs.tz(date, timeZone).minute(value);
70
- onSelectDate(newDate);
71
- },
72
- [date, onSelectDate, timeZone]
73
- );
74
-
75
- const handlePeriodChange = useCallback(
76
- (newPeriod: Period) => {
77
- let newHour = hour12;
78
- if (newPeriod === 'PM' && hour12 < 12) {
79
- newHour = hour12 + 12;
80
- } else if (newPeriod === 'AM' && hour12 === 12) {
81
- newHour = 0;
82
- } else if (newPeriod === 'AM' && hour >= 12) {
83
- newHour = hour12;
84
- }
85
-
86
- const newDate = dayjs.tz(date || currentDate, timeZone).hour(newHour);
87
- onSelectDate(newDate);
88
- },
89
- [date, currentDate, onSelectDate, timeZone, hour, hour12]
90
- );
91
-
92
- return (
93
- <ScrollView
94
- horizontal={true}
95
- scrollEnabled={false}
96
- contentContainerStyle={styles.container}
97
- testID="time-selector"
98
- >
99
- <View style={styles.timePickerContainer}>
100
- <View style={styles.wheelContainer}>
101
- <Wheel value={use12Hours ? hour12 : hour} items={hours} setValue={handleChangeHour} />
102
- </View>
103
- <BodyText style={styles.timeSeparator}>:</BodyText>
104
- <View style={styles.wheelContainer}>
105
- <Wheel value={minute} items={minutes} setValue={handleChangeMinute} />
106
- </View>
107
- </View>
108
- {use12Hours && period ? (
109
- <View style={styles.periodContainer}>
110
- <PeriodPicker value={period} setValue={handlePeriodChange} />
111
- </View>
112
- ) : null}
113
- </ScrollView>
114
- );
115
- };
116
-
117
- const styles = StyleSheet.create({
118
- container: {
119
- flex: 1,
120
- alignItems: 'center',
121
- justifyContent: 'center',
122
- },
123
- wheelContainer: {
124
- flex: 1,
125
- },
126
- timePickerContainer: {
127
- alignItems: 'center',
128
- justifyContent: 'center',
129
- width: CONTAINER_HEIGHT / 2,
130
- height: CONTAINER_HEIGHT / 2,
131
- flexDirection: 'row',
132
- },
133
- timeSeparator: {
134
- marginHorizontal: 5,
135
- },
136
- periodContainer: {
137
- marginLeft: 10,
138
- },
139
- });
140
-
141
- export default TimePicker;
@@ -1,33 +0,0 @@
1
- import { Animated } from 'react-native';
2
-
3
- const FACTORIAL_3 = 3 * 2;
4
- const FACTORIAL_5 = 5 * 4 * FACTORIAL_3;
5
- const FACTORIAL_7 = 7 * 6 * FACTORIAL_5;
6
-
7
- function sin(animated: Animated.Animated) {
8
- const normalized = normalize(animated);
9
- const square = Animated.multiply(normalized, normalized);
10
- const pow3 = Animated.multiply(normalized, square);
11
- const pow5 = Animated.multiply(pow3, square);
12
- const pow7 = Animated.multiply(pow5, square);
13
-
14
- return Animated.add(
15
- Animated.add(normalized, Animated.multiply(pow3, -1 / FACTORIAL_3)),
16
- Animated.add(
17
- Animated.multiply(pow5, 1 / FACTORIAL_5),
18
- Animated.multiply(pow7, -1 / FACTORIAL_7)
19
- )
20
- );
21
- }
22
-
23
- function normalize(animated: Animated.Animated): Animated.Animated {
24
- return Animated.add(
25
- Animated.modulo(Animated.add(animated, Math.PI), Math.PI * 2),
26
- -Math.PI
27
- ).interpolate({
28
- inputRange: [-Math.PI, -Math.PI / 2, Math.PI / 2, Math.PI],
29
- outputRange: [0, -Math.PI / 2, Math.PI / 2, 0],
30
- });
31
- }
32
-
33
- export { sin, normalize };
@@ -1,34 +0,0 @@
1
- import { memo } from 'react';
2
- import { PickerOption } from '../DatePicker.props';
3
- import WheelPicker from './wheel-picker';
4
-
5
- interface PeriodProps {
6
- value: string;
7
- setValue?: (value: any) => void;
8
- }
9
-
10
- const options: PickerOption[] = [
11
- { value: 'AM', text: 'AM' },
12
- { value: 'PM', text: 'PM' },
13
- ];
14
-
15
- const PeriodNative = ({ value, setValue = () => {} }: PeriodProps) => {
16
- return (
17
- <WheelPicker
18
- value={value}
19
- options={options}
20
- onChange={setValue}
21
- //containerStyle={defaultStyles.container}
22
- itemHeight={44}
23
- decelerationRate="fast"
24
- />
25
- );
26
- };
27
-
28
- const customComparator = (prev: Readonly<PeriodProps>, next: Readonly<PeriodProps>) => {
29
- const areEqual = prev.value === next.value && prev.setValue === next.setValue;
30
-
31
- return areEqual;
32
- };
33
-
34
- export default memo(PeriodNative, customComparator);
@@ -1,16 +0,0 @@
1
- import { memo } from 'react';
2
- import { Platform } from 'react-native';
3
- import PeriodNative from './period-native';
4
- import PeriodWeb from './period-web';
5
-
6
- type PeriodProps = {
7
- value: string;
8
- setValue?: (value: any) => void;
9
- };
10
-
11
- const PeriodPicker = (props: PeriodProps) => {
12
- const Component = Platform.OS === 'web' ? PeriodWeb : PeriodNative;
13
- return <Component {...props} />;
14
- };
15
-
16
- export default memo(PeriodPicker);
@@ -1,36 +0,0 @@
1
- import { memo } from 'react';
2
- import { Pressable, View } from 'react-native';
3
- import { StyleSheet } from 'react-native-unistyles';
4
- import { BodyText } from '../../BodyText';
5
-
6
- interface PeriodProps {
7
- value: string;
8
- setValue?: (value: any) => void;
9
- }
10
-
11
- const PeriodWeb = ({ value, setValue = () => {} }: PeriodProps) => {
12
- return (
13
- <Pressable onPress={() => setValue(value == 'AM' ? 'PM' : 'AM')}>
14
- <View style={[styles.period]}>
15
- <BodyText>{value}</BodyText>
16
- </View>
17
- </Pressable>
18
- );
19
- };
20
-
21
- const styles = StyleSheet.create({
22
- period: {
23
- width: 65,
24
- height: 44,
25
- alignItems: 'center',
26
- justifyContent: 'center',
27
- },
28
- });
29
-
30
- const customComparator = (prev: Readonly<PeriodProps>, next: Readonly<PeriodProps>) => {
31
- const areEqual = prev.value === next.value && prev.setValue === next.setValue;
32
-
33
- return areEqual;
34
- };
35
-
36
- export default memo(PeriodWeb, customComparator);
@@ -1,37 +0,0 @@
1
- import { memo } from 'react';
2
- import { Platform } from 'react-native';
3
- import { StyleSheet } from 'react-native-unistyles';
4
- import { PickerOption } from '../DatePicker.props';
5
- import WheelPicker from './wheel-picker';
6
-
7
- interface WheelProps {
8
- value: number | string;
9
- setValue?: (value: any) => void;
10
- items: PickerOption[];
11
- }
12
-
13
- const WheelNative = ({ value, setValue = () => {}, items }: WheelProps) => {
14
- return (
15
- <WheelPicker
16
- value={value}
17
- options={items}
18
- onChange={setValue}
19
- containerStyle={styles.container}
20
- itemHeight={44}
21
- decelerationRate="fast"
22
- />
23
- );
24
- };
25
-
26
- const styles = StyleSheet.create({
27
- container: {
28
- display: 'flex',
29
- ...Platform.select({
30
- web: {
31
- userSelect: 'none',
32
- },
33
- }),
34
- },
35
- });
36
-
37
- export default memo(WheelNative);
@@ -1,3 +0,0 @@
1
- import WheelPicker from './wheel-picker';
2
-
3
- export default WheelPicker;
@@ -1,132 +0,0 @@
1
- import React from 'react';
2
- import { Animated, StyleProp, ViewStyle } from 'react-native';
3
- import { BodyText } from '../../../BodyText';
4
- import { PickerOption } from '../../DatePicker.props';
5
- import styles from './wheel-picker.style';
6
-
7
- interface ItemProps {
8
- style: StyleProp<ViewStyle>;
9
- option: PickerOption | null;
10
- height: number;
11
- index: number;
12
- currentScrollIndex: Animated.AnimatedAddition<number>;
13
- visibleRest: number;
14
- rotationFunction: (x: number) => number;
15
- opacityFunction: (x: number) => number;
16
- scaleFunction: (x: number) => number;
17
- }
18
-
19
- const WheelPickerItem: React.FC<ItemProps> = ({
20
- style,
21
- height,
22
- option,
23
- index,
24
- visibleRest,
25
- currentScrollIndex,
26
- opacityFunction,
27
- rotationFunction,
28
- scaleFunction,
29
- }) => {
30
- const relativeScrollIndex = Animated.subtract(index, currentScrollIndex);
31
-
32
- const translateY = relativeScrollIndex.interpolate({
33
- inputRange: (() => {
34
- const range = [0];
35
- for (let i = 1; i <= visibleRest + 1; i++) {
36
- range.unshift(-i);
37
- range.push(i);
38
- }
39
- return range;
40
- })(),
41
- outputRange: (() => {
42
- const range = [0];
43
- for (let i = 1; i <= visibleRest + 1; i++) {
44
- let y = (height / 2) * (1 - Math.sin(Math.PI / 2 - rotationFunction(i)));
45
- for (let j = 1; j < i; j++) {
46
- y += height * (1 - Math.sin(Math.PI / 2 - rotationFunction(j)));
47
- }
48
- range.unshift(y);
49
- range.push(-y);
50
- }
51
- return range;
52
- })(),
53
- });
54
-
55
- const opacity = relativeScrollIndex.interpolate({
56
- inputRange: (() => {
57
- const range = [0];
58
- for (let i = 1; i <= visibleRest + 1; i++) {
59
- range.unshift(-i);
60
- range.push(i);
61
- }
62
- return range;
63
- })(),
64
- outputRange: (() => {
65
- const range = [1];
66
- for (let x = 1; x <= visibleRest + 1; x++) {
67
- const y = opacityFunction(x);
68
- range.unshift(y);
69
- range.push(y);
70
- }
71
- return range;
72
- })(),
73
- });
74
-
75
- const scale = relativeScrollIndex.interpolate({
76
- inputRange: (() => {
77
- const range = [0];
78
- for (let i = 1; i <= visibleRest + 1; i++) {
79
- range.unshift(-i);
80
- range.push(i);
81
- }
82
- return range;
83
- })(),
84
- outputRange: (() => {
85
- const range = [1.0];
86
- for (let x = 1; x <= visibleRest + 1; x++) {
87
- const y = scaleFunction(x);
88
- range.unshift(y);
89
- range.push(y);
90
- }
91
- return range;
92
- })(),
93
- });
94
-
95
- const rotateX = relativeScrollIndex.interpolate({
96
- inputRange: (() => {
97
- const range = [0];
98
- for (let i = 1; i <= visibleRest + 1; i++) {
99
- range.unshift(-i);
100
- range.push(i);
101
- }
102
- return range;
103
- })(),
104
- outputRange: (() => {
105
- const range = ['0deg'];
106
- for (let x = 1; x <= visibleRest + 1; x++) {
107
- const y = rotationFunction(x);
108
- range.unshift(`${y}deg`);
109
- range.push(`${y}deg`);
110
- }
111
- return range;
112
- })(),
113
- });
114
-
115
- return (
116
- <Animated.View
117
- style={[
118
- styles.option,
119
- style,
120
- {
121
- height,
122
- opacity,
123
- transform: [{ translateY }, { rotateX }, { scale }],
124
- },
125
- ]}
126
- >
127
- <BodyText>{option?.text}</BodyText>
128
- </Animated.View>
129
- );
130
- };
131
-
132
- export default React.memo(WheelPickerItem);
@@ -1,22 +0,0 @@
1
- import { StyleSheet } from 'react-native-unistyles';
2
-
3
- export default StyleSheet.create({
4
- container: {
5
- position: 'relative',
6
- },
7
- selectedIndicator: {
8
- position: 'absolute',
9
- width: '100%',
10
- top: '50%',
11
- },
12
- scrollView: {
13
- overflow: 'hidden',
14
- flex: 1,
15
- },
16
- option: {
17
- alignItems: 'center',
18
- justifyContent: 'center',
19
- paddingHorizontal: 16,
20
- zIndex: 100,
21
- },
22
- });