为什么推荐使用ConstraintLayout
ConstraintLayout(约束布局)在2016年的Google I/O大会上就推出来了,经历这两年的迭代,功能已经非常的成熟了。一次偶然的机会,在项目中尝试了使用约束布局,从此被它的功能所深深折服。它能很轻易的将你从使用层层的嵌套去实现复杂的布局中解放出来。使用ConstraintLayout后基本可以抛弃LinearLayout和RelativeLayout的使用。完全不需要任何嵌套就可以实现复杂的UI,使用起来特别清爽。所以相信我,使用过就会爱上它。
约束布局的终极奥义!
① 如何才能使用?
因为ConstraintLayout的是在Support包中提供的,所以只需要在我们主Module的build.gradle中添加如下依赖:
代码语言:javascript复制implementation 'com.android.support.constraint:constraint-layout:1.1.3'
然后,我们就可以直接在我们的xml文件中直接应用了:
代码语言:javascript复制<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:tools="http://schemas.android.com/tools"
android:background="@color/white"
xmlns:app="http://schemas.android.com/apk/res-auto">
<!--具体布局-->
</android.support.constraint.ConstraintLayout>
② 可以用来干什么?
- layout_constraintDimensionRatio(控制布局比例): 我们经常会遇到某些布局需要展示特殊的比例(16:9、2:1、4:3等等)。在以前我们可能会自定义一个ViewGroup,动态的去计算比例,比较麻烦。而使用ConstraintLayout后,我们可以直接使用这个属性,以设置某个View的长宽比例为16:9为例:
<ImageView
android:layout_width="match_parent"
android:layout_height="@dimen/dimen_0dp"
app:layout_constraintDimensionRatio="16:9"/>
- layout_constraintRight_toRightOf(与RelativeLayout相似的属性toRightOf等一整套的属性): 如果你想使用RelativeLayout中的toLeftOf或者toRightOf等属性,约束布局同样提供了一套类似的属性。比如:按钮A在屏幕的左上方;按钮B在按钮A的右方;按钮C在按钮B的下方并且水平居中;按钮D在按钮C的下方并且处于屏幕的右侧。
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:tools="http://schemas.android.com/tools"
android:background="@color/white"
xmlns:app="http://schemas.android.com/apk/res-auto">
<Button
android:id="@ id/this_is_a"
android:layout_width="150dp"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="A"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
<Button
android:id="@ id/this_is_b"
android:layout_width="150dp"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="B"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="@ id/this_is_a"/>
<Button
android:id="@ id/this_is_c"
android:layout_width="150dp"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="C"
android:layout_marginTop="@dimen/dimen_10dp"
app:layout_constraintTop_toBottomOf="@ id/this_is_b"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"/>
<Button
android:id="@ id/this_is_d"
android:layout_width="150dp"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="D"
android:layout_marginTop="@dimen/dimen_10dp"
app:layout_constraintTop_toBottomOf="@ id/this_is_c"
app:layout_constraintRight_toRightOf="parent"/>
</android.support.constraint.ConstraintLayout>
- layout_constraintHorizontal_chainStyle 对于按钮A和按钮B在横向上,我们通过更改其chainStyle属性(packed、spread、spread_inside)。
<Button
android:id="@ id/this_is_a"
android:layout_width="150dp"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="A"
app:layout_constraintHorizontal_chainStyle="packed"
app:layout_constraintRight_toLeftOf="@ id/this_is_b"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
<Button
android:id="@ id/this_is_b"
android:layout_width="150dp"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="B"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintLeft_toRightOf="@ id/this_is_a"/>
- Barrier
我们经常会有这样的需求,我们某一个控件必须在某一组控件的某一侧。如下图所示button和textView无论位置或者长度怎么变化,checbox始终在他们的右侧。
xml中我们需要使用android.support.constraint.Barrier:
代码语言:javascript复制<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:tools="http://schemas.android.com/tools"
android:background="@color/white"
xmlns:app="http://schemas.android.com/apk/res-auto">
<Button
android:id="@ id/this_is_a"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="AAAAAAAAAAAAAAAAAA"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
<TextView
android:id="@ id/this_is_b"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="BBBB"
app:layout_constraintTop_toBottomOf="@ id/this_is_a"/>
<android.support.constraint.Barrier
android:id="@ id/this_is_barrier"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:barrierDirection="end"
app:constraint_referenced_ids="this_is_a,this_is_b"
/>
<CheckBox
android:id="@ id/this_is_c"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC"
android:layout_marginTop="@dimen/dimen_10dp"
app:layout_constraintLeft_toRightOf="@ id/this_is_barrier"/>
</android.support.constraint.ConstraintLayout>
- Group 在以前,如果我们需要控制某一组控件的隐藏或者显示,通常会使用一个ViewGroup包裹一下,但是现在有了Group,完全不需要了,还是上面同样的例子,我们加一个Group:
<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:tools="http://schemas.android.com/tools"
android:background="@color/white"
xmlns:app="http://schemas.android.com/apk/res-auto">
<Button
android:id="@ id/this_is_a"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="AAAAAAAAAAAAAAAAAA"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
<TextView
android:id="@ id/this_is_b"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="BBBB"
app:layout_constraintTop_toBottomOf="@ id/this_is_a"/>
<android.support.constraint.Group
android:id="@ id/this_is_group"
android:visibility="invisible"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:constraint_referenced_ids="this_is_a,this_is_b"/>
<android.support.constraint.Barrier
android:id="@ id/this_is_barrier"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:barrierDirection="end"
app:constraint_referenced_ids="this_is_a,this_is_b"
/>
<CheckBox
android:id="@ id/this_is_c"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="@dimen/dimen_20sp"
android:textColor="@color/black"
android:text="CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC"
android:layout_marginTop="@dimen/dimen_10dp"
app:layout_constraintLeft_toRightOf="@ id/this_is_barrier"/>
</android.support.constraint.ConstraintLayout>
通过控制Group的可见性即可控制referenced_ids中申明的控件组的可见性了。注意一点,不要把一个控件申明在不同的Group中,这样有可能会导致设置可见性失效哦。
- Guideline
利用这个控件,可以辅助我们布局UI。在实际运行以后,这条线我们是看不到的:
布局我们可以这么写:
代码语言:javascript复制<android.support.constraint.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.constraint.Guideline
android:id="@ id/guideline"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintGuide_begin="16dp" />
<TextView
android:id="@ id/textView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="16dp"
app:layout_constraintStart_toStartOf="@ id/guideline"
app:layout_constraintTop_toTopOf="parent"
tools:text="TextView" />
</android.support.constraint.ConstraintLayout>
有什么优点
上面介绍了ConstraintLayout的部分功能,强烈推荐你去使用感受一下,在你使用过程中才能真正的体会到爽快。那我们使用约束布局会有什么优点呢? 我们使用ConstraintLayout之后,减少了很多的嵌套的层级。这样View在渲染的时候,减少了很多多余的measure和layout的开销。据统计,使用约束布局替代以前的嵌套结构可以提升40%的速度。如果你嵌套的层次越多,提升的效果越明显。所以,建议我们现在的开发者强制推行使用ConstraintLayout,无论从开发速度还是页面的渲染速度都是提升明显的。