Change expandable indicator in ExpandableListView

100,391

Solution 1

expandable listview

 <ExpandableListView
    android:id="@+id/expandable_list"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:groupIndicator="@drawable/group_indicator"
    android:transcriptMode="alwaysScroll" />

setindicator here iam useing setindicator code like this this working nice

 DisplayMetrics metrics = new DisplayMetrics();
    getWindowManager().getDefaultDisplay().getMetrics(metrics);
    int width = metrics.widthPixels; 

 mExpandableList = (ExpandableListView)findViewById(R.id.expandable_list);
 mExpandableList.setIndicatorBounds(width - GetPixelFromDips(50), width - GetPixelFromDips(10));  

   public int GetPixelFromDips(float pixels) {
    // Get the screen's density scale 
    final float scale = getResources().getDisplayMetrics().density;
    // Convert the dps to pixels, based on density scale
    return (int) (pixels * scale + 0.5f);
}

res/drawable/group_indicator

  <?xml version="1.0" encoding="utf-8"?>

     <selector xmlns:android="http://schemas.android.com/apk/res/android">            
           <item android:drawable="@drawable/arrow_right" android:state_empty="true">  </item>            
           <item android:drawable="@drawable/arrow_down" android:state_expanded="true"></item>                
           <item android:drawable="@drawable/arrow_right"></item>
     </selector>

Solution 2

Try that for your settings_selector.xml:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >

    <item
        android:drawable="@drawable/arrow_right"
        android:state_expanded="true" />

    <item
        android:drawable="@drawable/arrow_down" />

</selector>

Solution 3

I had gone the way below: decide the left/right drawable for your groupView based on isExpanded flag.
By that way, it is easier for us to customize the padding/background and other things of the indicator drawable.

Hope it helps.

    public View getGroupView(int groupPosition, boolean isExpanded, View convertView,
            ViewGroup parent) {
        TextView textView = (TextView) mLayoutInflater.inflate(R.layout.menu_group, null);
        textView.setCompoundDrawablesWithIntrinsicBounds(0, 0, isExpanded ? 0 : android.R.drawable.ic_menu_more, 0);
        textView.setText(getGroup(groupPosition).toString());
        return textView;
    }

Solution 4

import java.util.ArrayList;

import android.app.Activity;
import android.content.Context;
import android.database.DataSetObserver;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.BaseExpandableListAdapter;
import android.widget.ExpandableListView;
import android.widget.TextView;

public class MyActivity extends Activity {

    private ExpandableListView mExpandableList;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_my);


        mExpandableList = (ExpandableListView)findViewById(R.id.expandable_list);
        mExpandableList.setGroupIndicator(null);
        ArrayList<Parent> arrayParents = new ArrayList<Parent>();
        ArrayList<String> arrayChildren = new ArrayList<String>();

        //here we set the parents and the children
        for (int i = 0; i < 10; i++){
            //for each "i" create a new Parent object to set the title and the children
            Parent parent = new Parent();
            parent.setTitle("Parent " + i);

            arrayChildren = new ArrayList<String>();
            for (int j = 0; j < 10; j++) {
                arrayChildren.add("Child " + j);
            }
            parent.setArrayChildren(arrayChildren);

            //in this array we add the Parent object. We will use the arrayParents at the setAdapter
            arrayParents.add(parent);
        }

        //sets the adapter that provides data to the list.
        mExpandableList.setAdapter(new MyCustomAdapter(MyActivity.this,arrayParents));

    }

    public class Parent {
        private String mTitle;
        private ArrayList<String> mArrayChildren;

        public String getTitle() {
            return mTitle;
        }

        public void setTitle(String mTitle) {
            this.mTitle = mTitle;
        }

        public ArrayList<String> getArrayChildren() {
            return mArrayChildren;
        }

        public void setArrayChildren(ArrayList<String> mArrayChildren) {
            this.mArrayChildren = mArrayChildren;
        }
    }




    public class MyCustomAdapter extends BaseExpandableListAdapter implements OnClickListener{


        private LayoutInflater inflater;
        private ArrayList<Parent> mParent;

        public MyCustomAdapter(Context context, ArrayList<Parent> parent){
            mParent = parent;
            inflater = LayoutInflater.from(context);
        }


        @Override
        //counts the number of group/parent items so the list knows how many times calls getGroupView() method
        public int getGroupCount() {
            return mParent.size();
        }

        @Override
        //counts the number of children items so the list knows how many times calls getChildView() method
        public int getChildrenCount(int i) {
            return mParent.get(i).getArrayChildren().size();
        }

        @Override
        //gets the title of each parent/group
        public Object getGroup(int i) {
            return mParent.get(i).getTitle();
        }

        @Override
        //gets the name of each item
        public Object getChild(int i, int i1) {
            return mParent.get(i).getArrayChildren().get(i1);
        }

        @Override
        public long getGroupId(int i) {
            return i;
        }

        @Override
        public long getChildId(int i, int i1) {
            return i1;
        }

        @Override
        public boolean hasStableIds() {
            return true;
        }

        @Override
        //in this method you must set the text to see the parent/group on the list
        public View getGroupView(int i, boolean b, View view, ViewGroup viewGroup) {

            if (view == null) {
                view = inflater.inflate(R.layout.list_item_parent, viewGroup,false);
            }
            view.findViewById(R.id.button).setTag(i);
            view.findViewById(R.id.button).setOnClickListener(this);
            TextView textView = (TextView) view.findViewById(R.id.list_item_text_view);
            //"i" is the position of the parent/group in the list
            textView.setText(getGroup(i).toString());

            //return the entire view
            return view;
        }

        @Override
        //in this method you must set the text to see the children on the list
        public View getChildView(int i, int i1, boolean b, View view, ViewGroup viewGroup) {
            if (view == null) {
                view = inflater.inflate(R.layout.list_item_child, viewGroup,false);
            }

            TextView textView = (TextView) view.findViewById(R.id.list_item_text_child);
            //"i" is the position of the parent/group in the list and
            //"i1" is the position of the child
            textView.setText(mParent.get(i).getArrayChildren().get(i1));

            //return the entire view
            return view;
        }

        @Override
        public boolean isChildSelectable(int i, int i1) {
            return true;
        }

        @Override
        public void registerDataSetObserver(DataSetObserver observer) {
            /* used to make the notifyDataSetChanged() method work */
            super.registerDataSetObserver(observer);
        }


        /* (non-Javadoc)
         * @see android.view.View.OnClickListener#onClick(android.view.View)
         * @since Mar 20, 2013
         * @author rajeshcp 
         */
        @Override
        public void onClick(View v) {
            if(mExpandableList.isGroupExpanded((Integer)v.getTag()))
        {
            mExpandableList.collapseGroup((Integer)v.getTag());
        }else
        {
            mExpandableList.expandGroup((Integer)v.getTag());
        }
        }
    }


}

Change your MyActivity like this and let me know what else you want ?

Solution 5

subject:

    int width = getResources().getDisplayMetrics().widthPixels;
    if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.JELLY_BEAN_MR2) {
        listView.setIndicatorBounds(width - getPixelValue(40), width - getPixelValue(10));
    } else {
        listView.setIndicatorBoundsRelative(width - getPixelValue(40), width - getPixelValue(10));
    }

and helper method:

public static int getPixelValue(int dp) {

    final float scale = getResources().getDisplayMetrics().density;
    return (int) (dp * scale + 0.5f);
}
Share:
100,391

Related videos on Youtube

NagarjunaReddy
Author by

NagarjunaReddy

My Gitlab Applications http://pnrandroid.blogspot.in/2018/03/how-to-handle-storage-permissions-in.html https://wordpress.com/stats/day/polamreddyn.wordpress.com Usfull Questions: 1) http://stackoverflow.com/questions/424752/any-good-graphing-packages-for-android 2) http://android-graphview.org/ 3) http://jaxenter.com/effort-free-graphs-on-android-with-achartengine-46199.html 4) http://www.dreamincode.net/forums/topic/303235-visualizing-sound-from-the-microphone/ 5) https://github.com/melanke/MlkAndroidChartApi 6) http://www.osciprime.com/?p=source 7) http://android.codeandmagic.org/achartengine-live-scrolling-graph/ 9) http://android-innovation.blogspot.in/2013/07/how-to-implement-pinch-and-pan-zoom-on.html 10) Full to Refresh https://github.com/chrisbanes/Android-PullToRefresh

Updated on July 09, 2022

Comments

  • NagarjunaReddy
    NagarjunaReddy almost 2 years

    Trying to create an ExpandableListView. The initial view with the groups shows up fine. However, when I click the list item, my arrow does not change. See the images below.

    enter image description here

    How can I change the arrow's direction?

    The layout XML:

      <ExpandableListView
            android:id="@+id/expandable_list"
            android:layout_width="fill_parent"
            android:layout_height="match_parent"            
            android:divider="@null"
            android:background="#ffffff"
            android:groupIndicator="@drawable/settings_selector"
            android:transcriptMode="alwaysScroll" />
    

    settings_selector.xml:

     <?xml version="1.0" encoding="utf-8"?>
    <animation-list xmlns:android="http://schemas.android.com/apk/res/android" >
    
    <selector xmlns:android="http://schemas.android.com/apk/res/android" >
        <item
            android:drawable="@drawable/arrow_down"
            android:state_empty="true"/>
        <item
            android:drawable="@drawable/arrow_right"
            android:state_expanded="true"/>
    </selector>
    
    </animation-list>
    
    • Triode
      Triode about 11 years
      Post the listView row xml
    • NagarjunaReddy
      NagarjunaReddy about 11 years
      @RajeshCP see update one
    • Triode
      Triode about 11 years
      Onclick of the onItemClick function you can change the source of the group_indicator for that you need a uparrow button or else you can rotate the bitmap by some dregree and set it as a source for that ImageView
    • NagarjunaReddy
      NagarjunaReddy about 11 years
      @RajeshCP in left side arrow working nice use this hrupin.com/2012/08/… one but how to solve right side arrow
    • Triode
      Triode about 11 years
      Edit your lay out accordingly for that
    • NagarjunaReddy
      NagarjunaReddy about 11 years
      for which one i want how to change that left side button to right side @RajeshCP
    • NagarjunaReddy
      NagarjunaReddy about 11 years
  • NagarjunaReddy
    NagarjunaReddy about 11 years
    in this no onitemclick in expandablelistview necessary to use an onitemclick.
  • Triode
    Triode about 11 years
    I really don understand what you want ?
  • NagarjunaReddy
    NagarjunaReddy about 11 years
    see hrupin.com/2012/08/… this example in place of left side image how change that image to right side.
  • NagarjunaReddy
    NagarjunaReddy about 11 years
    I'am useing that example only that image how to change like left to right side same as my image like in question have one image like that..
  • Triode
    Triode about 11 years
    hey see the edited answer after running the application just click on each buttons in the row
  • NagarjunaReddy
    NagarjunaReddy about 11 years
    Any way thanks my issue solved we see my answer working nice.
  • Benoit Duffez
    Benoit Duffez about 11 years
    You didn't post your answer when I posted mine :)
  • NagarjunaReddy
    NagarjunaReddy about 11 years
    becouse it is is usefull to any new developers.
  • Pratik Butani
    Pratik Butani about 10 years
    mExpandableList.setIndicatorBounds(width - 50, width - 10); gives Same output.. Why?????
  • Mourice
    Mourice about 10 years
    use expListView.setIndicatorBoundsRelative in android 4.3
  • gSorry
    gSorry about 8 years
    You can save indicator size in dimens.xml: <dimen name="indicator_bounds">-50dp</dimen> And then use built in method to calculate dp to pixels: getResources().getDimensionPixelSize(R.dimen.indicator_bound‌​s)
  • prasanthMurugan
    prasanthMurugan over 7 years
    icon is streched to the height of the layout