Relativelayout position view between two views - android

so I'm currently working on an app on Android, and I got stuck on a specific problem regarding the RelativeLayout, which I can't find a way to solve.
I have in the layout three views as follows: TextView, Textview and ImageView (laid horizontally), here is a screenshot of the ios counterpart:
the Textview at the middle should stick to the first one, until he gets to the Imageview, when he does, he keeps his minimum size (wrap content), while the first Textview truncate.
On IOS I setted priorities to the constraint to accomplish this, but I can't figure out how to solve this on Android.
Here what I tried:
<android.support.percent.PercentRelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:background="#drawable/daily_movie_title_box">
<TextView
android:id="#+id/daily_header_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="15dp"
android:text="New Text aawi oa ioawfwi"
android:textSize="16sp"
android:textStyle="bold"
android:textColor="#color/white"
android:lines="1"
android:singleLine="true"
android:layout_alignParentStart="true"
/>
<TextView
android:id="#+id/duration_text"
android:text="138 mins"
android:layout_width="100dp"
android:layout_height="wrap_content"
android:textSize="13sp"
android:textColor="#color/white"
android:lines="1"
android:layout_alignBaseline="#id/daily_header_textview"
android:layout_toStartOf="#+id/certification_icon"
android:layout_toEndOf="#id/daily_header_textview"
/>
<ImageView
android:id="#id/certification_icon"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_alignParentEnd="true"
android:src="#drawable/uk12a"
android:layout_alignBottom="#id/daily_header_textview"
app:layout_aspectRatio="100%"/>
</android.support.percent.PercentRelativeLayout>
Which resulted in this (which is what I want):
But when I increase the first Textview text it's not behaving as I desire...
Is it possible to achieve the behaviour I want in Android (keep the middle Textview wrap content, and truncate the first one if needed)?
I will post an update if I find a solution eventually, just wanted to see if anyone can find an easy way to achieve this behaviour, as I suspect there is.
Thanks.

From my understanding, you want the first TextView to be as large as possible, without adding space after the text if the text is too small. The second TextView should only wrap_content, but it should fill the rest of the parent layout when the row doesn't. The ImageView is set to wrap_content.
I tested it with this layout:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<TableLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:shrinkColumns="0"
android:stretchColumns="1">
<TableRow>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:singleLine="true"
android:text="Shrinking text dddddddddddddddddddddd"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Midle column"/>
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#mipmap/ic_launcher"/>
</TableRow>
</TableLayout>
</LinearLayout>
The only problem is that if the second column has a incredibly large text, it will push the other views out of the parent. But in your case, I don't think that will be a problem. Otherwise, I think it does the job.

These are some suggested solutions:
You can use LinearLayout with horizontal orientation and weight for each component (TextViews and ImageView).
You can set the minimum and maximum text length for the second TextView.
But i prefer to apply the first solution. You can assign a weight for each component ( amount of space on the screen ) using:
android:layout_height

Related

Keep ImageView on the right size of the text and yet prevent long text to push it out of view?

The situation is the same no matter if I use LinearLayout or RelativeLayout. I think this is a old Android XMl bug, but I have no idea why it still exists.
Namely, in a layout where an ImageView is on the right side of a TextView can disappear from the screen when text becomes too long. It simply pushes it off the screen. I must NOT make TextView single line.
Here is the XML.
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<TextView
android:id="#+id/txt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="some long text blahblahblahblahblah"
android:textAppearance="?android:attr/textAppearanceMedium"
android:textSize="17sp"
android:layout_marginRight="10dp"
android:layout_centerVertical="true"
/>
<ImageView
android:layout_toRightOf="#+id/txt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/key"
android:layout_centerVertical="true"
/>
</RelativeLayout>
I cannot use layout_weight attribute as image will then stick to the right side of the screen. It HAS to be on the right side of the text.
Anyone has any ideas how to solve this bug?
Check images when the text is short and long. On the 2nd image the text is long and the image is being pushed away from the screen.
You can achieve your task, if you use the layout_weight properly. Please refer the code below:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:orientation="horizontal"
>
<TextView
android:id="#+id/txt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="The quick brown fox jumps over the lazy dog. As you can see it easily handles the long length of the text"
android:textAppearance="?android:attr/textAppearanceMedium"
android:textSize="17sp"
android:layout_marginRight="10dp"
/>
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/ic_launcher"
/>
</LinearLayout>
The output for long text:
The output for short text:
EDIT:
This works because of the layout whose width is set as wrap_content. If it were match_parent then in all cases, all the extra space would have been given to TextView because of it's layout_weight but since the parent is wrap_content, there is no extra space for the TextView to fill when the text is small. But when the text is large, the weight property is applied to the TextView but since there is no layout_weight for the ImageView hence, it takes only the amount of space it has to.
Set
android:layout_marginRight="30dp"
for the TextView
and
android:layout_marginLeft="-20dp"
for the ImageView
You can change the values depending on your needs.
But, if the image can have different sizes, you will have to set margins programmatically.
there is 2 solutions for these
either set the image as a drawableRight to the textview
<TextView
android:id="#+id/txt"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="The quick brown fox jumps over the lazy dog. As you can see it easily handles the long length of the text"
android:textAppearance="?android:attr/textAppearanceMedium"
android:textSize="17sp"
android:layout_marginRight="10dp"
android:drawableRight="#drawable/ic_launcher"
/>
or
alignt the image to right and make textview toleft of the image

Cannot independently set padding on TextViews

While testing some designs for a LinearLayout for the elements in a ListView, I stumbled upon some weird behaviour. As you can see in the added code, I have three TextViews in a horizontal LinearLayout. I wanted to set the padding for one of these TextViews, but it seems that this value is also applied to the other TextViews as a margin of some sort (see pictures).
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="48dp">
<TextView
android:id="#+id/search_list_row_symbol"
android:layout_width="wrap_content"
android:layout_height="16dp"
android:paddingTop="0dp"
android:layout_marginTop="0dp"
android:textSize="16sp"
android:background="#android:color/holo_blue_light"
android:text="O"/>
<TextView
android:id="#+id/search_list_row_name"
android:layout_width="0dp"
android:layout_height="48dp"
android:layout_weight="1"
android:paddingTop="0dp"
android:layout_marginTop="0dp"
android:textSize="16sp"
android:background="#android:color/holo_red_light"
android:text="oxygen"/>
<TextView
android:id="#+id/search_list_row_number"
android:layout_width="wrap_content"
android:layout_height="20dp"
android:paddingTop="0dp"
android:layout_marginTop="0dp"
android:textSize="16sp"
android:background="#android:color/holo_green_light"
android:text="8"/>
</LinearLayout>
Set android:paddingTop="0dp" on all TextViews
Set android:paddingTop="16dp" only on first TextView
Do any of you know why the padding cannot be set independently on one of these TextViews?
The behavior seems correct as padding is applied to the content of a view - not to the view itself. However, the remaining child views following the padding from first child view seems erroneous.
As an alternate, I would suggest you to replace paddingTop with layout_marginTop and it should work fine.
Because you have given padding to only one text view. If you want all text view than you will have to keep all three within one LinearLayout and set property i.e setPadding() or setPaddingTop().
I think this might help you.

Issue with RadioButton in AlertDialog

I have two RadioButtons within a View that is set within an AlertDialog. Although the text for the first one appears horizontal, the text for the second button comes out vertical. Initially, I thought this was due to the View not filling the width of the dialog itself, but that doesn't appear to be the problem (I've tried making the text smaller and the I get the same result). I'm sure I've come across this in the past, but I can't remember how I resolved it. I'm using RadioButtons elsewhere in my app within AlertDialog's with no issue, so I'm pretty stumped. This is what it looks like. At no point do I hard-code the width of any layout or item in dp; I only ever use match_parent or wrap_content:
So, any help in trying to resolve this would be greatly appreciated!
My layout (LayoutInflator is called on it and then values/listeners are applied):
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/template"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="0dp"
android:orientation="horizontal">
<CheckBox
android:id="#+id/check_box"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="0.45"
android:textSize="16sp"
android:textColor="#color/Black" />
<RadioGroup
android:id="#+id/radio_group"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="0.55"
android:orientation="horizontal"
android:enabled="False">
<RadioButton
android:id="#+id/radio_button_1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="16sp"
android:textDirection="ltr"
android:enabled="False"
android:textColor="#color/Black"/>
<RadioButton
android:id="#+id/radio_button_2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="16sp"
android:enabled="False"
android:textColor="#color/Black"
android:checked="true"/>
</RadioGroup>
</LinearLayout>
Inflating the layout like this works fine and gives the desired output:
LinearLayout inflatedLayout = (LinearLayout) this.getLayoutInflater().inflate(R.layout.template, null);
currDialog = CreateDialog.getDialog(this, "Title", inflatedLayout );
currDialog.show();
However, when I add this to a TableRow object, which is then added to a TableLayout object, it gives the unexpected result. I'm going to try with a RelativeLayout first.
You're using layout weights, and you are forcing your RadioGroup take up only 55% of the space. Since the space is not enough, the text goes to vertical. To be 100% sure that your radiogroup will fit, you will need to set it's width to wrap_content.
<RadioGroup
android:id="#+id/radio_group"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:enabled="False">
You might also want to consider changing the orientation to vertical, in which case it will probably fit with only 55% of the space, but I still highly recommend wrap_content
android:id="#+id/radio_button_2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
There isn't enough available space for the second RadioButton to fit it's text, so it stretches the height to be able to fit the text.

Multiline TextView with width "wrap_content"

I am wondering how to have a TextView display its content on several lines without hardcoding the width in the XML.
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="right"
android:orientation="horizontal">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:singleLine="false"
android:text="Long multiline text"/>
<TextView
android:textColor="#color/text_color"
android:layout_width="130dp"
android:layout_height="wrap_content"
/>
</LinearLayout>
Any thought welcome.
EDIT: my problem is that when the text exceeds the width set (because it reaches the end of the screen) a portion of the text is just not displayed. I would expect the text to be split on two lines
Though I cannot reproduce the not wrapping problem, you can fix the positioning problem by using a weight on the first TextView. Using the following XML gives the expected output in the graphical layout view in Eclipse:
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="right"
android:orientation="horizontal">
<TextView
android:layout_width="0dp"
android:layout_weight="1"
android:layout_height="wrap_content"
android:singleLine="false"
android:text="Long multiline text"/>
<TextView
android:textColor="#color/text_color"
android:layout_width="130dp"
android:layout_height="wrap_content"
/>
</LinearLayout>
Also add
android:minLines="2"
android:scrollHorizontally="false"
You could try
android:inputType="textMultiLine"
in your TextView XML. This worked for me.
I think I had very similar problem. I had a TextView with a text, where I was not sure how much lines will it take. It was encapsulated by a LinearLayout having android:layout_width="match_parent" to ensure my text will fill out all the space horizontally. However, the problem was that my text did not fit into 1 line and when it did break into a new line, the next view component below it did not move downwards to give enough space for the second line to be viewable fully.
I could achieve the solution by changing the LinearLayout that was containing my TextView into a RelativeLayout. By this way, the element below the text (actually below the Layout itself) was moved automatically to give enough space for the multi-line text.

Automatically truncate TextView text so as not to overlap another TextView

I have a ListView that displays a bunch of homework assignments. The ListView items use a FrameLayout to position two TextViews. The first TextView is aligned to the left, and the second is aligned to the right. (Both are aligned in the center vertically.) The first displays a snippet of the assignment description, and the second displays the due date.
What I want to do is make it so that the due date takes up as much space as it needs and the description fills up the remaining space, like so:
|----------------------------------------------------|
| Read pgs 15-35, update tim... Fri, May 4|
|----------------------------------------------------|
Right now the description text will continue on to overlap the date. It will truncate at the end of the line though.
Is there anyway I can do this in XML, or do I have to do it in code by shortening the string before I set the TextView value (presumably in my getView call)? If I did it in code, I'd have to calculate the amount of horizontal space the strings would take up figure out how short the description needs to be. That seems like it could get messy...
Any other suggestions on how to accomplish this are greatly appreciated!
Try using the ellipsize attribute like :
<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:ellipsize="end"
android:singleLine="true"/>
Note that Android, or at least some versions, require both the "ellipsize" and the "singleline" attributes in order for the system to actually do the truncation and add the ellipsis.
Instead of a FrameLayout, this is the perfect place for a LinearLayout or RelativeLayout in combination with ellipsize:
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
<TextView
...
android:width="0dp"
android:height="wrap_content"
android:layout_weight="1"
android:ellipsize="end" />
<TextView
...
android:width="wrap_content"
android:height="wrap_content"
android:layout_weight="0" />
</LinearLayout>
Or alternately
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content" >
<TextView
...
android:id="#+id/secondTV"
android:width="wrap_content"
android:height="wrap_content"
android:layout_weight="0" />
<TextView
...
android:width="0dp"
android:height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_toLeftOf="#id/secondTV"
android:ellipsize="end"/>
</RelativeLayout>
Change the FrameLayout to a LinearLayout or RelativeLayout.
LinearLayout: Make the due date width "wrap_content" and the description width 0dp, then add layout_weight="1" to the description
RelativeLayout: Layout the due date first with width wrap_content, then layout the description with a rule that it should be to the left of the due date.
Both Anton and JRaymond were pretty much on (JRaymond helped me figure it out with his example). This is what I came up with:
<RelativeLayout android:layout_width="fill_parent"
android:layout_height="fill_parent">
<TextView android:id="#+id/due_date"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:layout_alignParentRight="true"
android:singleLine="true" />
<TextView android:id="#+id/description"
android:layout_width="0dp"
android:layout_height="fill_parent"
android:layout_alignParentLeft="true"
android:layout_toLeftOf="#id/due_date"
android:singleLine="true" />
</RelativeLayout>
(I needed to declare my due date label first so that I could reference it in the description. I also just realized that the android:ellipsize seems to be optional -- I guess it defaults to "end".)
Thanks a bunch!

Categories

Resources