I have an image button and I want to change the color of a button when pressed. First I show it with a transparent as a default state color as below. But it doesn't show highlighted when pressed. So I decided to use other color to highlight when pressed using state drawable. But how to keep background color through styles wise. Means by default it should be transparent and when pressed it has to show other color.
present code:
<ImageButton
android:id="#+id/imgbutton"
android:layout_width="20dp"
android:layout_height="match_parent"
android:layout_gravity="center"
android:src="#drawable/ic_launcher"
android:background="#android:color/transparent"
/>
Need to be coded:
<ImageButton
android:id="#+id/imgbutton"
android:layout_width="20dp"
android:layout_height="match_parent"
android:layout_gravity="center"
android:src="#drawable/ic_launcher"
android:background="#drawable/btnselector"
/>
So what should be the btnselector.xml here?
put it inside res/color
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true" android:color="#color/green_text_color"/> <!-- pressed -->
<item android:state_focused="true" android:color="#color/green_text_color"/> <!-- focused -->
<item android:color="#android:color/white"/> <!-- default -->
</selector>
create a new shape, inside res/drawable
<?xml version="1.0" encoding="UTF-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle">
<solid android:color="#color/yourxmlfile" />
</shape>
and put it as background
or a res/drawable selector
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:drawable="#drawable/green_botton_pressed"
android:state_pressed="true" />
<item android:drawable="#drawable/green_botton_highlited"
android:state_focused="true" />
<item android:drawable="#drawable/green_botton" />
</selector>
Related
How can I change color of rounded corners textView or button with transparent background like this
I want when clicked again the button unselect , not only select
Add xml file in drawable folder bg.xml
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" android:padding="10dp">
<!-- you can use any color you want I used here gray color-->
<stroke
android:height="1.0dip"
android:width="1.0dip"
android:color="#ffee82ee" />
<solid android:color="#android:color/transparent"/>
<corners android:radius="7dp"/>
</shape>
and in layout
<Button
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#drawable/bg"
android:textColor="#ffee82ee"/>
It will work..
You can use a selector with multiple state as drawable for background and text color.
<Button
android:id="#+id/button1"
android:background="#drawable/selector_xml_name"
android:layout_width="200dp"
android:layout_height="126dp"
android:text="Hello" />
drawable xml file :
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="#drawable/numpad_button_bg_selected" android:state_selected="true"></item>
<item android:drawable="#drawable/numpad_button_bg_pressed" android:state_pressed="true"></item>
<item android:drawable="#drawable/numpad_button_bg_normal"></item>
</selector>
You have to create a background with a selector
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_checked="true" android:state_pressed="true" android:drawable="#drawable/likeactivepressed" />
<item android:state_pressed="true" android:drawable="#drawable/likeinitialpressed"/>
<item android:state_checked="true" android:drawable="#drawable/likeon"/>
<item android:drawable="#drawable/likeinitial"/>
</selector>
then set your background to your button :
android:background="#drawable/like_button"
You have different options:
Just use the MaterialButton in the Material Components library with the Widget.MaterialComponents.Button.OutlinedButton style and the app:cornerRadius, app:strokeColor attributes.
Something like:
<com.google.android.material.button.MaterialButton
style="#style/Widget.MaterialComponents.Button.OutlinedButton"
android:text="BUTTON"
app:strokeColor="#color/myColor"
app:cornerRadius="16dp"
../>
To achieve the selection of the buttons you can use a MaterialButtonToggleGroup.
Something like:
<com.google.android.material.button.MaterialButtonToggleGroup
app:singleSelection="true"
...>
<com.google.android.material.button.MaterialButton
.../>
</com.google.android.material.button.MaterialButtonToggleGroup>
Use a Chip
Something like:
<com.google.android.material.chip.Chip
style="#style/Widget.MaterialComponents.Chip.Entry"
app:chipCornerRadius="16dp"
android:text="Chip"
.../>
I am using a drawable to change the background and text of textViews inside of my navigation drawer. I would like to keep the background white for the text area, but by testing keeping the background white does not show the ripple effect on the background, instead it does it to the text making the text gray. In the picture below, the middle one is being pressed causing the ripple effect.
Here are my drawable files that are used to make the changes in colors
Background:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="#color/selected" android:state_activated="true" />
<item android:drawable="#color/white" />
</selector>
Text:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:color="#color/primary" android:state_activated="true" />
<item android:color="#color/primary_text" />
</selector>
textView layout file
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentLeft="true"
android:layout_alignParentRight="true" >
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textSize="25.0sp"
android:background="#drawable/activated_background"
android:textColor="#drawable/activated_text"
android:id="#id/text1"
android:layout_weight="0"
android:layout_marginTop="8dip"
android:layout_marginBottom="8dip" />
</RelativeLayout>
you should use 2 drawable files and use it as your view background.
for pre-lolipop versions:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="#color/white_list_item_selected_background" android:state_pressed="true" />
<item android:drawable="#android:color/white" />
</selector>
for lolipop (v21):
<?xml version="1.0" encoding="utf-8"?>
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
android:color="#color/white_list_item_selected_background" >
<item android:drawable="#android:color/white" />
</ripple>
If you use custom background, ripple effect will not be shown. You may have to use other ripple library such as Material Ripple.
In my case ripple effect is working after the first click, but for first click it didn't work for me. Have changed the background selector file with android:state_activated="true" and in main.xml android:clickable="true" then it's work fine for all time.
selector.xml (under res\drawable\selector.xml)
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_activated="true" android:drawable="#drawable/card_bg_pressed" android:state_enabled="true" android:state_pressed="true"/>
<item android:state_activated="true" android:drawable="#drawable/card_bg_focused" android:state_enabled="true" android:state_focused="true"/>
<item android:state_activated="true" android:drawable="#drawable/card_bg_selected" android:state_enabled="false" android:state_selected="true"/>
</selector>
In activity_main.xml
<com.mysample.RecyclingImageView
android:id="#+id/imageview_overlay"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:background="#drawable/selector"
android:clickable="true" />
In my custom listview, I have used relativelayout and inside that added 2 textviews vertically.
Background image is set to relativelayout. Now I want to change background image as well as textcolor of textview when listview item is pressed.
How to do this, any one have idea?
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#drawable/item_bg"
android:orientation="vertical" >
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text=""
android:textColor="#color/orange"
android:textSize="18sp"
android:textStyle="bold"
android:layout_marginTop="10dip"
android:layout_marginLeft="10dip"
/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
android:layout_marginTop="8dip"
android:ellipsize="end"
android:maxLines="3"
android:duplicateParentState="true" <!-- this is a line to use..-->
android:textColor="#color/_textcolor"
android:textSize="14sp" >
</TextView>
item_bg.xml inside res/drawable folder:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:state_pressed="true" android:drawable="#drawable/bannerbg_hover"/>
<item android:state_focused="true" android:drawable="#drawable/bannerbg_hover" />
<item android:state_selected="true" android:drawable="#drawable/bannerbg_hover"/>
<item android:drawable="#drawable/bannerbg"/>
</selector>
_textcolor.xml inside res/color/ folder:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:state_pressed="true" android:color="#color/white"/>
<item android:state_focused="true" android:color="#color/white" />
<item android:state_selected="true" android:color="#color/white"/>
<item android:color="#color/dark_blue"/>
</selector>
Concerning the background, you should create a StateList Drawable and set it as the background of your rows.
Ex of a such drawable (could be named background_selector.xml) :
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true" android:drawable="#color/color1" /> <!-- pressed -->
<item android:drawable="#color/color2" /> <!-- default -->
</selector>
And in the layout declaration of your row :
...
android:background="#drawable/background_selector"
...
Use the same way for your text with the Color State List
I customized the Toggle button by using a drawable defined by using a selector. I use this drawable as background for the Toggle button.
<ToggleButton
android:id="#+id/mailbox:toggle_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:layout_weight="1"
android:background="#drawable/toggle_background"
android:gravity="center_horizontal|center_vertical" />
The toggle_background is defined here:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:drawable="#drawable/img1"
android:state_checked="true" />
<item
android:drawable="#drawable/img2"
android:state_checked="false" />
</selector>
The problem is that the image is always stretched. Is there a way to define an image for the two states that is not stretched?
What I need is a background that will be stretched and in the center of the button an icon that must not be stretched.
Is it possible?
This is my final solution.
In the layout:
<ToggleButton
android:id="#+id/mailbox:toggle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:background="#drawable/toggle_drawable_layers"/>
in the toggle_drawable_layers.xml
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:drawable="#drawable/toggle_drawable_bkg"></item>
<item android:left="10dp" android:drawable="#drawable/toggle_drawable_left"
android:gravity="center_vertical|center_horizontal" />
</layer-list>
in the toggle_drawable_left.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_checked="true">
<bitmap android:src="#drawable/bitmap_checked"
android:gravity="center_vertical|center_horizontal" />
</item>
<item android:state_checked="false">
<bitmap android:src="#drawable/bitmap_unchecked"
android:gravity="center_vertical|center_horizontal" />
</item>
</selector>
I did the same task this way, the button:
<ToggleButton android:id="#+id/mlAbout"
android:textOn="#string/about"
android:textOff="#string/about"
android:background="#drawable/ml_about" />
#drawable/ml_about:
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item android:drawable="#drawable/list_bg_top"></item>
<item android:left="10dp">
<bitmap android:src="#drawable/waiting_status_btn"
android:gravity="center_vertical|left" />
</item>
</layer-list>
#drawable/list_bg_top background image that will be stretched and #drawable/waiting_status_btn is the icon the will not be stretched with the widget
Just use bitmaps instead of drawables in your selector like so (no need to use layers):
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:drawable="#drawable/img1"
android:state_checked="true" />
<item
android:drawable="#drawable/img2"
android:state_checked="false" />
</selector>
Also, don't forget to declare
android:textOff=""
android:textOn=""
in your ToggleButton declaration
There is another way to overcome the issue of stretching:
Just convert the image into a Nine-Patch image, where the stretchable areas are just on all sides of the image.
Then Android will stretch the image only in invisible areas, and keep the visible image unchanged.
I followed this tutorial to create a color state list for a particular Android view. I just want it to highlight when clicked so the user knows why the screen just changed.
When the view is rendered, I get the following error:
org.xmlpull.v1.XmlPullParserException: Binary XML file line #3: tag requires a 'drawable' attribute or child tag defining a drawable
My color XML (in res/color/viewcolor.xml):
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true" android:color="#ff33ffff"/> <!-- pressed -->
<item android:color="#ff000000"/> <!-- default -->
</selector>
My layout XML (in res/layout/myview.xml):
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/myview"
android:orientation="horizontal"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="top"
android:background="#color/viewcolor">
<!--crap in the layout-->
</LinearLayout>
What did I miss?
I remember that I worked around this error by using state drawable instead of state color. For some reason layout background just doesn't work with stateful colors. So try creating a stateful drawable (for example list of shape drawables with different colors) and use it as background.
res/drawable/pressed.xml:
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="#ff33ffff" />
</shape>
res/drawable/normal.xml:
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="rectangle" >
<solid android:color="#ff000000" />
</shape>
res/drawable/background.xml:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true" android:drawable="#drawable/pressed" />
<item android:drawable="#drawable/normal" />
</selector>
Then use background.xml drawable as background :)
Instead of using shapes in your drawable, you can use the android:drawable attribute which accepts a color resource (e.g. #color/black).
layout.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/myview"
android:orientation="horizontal"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="top"
android:background="#drawable/myDrawable">
<!-- other views in layout-->
</LinearLayout>
my_drawable.xml
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<!-- focused -->
<item android:state_focused="true" android:drawable="#color/YOUR_COLOR_HERE" />
<!-- focused and pressed-->
<item android:state_focused="true" android:state_pressed="true" android:drawable="#color/YOUR_COLOR_HERE" />
<!-- pressed -->
<item android:state_pressed="true" android:drawable="#color/YOUR_COLOR_HERE" />
<!-- default -->
<item android:drawable="#color/YOUR_COLOR_HERE" />
</selector>
In my_drawable.xml you need to make sure that the colors you specify are defined in res/values/colors.xml, or this won't work.
If you want to use an image instead of a color change from a color resource to a drawable resource.
Example:
android:drawable="#color/YOUR_COLOR_HERE"
android:drawable="#drawable/YOUR_IMAGE_HERE"