Constraint Layout Vertical Align Center - Two Child Views - android

I have two TextViews, one above the other. I would like the vertical middle of the two TextViews to be at the same position as the vertical middle of the ImageView. (This is so, regardless of the amount of text that may go into either TextView, everything will always look neat, vertically.)
I created what I need perfectly using two LinearLayouts (as the space above the title is the same as the space beneath the description):
But Android Studio was unable to covert it to ConstraintLayout successfully, as it just dumped the TextViews at the bottom of the layout. I've played with a lot of attributes, but could not quite arrive at the desired layout.
My question is similar to this one, except that I am trying to center_vertical align a pair of views rather than a single one - which means I have no view edge to align to the centre of the ImageView/container.
Is it possible to achieve what I'm after with ConstraintLayout? (I expect I may be able to do it with a single RelativeLayout, but I would like to use the layout_constraintDimensionRatio attribute on my ImageView which presumably leave me needing to use ConstraintLayout.)
In case it helps, here's the code for my aforementioned LinearLayout:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
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:orientation="horizontal">
<ImageView
android:id="#+id/imageView"
android:layout_width="#dimen/resources_list_image_size"
android:layout_height="#dimen/resources_list_image_size"
android:layout_marginEnd="#dimen/activity_horizontal_margin"
android:layout_marginRight="#dimen/activity_horizontal_margin"
android:layout_gravity="center_vertical"
android:contentDescription="#string/resource_image"
android:scaleType="centerCrop"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:orientation="vertical">
<TextView
android:id="#+id/textViewTitle"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="#style/MyTextAppearanceMedium"
tools:text="Title" />
<TextView
android:id="#+id/textViewDescription"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textAppearance="#style/MyTextAppearanceSmall"
tools:text="Description" />
</LinearLayout>
</LinearLayout>
Update: Solution
Thanks to Ben P's answer, this is my final code:
<?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="wrap_content">
<!-- Add guideline to align imageView to. -->
<androidx.constraintlayout.widget.Guideline
android:id="#+id/guideline"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintGuide_percent="0.3" />
<ImageView
android:id="#+id/imageView"
android:layout_width="0dp"
android:layout_height="0dp"
android:contentDescription="#string/resource_image"
android:scaleType="centerCrop"
app:layout_constraintDimensionRatio="H,1:1"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="#id/guideline"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintBottom_toBottomOf="parent"/>
<TextView
android:id="#+id/textViewTitle"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="#dimen/activity_horizontal_margin"
android:layout_marginLeft="#dimen/activity_horizontal_margin"
app:layout_constraintBottom_toTopOf="#id/textViewDescription"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#id/imageView"
app:layout_constraintTop_toTopOf="parent"
android:textAppearance="#style/MyTextAppearanceMedium"
app:fontFamily="#font/roboto_slab_regular"
app:layout_constraintVertical_chainStyle="packed"
tools:text="#string/enter_title_colon" />
<TextView
android:id="#+id/textViewDescription"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="#dimen/activity_horizontal_margin"
android:layout_marginLeft="#dimen/activity_horizontal_margin"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#id/imageView"
app:layout_constraintTop_toBottomOf="#id/textViewTitle"
app:fontFamily="#font/roboto_slab_light"
android:textAppearance="#style/MyTextAppearanceSmall"
tools:text="Description" />
</androidx.constraintlayout.widget.ConstraintLayout>

It sounds like you could solve this problem by using a packed chain anchored to the top and bottom of the ImageView. You'll also need to use horizontal bias and a constrained width in order to get wrapping to work correctly.
<?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">
<View
android:id="#+id/anchor"
android:layout_width="80dp"
android:layout_height="80dp"
android:layout_margin="64dp"
android:background="#caf"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintTop_toTopOf="parent"/>
<TextView
android:id="#+id/one"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_constraintVertical_chainStyle="packed"
app:layout_constraintHorizontal_bias="0"
app:layout_constrainedWidth="true"
app:layout_constraintTop_toTopOf="#id/anchor"
app:layout_constraintStart_toEndOf="#id/anchor"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toTopOf="#id/two"/>
<TextView
android:id="#+id/two"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_constraintHorizontal_bias="0"
app:layout_constrainedWidth="true"
app:layout_constraintTop_toBottomOf="#id/one"
app:layout_constraintStart_toEndOf="#id/anchor"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="#id/anchor"/>
</androidx.constraintlayout.widget.ConstraintLayout>
The important attributes here are:
app:layout_constraintVertical_chainStyle="packed" on the first view, which causes the two textviews to stack right on top of each other
app:layout_constraintHorizontal_bias="0" on both views, which means that when the text is not long enough to reach the edge of the screen it will stick to the edge of the anchor view
app:layout_constrainedWidth="true" on both views, which prevents the textview from ever being wider than its constraints, and so the text wraps to a new line

If you want to use ConstraintLayout you could use something like this:
<?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">
<ImageView
android:id="#+id/imageView"
android:layout_width="200dp"
android:layout_height="200dp"
android:contentDescription="description"
android:scaleType="centerCrop"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<LinearLayout
android:id="#+id/linearLayout"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:orientation="vertical"
app:layout_constraintBottom_toBottomOf="#+id/imageView"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#+id/imageView"
app:layout_constraintTop_toTopOf="#+id/imageView">
<TextView
android:id="#+id/textViewTitle"
android:layout_width="match_parent"
android:layout_height="wrap_content"
tools:text="Title" />
<TextView
android:id="#+id/textViewDescription"
android:layout_width="match_parent"
android:layout_height="wrap_content"
tools:text="Description" />
</LinearLayout>
</androidx.constraintlayout.widget.ConstraintLayout>

You can use this layout:
<?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"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="#+id/textView2"
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#color/colorAccent"
android:text="I am 5% of the screen height"
app:layout_constraintBottom_toTopOf="#+id/textView3"
app:layout_constraintEnd_toEndOf="#+id/textView3"
app:layout_constraintHeight_percent="0.05"
app:layout_constraintHorizontal_bias="1.0"
app:layout_constraintStart_toStartOf="#+id/textView3"
app:layout_constraintTop_toTopOf="#+id/imageView2" />
<TextView
android:id="#+id/textView3"
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintHeight_percent="0.15"
android:layout_marginStart="8dp"
android:layout_marginEnd="8dp"
android:background="#color/colorPrimary"
android:text="I am 15% of the screen height (And the image is 20% screen size in height) "
app:layout_constraintBottom_toBottomOf="#+id/imageView2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#+id/imageView2"
app:layout_constraintTop_toBottomOf="#+id/textView2" />
<ImageView
android:id="#+id/imageView2"
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintHeight_percent="0.20"
app:layout_constraintDimensionRatio="1:1"
android:scaleType="fitXY"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:srcCompat="#drawable/rose" />
</android.support.constraint.ConstraintLayout>
It will look like this:
One important thing about this layout:
You can control your aspect ratio (for the image) with app:layout_constraintDimensionRatio="x:y" and by passing "1:1" make it square
And by the way - I am using support library for no reason on this example, you can use androidx

Related

One Textview overlaps another in ConstraintLayout

I have ConstraintLayout with two TextView inside:
<androidx.constraintlayout.widget.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">
<TextView
android:id="#+id/first"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="#+id/second"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="#+id/first"
app:layout_constraintRight_toRightOf="parent"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</androidx.constraintlayout.widget.ConstraintLayout>
I want to place the first one at the top left-corner of parent container and to place the second one at the top-right parent's corner. But both textviews can have text with any length. And when first one has very long text it overlaps the second textview. I can solve this problem by wrapping both textviews in LinearLayout. But this way seems to me inelegant. Maybe there is another way to do it? I mean with ConstraintLayout's feautures
First of all, remove the wrap_content from your widths as this makes the left/right constraints irrelevant. Use 0dp in its place to make it adhere to the constraints' rules.
Then create a horizontal chain between the views and have it as spread, so that the views don’t overlap at any point and they also stay at the edges of the screen at all times.
Finally, align the texts accordingly so that the left one aligns to the start of the view and the right one aligns to the end. In the example below you see that no matter how long the text is, the views don’t overlap and stick to their sides.
NOTE: It is considered better practice to use start/end constraints (as in my code) instead of left/right in order to cater for devices with different text direction. You can also modify the code below by adding the appropriate margins to have the text farther away from the edges of the screen.
<?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/first"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:textAlignment="viewStart"
app:layout_constraintEnd_toStartOf="#+id/second"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="#tools:sample/lorem/random" />
<TextView
android:id="#+id/second"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:textAlignment="viewEnd"
app:layout_constrainedWidth="true"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintStart_toEndOf="#id/first"
app:layout_constraintTop_toTopOf="parent"
tools:text="#tools:sample/lorem/random" />
</androidx.constraintlayout.widget.ConstraintLayout>
use this
<androidx.constraintlayout.widget.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">
<TextView
android:id="#+id/first"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="chauhan"/>
<TextView
android:id="#+id/second"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintRight_toRightOf="parent"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="mehul"/>
</androidx.constraintlayout.widget.ConstraintLayout>
<androidx.constraintlayout.widget.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">
<TextView
android:id="#+id/first"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="#+id/second"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="#+id/first"
app:layout_constraintRight_toRightOf="parent"
android:gravity="right"
android:layout_width="0dp"
android:layout_height="wrap_content" />
</androidx.constraintlayout.widget.ConstraintLayout>
This way second TextView won't overlap first one for sure, but there might happen that first is too long so that there is no place for second one. If that could be the case I would recommend setting maxWidth to first TextView, so that in worst case scenario there is some space left for second TextView.
Also I added graviti to second one to keep text on right side of TextView.
<androidx.constraintlayout.widget.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">
<TextView
android:id="#+id/first"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
android:layout_width="0dp"
app:layout_constraintRight_toLeftOf="#+id/second"
android:layout_height="wrap_content" />
<TextView
android:id="#+id/second"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toRightOf="#+id/first"
app:layout_constraintRight_toRightOf="parent"
android:layout_width="0dp"
android:layout_height="wrap_content" />
</androidx.constraintlayout.widget.ConstraintLayout>
<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<androidx.appcompat.widget.AppCompatTextView
android:id="#+id/tvFirst"
android:layout_width="0dp"
android:layout_height="wrap_content"
app:layout_constraintEnd_toStartOf="#+id/tvSecond"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<androidx.appcompat.widget.AppCompatTextView
android:id="#+id/tvSecond"
android:layout_width="0dp"
android:layout_height="wrap_content"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#+id/tvFirst"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>

Bottom align not working in ConstraintLayout with different ImageView sizes

I want some different sized ImageViews in ConstraintLayout to have the same bottom line.
The smaller picture has the size: 100x140:
The larger picture has the size: 206x316:
With the xml layout:
<?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="wrap_content"
android:background="#8E8392">
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/jbean"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="#+id/p2"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p1"/>
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/jellybig"
app:layout_constraintStart_toEndOf="#id/p1"
app:layout_constraintEnd_toStartOf="#+id/p3"
app:layout_constraintBottom_toBottomOf="#id/p1"
android:id="#+id/p2"
/>
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/jellybig"
app:layout_constraintStart_toEndOf="#id/p2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="#id/p2"
android:id="#+id/p3"
/>
</android.support.constraint.ConstraintLayout>
However it looks weird, as follows:
Update:
According to Tamir Abutbul's answer, I've updated the layout to:
<?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="200dp"
android:background="#8E8392">
<ImageView
android:layout_width="0dp"
app:layout_constraintWidth_percent="0.3"
app:layout_constraintHeight_percent="0.99"
android:layout_height="0dp"
android:src="#drawable/jbean"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="#+id/p2"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p1"/>
<ImageView
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintWidth_percent="0.3"
app:layout_constraintHeight_percent="0.99"
android:src="#drawable/jellybig"
app:layout_constraintStart_toEndOf="#id/p1"
app:layout_constraintEnd_toStartOf="#+id/p3"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p2"
/>
<ImageView
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintWidth_percent="0.3"
app:layout_constraintHeight_percent="0.99"
android:src="#drawable/jellybig"
app:layout_constraintStart_toEndOf="#id/p2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p3"
/>
</android.support.constraint.ConstraintLayout>
Which I think it couldn't work as expected.
hey unable to add this xml as comment, this is the xml for above image
<?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="200dp"
android:background="#ffffff">
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/small"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="#+id/p2"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p1"
app:layout_constraintHorizontal_bias="1"/>
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/big"
app:layout_constraintStart_toEndOf="#id/p1"
app:layout_constraintEnd_toStartOf="#+id/p3"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p2"
app:layout_constraintHorizontal_bias="1"
/>
<ImageView
android:id="#+id/p3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/big"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0"
app:layout_constraintStart_toEndOf="#id/p2" />
</android.support.constraint.ConstraintLayout>
Try below code
<?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="wrap_content"
android:background="#8E8392">
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/jbean"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintEnd_toStartOf="#+id/p2"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p1"/>
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/jellybig"
app:layout_constraintStart_toEndOf="#id/p1"
app:layout_constraintEnd_toStartOf="#+id/p3"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p2"
/>
<ImageView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:src="#drawable/jellybig"
app:layout_constraintStart_toEndOf="#id/p2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
android:id="#+id/p3"
/>
</android.support.constraint.ConstraintLayout>
Let me know if not working
Your code will work for images with the same height and look like this:
But Different phones got different screen size, your images have fixed size and the result is that what may look good on one screen (your android studio preview screen) will not look good on another screen (your actual phone).
In ConstraintLayout you can work with percent on your views like this:
<Button
android:layout_width="0dp"
android:layout_height="0dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHeight_percent="0.6" //line 1
app:layout_constraintWidth_percent="0.5" //line 2
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
/>
So what I did - I told my button to be equal to 60% of its parent in height (see line 1)
and also I told my button to be equal to 50% of its parent Width(see line 2).
You can implement this logic into your imageView to show different image size and keep a responsive layout.
do you want something like this??
I had a similar problem with an imageview that was constrained to the parents bottom but still showed some kind of margin. The solution was to add android:adjustViewBounds="true"

How to put text on right centre of image view on constraint layout

Following is a part of my whole xml of constraint Layout.
<ImageView
android:id="#+id/img_apn_not_set"
style="#style/DeviceManagementImageView"
android:contentDescription="#string/app_name"
android:src="#drawable/ic_sos"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="#+id/view1" />
<TextView
android:id="#+id/tv_apn_not_set"
style="#style/DeviceManagementHeaderText"
android:text="Apn not set"
android:layout_marginTop="5dp"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#+id/img_apn_not_set"
app:layout_constraintTop_toTopOf="#+id/img_apn_not_set" />
What I am trying to do is get the text view on exact centre on the right side of image view. In linear layout we achieve it mostly by gravity. Here I am using marginTop to achieve the same . So can I do the same by using any property . Is there a property something like rightOfCentreOf ?
Thanks
pls add one line in your textview
app:layout_constraintBottom_toBottomOf="#+id/img_apn_not_set"
also remove android:layout_marginTop="5dp"
hope it help you
Try this, If you want to move the text to the right or left use Horizontal bias, If you want to move your text to the top or bottom use vertical bias.
<TextView
android:id="#+id/tv_apn_not_set"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginBottom="8dp"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:layout_marginTop="8dp"
android:text="#string/app_name"
app:layout_constraintBottom_toBottomOf="#+id/img_apn_not_set"
app:layout_constraintEnd_toEndOf="#+id/img_apn_not_set"
app:layout_constraintHorizontal_bias="0.63"
app:layout_constraintStart_toStartOf="#+id/img_apn_not_set"
app:layout_constraintTop_toTopOf="#+id/img_apn_not_set" />
Try this
<?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"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<ImageView
android:id="#+id/AmountLabel"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/ic_launcher_background"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintBaseline_toBaselineOf="#id/Amount"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="#+id/Amount"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginTop="40dp"
android:text="NILESH"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_bias="0.0"
app:layout_constraintStart_toEndOf="#id/AmountLabel"
app:layout_constraintTop_toTopOf="parent" />
</android.support.constraint.ConstraintLayout>
RESULT
<?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">
<ImageView
android:id="#+id/img_apn_not_set"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#mipmap/ic_launcher"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
<TextView
android:id="#+id/tv_apn_not_set"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:text="Apn not set"
app:layout_constraintBottom_toBottomOf="#+id/img_apn_not_set"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#id/img_apn_not_set"
app:layout_constraintTop_toTopOf="parent" />
</android.support.constraint.ConstraintLayout>
You can use app:layout_constraintWidth_default="wrap" and give all 4 side constraint it will be at center
Example:
<?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">
<ImageView
android:id="#+id/img_apn_not_set"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:contentDescription="#string/app_name"
android:src="#drawable/ic_launcher_foreground"
app:layout_constraintLeft_toLeftOf="parent" />
<TextView
android:id="#+id/tv_apn_not_set"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:text="Apn not set"
app:layout_constraintWidth_default="wrap"
app:layout_constraintTop_toTopOf="#+id/img_apn_not_set"
app:layout_constraintBottom_toBottomOf="#+id/img_apn_not_set"
app:layout_constraintLeft_toRightOf="#+id/img_apn_not_set"
app:layout_constraintRight_toRightOf="parent" />
</android.support.constraint.ConstraintLayout>
It will look like this

app:layout_marginBottom is not working well with android constraint layout

Is there any reason why the following layout_marginBottom is not working?
However, if I use layout_marginTop on the second view it does work well
<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="#ade4ad">
<TextView
android:id="#+id/first"
android:layout_width="90dp"
android:layout_height="40dp"
app:layout_marginBottom="10dp"
android:background="#000"/>
<TextView
android:id="#+id/second"
android:layout_width="90dp"
android:layout_height="40dp"
android:background="#fff"
app:layout_constraintTop_toBottomOf="#+id/first"/>
</android.support.constraint.ConstraintLayout>
In order to
android:layout_marginBottom="20dp"
work well, you should use
app:layout_constraintBottom_toBottomOf="parent"
Layout top/bottom margin works only when:
constraints in the same direction need to connect with their next neighbor child, like a unidirectional linked list.
last constraint in the direction must be set.
In your case, you need to set "layout_constraintBottom_toXXXXX" for each view in the chain, and last view set bottom to parent.
<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="#ade4ad">
<TextView
android:id="#+id/first"
android:layout_width="90dp"
android:layout_height="40dp"
app:layout_marginBottom="10dp"
app:layout_constraintBottom_toTopOf="#+id/second"
android:background="#000"/>
<TextView
android:id="#+id/second"
android:layout_width="90dp"
android:layout_height="40dp"
app:layout_marginBottom="10dp"
app:layout_constraintBottom_toTopOf="#+id/third"
android:background="#fff"/>
<TextView
android:id="#+id/third"
android:layout_width="90dp"
android:layout_height="40dp"
android:background="#fff"
app:layout_constraintBottom_toBottomOf="parent"/>
</android.support.constraint.ConstraintLayout>
Moreover, reverse dependency is not required except you want "layout_marginTop" works.
you can use that trick, create a space bellow, align to parent bottom
<Space
android:id="#+id/space"
android:layout_width="wrap_content"
android:layout_height="80dp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent" />
and align your view on top of the space
app:layout_constraintBottom_toTopOf="#+id/space"
like so
<TextView
android:id="#+id/howNext"
style="#style/white_action_btn_no_border"
android:layout_width="344dp"
android:layout_height="60dp"
android:layout_marginBottom="8dp"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:text="#string/got_it_next"
app:layout_constraintBottom_toTopOf="#+id/space"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent" />
This is not LinearLayout or RelativeLayout, its ConstraintLayout so you have to give Left, Right, Bottom, Top Constraint to Relevant Layout, in your case You have to give TextView first Bottom_Top Constraint to TextView second. so you can get Margin between Two TextView.
Your layout should be like below.
<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:background="#ade4ad">
<TextView
android:id="#+id/first"
android:layout_width="90dp"
android:layout_height="40dp"
android:background="#000"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintLeft_toLeftOf="parent" />
<TextView
android:id="#+id/second"
android:layout_width="90dp"
android:layout_height="40dp"
android:background="#fff"
android:layout_marginTop="10dp"
app:layout_constraintTop_toBottomOf="#+id/first"
app:layout_constraintLeft_toLeftOf="#+id/first"
app:layout_constraintRight_toRightOf="#+id/first" />
</android.support.constraint.ConstraintLayout>

Distributing TextViews with layout_constraintVertical_weight

I am having a slight problem with layout_constraintVertical_weight, I am trying to get the two TextViews to share the amount of available vertical space in the assigned area but without me manually assigning this does not happen. I have tried adding in 0dp for the height but that doesn’t work, however it works flawlessly for the width. This is my XML:
<?xml version="1.0" encoding="utf-8"?>
<!-- Layout for a single list item -->
<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="#dimen/list_item_height"
android:background="#color/tan_background">
<ImageView
android:id="#+id/image"
android:layout_width="#dimen/list_item_height"
android:layout_height="#dimen/list_item_height"
android:src="#mipmap/ic_launcher" />
<TextView
android:id="#+id/miwok_text_view"
android:layout_width="0dp"
android:layout_height="44dp"
android:background="#color/category_colors"
app:layout_constraintLeft_toRightOf="#+id/image"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintVertical_weight="1"
tools:text="text1" />
<TextView
android:id="#+id/default_text_view"
android:layout_width="0dp"
android:layout_height="44dp"
android:background="#color/category_numbers"
app:layout_constraintLeft_toRightOf="#+id/image"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintVertical_weight="1"
tools:text="text2" />
</android.support.constraint.ConstraintLayout>
This is an img of how the layout looks: https://i.stack.imgur.com/ZOs9y.png
You have to create a chain with layout_height being 0dp for this to work
in order to create a chain ALL views in the chain must contain a constraint to the previous AND the next item in that chain, and the first one and the last one must be aligned to the parent
in your case in order for this to work you have to do something like this:
<TextView
android:id="#+id/miwok_text_view"
android:layout_width="0dp"
--this should be 0dp otherwise it will not use weight
android:layout_height="0dp"
android:background="#color/category_colors"
app:layout_constraintLeft_toRightOf="#+id/image"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
---this is what you have to add--
app:layout_constraintBottom_toTopOf="#+id/default_text_view"
app:layout_constraintVertical_weight="1"
tools:text="text1" />
<TextView
android:id="#+id/default_text_view"
android:layout_width="0dp"
-- again 0dp otherwise weight is ignored
android:layout_height="0dp"
android:background="#color/category_numbers"
app:layout_constraintLeft_toRightOf="#+id/image"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
-- again add this to create a chain
app:layout_constraintTop_toBottomOf="#+id/miwok_text_view"
app:layout_constraintVertical_weight="1"
tools:text="text2" />
After the above changes weights should work correctly
I managed to get it done using a guideline. Here is the XML:
<?xml version="1.0" encoding="utf-8"?>
<!-- Layout for a single list item -->
<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="#dimen/list_item_height"
android:background="#color/tan_background">
<android.support.constraint.Guideline
android:id="#+id/guideline"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
app:layout_constraintGuide_percent="0.5" />
<ImageView
android:id="#+id/image"
android:layout_width="#dimen/list_item_height"
android:layout_height="#dimen/list_item_height"
android:src="#mipmap/ic_launcher" />
<TextView
android:id="#+id/miwok_text_view"
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#color/category_colors"
app:layout_constraintBottom_toTopOf="#+id/guideline"
app:layout_constraintLeft_toRightOf="#+id/image"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
tools:text="text1" />
<TextView
android:id="#+id/default_text_view"
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#color/category_numbers"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toRightOf="#+id/image"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="#+id/miwok_text_view"
tools:text="text2" />
</android.support.constraint.ConstraintLayout>
Not sure it's the best way, but it works :)

Categories

Resources