如何响应ListView的内部按钮的点击事件呢?比如说listView上的item有一个ImageView控件,我要获取对应每个ImageView控件的点击事件,较为常见的办法是在自定义的adapter中的getView方法内为每个ImageView绑定监听器。当然这种方法能满足大部分的使用情况了,但某些情况下要在activity内获取点击事件下面给出方法。
</pre></p><p></p><p> 先上代码:(共四个文件)</p><p> 先看布局(尽量最简化啦)</p><p> activity_main.xml(主布局文件)<pre name="code" class="html"><RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<ListView
android:id="@+id/listView"
android:layout_width="match_parent"
android:layout_height="match_parent" >
</ListView>
</RelativeLayout>
item.xml(item布局)
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="40dp"
android:orientation="vertical" >
<ImageView
android:id="@+id/imageView"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="center"
android:src="@drawable/contact" />
</LinearLayout>
MainActivity.java(activity文件)
package com.developmc.listview;
import java.util.ArrayList;
import java.util.List;
import com.developmc.listview.MyAdapter.MyCallBack;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.ListView;
import android.widget.Toast;
public class MainActivity extends Activity implements MyCallBack {
private ListView listView ;
private List<String> lists ;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
listView=(ListView)findViewById(R.id.listView) ;
lists = new ArrayList<String>() ;
for(int i=0;i<20;i++)
{
lists.add(i+"") ;
}
//若在fragment中定义的listView,将第一个this替换成getContext()
MyAdapter adapter = new MyAdapter(this,lists,this) ;
listView.setAdapter(adapter);
}
@Override
public void onItemWidgetClickListener(View v) {
//item上有多个可点击的控件时,根据控件id找到相应事件(这里只有一个控件)
switch (v.getId()) {
case R.id.imageView:
Toast.makeText(this, "回调成功 ", Toast.LENGTH_SHORT).show();
break;
default:
break;
}
}
}
MyAdapter.java(自定义的适配器)
package com.developmc.listview;
import java.util.List;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.Toast;
public class MyAdapter extends BaseAdapter implements OnClickListener {
private Context context ;
private List<String> lists ;
private MyCallBack mCallBack ;
public MyAdapter(Context context,List<String> lists,MyCallBack mCallBack)
{
this.context=context ;
this.lists=lists ;
this.mCallBack = mCallBack ;
}
@Override
public int getCount() {
// TODO Auto-generated method stub
return lists.size();
}
@Override
public Object getItem(int position) {
// TODO Auto-generated method stub
return lists.get(position);
}
@Override
public long getItemId(int position) {
// TODO Auto-generated method stub
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
// TODO Auto-generated method stub
ViewHolder viewHolder = null ;
if(convertView==null)
{
viewHolder = new ViewHolder() ;
convertView = LayoutInflater.from(context).inflate(R.layout.item, null) ;
viewHolder.imageView = (ImageView)convertView.findViewById(R.id.imageView) ;
convertView.setTag(viewHolder);
}
else {
viewHolder = (ViewHolder)convertView.getTag() ;
}
viewHolder.imageView.setOnClickListener(this);
// viewHolder.imageView.setOnClickListener(new OnClickListener() {
//
// @Override
// public void onClick(View v) {
// // TODO Auto-generated method stub
// Toast.makeText(context, " "+position, Toast.LENGTH_SHORT).show();
// }
// });
return convertView;
}
//定义回调接口
public interface MyCallBack
{
//listView item下的控件点击事件(注意传入参数V)
public void onItemWidgetClickListener(View v) ;
}
@Override
public void onClick(View v) {
//在onClick中回调接口的OnItemClickListener
mCallBack.onItemWidgetClickListener(v);
}
private class ViewHolder{
private ImageView imageView ;
}
}
上面就是所有代码了,这里就已经实现在Activity或fragment中响应ListView内部按钮的点击事件。下面逐步分解过程:
1.依旧需要在adapter的getView下绑定控件监听器:
viewHolder.imageView.setOnClickListener(this); 让adapter继承OnClickListener,系统生成Onclick方法。
2.自定义一个回调接口:这里记得要将参数view
//定义回调接口
public interface MyCallBack
{
//listView item下的控件点击事件(注意传入参数V)
public void onItemWidgetClickListener(View v) ;
}
3.在Onclick中调用自定义的接口,传入view。需要先在构造函数获得接口对象。
mCallBack.onItemWidgetClickListener(v);
4.让MainActivity.java继承MyCallBack接口。
5.实现onItemWidgetClickListener(v);接口,在里边实现响应的点击事件。至此已经完成。
不足之处:通过此方法能够实现在activity或fragmen中响应内部listView控件的点击事件(可以通过为控件添加selector文件观察控件是否被点击),但无法通过回调得到点击控件所在的item位置,这是因为在geiview中position只在listView绘制的时候才会变动,相对于在getView中实现点击事件来说,如此回调不能将每次的位置的信息都回调。虽然,listView有onItemClickListener方法,然而并没有什么卵用。
总结:相对于常规的在geiView中实现控件的的点击事件,本文给出的方法能够现实,但不足之处(或许致命)是无法通过回调得到点击控件所在的item位置,引用老罗的话,生命不息,折腾不止啊!