单击ListView中的按钮,查找ListView的正确子视图

时间:2014-06-19 13:40:35

标签: android listview onclicklistener baseadapter

我正在进行一项实验,尝试了解ListView生命周期。

我有ListView,每行都有一个按钮和一个TextView,我的实验将是点击Button并将行涂成绿色,这里是代码:

编辑:

我尝试使用一组布尔值,但结果相同

    package com.ziv.test;

import java.util.ArrayList;

import com.ziv.test.Fr.mAdapter.ViewHolder;

import android.content.Context;
import android.graphics.Color;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.Button;
import android.widget.LinearLayout;
import android.widget.ListView;
import android.widget.TextView;

public class Fr extends Fragment {

    ArrayList<String> list;
    private ListView lv;

    public Fr() {
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
            Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_main, container, false);
        list = new ArrayList<String>();

        for (int i = 0; i < 50; i++) {
            list.add("item number " + i);
        }

        lv = (ListView) view.findViewById(R.id.listView1);

            mAdapter adapter = new mAdapter(list, lv);
            lv.setAdapter(a

dapter);

        return view;
    }

    public class mAdapter extends BaseAdapter {
    ArrayList<String> list;
    private LayoutInflater inflater;
    private ListView lv;

    // boolean[] for button state:
    private Boolean[] clickedButtonPositions;

    public mAdapter(ArrayList<String> list, ListView lv) {

        this.list = list;
        this.lv = lv;
        inflater = (LayoutInflater) getActivity().getSystemService(
                Context.LAYOUT_INFLATER_SERVICE);
         this.clickedButtonPositions = new Boolean[list.size()];
    }

    @Override
    public int getCount() {
        // TODO Auto-generated method stub
        return list.size();
    }

    @Override
    public Object getItem(int position) {
        // TODO Auto-generated method stub
        return null;
    }

    @Override
    public long getItemId(int position) {
        // TODO Auto-generated method stub
        return 0;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        // here you write everything is related to views...
        // do not forget to reuse...

        ViewHolder vh;
        if (convertView == null) {

            vh = new ViewHolder();
            convertView = inflater.inflate(R.layout.list_cell, null);

            vh.text = (TextView) convertView.findViewById(R.id.list_test);
            vh.btn = (Button) convertView.findViewById(R.id.list_button);

            convertView.setTag(vh);

        } else {


            vh = (ViewHolder) convertView.getTag();

        }
        vh.text.setText(list.get(position));

        vh.btn.setTag(R.id.list_button, position);

        vh.btn.setOnClickListener(OnClickButton);



        return convertView;

    }

    public class ViewHolder {
        TextView text;
        Button btn;

    }



    private View.OnClickListener OnClickButton = new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            // v will always be the view that received the click event, no
            // need to check.
            int pos = (int) v.getTag(R.id.list_button);
            LinearLayout view = (LinearLayout) lv.getChildAt(pos);

            // Switching the 'clicked' value for this button - If you want
            // the button to "turn off" the view
            clickedButtonPositions[pos] = !clickedButtonPositions[pos];
            // If you don't want the button to "turn off" the view use this
            // line instead:
            // clickedButtonPositions[pos] = true;

            // save button state in a local variable, optional
            boolean clicked = clickedButtonPositions[pos];

            // If you want a "turn off" behavior use this line with the '?:'
            // operator
            view.setBackgroundColor(clicked ? Color.GREEN : Color.LTGRAY);
            // If you don't want a "turn off" behavior this will do:

        }
    };
}

}

enter image description here

然而,令我失望的是,我点击的那一行并不是唯一一个涂成绿色的行,它的回收行也被涂上了,就在屏幕外面。 如何在点击事件中隔离我想要的行?

2 个答案:

答案 0 :(得分:1)

我在项目中遇到了类似的问题,并像你一样扩展了基础适配器。我的解决方案非常简单。它是这样的:

if(buttonClick)//any boolean variable indicating clicked
{
view.setBackgroundColor(Color.GREEN);
}else{
view.setBackgroundColor(Color.WHITE);
}

答案 1 :(得分:0)

您必须为所有ListView项添加布尔数组。

onClick()中,只对正确的位置设置为true / false。然后在适配器上调用notifyDatasetChanged()

getView()中,根据您的布尔数组设置颜色。