1. 程式人生 > >React Native 適配iPhone X

React Native 適配iPhone X

專案中,使用react-navigation和自定義Header,這樣保證iOS和安卓顯示的Header顯示一樣

navigation的頭部高度為,sizeHeader=84,
頭部內容為,sizeHeaderContent=44,
解決螢幕的高度問題,這時候直接在AppDelegate中實現
self.window = [[UIWindow alloc] initWithFrame:CGRectMake(0, 0, [UIScreen mainScreen].bounds.size.width, [UIScreen mainScreen].bounds.size.height-34)];

自定義Header

import React, { Component } from 'react';
import {
    StyleSheet,
    View,
    Dimensions,
    Image,
    StatusBar,
    TouchableOpacity,
    Platform,
} from 'react-native';

import { Widget } from 'rn-yunxi';
const { width, height } = Dimensions.get('window');
const BackIcon = require('./back.png'
); const Text = Widget.Text; //模組聲名並匯出 export default class Header extends Component { //屬性聲名 static propTypes = { navigation: React.PropTypes.any, showBackAction: React.PropTypes.bool, backAction: React.PropTypes.func, title: React.PropTypes.string, defaultStatusBar: React.PropTypes.bool
, rightTitle: React.PropTypes.string, rightAction: React.PropTypes.func, rightIcon: React.PropTypes.element, containerStyles:React.PropTypes.any, headerViewStyles:React.PropTypes.any, backIconSrc:React.PropTypes.number, showDivider: React.PropTypes.bool }; //預設屬性 static defaultProps = { title: '', defaultStatusBar: true, showBackAction: true, showDivider: true }; //建構函式 constructor(props) { super(props); this.state = { //狀態機變數宣告 } } //渲染 render() { return ( <View style={[styles.container,this.props.containerStyles]}> <View style={[styles.headerView,this.props.headerViewStyles]}> {Platform.OS === 'ios' ? <StatusBar barStyle={this.props.defaultStatusBar ? 'default' : 'light-content'} /> : null} <View style={styles.header}> <View style={styles.titleView}> <Text style={styles.title}>{this.props.title}</Text> </View> {this.props.showBackAction ? <TouchableOpacity onPress={() => { if (this.props.backAction) { this.props.backAction(); } else { if (this.props.navigation) { console.log(this.props.navigation); this.props.navigation.goBack(); } } }}> <View style={styles.backView}> <Image style={{width:22,height:22}} source={this.props.backIconSrc?this.props.backIconSrc:BackIcon} /> </View> </TouchableOpacity> : <View />} {this.props.rightTitle ? <TouchableOpacity onPress={() => { if (this.props.rightAction) { this.props.rightAction(); } }}> <View style={styles.rightView}> <Text style={this.props.rightTextStyle}>{this.props.rightTitle}</Text> </View> </TouchableOpacity> : null} {this.props.rightIcon} </View> </View> { this.props.showDivider == true ? <View style={GlobalStyle.styleDividerDefault} /> : null } { this.props.children } </View> ); } }; const sizeHeader = (Platform.OS === 'ios'&& ISIPHONEX)?84:Platform.OS === 'ios'?64: 50; const sizeHeaderMarginTop = Platform.OS === 'ios' ? ISIPHONEX ?35:20: 0 const sizeHeaderContent = Platform.OS === 'ios' ? 44 : 50; //iPhone X const ISIPHONEX = Dimensions.get('window').width==375 && Dimensions.get('window').height == 812 const styles = StyleSheet.create({ container: { flex: 1, backgroundColor: '#F3F3F3', width: width, height: height, }, headerView: { backgroundColor: '#FFFFFF', height: sizeHeader, }, header: { justifyContent: 'space-between', width: width, marginTop:sizeHeaderMarginTop, flexDirection: 'row', height: sizeHeaderContent, alignItems:'center', paddingRight:15 }, titleView: { left: 0, top: 0, height: sizeHeaderContent, position: 'absolute', width: width, justifyContent: 'center', alignItems: 'center' }, title: { fontSize: 18, }, backView: { justifyContent: 'center', paddingLeft: 10, width: 50, flex: 1, }, rightView: { flex: 1, justifyContent: 'center', paddingRight: 10, alignItems: 'flex-end', minWidth: 50 } });

AppDelegate.m

@property (nonatomic, strong) UIWindow *window;
@property (nonatomic,strong) UIViewController * rootViewController;

#define is_iPhoneX [UIScreen mainScreen].bounds.size.width == 375.0f && [UIScreen mainScreen].bounds.size.height == 812.0f   //判斷是否iPhoneX

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{ 

   self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds];
   _rootViewController = [UIViewController new];
   _rootViewController.view = rootView;
   self.window.rootViewController = _rootViewController;
   [self.window makeKeyAndVisible];
}

react-navigation的配置:


const renderTabImage = (image) => {
    return (
        <Image style={[{ width: Constant.scale(21), height: Constant.scale(21) }]} resizeMode="contain" source={image} />
    )

};

const TabStack = TabNavigator(
    {
        Tab1: {
            title: '首頁',
            login: true,
            screen: HomePage,
            navigationOptions: {
                header: null,
                tabBarLabel: '首頁',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_HOME : IMG_HOME_SELECTED)
                ),

            }
        },

        Tab2: {
            title: '產品目錄',
            login: true,
            screen: ProductSummary,
            navigationOptions: {
                header: null,
                tabBarLabel: '產品目錄',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_PM : IMG_PM_SELECTED)
                ),

            }
        },
        Tab3: {
            title: '加入如新',
            login: true,
            screen: MyIdentity,
            navigationOptions: {
                header: null,
                tabBarLabel: '加入如新',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_ADDNUSKIN : IMG_ADDNUSKIN_SELECTED)
                ),

            }
        },

        Tab4: {
            title: '個人中心',
            login: true,
            screen: MinePage,
            navigationOptions: {
                header: null,
                tabBarLabel: '個人中心',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_MINE : IMG_MINE_SELECTED)
                ),

            }
        },

    },
    {
        tabBarVisible: false,
        tabBarPosition: 'bottom',
        backBehavior: 'none',
        swipeEnabled: false,
        animationEnabled: false,
        lazy: true,
        tabBarOptions: {
            showIcon: true,
            scrollEnabled: false,
            activeTintColor: Constant.colorPrimary,
            inactiveTintColor: Constant.colorTxtDefault,
            style: {
                margin: 0,
                backgroundColor: 'white',
                paddingTop: 0,
                height:  ISIPHONEX ?  Constant.scale(74) : Constant.scale(50),
                // paddingTop
            },
            tabStyle: {
                borderTopWidth: Constant.sizeDividerNormal,
                borderTopColor: Constant.colorDivider,
                margin: 0,
                padding: 0,
            },
            indicatorStyle: {
                height: 0
            },
            labelStyle: {
                padding: 0,
                margin: 0,
                marginTop: 0,
                fontSize: 12,
                marginBottom: ISIPHONEX ? 30 : 6,
            },

        }
    }
);

const TabRuXin = TabNavigator(
    {
        Tab1: {
            title: '首頁',
            login: true,
            screen: HomePage,
            navigationOptions: {
                header: null,
                tabBarLabel: '首頁',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_HOME : IMG_HOME_SELECTED)
                ),

            }
        },

        Tab2: {
            title: '產品目錄',
            login: true,
            screen: ProductSummary,
            navigationOptions: {
                header: null,
                tabBarLabel: '產品目錄',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_PM : IMG_PM_SELECTED)
                ),

            }
        },
        Tab3: {
            title: '我的事業',
            login: true,
            screen: MyCareer,
            navigationOptions: {
                header: null,
                tabBarLabel: '我的事業',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_ADDNUSKIN : IMG_ADDNUSKIN_SELECTED)
                ),

            }
        },

        Tab4: {
            title: '個人中心',
            login: true,
            screen: MinePage,
            navigationOptions: {
                header: null,
                tabBarLabel: '個人中心',
                tabBarIcon: ({ focused, tintColor }) => (
                    renderTabImage(!focused ? IMG_MINE : IMG_MINE_SELECTED)
                ),

            }
        },

    },
    {
        tabBarVisible: false,
        tabBarPosition: 'bottom',
        backBehavior: 'none',
        swipeEnabled: false,
        animationEnabled: false,
        lazy: true,
        tabBarOptions: {
            showIcon: true,
            scrollEnabled: false,
            activeTintColor: Constant.colorPrimary,
            inactiveTintColor: Constant.colorTxtDefault,
            style: {
                margin: 0,
                backgroundColor: 'white',
                paddingTop: 0,
                height: Constant.scale(50),
            },
            tabStyle: {
                borderTopWidth: Constant.sizeDividerNormal,
                borderTopColor: Constant.colorDivider,
                margin: 0,
                padding: 0,
            },
            indicatorStyle: {
                height: 0
            },
            labelStyle: {
                padding: 0,
                margin: 0,
                marginTop: 1,
                fontSize: Constant.scale(11),
            },

        }
    }
);

Header的使用

  render() {
        return (
                <Header title={'庫存查詢'} navigation={this.props.navigation}>
                </Header>
        );
    }

這裡寫圖片描述