React Native:Flex 布局详解

上一篇开始学习React Native中我们以一个简单的demo

React Native 支持CSS3的Flex布局,但是阉割了一些功能(orderflex-shrinkflex-basis等)。Flex布局是一种当页面需要适应不同的屏幕大小以及设备类型时确保元素拥有恰当排布行为的布局方式。

Flex布局中的两个概念:Flex容器 (对应View等) 和 Flex项 (对应其他的可视化组件)。

flexbox

一、Style

在学习Flex相关的知识前,我们先来细说一下在react native中使用样式。

1.1 定义样式

使用StyleSheet.create({})方法定义样式。

const styles = StyleSheet.create({
  container: {
    flex: 1,
    justifyContent: 'center',
    alignItems: 'center',

  },
  commonbg: {
    backgroundColor: '#F5FCFF',
  },
});    

1.2 使用样式

组件可以通过指定style属性来应用样式,style属性也可以

<View style={styles.container}/>
<View style={[styles.container,styles.commonbg]} />

也可以直接使用内嵌写法指定组件的样式:

<View style={{backgroundColor: '#F5FCFF'}}/>

定义的样式也可以跟内嵌样式一起使用

<View style={[styles.container,{backgroundColor: '#F5FCFF'}]} />

1.3 盒子模型

react native 中的布局同CSS中的盒子模型。

组件的width=content.width, height=content.height

二、Flex容器

以下的5个属性设置在Flex容器上:

flex
flexWrap
flexDirection
justifyContent
alignItems

2.1 flex

flex属性可以指定容器的放大比例,默认值为0,即如果存在剩余空间,也不放大。我们也可以将flex设置为1,即如果容器中只有一个项目时,该项占满整个空间。

如下图所示,指定项目的flex为0.25,就是占屏幕的四分之一:

2.2 flexWrap

flexWrap属性指定如果在一条轴线上排不下时如何换行,取值如下

nowrap(默认值):不换行
wrap:换行

2.3 flexDirection

flexDirection属性指定容器内的项目按照什么样的方向布局,取值如下,默认值为column

row: 即容器内的项目按水平方向排列布局
column:即容器内的项目按垂直方向布局

2.4 justifyContent

justifyContent属性定义了Flex项如何在主轴(也就是水平方向)上的对齐方式,取值如下:

flex-start(默认值):主轴的起点对齐(或者说靠左对齐)
flex-end:主轴的终点对齐(或者说靠右对齐)
center    :主轴的中点对齐(或者说居中对齐)
space-between:两端对齐,项目之间的间隔都相等
space-around:每个项目两侧的间隔相等

2.5 alignItems

alignItems属性定义了Flex项如何在侧轴(也就是垂直方向)上的对齐方式,取值如下:

flex-start:侧轴的起点对齐(或者说靠上对齐)
flex-end :侧轴的终点对齐(或者说靠下对齐)
center:居中对齐
stretch(默认值):如果项目未设置高度或者设置为auto,则占满整个容器的高度

三、Flex 项

以下的属性设置在Flex项上

flex
alignSelf

flex属性同flex容器中。alignSelf允许Flex项可以与其他的Flex项有不同的对齐方式,可以覆盖容器的alignItems属性。默认值为auto,即表示继承父容器的alignItems属性。

auto(默认值):继承父容器的值
flex-start:侧轴的起点对齐(或者说靠上对齐)
flex-end:侧轴的终点对齐(或者说靠下对齐)
center:居中对齐
stretch:占满整个父容器

四、辅助布局

除了使用Flex容器和Flex项进行布局,通常我们需要用一些其他的属性来进行布局的微调。这些属性如下:

position
left | top | bottom | right 
width | height 
margin | marginBottom | marginLeft | marginRight | marginTop | marginHorizontal | marginVertical 
padding | paddingBottom | paddingLeft | paddingRight | paddingTop | paddingHorizontal | paddingVertical 

除了position需要讲一下,其他的结合着盒子模型很容易理解,就不多解释了。

4.1 position

当将Flex项的position属性设置为absolute时,该Flex项不参与父容器的Flex布局,而是由Flex项自己决定其布局方式。

上面是布局中经常用到的,显然,图片和气泡都是在同一容器中,气泡固定在容器的右上角。

<View style={styles.demo_overlapping_wrapper}>
    <Image style={styles.demo_overlapping_image} 
        source={{uri: 'https://pic3.zhimg.com/80582a810ef003826e17f45d81e0aa8e.jpg'}} />

    <View style={styles.demo_overlapping_num_wrapper}>
        <Text style={styles.demo_overlapping_num}>23</Text>
    </View>
</View>

再看看样式定义

demo_overlapping_wrapper: {
    top: 50,
    flex: 1,
}, 

demo_overlapping_image: {
    height: 200,
},

demo_overlapping_num_wrapper: {
    position: 'absolute',
    top: 12,
    right: 12,
    width: 30,
    height: 30,
    borderRadius: 15,
    backgroundColor: 'red',
    justifyContent: 'center',
    alignItems: 'center'
},

demo_overlapping_num: {
    color: '#fff',
    fontWeight: 'bold'
},

所有的代码都可以在这里找到。