I am using an AndroidX GridLayout to display a 2x2 grid of content using the following XML layout:
<androidx.gridlayout.widget.GridLayout
android:id="@+id/gridlayout_first"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@drawable/outline"
app:columnCount="2"
app:rowCount="2"
app:orientation="horizontal" >
<com.google.android.material.button.MaterialButton
android:text="@string/button_text"
app:layout_columnWeight="1"
app:layout_gravity="center"
app:iconSize="40dp"
app:icon="@drawable/ic_launcher_foreground" />
<com.google.android.material.button.MaterialButton
android:text="@string/button_text"
app:layout_columnWeight="1"
app:layout_gravity="center"
app:iconSize="40dp"
app:icon="@drawable/ic_launcher_foreground" />
<com.google.android.material.button.MaterialButton
android:text="@string/button_text"
app:layout_columnWeight="1"
app:layout_gravity="center"
app:iconSize="40dp"
app:icon="@drawable/ic_launcher_foreground" />
<com.google.android.material.button.MaterialButton
android:text="@string/button_text"
app:layout_columnWeight="1"
app:layout_gravity="center"
app:iconSize="40dp"
app:icon="@drawable/ic_launcher_foreground" />
</androidx.gridlayout.widget.GridLayout>
This is what it looks like when @string/button_text
is "button"
:
But when I increase the length of this string just a little, to "my button"
, the grid layout suddenly jumps to this:
I can understand how the content within a grid cell might be truncated or wrapped if too big, but I can't understand why the layout suddenly switches so that the second column is lost entirely.
I can solve this by putting an android:maxWidth
on each MaterialButton
, for example 170dp
, but this isn't ideal because it isn't very responsive and won't make use of more available width on larger screen sizes. And part of the problem is that the length of this string will change depending on which language is being used, so for some longer translations we really may need the extra width (if available).
So I'd rather not put a fixed arbitrary maximum on the button width, and instead just wrap the text within the button (ugly but less ugly than the above). Or better still, it would be great if the GridLayout
could automatically switch from 2x2 to 4x1 if any of the cell content is too big to fit.
So what is the correct way of preventing the grid layout jumping horribly like this, and instead just wrapping the text within the grid cell (button)... or switching grid layout to 4x1?
I've put the sample app used for the above code and screenshot here.
Your button is not moving to the next row, it just trying to take as width as possible because of using
app:layout_columnWeight="1"
so you have two possible solutions first is to remove weight and gravity
app:layout_columnWeight="1"
app:layout_gravity="center"
or make each column take half of gridlayout by adding width 0dp
android:layout_width="0dp"
Also if you want TextView to wrap its content and not fill parent as long as it doesn't need to, you will wrap it in another ViewGroup, FrameLayout is suitable for this, this thing is related to TextView not GridLayout
<FrameLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
app:layout_columnWeight="1"
app:layout_gravity="center_vertical">
<com.google.android.material.button.MaterialButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/button_textA"
app:icon="@drawable/ic_launcher_foreground"
android:layout_gravity="center"
app:iconSize="40dp" />
</FrameLayout>