React Navigation这个组件较以前版本还是变化挺大的, 这里做一下记录, 方便快速入门
为什么要用React Navigation?
优点:
- 所有内容都是使用 JavaScript 在 React Native 的基础上编写的, 因此可以做到
简单的OTA更新
,可调试
,可定制
- 大多数应用的自定义导航,需要使用包装原生导航的API来完成此操作,这需要你编写大量原生代码。但是
React Navigation
很容易自定义. - 据说这也是RN官方推荐使用的组件
缺点:
- API 有时不直观且难以使用,且改进它可能需要
破坏性
的修改
鉴于这个缺点, 备选方案是使用react-native-navigation
react-native-navigation
这个方案 使用 iOS 和 Android上 的基础原生 API,这是 React Navigation 的流行替代方案,值得考虑,如果你重视完全遵守平台约定,并且不关心定制化。
题外话: React Navigation
的大部分逻辑都是用 JavaScript
而不是原生实现的,所以多关注 JavaScript
的线程阻塞是很有用的。
如何使用React Navigation?
安装
$ yarn add react-navigation
或者
$ npm install --save react-navigation
由于StackNavigator 内部用到了手势状态相关, 所以使用 StackNavigator 时需要导入以下库.
$ yarn add react-native-gesture-handler
添加完需要链接到本地库
$ react-native link react-native-gesture-handler
或者
$ react-native link
使用
在react-navigation
中有以下三种类型的导航器:
- Stack Navigation: 屏幕上方拥有导航栏的导航器
- Tab Navigation: 屏幕下方拥有标签栏的导航器.
- Drawer Navigation: 拥有抽屉效果的导航器. (此文暂不涉及)
Stack Navigation:
这种导航器采用一种栈的方式来管理控制器, 以First In Last Out
的原则来处理控制器的跳转.
创建StackNavigator
const HomeStack = createStackNavigator({
// key: vc的名字, value: vc
Home: HomeScene,
Nearby: NearbyScene,
Order: OrderScene,
Mine: MineScene
}, {
initialRouteName: 'Home',
// 配置统一的导航栏样式
navigationOptions: {
headerStyle: {
backgroundColor: 'black'
},
headerTintColor: '#fff',
headerTitleStyle: {
fontWeight: 'bold'
}
}
})
在HomeScene
内部设置导航栏样式, 跳转vc
export default class HomeScene extends PureComponent {
// 设置样式
static navigationOptions = {
title: 'Home_Title',
headerStyle: {
backgroundColor: '#f4511e',
},
headerTintColor: '#fff',
headerTitleStyle: {
fontWeight: 'bold',
fontSize: 20
},
}
render() {
return (
HomeScene
// 跳转到 'Nearby' 这个控制器, 这个前面已经注册过
// navigate方法: param1为vc名称, param2为传递的参数
);
}
}
在NearbyScene
处理传递参数
export default class NearbyScene extends PureComponent {
render() {
/**
* 第一种: 直接获取param,
* 第二种, 未获取到对应的param, 返回的是默认值
* 第三种: 直接获取param, 但是无法处理值为nil的情况
*/
const { navigation } = this.props;
const itemId = navigation.getParam('itemId', 'defaultID')
const otherParam = navigation.getParam('otherParam2', 'defaultValue');
const thirdParam = navigation.state.params.thirdParam
return (
// 显示传递的参数
itemId: {JSON.stringify(itemId)}
otherParam: {JSON.stringify(otherParam)}
thirdParam: {JSON.stringify(thirdParam)}
// 修改参数值
控制器之间的跳转
跳到下一个界面, 但是不能跳到当前界面
this.props.navigation.navigate('Home')
跳到下一个界面, 但是不能跳到当前界面
this.props.navigation.push('Nearby')
返回上一个界面
this.props.navigation.goBack()
在栈控制器里, 返回到上一个界面
this.props.navigation.pop()
在栈控制器里, 返回到栈底控制器
this.props.navigation.popToTop()
自定义导航栏
static navigationOptions = ({ navigation, navigationOptions }) => {
const { params } = navigation.state
return {
// 自定义TitleView
headerTitle: ,
// 自定义右侧
headerRight: (
Tab Navigation
一般来说, 标签栏控制器会嵌套导航栏控制器使用
/**
* 子Tab
*/
const HomeTab = createStackNavigator({
Home: HomeScene
})
const NearbyTab = createStackNavigator({
Nearby: NearbyScene
})
/**
* 主Tab
*/
const MainTab = createBottomTabNavigator({
Home: {
screen: HomeTab,
navigationOptions: () => ({
tabBarLabel: '团购',
tabBarIcon: ({focused, tintColor}) => (
)
})
},
Nearby: {
screen: NearbyTab,
navigationOptions: () => ({
tabBarLabel: '附近',
tabBarIcon: ({focused, tintColor}) => (
// 这是自定义的控件
)
})
},
}, {
tabBarPosition: 'bottom',
lazy: true,
animationEnabled: false,
swipeEnabled: false,
tabBarOptions: {
activeTintColor: 'red',
inactiveTintColor: 'gray',
style: {
backgroundColor: 'white'
}
}
})
参考
官方演示Demo, 不可直接运行
其他演示Demo, 可直接运行查看效果, 不全.