Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Textview with long text pushes out other views in GridLayout despite ellipsize=end

My problem is very similar to How to get a layout where one text can grow and ellipsize, but not gobble up the other elements on the layout, but read on below why I can't use TableLayouts as proposed there.

I'm trying to create a listview row that basically looks like this:

| TextView | View 1 | View 2 |

All views contain variable width elements. The TextView has ellipsize="end" set. View 1 should align left of the TextView, while View 2 should align to the right of the screen. So, normally, there would be whitespace between View 1 and View 2. As the text in the TextView grows longer, the TextView should grow, pushing View 1 to the right until there is no more whitespace left. Then, ellipsize should kick in, cutting of the text in TextView and appending an ellipsis ("...") at the end.

So, the result should look something like this:

+----------------------------------------+
| short text [view1]             [view2] |
+----------------------------------------+
| long text with ell ... [view1] [view2] |
+----------------------------------------+

I've tried:

  • TableLayouts, but they seem to make scrolling extremely slow on some devices.
  • RelativeLayouts, but I either had overlapping views, or view1 or view2 disappeared completely.
  • GridLayouts, but the TextView always grows until it takes up the whole width of the screen, thus pushing view1 and view2 out of the screen.

This is the GridLayout I tried:

<GridLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content" >

    <TextView
        android:layout_gravity="left|fill_horizontal"
        android:ellipsize="end"
        android:singleLine="true"
        android:text="Long text to demonstrate problem with TextView in GridLayout taking up too much space despite ellipsis" />

    <TextView
        android:layout_gravity="left"
        android:text="(view1)" />

    <TextView
        android:layout_gravity="right"
        android:text="(view2)" />
</GridLayout>

View 1 and View 2 are not really TextViews, I just used them in the example to simplify things.

Is there any way to achieve this without using TableLayouts?

EDIT: As requested, here is my attempt at solving this with a RelativeLayout. The TextView takes up the full width of the screen in this case, so neither view1 nor view2 are visible.

<RelativeLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content" >

    <TextView
        android:id="@+id/rl0"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentLeft="true"
        android:ellipsize="end"
        android:singleLine="true"
        android:text="Long text to demonstrate problem with TextView in GridLayout taking up too much space despite ellipsis" />

    <TextView
        android:id="@+id/rl1"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@id/rl0"
        android:layout_marginLeft="10dp"
        android:text="(view1)" />

    <TextView
        android:id="@+id/rl2"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@id/rl1"
        android:layout_alignParentRight="true"
        android:layout_marginLeft="10dp"
        android:text="(view2)" />
</RelativeLayout>
like image 688
Stefan Frye Avatar asked Jul 15 '13 13:07

Stefan Frye


People also ask

How do I limit text in TextView?

you can extend the TextView class and overwrite the setText() function. In this function you check for text length or word cound. Better than counting the text length or the word cound a better way would be to use the "maxLines" attribute along with "ellipsize" attribute to attain the desired effect.

How do you get 3 dots at the end of a TextView text?

You are applying to your TextView a compound Drawable on the right.. to make the three dots appear in this scenario, you have to apply a android:drawablePadding="{something}dp" attribute to the TextView as well. Hope it helps!

What is Ellipsize in TextView?

Android Ellipsize Android TextView ellipsize property Causes words in the text that are longer than the view's width to be ellipsized ( means to shorten text using an ellipsis, i.e. three dots …) instead of broken in the middle to fit it inside the given view.


4 Answers

I seem to have found a potential solution to prevent a TextView in GridLayout from growing unboundedly and pushing out other views. Not sure if this has been documented before.

You need to use fill layout_gravity and set an arbitrary layout_width or width on the long TextView in need of ellipsizing.

android:layout_gravity="fill"
android:layout_width="1dp"

Works for both GridLayout and android.support.v7.widget.GridLayout

like image 148
Yuntao Avatar answered Oct 17 '22 14:10

Yuntao


I'm a big fan of LinearLayouts, so here's my suggestion using those:

<LinearLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="horizontal" >

    <LinearLayout
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:layout_weight="1" >

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:ellipsize="end"
            android:singleLine="true"
            android:text="Long text to demonstrate problem with TextView in GridLayout taking up too much space despite ellipsis" />

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="(view1)" />
    </LinearLayout>

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="right"
        android:text="(view2)" />
</LinearLayout>
like image 37
invertigo Avatar answered Oct 17 '22 13:10

invertigo


I will suggest you to play with layout_weight property of your widget

Example:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity" >

    <LinearLayout
    android:layout_width="fill_parent"
    android:layout_height="wrap_content" 
    android:orientation="horizontal"
    android:weightSum="10">

    <LinearLayout
       android:id="@+id/ll_twoViewContainer"
       android:layout_weight="8"
       android:layout_width="0dp"
       android:layout_height="wrap_content" 
       android:orientation="horizontal">

      <TextView
          android:id="@+id/rl0"
          android:layout_width="wrap_content"
          android:layout_height="wrap_content"
          android:layout_alignParentLeft="true"
          android:layout_weight="1"
          android:ellipsize="end"
          android:singleLine="true"
          android:text="Long text" />

      <TextView
          android:id="@+id/rl1"
          android:layout_width="wrap_content"
          android:layout_height="wrap_content"
          android:layout_marginLeft="10dp"
          android:layout_toRightOf="@id/rl0"
          android:layout_weight="1"
          android:minWidth="120dp"
          android:text="(view1)" />

    </LinearLayout>
    <TextView
        android:id="@+id/rl2"
        android:layout_weight="2"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@id/rl1"
        android:layout_alignParentRight="true"
        android:layout_marginLeft="10dp"
        android:text="(view2)" />
  </LinearLayout>

</LinearLayout>

finally your layout will look like as follow:

+----------------------------------------+
| short text [view1]             [view2] |
+----------------------------------------+
| long text with ell ... [view1] [view2] |
+----------------------------------------+
like image 4
dinesh sharma Avatar answered Oct 17 '22 14:10

dinesh sharma


I think you should create custom layout for your purpose. I don't know how to do this using only default layouts/view and make it work for all cases.

like image 3
Leonidos Avatar answered Oct 17 '22 14:10

Leonidos