React Native开发我爱编程React Native学习

React Native之react-navigation总结

2018-08-23  本文已影响23人  一只路过的小学生

react-navigation号称拥有近乎原生页面切换的性能,在项目中开始投入使用以来,确实发现了其优越性,一定程度上解决了RN在页面路由管理方面上的薄弱,下面就我在项目中遇到的坑和难点做一个总结。

1、Header的参数设置后无效

  每一个navigator只会查看其直接子级进行配置,比如一个页面在一个stackNavigator里,而这个stackNavigator在一个tabNavigator里,那么直接在页面配置 navigationOptions 是无效的,要在stackNavigator里进行配置,例如:

let HomeStack = createStackNavigator({ A });
let SettingsStack = createStackNavigator({ B });

HomeStack.navigationOptions = {
  tabBarLabel: 'Home!',
};

SettingsStack.navigationOptions = {
  tabBarLabel: 'Settings!',
};

export default createBottomTabNavigator({
  HomeStack,
  SettingsStack,
});

2、react-navigation的Header太过繁琐,自由度不高,与组件的信息交互里十分不友好

3、对于常见的‘底部标签式导航’布局,应该如何进行构建

const RootStack = createSwitchNavigator(
  {
    Splash: SplashScreen,
    App: AppStack,
    Login: LoginScreen
  },
  {
    initialRouteName: 'Splash'
  }
)

export default class App extends React.Component<Props> {
  render() {
    return (
      <RootStack
        ref={navigatorRef => {
          NavigationService.setTopLevelNavigator(navigatorRef)
        }}
      />
    )
  }
}
const tabScreens = {
  first: {
    screen: FirstScreen,
    navigationOptions: {
      tabBarLabel: '首页',
      tabBarIcon: ({ tintColor }) => renderIcon('home', tintColor)
    }
  },
  message: {
    screen: MessageScreen,
    navigationOptions: {
      tabBarLabel: '消息',
      tabBarIcon: ({ tintColor }) => renderIcon('comments-o', tintColor)
    }
  },
  mine: {
    screen: MineScreen,
    navigationOptions: {
      tabBarLabel: '我的',
      tabBarIcon: ({ tintColor }) => renderIcon('user', tintColor)
    }
  }
}
const tabConfig = {
  tabBarPosition: 'bottom',
  tabBarOptions: {
    inactiveTintColor: '#a0a0a0',
    activeTintColor: basicColor.mainColor,
    indicatorStyle: { backgroundColor: 'transparent' },
    showIcon: true,
    style: {
      margin: 0,
      backgroundColor: '#ffffff',
      borderTopWidth: 0.66,
      borderTopColor: '#dddddd'
    },
    tabStyle: {
      padding: 0,
      margin: 0
    },
    labelStyle: {
      fontSize: 11,
      margin: 0,
      marginBottom: 5
    },
    iconStyle: {
      marginTop: -3,
      marginBottom: 0
    }
  },
  swipeEnabled: false
}
const HomeTab = createBottomTabNavigator(tabScreens, tabConfig)

4、在android上页面跳转如何实现ios左右切换的效果

其实react-navigation本身就实现了这个效果,目前文件在 'react-navigation/src/views/StackView/StackViewStyleInterpolator.js',可能版本更新之后又会改变路径

import StackStyleInterpolator from 'react-navigation/src/views/StackView/StackViewStyleInterpolator.js'
const AppStack = createStackNavigator(
  {
    Home: HomeScreen,
    Front: FrontScreen,
    Setting: SettingScreen
  },
  {
    headerMode: 'none',
    transitionConfig: () => ({
      //设置横向切换动画
      screenInterpolator: StackStyleInterpolator.forHorizontal
    })
  }
)

5、状态栏StatusBar的位置应该配置在哪

首先我们应该明白StatusBar对于不同的navigator有不同的表现形式:

1.在 SwitchNavigator中的页面配置:每一个页面的statusBar设置都不会影响到另外的页面

2.在StackNavigator、DrawerNavigator中的页面配置:每一次设置statusBar都会重新设置状态栏

3.在TabNavigator中的页面配置:只有页面第一次加载才会重新设置状态栏。

4.综上所诉,结合到项目具体的结构,我们需要对登录和加载页面设置statusBar,首页FrontScreen作为登录后第一个加载的页面也需要设置statusBar,因为我们项目是采用半透明式状态栏,所以不需要考虑状态栏随不同页面改变而改变的情况,如果有需要可以参考基于路由的不同状态栏配置

6、如何跳转到一个不存在于当前navigator的页面(比如用户信息过期需跳转到登录界面)

import { NavigationActions, StackActions } from 'react-navigation'
let _navigator

function setTopLevelNavigator(navigatorRef) {
  _navigator = navigatorRef
}

function navigate(routeName, params) {
  _navigator.dispatch(
    NavigationActions.navigate({
      routeName,
      params
    })
  )
}

function resetTo(routeName) {
  const resetAction = StackActions.reset({
    index: 0,
    actions: [NavigationActions.navigate({ routeName: routeName })]
  })
  _navigator.dispatch(resetAction)
}
function goBack() {
  _navigator.dispatch(NavigationActions.back())
}
export default { navigate, resetTo, setTopLevelNavigator, goBack }

然后在根Navigator里调用setTopLevelNavigator

<RootStack
        ref={navigatorRef => {
          NavigationService.setTopLevelNavigator(navigatorRef)
        }}
      />

在其他地方调用NavigationService里的相应方法就可以从根导航器里跳转到任一个界面

7、如何在不传递navigation的情况下在自己封装的Header里调用goback()

上一篇 下一篇

猜你喜欢

热点阅读