Skip to content

Commit 5f94cb9

Browse files
committed
Add snack links to params
1 parent 9c68751 commit 5f94cb9

File tree

1 file changed

+183
-23
lines changed

1 file changed

+183
-23
lines changed

versioned_docs/version-7.x/params.md

Lines changed: 183 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -22,9 +22,16 @@ We recommend that the params you pass are JSON-serializable. That way, you'll be
2222

2323
:::
2424

25-
<samp id="passing-params" />
26-
27-
```js
25+
```js name="Passing params" snack version=7
26+
import * as React from 'react';
27+
import { Button, View, Text } from 'react-native';
28+
import {
29+
createStaticNavigation,
30+
useNavigation,
31+
} from '@react-navigation/native';
32+
import { createNativeStackNavigator } from '@react-navigation/native-stack';
33+
34+
// codeblock-focus-start
2835
function HomeScreen() {
2936
const navigation = useNavigation();
3037

@@ -35,10 +42,12 @@ function HomeScreen() {
3542
title="Go to Details"
3643
onPress={() => {
3744
/* 1. Navigate to the Details route with params */
45+
// highlight-start
3846
navigation.navigate('Details', {
3947
itemId: 86,
4048
otherParam: 'anything you want here',
4149
});
50+
// highlight-end
4251
}}
4352
/>
4453
</View>
@@ -49,25 +58,44 @@ function DetailsScreen({ route }) {
4958
const navigation = useNavigation();
5059

5160
/* 2. Get the param */
61+
// highlight-next-line
5262
const { itemId, otherParam } = route.params;
63+
5364
return (
5465
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
5566
<Text>Details Screen</Text>
5667
<Text>itemId: {JSON.stringify(itemId)}</Text>
5768
<Text>otherParam: {JSON.stringify(otherParam)}</Text>
5869
<Button
5970
title="Go to Details... again"
60-
onPress={() =>
61-
navigation.push('Details', {
62-
itemId: Math.floor(Math.random() * 100),
63-
})
71+
onPress={
72+
() =>
73+
// highlight-start
74+
navigation.push('Details', {
75+
itemId: Math.floor(Math.random() * 100),
76+
})
77+
// highlight-end
6478
}
6579
/>
6680
<Button title="Go to Home" onPress={() => navigation.navigate('Home')} />
6781
<Button title="Go back" onPress={() => navigation.goBack()} />
6882
</View>
6983
);
7084
}
85+
// codeblock-focus-end
86+
87+
const RootStack = createNativeStackNavigator({
88+
screens: {
89+
Home: HomeScreen,
90+
Details: DetailsScreen,
91+
},
92+
});
93+
94+
const Navigation = createStaticNavigation(RootStack);
95+
96+
export default function App() {
97+
return <Navigation />;
98+
}
7199
```
72100

73101
![Screen with passed parameters](/assets/navigators/passing_params.png)
@@ -83,6 +111,7 @@ You can also pass some initial params to a screen. If you didn't specify any par
83111
{
84112
Details: {
85113
screen: DetailsScreen,
114+
// highlight-next-line
86115
initialParams: { itemId: 42 },
87116
},
88117
}
@@ -97,6 +126,7 @@ You can also pass some initial params to a screen. If you didn't specify any par
97126
<Stack.Screen
98127
name="Details"
99128
component={DetailsScreen}
129+
// highlight-next-line
100130
initialParams={{ itemId: 42 }}
101131
/>
102132
```
@@ -110,12 +140,52 @@ Screens can also update their params, like they can update their state. The `nav
110140

111141
Basic usage:
112142

113-
<samp id="updating-params" />
143+
```js name="Updating params" snack version=7
144+
import * as React from 'react';
145+
import { Text, View, Button } from 'react-native';
146+
import {
147+
createStaticNavigation,
148+
useNavigation,
149+
} from '@react-navigation/native';
150+
import { createNativeStackNavigator } from '@react-navigation/native-stack';
114151

115-
```js
116-
navigation.setParams({
117-
query: 'someText',
152+
function HomeScreen({ route }) {
153+
const navigation = useNavigation();
154+
const { itemId } = route.params;
155+
156+
return (
157+
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
158+
<Text>Home Screen</Text>
159+
<Text>itemId: {JSON.stringify(itemId)}</Text>
160+
<Button
161+
title="Update param"
162+
onPress={
163+
() =>
164+
// codeblock-focus-start
165+
navigation.setParams({
166+
itemId: Math.floor(Math.random() * 100),
167+
})
168+
// codeblock-focus-end
169+
}
170+
/>
171+
</View>
172+
);
173+
}
174+
175+
const RootStack = createNativeStackNavigator({
176+
screens: {
177+
Home: {
178+
screen: HomeScreen,
179+
initialParams: { itemId: 42 },
180+
},
181+
},
118182
});
183+
184+
const Navigation = createStaticNavigation(RootStack);
185+
186+
export default function App() {
187+
return <Navigation />;
188+
}
119189
```
120190

121191
:::note
@@ -130,16 +200,24 @@ Params aren't only useful for passing some data to a new screen, but they can al
130200

131201
To achieve this, you can use the `navigate` method, which acts like `goBack` if the screen already exists. You can pass the `params` with `navigate` to pass the data back:
132202

133-
<samp id="passing-params-back" />
203+
```js name="Passing params back" snack version=7
204+
import * as React from 'react';
205+
import { Text, View, TextInput, Button } from 'react-native';
206+
import {
207+
createStaticNavigation,
208+
useNavigation,
209+
} from '@react-navigation/native';
210+
import { createNativeStackNavigator } from '@react-navigation/native-stack';
134211

135-
```js
212+
// codeblock-focus-start
136213
function HomeScreen({ route }) {
137214
const navigation = useNavigation();
138215

139216
React.useEffect(() => {
140217
if (route.params?.post) {
141218
// Post updated, do something with `route.params.post`
142219
// For example, send the post to the server
220+
console.log('Post', route.params?.post);
143221
}
144222
}, [route.params?.post]);
145223

@@ -181,21 +259,103 @@ function CreatePostScreen({ route }) {
181259
</>
182260
);
183261
}
262+
// codeblock-focus-end
263+
264+
const RootStack = createNativeStackNavigator({
265+
screens: {
266+
Home: HomeScreen,
267+
CreatePost: CreatePostScreen,
268+
},
269+
});
270+
271+
const Navigation = createStaticNavigation(RootStack);
272+
273+
export default function App() {
274+
return <Navigation />;
275+
}
184276
```
185277
186278
Here, after you press "Done", the home screen's `route.params` will be updated to reflect the post text that you passed in `navigate`.
187279
188-
## Passing params to nested navigators
280+
## Passing params to a nested screen
189281
190-
If you have nested navigators, you need to pass params a bit differently. For example, say you have a navigator inside the `Account` screen, and want to pass params to the `Settings` screen inside that navigator. Then you can pass params as following:
282+
If you have nested navigators, you need to pass params a bit differently. For example, say you have a navigator inside the `More` screen and want to pass params to the `Settings` screen inside that navigator. Then you can pass params as the following:
191283
192-
<samp id="params-nested-navigators" />
284+
```js name="Passing params to nested screen" snack version=7
285+
import * as React from 'react';
286+
import { Text, View, TextInput, Button } from 'react-native';
287+
import {
288+
createStaticNavigation,
289+
useNavigation,
290+
} from '@react-navigation/native';
291+
import { createNativeStackNavigator } from '@react-navigation/native-stack';
292+
import { createBottomTabNavigator } from '@react-navigation/bottom-tabs';
193293

194-
```js
195-
navigation.navigate('Account', {
196-
screen: 'Settings',
197-
params: { user: 'jane' },
294+
function SettingsScreen({ route }) {
295+
const navigation = useNavigation();
296+
const { user } = route.params;
297+
298+
return (
299+
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
300+
<Text>Settings Screen</Text>
301+
<Text>userParam: {JSON.stringify(user)}</Text>
302+
<Button
303+
title="Go to Profile"
304+
onPress={() => navigation.navigate('Profile')}
305+
/>
306+
</View>
307+
);
308+
}
309+
310+
function ProfileScreen() {
311+
return (
312+
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
313+
<Text>Profile Screen</Text>
314+
</View>
315+
);
316+
}
317+
318+
function HomeScreen() {
319+
const navigation = useNavigation();
320+
321+
return (
322+
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
323+
<Text>Home Screen</Text>
324+
<Button
325+
title="Go to Settings"
326+
onPress={
327+
() =>
328+
// codeblock-focus-start
329+
navigation.navigate('More', {
330+
screen: 'Settings',
331+
params: { user: 'jane' },
332+
})
333+
// codeblock-focus-end
334+
}
335+
/>
336+
</View>
337+
);
338+
}
339+
340+
const MoreStack = createNativeStackNavigator({
341+
screens: {
342+
Settings: SettingsScreen,
343+
Profile: ProfileScreen,
344+
},
198345
});
346+
347+
const RootTabs = createBottomTabNavigator({
348+
screens: {
349+
Home: HomeScreen,
350+
More: MoreStack,
351+
},
352+
});
353+
354+
const Navigation = createStaticNavigation(RootTabs);
355+
356+
export default function App() {
357+
return <Navigation />;
358+
}
199359
```
200360
201361
See [Nesting navigators](nesting-navigators.md) for more details on nesting.
@@ -220,14 +380,14 @@ navigation.navigate('Profile', {
220380
});
221381
```
222382
223-
This looks convenient, and lets you access the user objects with `route.params.user` without any extra work.
383+
This looks convenient and lets you access the user objects with `route.params.user` without any extra work.
224384
225-
However, this is an anti-pattern. Data such as user objects should be in your global store instead of the navigation state. Otherwise you have the same data duplicated in multiple places. This can lead to bugs such as the profile screen showing outdated data even if the user object has changed after navigation.
385+
However, this is an anti-pattern. Data such as user objects should be in your global store instead of the navigation state. Otherwise, you have the same data duplicated in multiple places. This can lead to bugs such as the profile screen showing outdated data even if the user object has changed after navigation.
226386
227387
It also becomes problematic to link to the screen via deep linking or on the Web, since:
228388
229389
1. The URL is a representation of the screen, so it also needs to contain the params, i.e. full user object, which can make the URL very long and unreadable
230-
2. Since the user object is in the URL, it's possible to pass a random user object representing a user which doesn't exist, or has incorrect data in the profile
390+
2. Since the user object is in the URL, it's possible to pass a random user object representing a user which doesn't exist or has incorrect data in the profile
231391
3. If the user object isn't passed, or improperly formatted, this could result in crashes as the screen won't know how to handle it
232392
233393
A better way is to pass only the ID of the user in params:

0 commit comments

Comments
 (0)