2

在我的具有 ListActivity 的应用程序中,onListItemClick通过单击ListView项目不会触发覆盖的回调。

我已经使用以下 xml 文件,permissionview.xml 定义了一个自定义列表视图

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:orientation="vertical" >

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal" >

        <Button
            android:id="@+id/btn_Apply"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="@string/btn_apply"
            android:onClick="onApplyClick" />

        <Button
            android:id="@+id/btn_install"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="@string/btn_install"
            android:onClick="onInstallClick" />

        <Button
            android:id="@+id/btn_cancel"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Cancel" />

    </LinearLayout>

    <ListView android:id="@android:id/list" 
            android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:focusable="false">

    </ListView>  
</LinearLayout>

和 viewitem 布局checkable.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" >


   <ImageView android:id="@+id/img" android:layout_width="wrap_content"
        android:layout_height="wrap_content" android:layout_alignParentLeft="true"
        android:layout_alignParentTop="true" android:layout_alignParentBottom="true"
        android:src="@drawable/ic_launcher" android:focusable="false" />

    <CheckBox
        android:id="@+id/check"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
       android:layout_alignParentRight="true"
        android:layout_marginLeft="4px"
    android:layout_marginRight="10px"

    android:clickable="true">

 </CheckBox>

    <TextView
        android:id="@+id/label"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerVertical="true"
        android:layout_toRightOf="@+id/img"
        android:gravity="bottom"
        android:text="@+id/label"
        android:textSize="15px"/>
</RelativeLayout>

定义ArrayAdapter如下:

     public class InteractiveArrayAdapter extends ArrayAdapter<Model> {


    private final List<Model> list;
    private final Activity context;
    private boolean changeable;

    public InteractiveArrayAdapter(Activity context, List<Model> list, boolean changeable) {
        super(context, R.layout.checkable, list);
        this.context = context;
        this.list = list;
        this.changeable = changeable;
    }

    static class ViewHolder {
        protected TextView text;
        protected CheckBox checkbox;
        protected ImageView image;
        protected int pos;
    }

    public View getView(int position, View convertView, ViewGroup parent) {
        View view = null;
        if (convertView == null) {
            LayoutInflater inflater = context.getLayoutInflater();
                view = inflater.inflate(R.layout.checkable, null);


            final ViewHolder viewHolder = new ViewHolder();
            viewHolder.text = (TextView) view.findViewById(R.id.label);
            viewHolder.checkbox = (CheckBox) view.findViewById(R.id.check);
            viewHolder.image = (ImageView) view.findViewById(R.id.img);
            viewHolder.pos = position;


            view.setClickable(true);

            if (!changeable)viewHolder.checkbox.setEnabled(false);


            viewHolder.checkbox.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {



                public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                    Model element = (Model) viewHolder.checkbox.getTag();

                    element.setActive(buttonView.isChecked());
                }

            }
            );



            view.setTag(viewHolder);
            viewHolder.checkbox.setTag(list.get(position));

        } else {
            view = convertView;
            ((ViewHolder) view.getTag()).checkbox.setTag(list.get(position));

        }
        ViewHolder holder = (ViewHolder) view.getTag();
        holder.text.setText(list.get(position).showPermission());
        holder.checkbox.setChecked(list.get(position).isActive());

        if (list.get(position).isRedundant()) {
            holder.image.setImageDrawable(context.getResources().getDrawable(R.drawable.warning));
        } else {
            holder.image.setImageDrawable(context.getResources().getDrawable(R.drawable.ok));
        }
        return view;

    }

}

在扩展 ListActivity 的类中,定义的 ArrayAdapter 用 asyncTask 中的 arrayList 填充(列表信息在doInBackground()方法中计算):

public class PermissionViewActivity extends ListActivity {

    private final static String TAG = "PMA";
    ...
     @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.permissionview);
        ...
    }

    ... 

     private class CurrentPermissions extends AsyncTask<String, Integer, String> {

        private ListActivity la;
        private Context context;



        private int progress = 0;

        public CurrentPermissions(ListActivity la) {
            this.la = la;
            this.context = la;

        }

        protected void onPreExecute() {
        ...

        protected void onPostExecute(String result) {
          adapter = new InteractiveArrayAdapter(la, permissionList, changeable);
          la.setListAdapter(adapter);
          /output with number of listitems
              System.out.println("DEBUG1 " + la.getListAdapter().getCount());
        }
     }
      ...
      @Override
      protected void onListItemClick(ListView l,  View view, int position, long id) {
        super.onListItemClick(l, view, position, id);
        System.out.println("clicked !");
      }
      ...
    }

onListItemClick方法未执行。在 ArrayAdapter 中定义 onClickListener 时,单击事件有效:

 view.setOnClickListener(new OnClickListener() {
                public void onClick(View v) {

                    System.out.println("Klick D1 " + list.get(viewHolder.pos));

                }

            });

为什么 ArrayAdapter 中单击事件的定义有效,但在 ListActivity 中覆盖无效?我找不到失败。

4

4 回答 4

4

尝试也将CheckBox行布局设置为 not focusable

//...
 <CheckBox
    android:id="@+id/check"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignParentRight="true"
    android:layout_marginLeft="4px"
    android:layout_marginRight="10px"
    android:focusable="false" 
    android:clickable="true">

//...
于 2012-05-22T20:42:04.477 回答
0

如果你想要一个“通用”点击监听器(适用于你的列表视图中的所有项目)你的活动应该实现 OnItemClickListener

public class PermissionViewActivity extends ListActivity implements OnItemClickListener

您将需要覆盖该方法

@Override
public void onItemClick(AdapterView<?> arg0, View v, int position, long arg3)
{
     Toast.makeText(this, "Clicked", Toast.LENGTH_SHORT).show();
}

然后你必须在你的列表视图上手动设置点击监听器

前任。

public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.permissionview);
        ...
        getListView().setOnItemClickListener(this);
}
于 2012-05-22T20:34:42.263 回答
0

我在包含 ListView 的视图中通过以下方式执行此操作:

ListView lv = (ListView)findViewById(R.id.myList);
lv.setAdapter(new myCustomAdapter,items);
lv.setOnItemClickListener(new AdapterView.OnItemClickListener(){
    public void onItemClick(AdapterView<?> arg0, View arg1, int position, long id){
        /* do something i've been clicked */

});

或在 onItemSelected 事件中

lv.setOnItemSelectedListener(new AdapterView.onItemSelectedListener(){
    public void onItemSelected(AdapterView<?> arg0, View arg1, int position, long id){
        ...
    }
    public void onNothingSelected(AdapterView<?> arg0){
        ...
    }
});

希望这可以帮助

于 2012-05-22T20:53:27.327 回答
0

如果 ListItem 中有可单击视图,则需要将可聚焦标志设置为 false。通过在布局中设置 focusable=false,当以编程方式设置 Listener 时,它将被覆盖。

我的解决方案通过以编程方式调用设置可聚焦性为我工作

listview.setOnItemClickListener(this);
listview.setFocusable(false);
于 2014-09-11T11:37:39.917 回答