Horizontal LinearLayout with Multiple Children, Move Children Below on New Line When No More Horizontal Space
Asked Answered
A

2

22

I would like to have a horizontal LinearLayout that is as wide as the screen and as high as its children, but the trick is that its children will have dynamic width each and I don't want them going off screen (cut out). I want them to flow/break in a new line so that they are all visible.

Although totally irrelevant to Android, it should work similar to how inline <div>'s work in HTML.

Here's what I have right now:

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content">
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="If you would enter some digits in this field " />
        <EditText
            android:id="@+id/tvDistance"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:hint="enter some digits here"/>
        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text=" that would be great" />
    </LinearLayout>

But as soon as the children of the LinearLayout get wider than the screen the extra part gets off the screen/invisible.

Aq answered 24/8, 2013 at 0:15 Comment(2)
I don't think that is doable in Android layout. Unless you implement listeners that measure the width and what not and move views down. The other option is to create a WebView and populate it, I know it is doable like that, however I do not have experience in that aspect. Good Luck.Unilobed
Try ChipGroup. It is meant to hold Chip but it is not limited to that. It can be a container for other views as well. ChipGroup has the feature to overflow its views to the next line if they are not fitting in one line.Sacksen
A
26

I would like to have a horizontal LinearLayout that is as wide as the screen and as high as its children, but the trick is that its children will have dynamic width each and I don't want them going off screen (cut out).

A LinearLayout can't do that(any default layout from the SDK can't do that) because the LinearLayout is set to place all the children in one horizontal or vertical line. Also, any type of conditional layout rules based on dimensions not yet available(like in your case the available width for the LinearLayout) are not possible in the xml anyway.

What you need is a custom layout which measures the children to use the available space moving any non fitting children on a new line below(a so called FlowLayout).

Edit:

Google now provides the flexbox library which implements the web's flexbox layout on Android. Using that library, the children of a FlexboxLayout will be placed on multiple lines based on their widths by using the flexDirection(with a value of row) and flexWrap(with a value of wrap) attributes.

Anyaanyah answered 24/8, 2013 at 6:58 Comment(5)
broken video linkMaloriemalory
@ViperAlpha Yes, the parleys site is gone. I've looked for a replacement video but I couldn't find any. The video was from Chet Haase one of the android SDK developers talking about creating custom views and making a FlowLayout in the process. There are libraries that implement that layout if you needed, libraries like github.com/ApmeM/android-flowlayoutAnyaanyah
Found out that Google implemented their own: github.com/google/flexbox-layout , It would be nice for you to add it in your anwerMaloriemalory
@ViperAlpha Yes, that is the library to use. I've edited my answer to point users to Google's library. Thanks for the observation.Anyaanyah
Actually ChipGroup canSacksen
F
10

In addition to Flexbox you could use ChipGroup which is part of the Material Design Library The ChipGroup can be a container for other components as well, it doesn't have to be a Chip, it could be a button etc.

A ChipGroup is used to hold multiple Chips. By default, the chips are reflowed across multiple lines. Set the app:singleLine attribute to constrain the chips to a single horizontal line. If you do so, you'll usually want to wrap this ChipGroup in a HorizontalScrollView.

<com.google.android.material.chip.ChipGroup
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="16dp">

        <com.google.android.material.chip.Chip
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            app:chipText="This" />

        <com.google.android.material.chip.Chip
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            app:chipText="is" />

        <com.google.android.material.chip.Chip
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            app:chipText="a" />

        <com.google.android.material.chip.Chip
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            app:chipText="because" />

        <com.google.android.material.chip.Chip
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            app:chipText="chip" />

        <com.google.android.material.chip.Chip
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            app:chipText="group" />


    </com.google.android.material.chip.ChipGroup>

Updated:

Starting with Constraint Layout 2.0 we can now use Flow

<androidx.constraintlayout.helper.widget.Flow
   android:layout_width="0dp"
   android:layout_height="wrap_content"
   app:layout_constraintStart_toStartOf="parent"
   app:layout_constraintEnd_toEndOf="parent"
   app:layout_constraintTop_toTopOf="parent"
   app:flow_wrapMode="chain"
   app:constraint_referenced_ids="card1, card2, card3"
   />

Notice app:constraint_referenced_ids and app:flow_wrapMode

First one is about passing the views and the second one about handling the way we wrap them.

Make sure to read about it on the official documentation

Fact answered 6/8, 2020 at 14:1 Comment(2)
this is too a good solution. but for recycler view i think the best is to use github.com/google/flexbox-layoutAltissimo
@Altissimo updated my answer as i found out that constraint layout 2.0 takes care of this problemFact

© 2022 - 2024 — McMap. All rights reserved.