简体   繁体   中英

ListView's row pressed color with gradient background

I want to have rows with gradient background in my ListView and i want them to change to a solid color when pressed. But i can't get it right. I know about the problem ListViews have and i read some solutions in other topics but none of them seems to work for me. Any help would be great.

When i run the following code i get this image that is ok: 按下之前

But when i press on item 2, all rows will be green!: 按下后

Here is my Adapter:

public class MyAdapter extends BaseAdapter {

    private final Context mContext;
    private ArrayList<String> mMenuItems;

    StateListDrawable mBackgroundDrawable;

    public MyAdapter(Context context) {

        this.mContext = context;

        mMenuItems= new ArrayList<>();
        for (int i = 0; i < 10; i++) {
            mMenuItems.add(String.format("Item %d", i));
        }

        // make background drawable
        GradientDrawable backgroundDrawable = new GradientDrawable(
                GradientDrawable.Orientation.TOP_BOTTOM,
                new int[]{  Color.RED, Color.YELLOW, Color.RED});
        backgroundDrawable.setCornerRadius(0f);

        ColorDrawable selectedColorDrawable= new ColorDrawable(Color.GREEN);

        mBackgroundDrawable = new StateListDrawable();
        mBackgroundDrawable.addState(new int[] {android.R.attr.state_pressed}, selectedColorDrawable);
        mBackgroundDrawable.addState(new int[] {android.R.attr.state_focused}, selectedColorDrawable);
        mBackgroundDrawable.addState(new int[] {android.R.attr.state_selected}, selectedColorDrawable);
        mBackgroundDrawable.addState(new int[] {}, backgroundDrawable);
    }

    @Override
    public int getCount() {
        return mMenuItems.size();
    }

    @Override
    public Object getItem(int position) {
        return mMenuItems.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        ViewGroup item = getViewGroup(convertView);
        if (Build.VERSION.SDK_INT<Build.VERSION_CODES.JELLY_BEAN) {
            item.setBackgroundDrawable(mBackgroundDrawable);
        } else {
            item.setBackground(mBackgroundDrawable);
        }
        // set title
        TextView titleView= (TextView) item.findViewById(R.id.menu_title);
        titleView.setText(mMenuItems.get(position));
        return item;
    }

    public ViewGroup getViewGroup(View reuse)
    {
        if(reuse instanceof ViewGroup)
            return (ViewGroup)reuse;

        LayoutInflater inflater = LayoutInflater.from(mContext);
        ViewGroup item = (ViewGroup)inflater.inflate(R.layout.row_menu, null);

        return item;
    }
}

My row_menu.xml:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:padding="5dp">

    <TextView
        android:id="@+id/menu_title"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerVertical="true"/>

</RelativeLayout>

My activity's layout:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:padding="10dp">

    <ListView
        android:id="@+id/activity_main_listview"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        />
</LinearLayout>

My activity:

public class MainActivity extends ActionBarActivity{

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        ListView list = (ListView) findViewById(R.id.activity_main_listview);
        list.setAdapter(new MyAdapter(this));
    }
}

mBackgroundDrawable is common for all your Rows. You need to attach a unique mBackgroundDrawable to every row (for example inside your loop where you add it). This is pretty much straightforward, but feel free to ask if you need a specific example ! ;)

You could achieve it through the XML it self.

ListView

<ListView
        android:id="@+id/list_slidermenu"
        android:layout_width="240dp"
        android:layout_height="match_parent"
        android:layout_gravity="start"
        android:choiceMode="singleChoice"
        android:divider="@color/list_divider"
        android:dividerHeight="1dp"       
        android:listSelector="@drawable/list_selector"
        android:background="@color/list_background"/>

drawables/list_selector.xml

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

    <item android:drawable="@drawable/list_item_bg_normal" android:state_activated="false"/>
    <item android:drawable="@drawable/list_item_bg_pressed" android:state_pressed="true"/>
    <item android:drawable="@drawable/list_item_bg_pressed" android:state_activated="true"/>

</selector>

drawables/list_item_bg_pressed.xml

<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
  <gradient
      android:startColor="@color/list_background_pressed"
      android:endColor="@color/list_background_pressed"
      android:angle="90" />
</shape>

drawables/list_item_bg_normal.xml

<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:shape="rectangle">
  <gradient
      android:startColor="@color/list_background"
      android:endColor="@color/list_background"
      android:angle="90" />
</shape>

As you can see the ListView has an attr named android:listSelector and it's value is "@drawable/list_selector". This is where we setting the selector. and i think the rest is Self Explanatory.

If you need more clarification, read this http://javatechig.com/android/android-listview-tutorial

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM