On a button, text and drawable are too far away when centered - android

when I make a button width match parent, the drawable start and text are too far away, and they don't seem to respect android:drawablePadding setting. I tried as well with android:gravity="center" and android:textAlignment="center" to no avail. Setting some paddingStart/End affect indirectly how close they are to each other.
See the result below:
The code for button:
<Button
style="#style/ActionButton.Primary.Light.Large"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_margin="0dp"
android:drawableLeft="#drawable/ic_filter_and_sort_white"
android:drawablePadding="0dp"
android:textAlignment="center"
android:text="Apply filters"
app:layout_constraintBottom_toTopOf="#id/someViewBelow"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="#id/someViewAbove" />
the style defines background, textColor, margins, minDimensions, paddings, radiuses, textSize, textAllCaps, radiuses, stateListAnimator, fontPath - so nothing that should affect what I'm looking for.

Use the MaterialButton with app:iconGravity="start" and defining the padding between the icon and the text with the app:iconPadding attribute.
Something like:
<com.google.android.material.button.MaterialButton
style="#style/Widget.MaterialComponents.Button.Icon"
app:icon="#drawable/...."
app:iconGravity="start"
app:iconPadding="..."
This value can be negative.
Otherwise you can use app:iconGravity="textStart".
Here the difference of using start and textStart as iconGravity.

You can use the MaterialButton now which lets setting the icon gravity ex:app:iconGravity="textStart".
<com.google.android.material.button.MaterialButton
android:layout_width="0dp"
android:layout_height="56dp"
android:layout_margin="16dp"
android:gravity="center"
android:textAllCaps="true"
app:backgroundTint="#fc0"
app:icon="#drawable/ic_filter_and_sort_white"
app:iconGravity="textStart"
app:iconPadding="10dp"
app:iconTint="#f00"
app:layout_constraintBottom_toTopOf="#id/someViewBelow"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="#id/someViewAbove"
tools:text="Download Pdf" />
Add dependency implementation 'com.google.android.material:material:1.1.0-alpha10'
Reference

Did you try to use android:textAlignment="textStart"?

Try with this, it should work.
<Button
style="#style/ActionButton.Primary.Light.Large"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_margin="0dp"
android:drawableLeft="#drawable/ic_filter_and_sort_white"
android:drawablePadding="5dp"
android:textAlignment="textStart"
android:layout_gravity="start"
android:text="Apply filters"
app:layout_constraintBottom_toTopOf="#id/someViewBelow"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="#id/someViewAbove" />

Related

how to align text and icon left on MaterialButton (with icon directly after text)?

I want to create Button with text and Icon, both left-aligned.
I am using app:iconGravity="textEnd" to place the icon directly after the button-text, but the icon stays in old centered position if I change text positioning to left by using android:gravity="left"
my layout-xml:
<com.google.android.material.button.MaterialButton
android:id="#+id/listentry_button"
style="#style/Widget.MaterialComponents.Button.TextButton.Icon"
app:icon="#drawable/ic_arrow_straight_right"
app:iconGravity="textEnd"
android:gravity="left"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginEnd="8dp"
android:text="#string/account_data_personal_data"
android:textColor="#color/primaryTextColor"
app:iconTint="#color/secondaryColor"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
any idea how to achieve this with material-button or is is it impossible?
<com.google.android.material.button.MaterialButton
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="My button"
app:icon="#drawable/ic_arrow"
app:iconGravity="textEnd"
/>
above code can give you the following result
OR
<com.google.android.material.button.MaterialButton
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="My button"
android:gravity="left|center_vertical"
app:icon="#drawable/ic_arrow"
app:iconGravity="textStart"
/>
above code can give you the following result
Did you try changing the layout width to wrap content?
android:layout_width="wrap_content"

TextView going out of screen with constraintLayout

I am using ConstraintLayout to create below xml in my application.
As you can see my first item is fine, But in the second one, some parts of my textView are not on the screen!
This is my XML code:
<android.support.constraint.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="#+id/ly_user"
android:padding="8dp"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<ImageView
app:layout_constraintRight_toRightOf="parent"
android:id="#+id/im_user_icon"
android:layout_width="#dimen/default_message_icon_size"
android:layout_height="#dimen/default_message_icon_size"
android:src="#drawable/user_pacific"/>
<ImageView
app:layout_constraintTop_toBottomOf="#+id/im_user_icon"
app:layout_constraintRight_toLeftOf="#+id/im_user_icon"
android:id="#+id/im_user_arrow"
android:layout_width="30dp"
android:layout_height="30dp"
android:src="#drawable/arrow_bg1"/>
<View
android:id="#+id/view_user_guidLine"
android:layout_width="1dp"
android:layout_height="0dp"
app:layout_constraintLeft_toLeftOf="#id/im_user_arrow"
app:layout_constraintRight_toRightOf="#id/im_user_arrow"/>
<TextView
app:layout_constraintTop_toBottomOf="#+id/im_user_icon"
app:layout_constraintRight_toLeftOf="#+id/view_user_guidLine"
android:id="#+id/tv_user_message"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:gravity="right"
android:padding="8dp"
android:minWidth="#dimen/default_message_textarea_width"
android:minHeight="#dimen/default_message_textarea_height"
android:background="#drawable/bg_right_text"
android:textColor="#android:color/white"/>
</android.support.constraint.ConstraintLayout>
I Know I can fix this problem to adding below line to the textView, But I need my textView be wrapContent.
app:layout_constraintLeft_toLeftOf="parent"
You can set your TextView's width to wrap_content, but to prevent it from expanding outside of screen you need to add the left constraint as well and use app:layout_constrainedWidth="true" to enforce constraints.
Now, to make the TextView stick to the right, you need to add app:layout_constraintHorizontal_bias="1", which will align it to its right constraint.
So all in all, these are the changes needed for the TextView:
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constrainedWidth="true"
app:layout_constraintHorizontal_bias="1"
android:layout_width="wrap_content"
Add these following line in your code in your TextView
app:layout_constraintWidth_percent="0.6"
first line layout_constraintWidth_percent is 60 percent of your phone screen width you can change it according to your need.
Accepted answered works but on my side I use android:layout_width="0dp" because my TextView is in the middle of two elements.
<TextView
android:id="#+id/my_id_text_view"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:text="#string/long_text"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toStartOf="#+id/second_vertical_divider_view"
app:layout_constraintStart_toEndOf="#+id/first_vertical_divider_view"
app:layout_constraintTop_toTopOf="parent" />
Accepted answer didn't helped in my case. Alternative solution can look like that:
<ConstraintLayout>
<TextView
android:id="#+id/title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:ellipsize="end"
android:maxLines="2"
app:layout_constraintEnd_toStartOf="#+id/option_info"
app:layout_constraintHorizontal_chainStyle="packed"
app:layout_constraintHorizontal_weight="1"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintWidth_max="wrap" />
<ImageView
android:id="#+id/option_info"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:src="#drawable/ic_info"
app:layout_constraintBottom_toBottomOf="#+id/title"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toEndOf="#+id/title"
app:layout_constraintTop_toTopOf="#+id/title" />
</ConstraintLayout>
The idea is to prevent one view pushing another while expanding by creating a chain and add some constraint params to hold influenced view in view's border.
Hope it still will help somebody!

TextView not starting at left

Here's a picture to help me explain my problem:
The black box is the whole screen. The red box is the TextView. The green is the text. When I run my code, it looks like the left screen, but I want to it look as it does on the right. (start from left)
Here is the TextView code:
<TextView
android:id="#+id/info_ruta"
android:layout_width="256dp"
android:layout_height="80dp"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:layout_marginTop="8dp"
android:text="#string/info_sumary"
android:textColor="#FFF"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="#+id/day_seven_id" />
When trying to add android:gravity="left" or ="start" it does not help with my problem. What am I missing here?
use android:layout_width="match_parent" instead of fixed width android:layout_height="80dp" so it would be
<TextView
android:id="#+id/info_ruta"
android:layout_width="match_parent"
android:layout_height="80dp"
android:layout_marginEnd="8dp"
android:layout_marginStart="8dp"
android:layout_marginTop="8dp"
android:text="#string/info_sumary"
android:textColor="#FFF"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toBottomOf="#+id/day_seven_id" />
match_parent with android:width mean cover the complete width which is occupied by the parent container.
Use android:layout_width="match_parent" and android:gravity="left" on attributes of XML.
The match_parent is fundamental for this.

Set drawable position inside button

I've got a button and a drawable on the left of the text, but I want the drawable to be closer to the text. So I need to move the drawable.
I've defined android:drawableLeft but the content of the button is not centered.
Here is my code:
<Button
android:id="#+id/addsubject"
android:layout_width="250dp"
android:layout_height="wrap_content"
android:drawableLeft="#drawable/ic_action_add"
android:layout_centerHorizontal="true"
android:layout_alignParentTop="true"
android:layout_marginTop="20dp"
android:text="#string/addsubject"
android:textColor="#color/white"
android:background="#drawable/custombutton1" />
Here is how it looks now:
And here is how I'd like it to be:
Thank you!
Use the app:iconGravity="textStart" attribute in the MaterialButton
<com.google.android.material.button.MaterialButton
app:icon="#drawable/ic_add_24px"
app:iconGravity="textStart"
../>
If you want to reduce the padding between the icon and the text just use the app:iconPadding attribute:
<com.google.android.material.button.MaterialButton
app:icon="#drawable/ic_add_24px"
app:iconGravity="textStart"
app:iconPadding="0dp"/>
try this
<Button
android:id="#+id/addsubject"
android:layout_width="160dip"
android:layout_height="60dip"
android:layout_gravity="center"
android:drawableLeft="#drawable/ic_action_add"
android:drawablePadding="2dip"
android:gravity="center"
android:paddingLeft="30dip"
android:paddingRight="26dip"
android:singleLine="true"
android:text="#string/addsubject"
android:textSize="13dip" />
I got this result by simply putting these properties to the button specifically
<Button
...
android:paddingLeft="60dp"
android:drawablePadding="-50dp"
android:gravity="center"
android:drawableLeft="#drawable/your_button_icon"
/>
You can tune in with your own values for your desired results.
Cheers :-)
I done this simply using paddingLeft and paddingRight. Its works!
...
android:paddingLeft="25dp"
android:paddingRight="25dp"/>
You can use LinearLayout as your button by adding OnClickListener and customize however you want.
<LinearLayout
android:layout_width="160dip"
android:layout_height="60dip"
android:orientation="horizontal"
android:background="#drawable/custombutton1">
<ImageView android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:src="#drawable/ic_action_add"
android:layout_gravity="center"
android:layout_weight="1"
android:scaleType="center">
</ImageView>
<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="#string/addsubject"
android:layout_gravity="center"
android:layout_weight="1"/>
</LinearLayout>
The padding between the left border of button and right border of the icon is controlled by android:paddingLeft property. The padding between the icon and the text is defined by android:drawablePadding property.
Add these two properties to you button and set the values you are happy with.
<Button
...
android:paddingLeft="24dp"
android:drawablePadding="8dp"
/>
There's also other possibilities that you want to inflate the drawable/icon programatically, after reading a while and using a lot of combination using XMLs, but still doesn't works,
You might want to fork below library instead, to suits your use-cases, such as, customizing the view, position, etc programatically, see below reference:
Drawable/icon aligned with text, see sample here
Button like facebook sign-in, see sample here
For RadioButton, see full gist code here
P.S: Copyrighted and regards to the author
for Materialbutton, you have to use the icon attribute and you can also change its tint with iconTint like this example:
<com.google.android.material.button.MaterialButton
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:icon="#drawable/ic_cancel"
app:iconTint="#color/black"
android:text="text" />

Android button with icon and text

I have some buttons like this in my app:
<Button
android:id="#+id/bSearch"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:padding="16dp"
android:text="Search"
android:textSize="24sp" />
I'm trying to create a same button with text and a icon.
android:drawableLeft doesn't work for me (Maybe it would, but i don't know how to set a max height to the icon).
So i created a LinearLayout with a ImageView and a TextView and made it act like a button:
<LinearLayout
android:id="#+id/bSearch2"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:background="#android:drawable/btn_default"
android:clickable="true"
android:padding="16dp"
android:orientation="horizontal" >
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:layout_marginLeft="5dp"
android:adjustViewBounds="true"
android:maxHeight="30dp"
android:maxWidth="30dp"
android:scaleType="fitCenter"
android:src="#drawable/search_icon" />
<TextView
android:id="#+id/tvSearchCaption"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:textSize="24sp"
android:paddingRight="30dp"
android:gravity="center"
android:text="Search" />
</LinearLayout>
My new button is exactly what i want (font size, icon and text placement).
But it doesn't look like my default buttons:
So i tried, to change the background and the text color of my new Button:
Button Search = (Button) findViewById(R.id.bSearch);
LinearLayout bSearch2 = (LinearLayout) findViewById(R.id.bSearch2);
bSearch2.setBackground(bSearch.getBackground());
TextView tvSearchCaption = (TextView)findViewById(R.id.tvSearchCaption);
tvSearchCaption.setTextColor(bSearch.getTextColors().getDefaultColor());
This gives a strange result, my old button, gets messed up:
When i change the order of these two buttons in the XML, so the "new button" goes first, it makes another strange result:
Now i noticed, that when i try to press the old button, the new one gets pressed.
Any ideas?
Try this one.
<Button
android:id="#+id/bSearch"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:padding="16dp"
android:text="Search"
android:drawableLeft="#android:drawable/ic_menu_search"
android:textSize="24sp"/>
To add an image to left, right, top or bottom, you can use attributes like this:
android:drawableLeft
android:drawableRight
android:drawableTop
android:drawableBottom
The sample code is given above. You can also achieve this using relative layout.
You can use the Material Components Library and the MaterialButton component.
Use the app:icon and app:iconGravity="start" attributes.
Something like:
<com.google.android.material.button.MaterialButton
style="#style/Widget.MaterialComponents.Button.Icon"
app:icon="#drawable/..."
app:iconGravity="start"
../>
For anyone looking to do this dynamically then setCompoundDrawablesWithIntrinsicBounds(Drawable left, Drawable top, Drawable right, Drawable bottom) on the buttons object will assist.
Sample
Button search = (Button) findViewById(R.id.yoursearchbutton);
search.setCompoundDrawablesWithIntrinsicBounds('your_drawable',null,null,null);
This is what you really want.
<Button
android:id="#+id/settings"
android:layout_width="190dp"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:background="#color/colorAccent"
android:drawableStart="#drawable/ic_settings_black_24dp"
android:paddingStart="40dp"
android:paddingEnd="40dp"
android:text="settings"
android:textColor="#FFF" />
#Liem Vo's answer is correct if you are using android.widget.Button without any overriding. If you are overriding your theme using MaterialComponents, this will not solve the issue.
So if you are
Using com.google.android.material.button.MaterialButton
or
Overriding AppTheme using MaterialComponents
Use app:icon parameter.
<Button
android:id="#+id/bSearch"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:padding="16dp"
android:text="Search"
android:textSize="24sp"
app:icon="#android:drawable/ic_menu_search" />
What about like this?
<Button
android:id="#+id/yourID"
android:drawableStart="#drawable/ic_flag"
android:textColor="#FFFFFF"
android:textSize="12sp"
android:textStyle="bold"
android:textAlignment="textStart"
android:background="#drawable/btn_background"
android:fontFamily="#font/YourFont"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="Your Text" />
try It:-
position-> left,right,top,bottom
android:drawableposition="#android:drawable/-yourImage-"
android:drawabletop="-Yourfilesrc-"
android:drawablebottom="-Yourfilesrc-"
android:drawableleft="-Yourfilesrc-"
android:drawableright="-Yourfilesrc-"
I was experiencing the same problem with pure Button view. In my case XML solution was not usefull, because I have some logic to show/hide this icon.
There is one more solution using pure Kotlin:
(bSearch as? MaterialButton)?.let {
icon = AppCompatResources.getDrawable(context, R.drawable.search_icon)
iconGravity = MaterialButton.ICON_GRAVITY_START
}
P.S. We can cast Button to MaterialButton as fair as we can use icon param in Button: icon param is not actually Button param - it is sneaky MaterialButton param somehow working with Buttons.

Categories

Resources