Comment aligner et centrer verticalement des objets dans une mise en forme de contrainte? Il est possible d'aligner verticalement ou horizontalement, mais je n'ai pas trouvé le moyen de centrer en même temps à côté de la contrainte des vues entre deux lignes de la grille.
Il semble que le centrage soit un gros problème avec la disposition des contraintes, ce qui me force à revenir à la disposition relative pour "centerInParent", "centerVertical" et "centerHorizontal".
Je voudrais créer la mise en page encadrée en rouge en utilisant la disposition de contrainte:
Malheureusement, la seule solution que j'ai trouvée sans utiliser deux lignes de grille est d'utiliser les options Relative et LinearLayouts (qui sont supposés avoir été conçus par Constraint Layout pour résoudre ce scénario exact!).
Mise en page utilisant la mise en page relative et linéaire:
<RelativeLayout
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:layout_marginTop="12dp"
app:layout_constraintTop_toBottomOf="@id/user_points"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent">
<LinearLayout
Android:id="@+id/stat_1_layout"
Android:layout_width="60dp"
Android:layout_height="wrap_content"
Android:layout_marginLeft="12dp"
Android:layout_marginRight="12dp"
Android:layout_centerVertical="true"
Android:layout_toLeftOf="@+id/divider_1"
Android:orientation="vertical">
<TextView
Android:id="@+id/stat_1"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center_horizontal"
Android:gravity="center_horizontal"
Android:text="10"
Android:textSize="16dp"
Android:textColor="@color/textSecondaryDark"
Android:maxLines="1"/>
<TextView
Android:id="@+id/stat_detail_1"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center_horizontal"
Android:gravity="center"
Android:text="Streak"
Android:textSize="8sp"
Android:textColor="@color/textSecondary"
Android:maxLines="1"/>
</LinearLayout>
<View
Android:id="@+id/divider_1"
Android:layout_width="1dp"
Android:layout_height="38dp"
Android:layout_toLeftOf="@+id/stat_2_layout"
Android:background="@drawable/linedivider"/>
<LinearLayout
Android:id="@+id/stat_2_layout"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_marginLeft="18dp"
Android:layout_marginRight="18dp"
Android:layout_centerInParent="true"
Android:orientation="vertical">
<TextView
Android:id="@+id/stat_2"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center_horizontal"
Android:gravity="center_horizontal"
Android:text="243"
Android:textSize="16dp"
Android:textColor="@color/textSecondaryDark"
Android:maxLines="1"/>
<TextView
Android:id="@+id/stat_detail_2"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center_horizontal"
Android:gravity="center"
Android:text="Calories Burned"
Android:textSize="8sp"
Android:textColor="@color/textSecondary"
Android:maxLines="1"/>
</LinearLayout>
<View
Android:id="@+id/divider_2"
Android:layout_width="1dp"
Android:layout_height="38dp"
Android:layout_toRightOf="@+id/stat_2_layout"
Android:background="@drawable/linedivider"/>
<LinearLayout
Android:id="@+id/stat_3_layout"
Android:layout_width="60dp"
Android:layout_height="wrap_content"
Android:layout_marginLeft="12dp"
Android:layout_marginRight="12dp"
Android:layout_toRightOf="@+id/divider_2"
Android:layout_centerVertical="true"
Android:orientation="vertical">
<TextView
Android:id="@+id/stat_3"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center_horizontal"
Android:gravity="center_horizontal"
Android:text="3200"
Android:textSize="16dp"
Android:textColor="@color/textSecondaryDark"
Android:maxLines="1"/>
<TextView
Android:id="@+id/stat_detail_3"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_gravity="center_horizontal"
Android:gravity="center"
Android:text="Steps"
Android:textSize="8sp"
Android:textColor="@color/textSecondary"
Android:maxLines="1"/>
</LinearLayout>
</RelativeLayout>
Il est possible de définir la vue centrée comme ancre pour d'autres vues. Dans l'exemple ci-dessous, "@ + id/stat_2" est centré horizontalement dans parent et sert d'ancrage aux autres vues de cette présentation.
<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">
<TextView
Android:id="@+id/stat_1"
Android:layout_width="80dp"
Android:layout_height="wrap_content"
Android:layout_marginEnd="8dp"
Android:gravity="center"
Android:maxLines="1"
Android:text="10"
Android:textColor="#777"
Android:textSize="22sp"
app:layout_constraintTop_toTopOf="@+id/stat_2"
app:layout_constraintEnd_toStartOf="@+id/divider_1" />
<TextView
Android:id="@+id/stat_detail_1"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text="Streak"
Android:textColor="#777"
Android:textSize="12sp"
app:layout_constraintTop_toBottomOf="@+id/stat_1"
app:layout_constraintStart_toStartOf="@+id/stat_1"
app:layout_constraintEnd_toEndOf="@+id/stat_1" />
<View
Android:id="@+id/divider_1"
Android:layout_width="1dp"
Android:layout_height="0dp"
Android:layout_marginEnd="16dp"
Android:background="#ccc"
app:layout_constraintTop_toTopOf="@+id/stat_2"
app:layout_constraintEnd_toStartOf="@+id/stat_2"
app:layout_constraintBottom_toBottomOf="@+id/stat_detail_2" />
<TextView
Android:id="@+id/stat_2"
Android:layout_width="80dp"
Android:layout_height="wrap_content"
Android:gravity="center"
Android:maxLines="1"
Android:text="243"
Android:textColor="#777"
Android:textSize="22sp"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="parent" />
<TextView
Android:id="@+id/stat_detail_2"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:maxLines="1"
Android:text="Calories Burned"
Android:textColor="#777"
Android:textSize="12sp"
app:layout_constraintTop_toBottomOf="@+id/stat_2"
app:layout_constraintStart_toStartOf="@+id/stat_2"
app:layout_constraintEnd_toEndOf="@+id/stat_2" />
<View
Android:id="@+id/divider_2"
Android:layout_width="1dp"
Android:layout_height="0dp"
Android:layout_marginStart="16dp"
Android:background="#ccc"
app:layout_constraintBottom_toBottomOf="@+id/stat_detail_2"
app:layout_constraintStart_toEndOf="@+id/stat_2"
app:layout_constraintTop_toTopOf="@+id/stat_2" />
<TextView
Android:id="@+id/stat_3"
Android:layout_width="80dp"
Android:layout_height="wrap_content"
Android:layout_marginStart="8dp"
Android:gravity="center"
Android:maxLines="1"
Android:text="3200"
Android:textColor="#777"
Android:textSize="22sp"
app:layout_constraintTop_toTopOf="@+id/stat_2"
app:layout_constraintStart_toEndOf="@+id/divider_2" />
<TextView
Android:id="@+id/stat_detail_3"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:maxLines="1"
Android:text="Steps"
Android:textColor="#777"
Android:textSize="12sp"
app:layout_constraintTop_toBottomOf="@+id/stat_3"
app:layout_constraintStart_toStartOf="@+id/stat_3"
app:layout_constraintEnd_toEndOf="@+id/stat_3" />
</Android.support.constraint.ConstraintLayout>
Voici comment cela fonctionne sur le plus petit smartphone (3,7 480x800 Nexus One) par rapport au plus grand smartphone (5,5 1440x2560 Pixel XL)
Si vous avez un ConstraintLayout
avec une certaine taille et un enfant View
avec une taille plus petite, vous pouvez effectuer le centrage en contraignant les deux bords de l'enfant aux deux mêmes bords du parent. C'est-à-dire que vous pouvez écrire:
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
ou
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
Comme la vue est plus petite, ces contraintes sont impossibles. Mais ConstraintLayout
fera de son mieux, et chaque contrainte "tirera" uniformément sur la vue enfant, la centrant ainsi.
Ce concept fonctionne avec n'importe quelle vue cible, pas seulement le parent.
Ci-dessous se trouve XML qui réalise votre interface utilisateur souhaitée sans imbrication de vues ni Guideline
s (bien que les recommandations ne soient pas intrinsèquement mauvaises).
<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="wrap_content"
Android:background="#eee">
<TextView
Android:id="@+id/title1"
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:layout_marginBottom="12dp"
Android:gravity="center"
Android:textColor="#777"
Android:textSize="22sp"
Android:text="10"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toLeftOf="@+id/divider1"
app:layout_constraintBottom_toBottomOf="parent"/>
<TextView
Android:id="@+id/label1"
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:gravity="center"
Android:textColor="#777"
Android:textSize="12sp"
Android:text="Streak"
app:layout_constraintTop_toBottomOf="@+id/title1"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toLeftOf="@+id/divider1"/>
<View
Android:id="@+id/divider1"
Android:layout_width="1dp"
Android:layout_height="55dp"
Android:layout_marginTop="12dp"
Android:layout_marginBottom="12dp"
Android:background="#ccc"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="@+id/title1"
app:layout_constraintRight_toLeftOf="@+id/title2"
app:layout_constraintBottom_toBottomOf="parent"/>
<TextView
Android:id="@+id/title2"
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:layout_marginBottom="12dp"
Android:gravity="center"
Android:textColor="#777"
Android:textSize="22sp"
Android:text="243"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="@+id/divider1"
app:layout_constraintRight_toLeftOf="@+id/divider2"
app:layout_constraintBottom_toBottomOf="parent"/>
<TextView
Android:id="@+id/label2"
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:gravity="center"
Android:textColor="#777"
Android:textSize="12sp"
Android:text="Calories Burned"
app:layout_constraintTop_toBottomOf="@+id/title2"
app:layout_constraintLeft_toRightOf="@+id/divider1"
app:layout_constraintRight_toLeftOf="@+id/divider2"/>
<View
Android:id="@+id/divider2"
Android:layout_width="1dp"
Android:layout_height="55dp"
Android:layout_marginTop="12dp"
Android:layout_marginBottom="12dp"
Android:background="#ccc"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="@+id/title2"
app:layout_constraintRight_toLeftOf="@+id/title3"
app:layout_constraintBottom_toBottomOf="parent"/>
<TextView
Android:id="@+id/title3"
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:layout_marginBottom="12dp"
Android:gravity="center"
Android:textColor="#777"
Android:textSize="22sp"
Android:text="3200"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="@+id/divider2"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintBottom_toBottomOf="parent"/>
<TextView
Android:id="@+id/label3"
Android:layout_width="0dp"
Android:layout_height="wrap_content"
Android:gravity="center"
Android:textColor="#777"
Android:textSize="12sp"
Android:text="Steps"
app:layout_constraintTop_toBottomOf="@+id/title3"
app:layout_constraintLeft_toRightOf="@+id/divider2"
app:layout_constraintRight_toRightOf="parent"/>
</Android.support.constraint.ConstraintLayout>
<TextView
Android:id="@+id/tvName"
style="@style/textViewBoldLarge"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:layout_marginTop="10dp"
Android:text="Welcome"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintBottom_toBottomOf="parent"/>
Peut-être que je ne comprenais pas tout à fait le problème, mais centrer toute la vue dans ConstraintLayout semble très simple. C'est ce que j'ai utilisé:
<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="wrap_content"
Android:layout_gravity="center">
Les deux dernières lignes ont fait l'affaire!
Vous pouvez facilement centrer plusieurs choses en créant une chaîne. Cela fonctionne à la fois verticalement et horizontalement
Lien vers la documentation officielle sur les chaînes
Modifier pour répondre au commentaire :
<?xml version="1.0" encoding="utf-8"?>
<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"
>
<TextView
Android:id="@+id/first_score"
Android:layout_width="60dp"
Android:layout_height="wrap_content"
Android:text="10"
app:layout_constraintEnd_toStartOf="@+id/second_score"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="@+id/second_score"
app:layout_constraintBottom_toTopOf="@+id/subtitle"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintVertical_chainStyle="packed"
Android:gravity="center"
/>
<TextView
Android:id="@+id/subtitle"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text="Subtitle"
app:layout_constraintTop_toBottomOf="@+id/first_score"
app:layout_constraintBottom_toBottomOf="@+id/second_score"
app:layout_constraintStart_toStartOf="@id/first_score"
app:layout_constraintEnd_toEndOf="@id/first_score"
/>
<TextView
Android:id="@+id/second_score"
Android:layout_width="60dp"
Android:layout_height="120sp"
Android:text="243"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toStartOf="@+id/thrid_score"
app:layout_constraintStart_toEndOf="@id/first_score"
app:layout_constraintTop_toTopOf="parent"
Android:gravity="center"
/>
<TextView
Android:id="@+id/thrid_score"
Android:layout_width="60dp"
Android:layout_height="wrap_content"
Android:text="3200"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="@id/second_score"
app:layout_constraintTop_toTopOf="@id/second_score"
app:layout_constraintBottom_toBottomOf="@id/second_score"
Android:gravity="center"
/>
</Android.support.constraint.ConstraintLayout>
Vous avez la chaîne horizontale: first_score <=> second_score <=> third_score
. second_score
est centré verticalement. Les autres partitions sont centrées verticalement en fonction de celle-ci.
Vous pouvez certainement créer une chaîne verticale first_score <=> subtitle
et la centrer selon second_score