從 Android Studio 2.3起,官方的模板默認使用 ConstraintLayout。ConstraintLayout 官方文檔,之前項目中用的比較少,有些屬性不是很熟練,做個筆記方便查找
相對定位的常用屬性:
layout_constraintLeft_toLeftOf
layout_constraintLeft_toRightOf
layout_constraintRight_toLeftOf
layout_constraintRight_toRightOf
layout_constraintTop_toTopOf
layout_constraintTop_toBottomOf
layout_constraintBottom_toTopOf
layout_constraintBottom_toBottomOf
layout_constraintBaseline_toBaselineOf
layout_constraintStart_toEndOf
layout_constraintStart_toStartOf
layout_constraintEnd_toStartOf
layout_constraintEnd_toEndOf
注意點:
- 對於一個view,使用佈局必須要設置水平方向及垂直方向的定位屬性,不然會報錯。
- 設置同一方向設置,比如水平方向,僅設置constraintLeft則會爲左對齊,僅設置constraintRight則會右對齊,兩者都設置默認居中對齊。如果不想居中對齊,則需要設置屬性
layout_constraintHorizontal_bias
範圍爲0~1,默認居中爲0.5.
layout_constraintVertical_bias
垂直偏移
兩個TextView
的高度不一致,但是又希望他們文本對齊,這個時候就可以使用layout_constraintBaseline_toBaselineOf
邊距
常用margin ConstraintLayout的邊距常用屬性如下:
android:layout_marginStart
android:layout_marginEnd
android:layout_marginLeft
android:layout_marginTop
android:layout_marginRight
android:layout_marginBottom
我們只有設置了相應的約束margin纔有效,如設置了layout_constraintLeft_toLeftOf
或者
layout_constraintLeft_toRightOf
後layout_marginLeft
纔會生效。
goneMargin
goneMargin
主要用於約束的控件可見性被設置爲gone
的時候,使用的margin值是否有效,屬性如下:
layout_goneMarginStart
layout_goneMarginEnd
layout_goneMarginLeft
layout_goneMarginTop
layout_goneMarginRight
layout_goneMarginBottom
尺寸約束
控件的尺寸可以通過四種不同方式指定:
1. 使用指定的尺寸
2.使用wrap_content
,讓控件自己計算大小
當控件的高度或寬度爲wrap_content時,可以使用下列屬性來控制最大、最小的高度或寬度:
android:minWidth
最小的寬度
android:minHeight
最小的高度
android:maxWidth
最大的寬度
android:maxHeight
最大的高度
注意!當ConstraintLayout爲1.1版本以下時,使用這些屬性需要加上強制約束,如下所示:
app:constrainedWidth=”true”
app:constrainedHeight=”true”
3.使用 0dp (MATCH_CONSTRAINT)
官方不推薦在ConstraintLayout中使用match_parent
,可以設置 0dp (MATCH_CONSTRAINT) 配合約束代替match_parent
4.寬高比
當寬或高至少有一個尺寸被設置爲0dp時,可以通過屬性layout_constraintDimensionRatio
設置寬高比
app:layout_constraintDimensionRatio="H,2:3"指的是 高:寬=2:3
app:layout_constraintDimensionRatio="W,2:3"指的是 寬:高=2:3
鏈
如果兩個或以上控件通過下圖的方式約束在一起,就可以認爲是他們是一條鏈(圖爲橫向的鏈,縱向同理)。
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<TextView
android:id="@+id/text1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="text1"
android:background="@color/colorAccent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="@id/text2"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/text2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="text2"
android:background="@color/colorPrimary"
app:layout_constraintStart_toEndOf="@id/text1"
app:layout_constraintEnd_toStartOf="@id/text3"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/text3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="text3"
android:background="#921"
app:layout_constraintStart_toEndOf="@id/text2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
layout_constraintHorizontal_chainStyle
默認爲spread
,效果如圖
另外兩個取值packed
spread_inside
輔助工具
Guideline
Guildline是一條輔助線,幫助你完成佈局但它不會顯示在界面上。
Guildline的主要屬性:
android:orientation
:垂直vertical
,水平horizontal
layout_constraintGuide_begin
指定位置距離開始
layout_constraintGuide_end
指定位置距離結束
layout_constraintGuide_percent
距離頂部的百分比(orientation = horizontal時則爲距離左邊)
Barrier
假設有3個控件ABC,C在AB的右邊,但是AB的寬是不固定的,這個時候C無論約束在A的右邊或者B的右邊都不對。當出現這種情況可以用Barrier來解決。Barrier可以在多個控件的一側建立一個屏障,如下所示:
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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">
<TextView
android:id="@+id/text1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@color/colorAccent"
android:padding="10dp"
android:text="text1"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="@+id/text2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@color/colorPrimary"
android:padding="10dp"
android:text="this is the text2"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/text1" />
<androidx.constraintlayout.widget.Barrier
android:id="@+id/barrier"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:barrierDirection="right"
app:constraint_referenced_ids="text1,text2" />
<TextView
android:id="@+id/text3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#872"
android:padding="10dp"
android:text="text3"
app:layout_constraintLeft_toRightOf="@+id/barrier" />
</androidx.constraintlayout.widget.ConstraintLayout>
效果如下
app:barrierDirection
爲屏障所在的位置,可設置的值有:bottom
、end
、left
、right
、start
、top
app:constraint_referenced_ids
爲屏障引用的控件,可設置多個,用“,”隔開
Group
Group可以把多個控件歸爲一組,方便隱藏或顯示一組控件,舉個例子:
<android.support.constraint.Group
android:id="@+id/group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:visibility="invisible"
app:constraint_referenced_ids="text1,text3" />
設置group
的visibility
爲invisible
,則text1與text3均不可見。
Placeholder
Placeholder
指的是佔位符,可以定義一個位置,當給Placeholder
使用setContentId()
設置另一個控件的id,使這個控件移動到佔位符的位置了
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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">
<Button
android:id="@+id/left_btn"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:background="#ffff0000"
android:text="left_top"
android:textColor="@android:color/white"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
android:onClick="clickview"
/>
<Button
android:id="@+id/right_btn"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:background="#ffff0000"
android:text="right_top"
android:textColor="@android:color/white"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintTop_toTopOf="parent"
android:onClick="clickview"/>
<Button
android:id="@+id/left_bot_btn"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:background="#ffff0000"
android:text="left_bot"
android:textColor="@android:color/white"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
android:onClick="clickview"/>
<Button
android:id="@+id/right_bot_btn"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:background="#ffff0000"
android:text="right_bot"
android:textColor="@android:color/white"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
android:onClick="clickview"/>
<androidx.constraintlayout.widget.Placeholder
android:id="@+id/place_holder"
android:layout_width="wrap_content"
android:layout_height="50dp"
android:background="#ffff0000"
android:text="right"
android:textColor="@android:color/white"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
/>
</androidx.constraintlayout.widget.ConstraintLayout>
在Activity中設置
placeholder=findViewById(R.id.place_holder);
public void clickview(View view){
placeholder.setContentId(view.getId());
}
實現點擊四個角的那一個按鈕,那麼該按鈕就會顯示在正中間