@react-navigation/routers 8.0.0-alpha.13 → 8.0.0-alpha.14
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/lib/module/BaseRouter.js +64 -62
- package/lib/module/BaseRouter.js.map +1 -1
- package/lib/module/DrawerRouter.js +15 -14
- package/lib/module/DrawerRouter.js.map +1 -1
- package/lib/module/StackRouter.js +17 -11
- package/lib/module/StackRouter.js.map +1 -1
- package/lib/module/SwitchRouter.js +369 -0
- package/lib/module/SwitchRouter.js.map +1 -0
- package/lib/module/TabRouter.js +14 -331
- package/lib/module/TabRouter.js.map +1 -1
- package/lib/typescript/src/BaseRouter.d.ts +3 -1
- package/lib/typescript/src/BaseRouter.d.ts.map +1 -1
- package/lib/typescript/src/DrawerRouter.d.ts +1 -0
- package/lib/typescript/src/DrawerRouter.d.ts.map +1 -1
- package/lib/typescript/src/StackRouter.d.ts.map +1 -1
- package/lib/typescript/src/SwitchRouter.d.ts +69 -0
- package/lib/typescript/src/SwitchRouter.d.ts.map +1 -0
- package/lib/typescript/src/TabRouter.d.ts +4 -24
- package/lib/typescript/src/TabRouter.d.ts.map +1 -1
- package/package.json +2 -2
- package/src/BaseRouter.tsx +93 -82
- package/src/DrawerRouter.tsx +25 -19
- package/src/StackRouter.tsx +27 -17
- package/src/SwitchRouter.tsx +621 -0
- package/src/TabRouter.tsx +24 -524
package/src/BaseRouter.tsx
CHANGED
|
@@ -6,105 +6,116 @@ import type {
|
|
|
6
6
|
PartialState,
|
|
7
7
|
} from './types';
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
)
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
: state.index;
|
|
24
|
-
|
|
25
|
-
if (index === -1) {
|
|
26
|
-
return null;
|
|
27
|
-
}
|
|
9
|
+
function getStateForAction<State extends NavigationState>(
|
|
10
|
+
state: State,
|
|
11
|
+
action: CommonNavigationAction
|
|
12
|
+
): State | PartialState<State> | null;
|
|
13
|
+
function getStateForAction(
|
|
14
|
+
state: NavigationState,
|
|
15
|
+
action: CommonNavigationAction
|
|
16
|
+
) {
|
|
17
|
+
switch (action.type) {
|
|
18
|
+
case 'SET_PARAMS':
|
|
19
|
+
case 'REPLACE_PARAMS': {
|
|
20
|
+
const index = action.source
|
|
21
|
+
? state.routes.findIndex((r) => r.key === action.source)
|
|
22
|
+
: state.index;
|
|
28
23
|
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
routes: state.routes.map((r, i) =>
|
|
32
|
-
i === index
|
|
33
|
-
? {
|
|
34
|
-
...r,
|
|
35
|
-
params:
|
|
36
|
-
action.type === 'REPLACE_PARAMS'
|
|
37
|
-
? action.payload.params
|
|
38
|
-
: { ...r.params, ...action.payload.params },
|
|
39
|
-
}
|
|
40
|
-
: r
|
|
41
|
-
),
|
|
42
|
-
};
|
|
24
|
+
if (index === -1) {
|
|
25
|
+
return null;
|
|
43
26
|
}
|
|
44
27
|
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
28
|
+
return {
|
|
29
|
+
...state,
|
|
30
|
+
routes: state.routes.map((r, i) =>
|
|
31
|
+
i === index
|
|
32
|
+
? {
|
|
33
|
+
...r,
|
|
34
|
+
params:
|
|
35
|
+
action.type === 'REPLACE_PARAMS'
|
|
36
|
+
? action.payload.params
|
|
37
|
+
: { ...r.params, ...action.payload.params },
|
|
38
|
+
}
|
|
39
|
+
: r
|
|
40
|
+
),
|
|
41
|
+
};
|
|
42
|
+
}
|
|
49
43
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
44
|
+
case 'PUSH_PARAMS': {
|
|
45
|
+
const index = action.source
|
|
46
|
+
? state.routes.findIndex((r) => r.key === action.source)
|
|
47
|
+
: state.index;
|
|
53
48
|
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
routes: state.routes.map((r, i) =>
|
|
57
|
-
i === index
|
|
58
|
-
? {
|
|
59
|
-
...r,
|
|
60
|
-
params: action.payload.params,
|
|
61
|
-
history: [
|
|
62
|
-
...(r.history ?? []),
|
|
63
|
-
{ type: 'params', params: r.params },
|
|
64
|
-
],
|
|
65
|
-
}
|
|
66
|
-
: r
|
|
67
|
-
),
|
|
68
|
-
};
|
|
49
|
+
if (index === -1) {
|
|
50
|
+
return null;
|
|
69
51
|
}
|
|
70
52
|
|
|
71
|
-
|
|
72
|
-
|
|
53
|
+
return {
|
|
54
|
+
...state,
|
|
55
|
+
routes: state.routes.map((r, i) =>
|
|
56
|
+
i === index
|
|
57
|
+
? {
|
|
58
|
+
...r,
|
|
59
|
+
params: action.payload.params,
|
|
60
|
+
history: [
|
|
61
|
+
...(r.history ?? []),
|
|
62
|
+
{ type: 'params', params: r.params },
|
|
63
|
+
],
|
|
64
|
+
}
|
|
65
|
+
: r
|
|
66
|
+
),
|
|
67
|
+
};
|
|
68
|
+
}
|
|
73
69
|
|
|
74
|
-
|
|
70
|
+
case 'RESET': {
|
|
71
|
+
const nextState = action.payload;
|
|
75
72
|
|
|
73
|
+
const routeNamesSet = new Set(state.routeNames);
|
|
74
|
+
|
|
75
|
+
if (
|
|
76
|
+
nextState.routes.length === 0 ||
|
|
77
|
+
nextState.routes.some(
|
|
78
|
+
(route: { name: string }) => !routeNamesSet.has(route.name)
|
|
79
|
+
)
|
|
80
|
+
) {
|
|
81
|
+
return null;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
if (nextState.stale === false) {
|
|
76
85
|
if (
|
|
77
|
-
|
|
78
|
-
nextState.
|
|
79
|
-
|
|
80
|
-
|
|
86
|
+
state.routeNames.length !== nextState.routeNames.length ||
|
|
87
|
+
nextState.routeNames.some((name) => !routeNamesSet.has(name)) ||
|
|
88
|
+
!Number.isInteger(nextState.index) ||
|
|
89
|
+
nextState.index < 0 ||
|
|
90
|
+
nextState.index >= nextState.routes.length
|
|
81
91
|
) {
|
|
82
92
|
return null;
|
|
83
93
|
}
|
|
84
94
|
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
return {
|
|
94
|
-
...nextState,
|
|
95
|
-
routes: nextState.routes.map((route) =>
|
|
96
|
-
route.key ? route : { ...route, key: `${route.name}-${nanoid()}` }
|
|
97
|
-
),
|
|
98
|
-
};
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
return nextState;
|
|
95
|
+
return {
|
|
96
|
+
...nextState,
|
|
97
|
+
routes: nextState.routes.map((route) =>
|
|
98
|
+
'key' in route && route.key
|
|
99
|
+
? route
|
|
100
|
+
: { ...route, key: `${route.name}-${nanoid()}` }
|
|
101
|
+
),
|
|
102
|
+
};
|
|
102
103
|
}
|
|
103
104
|
|
|
104
|
-
|
|
105
|
-
return null;
|
|
105
|
+
return nextState;
|
|
106
106
|
}
|
|
107
|
-
|
|
107
|
+
|
|
108
|
+
default:
|
|
109
|
+
return null;
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
/**
|
|
114
|
+
* Base router object that can be used when writing custom routers.
|
|
115
|
+
* This provides few helper methods to handle common actions such as `RESET`.
|
|
116
|
+
*/
|
|
117
|
+
export const BaseRouter = {
|
|
118
|
+
getStateForAction,
|
|
108
119
|
|
|
109
120
|
shouldActionChangeFocus(action: CommonNavigationAction) {
|
|
110
121
|
return action.type === 'NAVIGATE';
|
package/src/DrawerRouter.tsx
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
1
|
import { nanoid } from 'nanoid/non-secure';
|
|
2
2
|
|
|
3
|
+
import { SwitchRouter } from './SwitchRouter';
|
|
3
4
|
import {
|
|
4
5
|
type TabActionHelpers,
|
|
5
6
|
TabActions,
|
|
6
7
|
type TabActionType,
|
|
7
8
|
type TabNavigationState,
|
|
8
|
-
TabRouter,
|
|
9
9
|
type TabRouterOptions,
|
|
10
10
|
} from './TabRouter';
|
|
11
11
|
import type {
|
|
@@ -14,6 +14,7 @@ import type {
|
|
|
14
14
|
PartialState,
|
|
15
15
|
Router,
|
|
16
16
|
} from './types';
|
|
17
|
+
|
|
17
18
|
export type DrawerStatus = 'open' | 'closed';
|
|
18
19
|
|
|
19
20
|
export type DrawerActionType =
|
|
@@ -44,7 +45,11 @@ export type DrawerNavigationState<ParamList extends ParamListBase> = Omit<
|
|
|
44
45
|
* List of previously visited route keys and drawer open status.
|
|
45
46
|
*/
|
|
46
47
|
history: (
|
|
47
|
-
| {
|
|
48
|
+
| {
|
|
49
|
+
type: 'route';
|
|
50
|
+
key: string;
|
|
51
|
+
params?: object | undefined;
|
|
52
|
+
}
|
|
48
53
|
| { type: 'drawer'; status: DrawerStatus }
|
|
49
54
|
)[];
|
|
50
55
|
};
|
|
@@ -87,10 +92,7 @@ export function DrawerRouter({
|
|
|
87
92
|
DrawerNavigationState<ParamListBase>,
|
|
88
93
|
DrawerActionType | CommonNavigationAction
|
|
89
94
|
> {
|
|
90
|
-
const router =
|
|
91
|
-
DrawerNavigationState<ParamListBase>,
|
|
92
|
-
TabActionType | CommonNavigationAction
|
|
93
|
-
>;
|
|
95
|
+
const router = SwitchRouter<'drawer'>(rest);
|
|
94
96
|
|
|
95
97
|
const isDrawerInHistory = (
|
|
96
98
|
state:
|
|
@@ -179,11 +181,16 @@ export function DrawerRouter({
|
|
|
179
181
|
return partialState;
|
|
180
182
|
}
|
|
181
183
|
|
|
182
|
-
let state =
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
184
|
+
let state: DrawerNavigationState<ParamListBase> = {
|
|
185
|
+
...router.getRehydratedState(partialState, {
|
|
186
|
+
routeNames,
|
|
187
|
+
routeParamList,
|
|
188
|
+
routeGetIdList,
|
|
189
|
+
}),
|
|
190
|
+
default: defaultStatus,
|
|
191
|
+
type: 'drawer',
|
|
192
|
+
key: `drawer-${nanoid()}`,
|
|
193
|
+
};
|
|
187
194
|
|
|
188
195
|
if (isDrawerInHistory(partialState)) {
|
|
189
196
|
// Re-sync the drawer entry in history to correct it if it was wrong
|
|
@@ -191,12 +198,7 @@ export function DrawerRouter({
|
|
|
191
198
|
state = addDrawerToHistory(state);
|
|
192
199
|
}
|
|
193
200
|
|
|
194
|
-
return
|
|
195
|
-
...state,
|
|
196
|
-
default: defaultStatus,
|
|
197
|
-
type: 'drawer',
|
|
198
|
-
key: `drawer-${nanoid()}`,
|
|
199
|
-
};
|
|
201
|
+
return state;
|
|
200
202
|
},
|
|
201
203
|
|
|
202
204
|
getStateForRouteFocus(state, key) {
|
|
@@ -224,8 +226,12 @@ export function DrawerRouter({
|
|
|
224
226
|
case 'NAVIGATE': {
|
|
225
227
|
const result = router.getStateForAction(state, action, options);
|
|
226
228
|
|
|
227
|
-
if (
|
|
228
|
-
|
|
229
|
+
if (
|
|
230
|
+
result != null &&
|
|
231
|
+
result.stale === false &&
|
|
232
|
+
result.index !== state.index
|
|
233
|
+
) {
|
|
234
|
+
return closeDrawer(result);
|
|
229
235
|
}
|
|
230
236
|
|
|
231
237
|
return result;
|
package/src/StackRouter.tsx
CHANGED
|
@@ -703,20 +703,23 @@ export function StackRouter(options: StackRouterOptions) {
|
|
|
703
703
|
/**
|
|
704
704
|
* When popping entries,
|
|
705
705
|
* - Pop entries from route.history
|
|
706
|
-
* - Pop
|
|
706
|
+
* - Pop the route itself and continue from the route below it
|
|
707
707
|
*
|
|
708
708
|
* Repeat until:
|
|
709
709
|
* - We have popped the amount of items in count
|
|
710
710
|
* - There are no more items to pop
|
|
711
|
+
*
|
|
712
|
+
* Routes above the current route (e.g. above the source) are kept intact
|
|
711
713
|
*/
|
|
712
714
|
if (route.history?.length || currentIndex > 0) {
|
|
713
715
|
let count = action.payload.count;
|
|
714
|
-
|
|
716
|
+
|
|
717
|
+
let removedFromIndex: number | undefined;
|
|
718
|
+
|
|
719
|
+
const sourceIndex = currentIndex;
|
|
715
720
|
|
|
716
721
|
while (count > 0 && (route.history?.length || currentIndex > 0)) {
|
|
717
722
|
if (route.history?.length) {
|
|
718
|
-
nextRoutes = [...nextRoutes];
|
|
719
|
-
|
|
720
723
|
const end = Math.min(count, route.history.length);
|
|
721
724
|
const last = route.history.at(-end);
|
|
722
725
|
const history = route.history.slice(0, -end);
|
|
@@ -724,7 +727,7 @@ export function StackRouter(options: StackRouterOptions) {
|
|
|
724
727
|
|
|
725
728
|
count = count - removed;
|
|
726
729
|
|
|
727
|
-
|
|
730
|
+
route = {
|
|
728
731
|
...route,
|
|
729
732
|
params: last?.type === 'params' ? last.params : route.params,
|
|
730
733
|
history,
|
|
@@ -732,19 +735,11 @@ export function StackRouter(options: StackRouterOptions) {
|
|
|
732
735
|
}
|
|
733
736
|
|
|
734
737
|
if (currentIndex > 0 && count > 0) {
|
|
735
|
-
|
|
736
|
-
|
|
738
|
+
count = count - 1;
|
|
739
|
+
removedFromIndex = currentIndex;
|
|
740
|
+
currentIndex = currentIndex - 1;
|
|
737
741
|
|
|
738
|
-
|
|
739
|
-
.slice(0, end)
|
|
740
|
-
.concat(nextRoutes.slice(currentIndex + 1));
|
|
741
|
-
|
|
742
|
-
const removed = length - nextRoutes.length;
|
|
743
|
-
|
|
744
|
-
count = count - removed;
|
|
745
|
-
currentIndex = nextRoutes.length - 1;
|
|
746
|
-
|
|
747
|
-
const currentRoute = nextRoutes[currentIndex];
|
|
742
|
+
const currentRoute = routes[currentIndex];
|
|
748
743
|
|
|
749
744
|
if (currentRoute == null) {
|
|
750
745
|
throw new Error(
|
|
@@ -756,6 +751,21 @@ export function StackRouter(options: StackRouterOptions) {
|
|
|
756
751
|
}
|
|
757
752
|
}
|
|
758
753
|
|
|
754
|
+
let nextRoutes =
|
|
755
|
+
removedFromIndex === undefined
|
|
756
|
+
? routes
|
|
757
|
+
: routes
|
|
758
|
+
.slice(0, removedFromIndex)
|
|
759
|
+
.concat(routes.slice(sourceIndex + 1));
|
|
760
|
+
|
|
761
|
+
if (route !== routes[currentIndex]) {
|
|
762
|
+
if (nextRoutes === routes) {
|
|
763
|
+
nextRoutes = [...routes];
|
|
764
|
+
}
|
|
765
|
+
|
|
766
|
+
nextRoutes[currentIndex] = route;
|
|
767
|
+
}
|
|
768
|
+
|
|
759
769
|
return retainRoutes(state, getStateWithRoutes(state, nextRoutes));
|
|
760
770
|
}
|
|
761
771
|
|