REACT NAVIGATION August 29, 2018

【React Navigation】十三、在任意组件中使用navigation属性

Words count 9.9k Reading time 9 mins. Read count 0

withNavigation是一个更高阶的组件,它可以将navigation属性传递给一个包装好的组件。当您无法直接将navigation传递到组件中,或者不想在深层嵌套的子项中传递它时,它将很有用。

1
2
3
4
5
6
7
8
9
10
11
import React from 'react';
import { Button } from 'react-native';
import { withNavigation } from 'react-navigation';

export default class MyBackButton extends React.Component {
render() {
// This will throw an 'undefined is not a function' exception because the navigation
// prop is undefined.
return <Button title="Back" onPress={() => { this.props.navigation.goBack() }} />;
}
}

要处理上边出现的异常,你可以在屏幕渲染时将navigation传递给MyBackButton,如:

或者,您可以使用withNavigation函数来自动提供navigation。此函数的行为与Redux的connect函数类似,connect为它包装的组件提供dispatch,而withNavigation则为组件提供navigation。

1
2
3
4
5
6
7
8
9
10
11
12
13
import React from 'react';
import { Button } from 'react-native';
import { withNavigation } from 'react-navigation';

class MyBackButton extends React.Component {
render() {
return <Button title="Back" onPress={() => { this.props.navigation.goBack() }} />;
}
}

// withNavigation returns a component that wraps MyBackButton and passes in the
// navigation prop
export default withNavigation(MyBackButton);

完整可执行代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
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
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
import React from 'react';
import { View, Text, TouchableHighlight,Button } from 'react-native';
import {
createStackNavigator,
createBottomTabNavigator,
createDrawerNavigator,
withNavigation,
} from 'react-navigation';

class MyBackButton extends React.Component {
render() {
return <Button title="Back" onPress={() => { this.props.navigation.navigate('Details') }} />;
}
}

// withNavigation returns a component that wraps MyBackButton and passes in the
// navigation prop
const MyButton = withNavigation(MyBackButton);

const Placeholder = ({ text }) => (
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
<Text>{text}</Text>
</View>
);

class FeedScreen extends React.Component {


render() {
return (
<View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
<MyButton />
</View>
);
}
}
FeedScreen.navigationOptions = {
title: "FeedScreen",
};

class DetailsScreen extends React.Component {
render() {
return <Placeholder text="DetailsScreen!" />;
}
}
DetailsScreen.navigationOptions = {
title: "DetailsScreen",
};

class ProfileScreen extends React.Component {
render() {
return <Placeholder text="ProfileScreen!" />;
}
}

const FeedStack = createStackNavigator({
FeedHome: FeedScreen,
Details: DetailsScreen,
});

export default createDrawerNavigator({
Feed: FeedStack,
Profile: ProfileScreen,
});

FeedStack.navigationOptions = ({ navigation }) => {
let drawerLockMode = 'unlocked';
if (navigation.state.index > 0) {
drawerLockMode = 'locked-closed';
}

return {
drawerLockMode,
};
};

0%