@hero-design/rn 8.35.0-alpha.4 → 8.36.0-alpha.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.
- package/.eslintrc.js +1 -0
- package/.turbo/turbo-build.log +1 -1
- package/.turbo/turbo-build:types.log +0 -8
- package/.turbo/turbo-lint.log +20 -11
- package/.turbo/turbo-test.log +0 -724
- package/es/index.js +578 -639
- package/jest.config.js +1 -1
- package/lib/index.js +588 -649
- package/package.json +9 -9
- package/src/components/Attachment/__tests__/__snapshots__/index.spec.tsx.snap +1 -1
- package/src/components/Badge/__tests__/__snapshots__/Badge.spec.tsx.snap +3 -3
- package/src/components/Badge/__tests__/__snapshots__/Status.spec.tsx.snap +1 -1
- package/src/components/Button/LoadingIndicator/__tests__/__snapshots__/StyledLoadingIndicator.spec.tsx.snap +2 -2
- package/src/components/Button/LoadingIndicator/__tests__/__snapshots__/index.spec.tsx.snap +6 -6
- package/src/components/Button/UtilityButton/__tests__/__snapshots__/index.spec.tsx.snap +2 -2
- package/src/components/Button/__tests__/__snapshots__/Button.spec.tsx.snap +4 -4
- package/src/components/Button/__tests__/__snapshots__/StyledButton.spec.tsx.snap +6 -6
- package/src/components/Calendar/__tests__/index.spec.tsx +29 -0
- package/src/components/Calendar/index.tsx +10 -1
- package/src/components/Carousel/__tests__/__snapshots__/index.spec.tsx.snap +75 -74
- package/src/components/Carousel/index.tsx +1 -1
- package/src/components/DatePicker/DatePickerCalendar.tsx +23 -14
- package/src/components/FAB/ActionGroup/StyledActionGroup.tsx +12 -0
- package/src/components/FAB/ActionGroup/__tests__/__snapshots__/index.spec.tsx.snap +801 -1251
- package/src/components/FAB/ActionGroup/__tests__/index.spec.tsx +45 -35
- package/src/components/FAB/ActionGroup/index.tsx +65 -45
- package/src/components/FAB/__tests__/__snapshots__/StyledFAB.spec.tsx.snap +1 -1
- package/src/components/FAB/index.tsx +0 -4
- package/src/components/Icon/__tests__/__snapshots__/index.spec.tsx.snap +1 -1
- package/src/components/PinInput/__tests__/__snapshots__/PinCell.spec.tsx.snap +4 -4
- package/src/components/PinInput/__tests__/__snapshots__/index.spec.tsx.snap +12 -12
- package/src/components/Portal/PortalHost.tsx +24 -0
- package/src/components/Portal/PortalProvider.tsx +29 -0
- package/src/components/Portal/__tests__/PortalHost.spec.tsx +50 -0
- package/src/components/Portal/__tests__/PortalProvider.spec.tsx +24 -0
- package/src/components/Portal/__tests__/index.spec.tsx +29 -0
- package/src/components/Portal/__tests__/reducer.spec.tsx +110 -0
- package/src/components/Portal/constants.ts +10 -0
- package/src/components/Portal/contexts.ts +14 -0
- package/src/components/Portal/index.tsx +42 -0
- package/src/components/Portal/reducer.ts +106 -0
- package/src/components/Portal/types.tsx +31 -0
- package/src/components/Portal/usePortal.ts +50 -0
- package/src/components/Portal/usePortalState.ts +11 -0
- package/src/components/Progress/StyledProgressBar.tsx +1 -0
- package/src/components/Progress/__tests__/__snapshots__/index.spec.js.snap +46 -44
- package/src/components/RichTextEditor/__tests__/__snapshots__/RichTextEditor.spec.tsx.snap +6 -6
- package/src/components/SectionHeading/__tests__/__snapshots__/index.spec.tsx.snap +1 -1
- package/src/components/Skeleton/__tests__/__snapshots__/index.spec.tsx.snap +7 -7
- package/src/components/Swipeable/__tests__/__snapshots__/index.spec.tsx.snap +5 -0
- package/src/components/Swipeable/index.tsx +6 -1
- package/src/components/Switch/SelectorSwitch/StyledSelectorSwitch.tsx +4 -7
- package/src/components/Switch/SelectorSwitch/__tests__/__snapshots__/Option.spec.tsx.snap +3 -3
- package/src/components/Switch/SelectorSwitch/__tests__/__snapshots__/index.spec.tsx.snap +9 -9
- package/src/components/Switch/SelectorSwitch/index.tsx +7 -15
- package/src/components/Tabs/__tests__/__snapshots__/ScrollableTabs.spec.tsx.snap +21 -21
- package/src/components/Tabs/__tests__/__snapshots__/ScrollableTabsHeader.spec.tsx.snap +6 -6
- package/src/components/Tabs/__tests__/__snapshots__/TabWithBadge.spec.tsx.snap +2 -2
- package/src/components/Tabs/__tests__/__snapshots__/index.spec.tsx.snap +9 -9
- package/src/components/Tag/StyledTag.tsx +6 -35
- package/src/components/Tag/__tests__/Tag.spec.tsx +13 -13
- package/src/components/Tag/__tests__/__snapshots__/Tag.spec.tsx.snap +40 -79
- package/src/components/Tag/index.tsx +8 -6
- package/src/components/TextInput/__tests__/__snapshots__/StyledTextInput.spec.tsx.snap +7 -7
- package/src/components/TextInput/__tests__/__snapshots__/index.spec.tsx.snap +20 -20
- package/src/components/Toolbar/__tests__/__snapshots__/ToolbarItem.spec.tsx.snap +1 -1
- package/src/components/Typography/Body/__tests__/__snapshots__/StyledBody.tsx.snap +1 -1
- package/src/components/Typography/Body/__tests__/__snapshots__/index.spec.tsx.snap +2 -2
- package/src/components/Typography/Caption/__tests__/__snapshots__/StyledCaption.spec.tsx.snap +1 -1
- package/src/components/Typography/Caption/__tests__/__snapshots__/index.spec.tsx.snap +2 -2
- package/src/components/Typography/Label/__tests__/__snapshots__/StyledLabel.tsx.snap +1 -1
- package/src/components/Typography/Label/__tests__/__snapshots__/index.spec.tsx.snap +2 -2
- package/src/components/Typography/Text/__tests__/__snapshots__/StyledText.spec.tsx.snap +1 -1
- package/src/components/Typography/Title/__tests__/__snapshots__/StyledTitle.tsx.snap +3 -3
- package/src/components/Typography/Title/__tests__/__snapshots__/index.spec.tsx.snap +4 -4
- package/src/index.ts +2 -2
- package/src/theme/__tests__/__snapshots__/index.spec.ts.snap +49 -46
- package/src/theme/components/button.ts +1 -1
- package/src/theme/components/progress.ts +2 -2
- package/src/theme/components/swipeable.ts +5 -1
- package/src/theme/components/switch.ts +4 -4
- package/src/theme/components/tabs.ts +1 -1
- package/src/theme/components/tag.ts +2 -2
- package/src/theme/components/typography.ts +2 -2
- package/src/theme/global/colors/__tests__/__snapshots__/eBens.spec.ts.snap +7 -7
- package/src/theme/global/colors/__tests__/__snapshots__/global.spec.ts.snap +5 -5
- package/src/theme/global/colors/__tests__/__snapshots__/jobs.spec.ts.snap +6 -6
- package/src/theme/global/colors/__tests__/__snapshots__/swag.spec.ts.snap +6 -6
- package/src/theme/global/colors/__tests__/__snapshots__/wallet.spec.ts.snap +7 -7
- package/src/theme/global/colors/__tests__/__snapshots__/work.spec.ts.snap +5 -5
- package/src/theme/global/colors/eBens.ts +2 -2
- package/src/theme/global/colors/global.ts +5 -5
- package/src/theme/global/colors/jobs.ts +1 -1
- package/src/theme/global/colors/swag.ts +1 -1
- package/src/theme/global/colors/wallet.ts +2 -2
- package/types/components/Calendar/index.d.ts +2 -1
- package/types/components/FAB/ActionGroup/StyledActionGroup.d.ts +7 -1
- package/types/components/FAB/index.d.ts +0 -3
- package/types/components/Portal/PortalHost.d.ts +5 -0
- package/types/components/Portal/PortalProvider.d.ts +7 -0
- package/types/components/Portal/constants.d.ts +8 -0
- package/types/components/Portal/contexts.d.ts +9 -0
- package/types/components/Portal/index.d.ts +13 -0
- package/types/components/Portal/reducer.d.ts +5 -0
- package/types/components/Portal/types.d.ts +22 -0
- package/types/components/Portal/usePortal.d.ts +8 -0
- package/types/components/Portal/usePortalState.d.ts +1 -0
- package/types/components/Swipeable/index.d.ts +1 -1
- package/types/components/Tag/StyledTag.d.ts +1 -4
- package/types/components/Tag/index.d.ts +1 -0
- package/types/index.d.ts +2 -2
- package/types/theme/components/swipeable.d.ts +3 -0
- package/types/theme/components/switch.d.ts +1 -1
- package/types/theme/components/tag.d.ts +1 -1
|
@@ -10,52 +10,53 @@ describe('ActionGroup', () => {
|
|
|
10
10
|
${true}
|
|
11
11
|
${false}
|
|
12
12
|
`('has active $active', ({ active }) => {
|
|
13
|
-
const { toJSON, getByTestId, getByText } =
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
{
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
13
|
+
const { toJSON, getByTestId, getByText, queryByTestId, queryByText } =
|
|
14
|
+
renderWithTheme(
|
|
15
|
+
<ActionGroup
|
|
16
|
+
fabTitle="Shout out"
|
|
17
|
+
active={active}
|
|
18
|
+
headerTitle="What would you like to create?"
|
|
19
|
+
items={[
|
|
20
|
+
{
|
|
21
|
+
icon: 'speaker',
|
|
22
|
+
title: 'Give shout out',
|
|
23
|
+
testID: 'speaker-action-item',
|
|
24
|
+
},
|
|
25
|
+
{ icon: 'target', title: 'Goal', testID: 'target-action-item' },
|
|
26
|
+
{
|
|
27
|
+
icon: 'plane',
|
|
28
|
+
title: 'Leave request',
|
|
29
|
+
testID: 'plane-action-item',
|
|
30
|
+
},
|
|
31
|
+
{
|
|
32
|
+
icon: 'health-bag',
|
|
33
|
+
title: 'Safety incident',
|
|
34
|
+
testID: 'health-bag-action-item',
|
|
35
|
+
},
|
|
36
|
+
{ icon: 'clock', title: 'Timesheets', testID: 'clock-action-item' },
|
|
37
|
+
]}
|
|
38
|
+
/>
|
|
39
|
+
);
|
|
39
40
|
|
|
40
41
|
expect(toJSON()).toMatchSnapshot();
|
|
41
42
|
|
|
42
|
-
expect(getByText('What would you like to create?')).toBeDefined();
|
|
43
|
-
expect(getByTestId('speaker-action-item')).toBeDefined();
|
|
44
|
-
expect(getByTestId('target-action-item')).toBeDefined();
|
|
45
|
-
expect(getByTestId('plane-action-item')).toBeDefined();
|
|
46
|
-
expect(getByTestId('health-bag-action-item')).toBeDefined();
|
|
47
|
-
|
|
48
43
|
if (active) {
|
|
49
44
|
// verify backdrop appears
|
|
50
|
-
expect(
|
|
45
|
+
expect(queryByTestId('back-drop')).toBeDefined();
|
|
46
|
+
expect(getByText('What would you like to create?')).toBeDefined();
|
|
47
|
+
expect(getByTestId('speaker-action-item')).toBeDefined();
|
|
48
|
+
expect(getByTestId('target-action-item')).toBeDefined();
|
|
49
|
+
expect(getByTestId('plane-action-item')).toBeDefined();
|
|
50
|
+
expect(getByTestId('health-bag-action-item')).toBeDefined();
|
|
51
51
|
} else {
|
|
52
52
|
// verify backdrop disappears
|
|
53
|
-
expect(
|
|
53
|
+
expect(queryByTestId('back-drop')).toBeNull();
|
|
54
|
+
expect(queryByText('What would you like to create?')).toBeNull();
|
|
54
55
|
}
|
|
55
56
|
});
|
|
56
57
|
|
|
57
58
|
describe('when user presses', () => {
|
|
58
|
-
it('calls onPress', () => {
|
|
59
|
+
it('calls onPress when active = false', () => {
|
|
59
60
|
const onPressSpy = jest.fn();
|
|
60
61
|
const { getByTestId } = renderWithTheme(
|
|
61
62
|
<ActionGroup onPress={onPressSpy} />
|
|
@@ -63,5 +64,14 @@ describe('ActionGroup', () => {
|
|
|
63
64
|
fireEvent(getByTestId('fab'), 'press');
|
|
64
65
|
expect(onPressSpy).toBeCalledTimes(1);
|
|
65
66
|
});
|
|
67
|
+
|
|
68
|
+
it('calls onPress when active = true', () => {
|
|
69
|
+
const onPressSpy = jest.fn();
|
|
70
|
+
const { getByTestId } = renderWithTheme(
|
|
71
|
+
<ActionGroup onPress={onPressSpy} active />
|
|
72
|
+
);
|
|
73
|
+
fireEvent(getByTestId('fab-in-portal'), 'press');
|
|
74
|
+
expect(onPressSpy).toBeCalledTimes(1);
|
|
75
|
+
});
|
|
66
76
|
});
|
|
67
77
|
});
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import React, { forwardRef, useRef } from 'react';
|
|
2
2
|
import type { StyleProp, ViewStyle } from 'react-native';
|
|
3
|
-
import { Animated, Platform } from 'react-native';
|
|
3
|
+
import { Animated, Platform, Modal } from 'react-native';
|
|
4
4
|
import type { IconName } from '../../Icon';
|
|
5
5
|
import type { ActionItemProps } from './ActionItem';
|
|
6
6
|
import ActionItem from './ActionItem';
|
|
@@ -8,6 +8,7 @@ import {
|
|
|
8
8
|
StyledActionGroupContainer,
|
|
9
9
|
StyledBackdrop,
|
|
10
10
|
StyledContainer,
|
|
11
|
+
StyledContainerInModal,
|
|
11
12
|
StyledFAB,
|
|
12
13
|
StyledHeaderText,
|
|
13
14
|
} from './StyledActionGroup';
|
|
@@ -110,64 +111,83 @@ const ActionGroup = forwardRef<ActionGroupHandles, ActionGroupProps>(
|
|
|
110
111
|
}),
|
|
111
112
|
]).start();
|
|
112
113
|
}, [active]);
|
|
113
|
-
|
|
114
|
-
const interpolatedBackdropOpacityAnimation =
|
|
114
|
+
const interpolatedActionGroupOpacityAnimation =
|
|
115
115
|
tranlateXAnimation.current.interpolate({
|
|
116
116
|
inputRange: [0, 1],
|
|
117
|
-
outputRange: [0,
|
|
117
|
+
outputRange: [0, 1],
|
|
118
118
|
});
|
|
119
119
|
|
|
120
|
-
const
|
|
120
|
+
const interpolatedFABOpacityAnimation =
|
|
121
121
|
tranlateXAnimation.current.interpolate({
|
|
122
122
|
inputRange: [0, 1],
|
|
123
|
-
outputRange: [
|
|
123
|
+
outputRange: [1, 0],
|
|
124
124
|
});
|
|
125
125
|
|
|
126
126
|
return (
|
|
127
127
|
<StyledContainer testID={testID} pointerEvents="box-none" style={style}>
|
|
128
|
-
<
|
|
129
|
-
pointerEvents={active ? 'auto' : 'box-none'}
|
|
130
|
-
testID="back-drop"
|
|
131
|
-
style={{ opacity: interpolatedBackdropOpacityAnimation }}
|
|
132
|
-
/>
|
|
133
|
-
<StyledActionGroupContainer
|
|
134
|
-
pointerEvents={active ? 'auto' : 'none'}
|
|
135
|
-
testID="action-group"
|
|
128
|
+
<Animated.View
|
|
136
129
|
style={{
|
|
137
|
-
opacity:
|
|
130
|
+
opacity: interpolatedFABOpacityAnimation,
|
|
138
131
|
}}
|
|
139
132
|
>
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
133
|
+
<StyledFAB
|
|
134
|
+
key="fab"
|
|
135
|
+
testID="fab"
|
|
136
|
+
icon={fabIcon}
|
|
137
|
+
onPress={onPress}
|
|
138
|
+
animated
|
|
139
|
+
active={active}
|
|
140
|
+
title={fabTitle}
|
|
141
|
+
ref={fabRef}
|
|
142
|
+
/>
|
|
143
|
+
</Animated.View>
|
|
144
|
+
<Modal
|
|
145
|
+
visible={active}
|
|
146
|
+
animationType="fade"
|
|
147
|
+
transparent
|
|
148
|
+
statusBarTranslucent={true}
|
|
149
|
+
>
|
|
150
|
+
<StyledContainerInModal testID={testID} style={[style]}>
|
|
151
|
+
<StyledBackdrop testID="back-drop" />
|
|
152
|
+
<StyledActionGroupContainer
|
|
153
|
+
testID="action-group"
|
|
154
|
+
style={{
|
|
155
|
+
opacity: interpolatedActionGroupOpacityAnimation,
|
|
156
|
+
}}
|
|
143
157
|
>
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
158
|
+
{!!headerTitle && (
|
|
159
|
+
<Animated.View
|
|
160
|
+
style={{ transform: [{ translateY: titleTranslateY }] }}
|
|
161
|
+
>
|
|
162
|
+
<StyledHeaderText testID="header-text" level="h4">
|
|
163
|
+
{headerTitle}
|
|
164
|
+
</StyledHeaderText>
|
|
165
|
+
</Animated.View>
|
|
166
|
+
)}
|
|
167
|
+
|
|
168
|
+
<Box style={[style, { paddingBottom: 0 }]}>
|
|
169
|
+
{items?.map((itemProp, index) => (
|
|
170
|
+
<ActionItem
|
|
171
|
+
key={itemProp.key || `${itemProp.icon}_${itemProp.title}`}
|
|
172
|
+
{...itemProp}
|
|
173
|
+
index={active ? index : items.length - index}
|
|
174
|
+
active={active}
|
|
175
|
+
/>
|
|
176
|
+
))}
|
|
177
|
+
</Box>
|
|
178
|
+
</StyledActionGroupContainer>
|
|
179
|
+
|
|
180
|
+
<StyledFAB
|
|
181
|
+
key="fab-in-portal"
|
|
182
|
+
testID="fab-in-portal"
|
|
183
|
+
icon={fabIcon}
|
|
184
|
+
onPress={onPress}
|
|
185
|
+
animated
|
|
186
|
+
active={active}
|
|
187
|
+
title={fabTitle}
|
|
188
|
+
/>
|
|
189
|
+
</StyledContainerInModal>
|
|
190
|
+
</Modal>
|
|
171
191
|
</StyledContainer>
|
|
172
192
|
);
|
|
173
193
|
}
|
|
@@ -1,10 +1,6 @@
|
|
|
1
1
|
import FAB from './FAB';
|
|
2
2
|
import ActionGroup from './ActionGroup';
|
|
3
|
-
import { Portal, PortalHost, PortalProvider } from '@gorhom/portal';
|
|
4
3
|
|
|
5
4
|
export default Object.assign(FAB, {
|
|
6
5
|
ActionGroup,
|
|
7
|
-
Portal: Portal,
|
|
8
|
-
PortalHost: PortalHost,
|
|
9
|
-
Provider: PortalProvider,
|
|
10
6
|
});
|
|
@@ -102,7 +102,7 @@ exports[`PinCell renders correctly when focused is false, state is error 1`] = `
|
|
|
102
102
|
Array [
|
|
103
103
|
Object {
|
|
104
104
|
"alignItems": "center",
|
|
105
|
-
"borderColor": "#
|
|
105
|
+
"borderColor": "#cb300a",
|
|
106
106
|
"borderRadius": 8,
|
|
107
107
|
"borderWidth": 1,
|
|
108
108
|
"height": 48,
|
|
@@ -128,7 +128,7 @@ exports[`PinCell renders correctly when focused is false, state is error 1`] = `
|
|
|
128
128
|
},
|
|
129
129
|
Array [
|
|
130
130
|
Object {
|
|
131
|
-
"color": "#
|
|
131
|
+
"color": "#cb300a",
|
|
132
132
|
},
|
|
133
133
|
undefined,
|
|
134
134
|
],
|
|
@@ -198,7 +198,7 @@ exports[`PinCell renders correctly when focused is true, state is error 1`] = `
|
|
|
198
198
|
Array [
|
|
199
199
|
Object {
|
|
200
200
|
"alignItems": "center",
|
|
201
|
-
"borderColor": "#
|
|
201
|
+
"borderColor": "#cb300a",
|
|
202
202
|
"borderRadius": 8,
|
|
203
203
|
"borderWidth": 2,
|
|
204
204
|
"height": 48,
|
|
@@ -224,7 +224,7 @@ exports[`PinCell renders correctly when focused is true, state is error 1`] = `
|
|
|
224
224
|
},
|
|
225
225
|
Array [
|
|
226
226
|
Object {
|
|
227
|
-
"color": "#
|
|
227
|
+
"color": "#cb300a",
|
|
228
228
|
},
|
|
229
229
|
undefined,
|
|
230
230
|
],
|
|
@@ -822,7 +822,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
822
822
|
Array [
|
|
823
823
|
Object {
|
|
824
824
|
"alignItems": "center",
|
|
825
|
-
"borderColor": "#
|
|
825
|
+
"borderColor": "#cb300a",
|
|
826
826
|
"borderRadius": 8,
|
|
827
827
|
"borderWidth": 1,
|
|
828
828
|
"height": 48,
|
|
@@ -839,8 +839,8 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
839
839
|
style={
|
|
840
840
|
Array [
|
|
841
841
|
Object {
|
|
842
|
-
"backgroundColor": "#
|
|
843
|
-
"borderColor": "#
|
|
842
|
+
"backgroundColor": "#cb300a",
|
|
843
|
+
"borderColor": "#cb300a",
|
|
844
844
|
"borderRadius": 999,
|
|
845
845
|
"borderWidth": 1,
|
|
846
846
|
"height": 16,
|
|
@@ -868,7 +868,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
868
868
|
Array [
|
|
869
869
|
Object {
|
|
870
870
|
"alignItems": "center",
|
|
871
|
-
"borderColor": "#
|
|
871
|
+
"borderColor": "#cb300a",
|
|
872
872
|
"borderRadius": 8,
|
|
873
873
|
"borderWidth": 1,
|
|
874
874
|
"height": 48,
|
|
@@ -885,8 +885,8 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
885
885
|
style={
|
|
886
886
|
Array [
|
|
887
887
|
Object {
|
|
888
|
-
"backgroundColor": "#
|
|
889
|
-
"borderColor": "#
|
|
888
|
+
"backgroundColor": "#cb300a",
|
|
889
|
+
"borderColor": "#cb300a",
|
|
890
890
|
"borderRadius": 999,
|
|
891
891
|
"borderWidth": 1,
|
|
892
892
|
"height": 16,
|
|
@@ -914,7 +914,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
914
914
|
Array [
|
|
915
915
|
Object {
|
|
916
916
|
"alignItems": "center",
|
|
917
|
-
"borderColor": "#
|
|
917
|
+
"borderColor": "#cb300a",
|
|
918
918
|
"borderRadius": 8,
|
|
919
919
|
"borderWidth": 1,
|
|
920
920
|
"height": 48,
|
|
@@ -931,7 +931,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
931
931
|
style={
|
|
932
932
|
Array [
|
|
933
933
|
Object {
|
|
934
|
-
"borderColor": "#
|
|
934
|
+
"borderColor": "#cb300a",
|
|
935
935
|
"borderRadius": 999,
|
|
936
936
|
"borderWidth": 1,
|
|
937
937
|
"height": 16,
|
|
@@ -959,7 +959,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
959
959
|
Array [
|
|
960
960
|
Object {
|
|
961
961
|
"alignItems": "center",
|
|
962
|
-
"borderColor": "#
|
|
962
|
+
"borderColor": "#cb300a",
|
|
963
963
|
"borderRadius": 8,
|
|
964
964
|
"borderWidth": 1,
|
|
965
965
|
"height": 48,
|
|
@@ -976,7 +976,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
976
976
|
style={
|
|
977
977
|
Array [
|
|
978
978
|
Object {
|
|
979
|
-
"borderColor": "#
|
|
979
|
+
"borderColor": "#cb300a",
|
|
980
980
|
"borderRadius": 999,
|
|
981
981
|
"borderWidth": 1,
|
|
982
982
|
"height": 16,
|
|
@@ -1007,7 +1007,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
1007
1007
|
style={
|
|
1008
1008
|
Array [
|
|
1009
1009
|
Object {
|
|
1010
|
-
"color": "#
|
|
1010
|
+
"color": "#cb300a",
|
|
1011
1011
|
"fontSize": 16,
|
|
1012
1012
|
},
|
|
1013
1013
|
undefined,
|
|
@@ -1030,7 +1030,7 @@ exports[`rendering renders correctly when there is error 1`] = `
|
|
|
1030
1030
|
},
|
|
1031
1031
|
Array [
|
|
1032
1032
|
Object {
|
|
1033
|
-
"color": "#
|
|
1033
|
+
"color": "#cb300a",
|
|
1034
1034
|
"paddingLeft": 4,
|
|
1035
1035
|
},
|
|
1036
1036
|
undefined,
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import React, { memo, useEffect } from 'react';
|
|
2
|
+
import { usePortal } from './usePortal';
|
|
3
|
+
import { usePortalState } from './usePortalState';
|
|
4
|
+
import { PortalType } from './contexts';
|
|
5
|
+
|
|
6
|
+
export interface PortalHostProps {
|
|
7
|
+
name: string;
|
|
8
|
+
}
|
|
9
|
+
const PortalHostComponent = ({ name }: PortalHostProps) => {
|
|
10
|
+
const state = usePortalState(name);
|
|
11
|
+
const { registerHost, deregisterHost } = usePortal(name);
|
|
12
|
+
|
|
13
|
+
useEffect(() => {
|
|
14
|
+
registerHost();
|
|
15
|
+
return () => {
|
|
16
|
+
deregisterHost();
|
|
17
|
+
};
|
|
18
|
+
}, []);
|
|
19
|
+
|
|
20
|
+
return <>{state.map((item: PortalType) => item.node)}</>;
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
export const PortalHost = memo(PortalHostComponent);
|
|
24
|
+
PortalHost.displayName = 'PortalHost';
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import React, { memo, useReducer } from 'react';
|
|
2
|
+
import type { ReactNode } from 'react';
|
|
3
|
+
import { PortalHost } from './PortalHost';
|
|
4
|
+
import { reducer } from './reducer';
|
|
5
|
+
import { INITIAL_STATE } from './constants';
|
|
6
|
+
import { PortalDispatchContext, PortalStateContext } from './contexts';
|
|
7
|
+
|
|
8
|
+
export interface PortalProviderProps {
|
|
9
|
+
rootHostName?: string;
|
|
10
|
+
children: ReactNode | ReactNode[];
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
const PortalProviderComponent = ({
|
|
14
|
+
rootHostName = 'root',
|
|
15
|
+
children,
|
|
16
|
+
}: PortalProviderProps) => {
|
|
17
|
+
const [state, dispatch] = useReducer(reducer, INITIAL_STATE);
|
|
18
|
+
return (
|
|
19
|
+
<PortalDispatchContext.Provider value={dispatch}>
|
|
20
|
+
<PortalStateContext.Provider value={state}>
|
|
21
|
+
{children}
|
|
22
|
+
<PortalHost name={rootHostName} />
|
|
23
|
+
</PortalStateContext.Provider>
|
|
24
|
+
</PortalDispatchContext.Provider>
|
|
25
|
+
);
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
export const PortalProvider = memo(PortalProviderComponent);
|
|
29
|
+
PortalProvider.displayName = 'PortalProvider';
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import React, { useContext } from 'react';
|
|
2
|
+
import { waitFor } from '@testing-library/react-native';
|
|
3
|
+
import { PortalHost } from '../PortalHost';
|
|
4
|
+
import { PortalProvider } from '../PortalProvider';
|
|
5
|
+
import Typography from '../../Typography';
|
|
6
|
+
import renderWithTheme from '../../../testHelpers/renderWithTheme';
|
|
7
|
+
import { PortalStateContext } from '../contexts';
|
|
8
|
+
import theme, { ThemeProvider } from '../../../theme';
|
|
9
|
+
|
|
10
|
+
/*
|
|
11
|
+
* This component is used to test the PortalHost hook
|
|
12
|
+
*/
|
|
13
|
+
const TestComponent = () => {
|
|
14
|
+
const state = useContext(PortalStateContext);
|
|
15
|
+
|
|
16
|
+
const text = 'host' in state! ? 'registered' : 'unregistered';
|
|
17
|
+
return <Typography.Body>{text}</Typography.Body>;
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
describe('PortalHost', () => {
|
|
21
|
+
it('should register portal when mount', async () => {
|
|
22
|
+
const { getByText } = renderWithTheme(
|
|
23
|
+
<PortalProvider>
|
|
24
|
+
<PortalHost name="host" />
|
|
25
|
+
<TestComponent />
|
|
26
|
+
</PortalProvider>
|
|
27
|
+
);
|
|
28
|
+
|
|
29
|
+
expect(getByText('registered')).toBeDefined();
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
it('should unregister portal when unmount', async () => {
|
|
33
|
+
const { getByText, rerender } = renderWithTheme(
|
|
34
|
+
<PortalProvider>
|
|
35
|
+
<PortalHost name="host" />
|
|
36
|
+
<TestComponent />
|
|
37
|
+
</PortalProvider>
|
|
38
|
+
);
|
|
39
|
+
|
|
40
|
+
rerender(
|
|
41
|
+
<ThemeProvider theme={theme}>
|
|
42
|
+
<PortalProvider>
|
|
43
|
+
<TestComponent />
|
|
44
|
+
</PortalProvider>
|
|
45
|
+
</ThemeProvider>
|
|
46
|
+
);
|
|
47
|
+
|
|
48
|
+
await waitFor(() => expect(getByText('unregistered')).toBeDefined());
|
|
49
|
+
});
|
|
50
|
+
});
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import React, { useContext } from 'react';
|
|
2
|
+
import { PortalStateContext } from '../contexts';
|
|
3
|
+
import Typography from '../../Typography';
|
|
4
|
+
import renderWithTheme from '../../../testHelpers/renderWithTheme';
|
|
5
|
+
import { PortalProvider } from '../PortalProvider';
|
|
6
|
+
|
|
7
|
+
const TestComponent = () => {
|
|
8
|
+
const state = useContext(PortalStateContext);
|
|
9
|
+
|
|
10
|
+
const text = 'root' in state! ? 'registered' : 'unregistered';
|
|
11
|
+
return <Typography.Body>{text}</Typography.Body>;
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
describe('PortalProvider', () => {
|
|
15
|
+
it('should register root portal when mount', async () => {
|
|
16
|
+
const { getByText } = renderWithTheme(
|
|
17
|
+
<PortalProvider>
|
|
18
|
+
<TestComponent />
|
|
19
|
+
</PortalProvider>
|
|
20
|
+
);
|
|
21
|
+
|
|
22
|
+
expect(getByText('registered')).toBeDefined();
|
|
23
|
+
});
|
|
24
|
+
});
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { View } from 'react-native';
|
|
3
|
+
import { waitFor, within } from '@testing-library/react-native';
|
|
4
|
+
import renderWithTheme from '../../../testHelpers/renderWithTheme';
|
|
5
|
+
import { PortalHost } from '../PortalHost';
|
|
6
|
+
import { PortalProvider } from '../PortalProvider';
|
|
7
|
+
import Typography from '../../Typography';
|
|
8
|
+
import Portal from '..';
|
|
9
|
+
|
|
10
|
+
describe('Portal', () => {
|
|
11
|
+
it('should render Typography inside Portal.Host', async () => {
|
|
12
|
+
const { getByTestId } = renderWithTheme(
|
|
13
|
+
<PortalProvider>
|
|
14
|
+
<View testID="portal-wrapper">
|
|
15
|
+
<PortalHost name="host" />
|
|
16
|
+
</View>
|
|
17
|
+
<Portal hostName="host">
|
|
18
|
+
<Typography.Body>portal</Typography.Body>;
|
|
19
|
+
</Portal>
|
|
20
|
+
</PortalProvider>
|
|
21
|
+
);
|
|
22
|
+
|
|
23
|
+
await waitFor(() =>
|
|
24
|
+
expect(
|
|
25
|
+
within(getByTestId('portal-wrapper')).getByText('portal')
|
|
26
|
+
).toBeDefined()
|
|
27
|
+
);
|
|
28
|
+
});
|
|
29
|
+
});
|