约束布局高宽比

考虑以下布局文件:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout
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.ConstraintLayout
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#FF0000"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin">


<ImageView
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#0000FF"
android:padding="16dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintDimensionRatio="H,3:1"
tools:layout_editor_absoluteX="16dp" />


</android.support.constraint.ConstraintLayout>


</RelativeLayout>

我不确定这个应用程序是如何工作的:。我的理解是宽高比永远是一样的。所以3:1总是会使 ImageView 显示为高度的3倍宽。前缀 H 或 W 告诉 ConstraintLayout 哪个维度应该尊重比率。如果它是 H,那么它意味着宽度将首先从其他约束计算,然后高度将根据纵横比调整。然而,这是布局的结果:

enter image description here

高度是宽度的3倍,这是意想不到的。有没有人能解释一下,这些维度是如何计算应用程序的:?

94979 次浏览

Take a look at these ImageView properties:

    app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"

These properties override the layout_constraintDimensionRatio due to which the ImageView is constrained to the bottom, top and left of the main parent resulting in the View occupying the left, top and bottom portions of the main screen.

    app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"

This would be one solution. You can omit layout_constraintBottom_toBottomOf if you want the View to appear on the top or vice-versa. It would probably be best to remove all the above constraints altogether except the layout_constraintDimensionRatio, which would be the most recommended solution.

Your understanding for the way app:layout_constraintDimensionRatio works is correct. If you set app:layout_constraintDimensionRatio="H,3:1" then it means width will be first computed from other constraints and then height will be adjusted according to the aspect ratio. The only problem with your implementation is that you added app:layout_constraintBottom_toBottomOf="parent" to the ImageView, so that it caused app:layout_constraintDimensionRatio to be ignored.

Here's the layout to size your ImageView in 3:1 aspect ratio:

<android.support.constraint.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#FF0000">


<ImageView
android:id="@+id/imageView"
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_marginStart="16dp"
android:layout_marginTop="16dp"
android:layout_marginEnd="16dp"
android:background="#0000FF"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintDimensionRatio="H,3:1" />


</android.support.constraint.ConstraintLayout>

and here's the result view:

ImageView in 3:1 aspect ratio

Basically, we have

layout_constraintDimensionRatio(width:height)

EXAMPLE

<!-- button which have width = it's content and height = 1/2 width -->
<Button
android:layout_width="wrap_content"
android:layout_height="0dp"
app:layout_constraintStart_toStartOf="parent" <!-- I still think that we don't need this attribute but I when I don't add this, constraint not working -->
android:text="Button TEST RATIO 1"
app:layout_constraintDimensionRatio="2:1" />

Output
enter image description here

<!-- button which have width = it's content and height = 1/2 width -->
<Button
android:layout_width="wrap_content"
android:layout_height="0dp"
app:layout_constraintStart_toStartOf="parent"
android:text="Button TEST RATIO 2"
app:layout_constraintDimensionRatio="2" /> <!-- 2 here <=> 2:1 <=> 2/1 (1:1 <=> 1, 1/2 <=> 0.5, ....) ->

Output
enter image description here

<!-- button which have width = match_parent and height = 1/2 width -->
<Button
android:layout_width="match_parent"
android:layout_height="0dp"
android:text="Button TEST RATIO 3"
app:layout_constraintDimensionRatio="2" />

Output
enter image description here

<!-- button which have width = match constraint and height = 1/2 width -->
<Button
android:layout_width="0dp"
android:layout_height="0dp"
android:text="Button TEST RATIO 4"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintDimensionRatio="2" />

Output
enter image description here

DEMO: https://github.com/PhanVanLinh/AndroidConstraintLayoutRatio