createStackNavigator

createStackNavigator

createStackNavigator提供APP屏幕之間切換的能力,它是以棧的形式還管理屏幕之間的切換,新切換到的屏幕會放在棧的頂部。html

屏幕轉場風格

默認狀況下,createStackNavigator提供了轉場過渡效果,在Android和iOS上過渡效果是不一樣的,這也是React Native重平臺性的一個體現,在Android上從屏幕底部淡入,在iOS上是從屏幕的右側劃入,固然你也能夠經過配置讓StackNavigator支持屏幕從底部滑入的效果。react

createStackNavigator API

createStackNavigator(RouteConfigs, StackNavigatorConfig):微信

  • RouteConfigs(必選):路由配置對象是從路由名稱到路由配置的映射,告訴導航器該路由呈現什麼。
  • StackNavigatorConfig(可選):配置導航器的路由(如:默認首屏,navigationOptions,paths等)樣式(如,轉場模式mode、頭部模式等)。

從createStackNavigator API上能夠看出createStackNavigator支持經過RouteConfigsStackNavigatorConfig兩個參數來建立createStackNavigator導航器。app

RouteConfigs

RouteConfigs支持三個參數screenpath以及navigationOptions函數

  • screen(必選):指定一個 React 組件做爲屏幕的主要顯示內容,當這個組件被createStackNavigator加載時,它會被分配一個navigation prop。學習

  • path(可選):用來設置支持schema跳轉時使用,具體使用會在下文的有關Schema章節中講到;ui

  • navigationOptions(可選):用以配置全局的屏幕導航選項如:title、headerRight、headerLeft等;this

    StackNavigatorConfig

    react-navigation源碼中能夠看出StackNavigatorConfig支持配置的參數有10個。spa

    function createStackNavigator(routeConfigMap, stackConfig = {}) {
      const {
        initialRouteKey,
        initialRouteName,
        initialRouteParams,
        paths,
        navigationOptions,
        disableKeyboardHandling,
        getCustomActionCreators
      } = stackConfig;
      ...

    這7個參數能夠根據做用不一樣分爲路由配置、視圖樣式配置兩類,首先看用於路由配置的參數:code

    用於路由配置的參數:

    • initialRouteName: 設置默認的頁面組件,必須是上面已註冊的頁面組件。
    • initialRouteParams: 初始路由的參數。
    • navigationOptions: 屏幕導航的默認選項,下文會詳細講解。
    • initialRouteKey - 初始路由的可選標識符。
    • paths: 用來設置支持schema跳轉時使用,具體使用會在下文的有關Schema章節中講到。

用於導航樣式配置的參數:

  • mode: 頁面切換模式: 左右是card(至關於iOS中的push效果), 上下是modal(至關於iOS中的modal效果)

    • card: 普通app經常使用的左右切換。
    • modal: 上下切換。
  • headerMode: 導航欄的顯示模式: screen: 有漸變透明效果, float: 無透明效果, none: 隱藏導航欄。

    • float: 無透明效果, 默認。
    • screen: 有漸變透明效果, 如微信QQ的同樣。
    • none: 隱藏導航欄。
  • headerBackTitleVisible : 提供合理的默認值以肯定後退按鈕標題是否可見,但若是要覆蓋它,則可使用true或` false 在此選項中。

    • fade-in-place: 標題組件交叉淡入淡出而不移動,相似於iOS的Twitter,Instagram和Facebook應用程序。 這是默認值。
    • uikit: iOS的默認行爲的近似值。 headerTransitionPreset: 指定在啓用headerMode:float時header應如何從一個屏幕轉換到另外一個屏幕。
  • cardStyle: 樣式(iOS上頁面切換會有白色漸變蒙層,想去掉則能夠這樣設置,cardStyle: { opacity: null },切換頁面時的頁面邊框也在這裏能夠設置)。

  • onTransitionStart: 頁面切換開始時的回調函數 (咱們能夠在這裏註冊一些通知,告知咱們切面切換的狀態,方便後面處理頁面切換事件)。

  • onTransitionEnd: 頁面切換結束時的回調函數。

navigationOptions(屏幕導航選項)

支持一下參數:

  • title: 能夠做爲headerTitle的備選字段(當沒設置headerTitle時會用該字段做爲標題),也能夠做爲TabNavigator的tabBarLabel以及DrawerNavigator的drawerLabel。
  • header: 自定義導航條,能夠經過設置null來隱藏導航條;
  • headerTitle: 標題;
  • headerTitleAllowFontScaling: 標題是否容許縮放,默認true;
  • headerBackTitle: 定義在iOS上當前頁面進入到下一頁面的回退標題,能夠經過設置null來禁用它;
  • headerTruncatedBackTitle: 當回退標題不能顯示的時候顯示此屬性的標題,好比回退標題太長了;
  • headerBackImage:React 元素或組件在標題的後退按鈕中顯示自定義圖片。 當組件被調用時,它會在渲染時收到許多 props 如:(tintColor,title)。 默認爲帶有 react-navigation/views/assets/back-icon.png 這張圖片的組件,後者是平臺的默認後圖標圖像(iOS上爲向左的符號,Android上爲箭頭)。
  • headerRight: 定義導航欄右邊視圖;
  • headerLeft: 定義導航欄左邊視圖;
  • headerStyle: 定義導航欄的樣式,好比背景色等;
  • headerTitleStyle: 定義標題的樣式;
  • headerLeftContainerStyle:自定義 headerLeft 組件容器的樣式,例如,增長 padding。
  • headerRightContainerStyle:自定義 headerRight 組件容器的樣式,,例如,增長 padding。
  • headerTitleContainerStyle:自定義 headerTitle 組件容器的樣式, 例如,增長 padding。
  • headerBackTitleStyle: 定義返回標題的樣式;
  • headerPressColorAndroid:顏色爲材料波紋 (Android >= 5.0);
  • headerTintColor: 定義導航條的tintColor,會覆蓋headerTitleStyle中的顏色;
  • headerTransparent:默認爲 false。若是 true, 則標頭將不會有背景, 除非您顯式提供 headerStyle 或 headerBackground。
  • headerBackground:與headerTransparent一塊兒使用,以提供在標題後臺呈現的組件。 例如,您可使用模糊視圖來建立半透明標題。
  • gesturesEnabled: 定義是否能側滑返回,iOS默認true,Android默認false;
  • gestureResponseDistance: 定義滑動返回的有效距離,水平狀態下默認:25,垂直狀態默認135;
  • gestureDirection: 設置關閉手勢的方向。默認從左向右,能夠設置從右到左的滑動操做。

【案例】使用StackNavigator作界面導航、配置navigationOptionsStackNavigator

第一步:建立一個StackNavigator類型的導航器

export const AppStackNavigator = createStackNavigator({
    HomePage: {
        screen: HomePage
    },
    Page1: {
        screen: Page1,
        navigationOptions: ({navigation}) => ({
            title: `${navigation.state.params.name}頁面名`//動態設置navigationOptions
        })
    },
    Page2: {
        screen: Page2,
        navigationOptions: {//在這裏定義每一個頁面的導航屬性,靜態配置
            title: "This is Page2.",
        }
    },
    Page3: {
        screen: Page3,
        navigationOptions: (props) => {//在這裏定義每一個頁面的導航屬性,動態配置
            const {navigation} = props;
            const {state, setParams} = navigation;
            const {params} = state;
            return {
                title: params.title ? params.title : 'This is Page3',
                headerRight: (
                    <Button
                        title={params.mode === 'edit' ? '保存' : '編輯'}
                        onPress={() =>
                            setParams({mode: params.mode === 'edit' ? '' : 'edit'})}
                    />
                ),
            }
        }
    },
}, {
    defaultNavigationOptions: {
        // header: null,// 能夠經過將header設爲null 來禁用StackNavigator的Navigation Bar
    }
});

提示:和本文配套的還有一個React Navigation3x的視頻教程,歡迎學習。

第二步:配置navigationOptions:

步驟一的代碼中經過兩種方式配值了navigationOptions:

靜態配置:

對Page2的navigationOptions配置是經過靜態配置完成的:

Page2: {
    screen: Page2,
    navigationOptions: {//在這裏定義每一個頁面的導航屬性,靜態配置
        title: "This is Page2.",
    }
},

這種方式被稱爲靜態配置,由於navigationOptions中的參數是直接Hard Code的不依賴於變量。

動態配置:

對Page3的navigationOptions配置是經過動態配置完成的:

Page3: {
    screen: Page3,
    navigationOptions: (props) => {//在這裏定義每一個頁面的導航屬性,動態配置
        const {navigation} = props;
        const {state, setParams} = navigation;
        const {params} = state;
        return {
            title: params.title ? params.title : 'This is Page3',
            headerRight: (
                <Button
                    title={params.mode === 'edit' ? '保存' : '編輯'}
                    onPress={() =>
                        setParams({mode: params.mode === 'edit' ? '' : 'edit'})}
                />
            ),
        }
    }
},

從上述代碼中能夠看出Page3的navigationOptions依賴於props這個變量因此是動態的,當props中的內容發生變化時,navigationOptions也會跟着變化;

提示:除了在建立createStackNavigator時配置navigationOptions外,在StackNavigator以外也能夠配置navigationOptions;

createStackNavigator以外也能夠配置navigationOptions

方式一:

Page2.navigationOptions = {
     title: "This is Page2.",
};

方式二:

export default class Page1 extends React.Component {
    //也可在這裏定義每一個頁面的導航屬性,這裏的定義會覆蓋掉別處的定義
    static navigationOptions = {
        title: 'Page1',
    };
    ...

提示:和本文配套的還有一個React Navigation3x的視頻教程,歡迎學習。

第三步:界面跳轉

export default class HomePage extends React.Component {
    //在這裏定義每一個頁面的導航屬性
    static navigationOptions = {
        title: 'Home',
        headerBackTitle:'返回哈哈',//設置返回此頁面的返回按鈕文案,有長度限制
    }

    render() {
        const {navigation} = this.props;
        return <View style=>
            <Text style={styles.text}>歡迎來到HomePage</Text>
            <Button
                title="Go To Page1"
                onPress={() => {
                    navigation.navigate('Page1', {name: '動態的'});
                }}
            />
            <Button
                title="Go To Page2"
                onPress={() => {
                    navigation.navigate('Page2');
                }}
            />
            <Button
                title="Go To Page3"
                onPress={() => {
                    navigation.navigate('Page3',{ name: 'Devio' });
                }}
            />
        </View>
    }
}

代碼解析:

頁面跳轉可分爲兩步:

    1. 獲取navigation:
    const {navigation} = this.props;
    1. 經過navigate(routeName, params, action)進行頁面跳轉:
    navigation.navigate('Page2');
       navigation.navigate('Page3',{ name: 'Devio' });

    這裏在跳轉到Page3的時候傳遞了參數{ name: 'Devio' }

提示:和本文配套的還有一個React Navigation3x的視頻教程,歡迎學習。

第四步:更新頁面Params與返回

export default class Page3 extends React.Component {
    render() {
        const {navigation} = this.props;
        const {state, setParams} = navigation;
        const {params} = state;
        const showText = params.mode === 'edit' ? '正在編輯' : '編輯完成';
        return <View style=>
            <Text style={styles.text}>歡迎來到Page3</Text>
            <Text style={styles.showText}>{showText}</Text>
            <TextInput
                style={styles.input}
                onChangeText={text=>{
                    setParams({title:text})
                }}
            />
            <Button
                title="Go Back"
                onPress={() => {
                    navigation.goBack();
                }}
            />
        </View>
    }
}

代碼解析:

在上述代碼中經過:

<TextInput
    style={styles.input}
    onChangeText={text=>{
        setParams({title:text})
    }}
/>

將輸入框中內容的變化,經過setParams({title:text})更新到頁面的標題上,你會看到當輸入框中內容發生變化時,標題也會跟着變。

當用戶單擊Go Back按鈕時,經過:

navigation.goBack();

實現了返回上一頁

相關文章
相關標籤/搜索