博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Android--ListView下拉刷新
阅读量:7060 次
发布时间:2019-06-28

本文共 9936 字,大约阅读时间需要 33 分钟。

整理了下以前写的小项目,ListView的下拉刷新,虽然小但还是想纪念下。。适合新手看,大神略过。。。

效果图:

   

 

代码:  实体类

package com.example.listviewrefreshdemo;/** * @author 超超boy */public class ApkEntity {	private String name;	private String des;	private String info;	public String getName() {		return name;	}	public void setName(String name) {		this.name = name;	}	public String getDes() {		return des;	}	public void setDes(String des) {		this.des = des;	}	public String getInfo() {		return info;	}	public void setInfo(String info) {		this.info = info;	}	}

 MainActivity:

package com.example.listviewrefreshdemo;import java.util.ArrayList;import com.example.listviewrefreshdemo.RefreshListView.IReflashListener;import android.app.Activity;import android.os.Bundle;import android.os.Handler;/** * @author 超超boy */public class MainActivity extends Activity implements IReflashListener{	ArrayList
apk_list; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); setData(); showList(apk_list); } MyAdapter adapter; RefreshListView listview; private void showList(ArrayList
apk_list) { if (adapter == null) { listview = (RefreshListView) findViewById(R.id.listview); listview.setIReflashListener(this); adapter = new MyAdapter(this, apk_list); listview.setAdapter(adapter); } else { adapter.onDateChange(apk_list); } } private void setData() { apk_list = new ArrayList
(); for (int i = 0; i < 10; i++) { ApkEntity entity = new ApkEntity(); entity.setName("默认数据"); entity.setDes("这是一个神奇的应用"); entity.setInfo("50w用户"); apk_list.add(entity); } } private void setReflashData() { for (int i = 0; i < 2; i++) { ApkEntity entity = new ApkEntity(); entity.setName("刷新数据"); entity.setDes("这是一个神奇的应用"); entity.setInfo("50w用户"); apk_list.add(i,entity); } } @Override public void onReflash() { // TODO Auto-generated method stub\ Handler handler = new Handler(); handler.postDelayed(new Runnable() { @Override public void run() { // TODO Auto-generated method stub //获取最新数据 setReflashData(); //通知界面显示 showList(apk_list); //通知listview 刷新数据完毕; listview.reflashComplete(); } }, 2000); } /** * 回掉方法 */ /*public void onReflash() { //获取最新数据 setReflashData(); //通知界面显示 showList(apk_list); //通知listview刷新数据完毕 listview.reflashComplete(); }*/}

  RefreshListView:

package com.example.listviewrefreshdemo;import java.text.SimpleDateFormat;import java.util.Date;import android.R.anim;import android.R.interpolator;import android.content.Context;import android.util.AttributeSet;import android.util.Log;import android.view.LayoutInflater;import android.view.MotionEvent;import android.view.View;import android.view.ViewGroup;import android.view.animation.RotateAnimation;import android.widget.AbsListView;import android.widget.ImageView;import android.widget.ListView;import android.widget.AbsListView.OnScrollListener;import android.widget.ProgressBar;import android.widget.TextView;/** * @author 超超boy */public class RefreshListView extends ListView implements OnScrollListener{	LayoutInflater inflater;	View header;	int headerHeight;   //顶部布局文件的高度	int firstVisibleItem; //当前第一个可见的item的位置	int scrollState;   //listview当前滚动状态	boolean isRemark;  //标记,当前是在listview的最顶部摁下的	int startY;   //摁下时的Y值	int state;  //当前的状态	final int NONE = 0;// 正常状态;	final int PULL = 1;// 提示下拉状态;	final int RELESE = 2;// 提示释放状态;	final int REFLASHING = 3;// 刷新状态;		IReflashListener reflashListener;	public RefreshListView(Context context) {		super(context);		initView(context);	}	public RefreshListView(Context context, AttributeSet attrs, int defStyle) {		super(context, attrs, defStyle);		initView(context);	}	public RefreshListView(Context context, AttributeSet attrs) {		super(context, attrs);		initView(context);	}    /**     * 初始化界面,添加顶部布局文件到ListView     * @param context     */	private void initView(Context context){		inflater = LayoutInflater.from(context);		header  =inflater.inflate(R.layout.header, null);		measureView(header);		headerHeight = header.getMeasuredHeight();		Log.i("tag", "headerHeight="+headerHeight);		topPadding(-headerHeight);  //负的高度,把它能没啦		this.addHeaderView(header);	    this.setOnScrollListener(this);	}	/**	 * 通知父布局,占用的宽高。	 * @param view	 */	private void measureView(View view){	  ViewGroup.LayoutParams p = view.getLayoutParams();	  if(p == null){		  p = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);	  }	  //spec:header的左右边距,padding内边距,childDimension字布局的宽度	  int width = ViewGroup.getChildMeasureSpec(0, 0, p.width);	  int height;	  int tempHeight = p.height;	  if(tempHeight > 0){ //高度不是空,需要填充这个布局		  //EXACTLY(完全),父元素决定自元素的确切大小,子元素将被限定在给定的边界里而忽略它本身大小;		  height = MeasureSpec.makeMeasureSpec(tempHeight, MeasureSpec.EXACTLY);	  }else{		  //UNSPECIFIED(未指定),父元素不对子元素施加任何束缚,子元素可以得到任意想要的大小;		  height = MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED);	  }	  view.measure(width, height);	}	/**	 * 设置header布局的上边距	 * @param topPadding	 */	private void topPadding(int topPadding){ //header的上边距		header.setPadding(header.getPaddingLeft(), topPadding, header.getPaddingRight(), header.getPaddingBottom());		header.invalidate();	}    /**     * 取得当前的滚动状态     */	public void onScrollStateChanged(AbsListView view, int scrollState) {				this.scrollState = scrollState; 	}	@Override	public void onScroll(AbsListView view, int firstVisibleItem,			int visibleItemCount, int totalItemCount) {		this.firstVisibleItem = firstVisibleItem;  //当前第一个可见的item的位置			}	    /**     * 触摸事件     */	public boolean onTouchEvent(MotionEvent ev) {		switch (ev.getAction()) {		case MotionEvent.ACTION_DOWN:  //下拉			if (firstVisibleItem == 0) { //在界面最顶端				isRemark = true;     //标记,当前是在listview的最顶部摁下的 				startY = (int) ev.getY();			}			break;		case MotionEvent.ACTION_MOVE:			 onMove(ev);			 break;		case MotionEvent.ACTION_UP:  //抬起			if (state == RELESE) {  //释放				state = REFLASHING; //正在刷新				// 加载最新数据;				reflashViewByState();				reflashListener.onReflash();			} else if (state == PULL) {  //下拉过程中,没到一定距离的时候				state = NONE;  // 正常状态;				isRemark = false;   //在顶部的标记				reflashViewByState();			}			break;		}		return super.onTouchEvent(ev);	}	/**	 * 判断移动过程的操作	 * @param ev	 */	private void onMove(MotionEvent ev) {		if(!isRemark){  //不在顶的时候移动			return;		}		//移动的过程中状态是不断改变的		int tempY = (int) ev.getY();		int sapce = tempY-startY;  //移动的距离		int topPadding = sapce - headerHeight; //移动过程中不断设置topPadding		switch (state) {		case NONE:   // 正常状态;			if(sapce>0){				state = PULL; // 提示下拉状态				reflashViewByState();			}			break;        case PULL:   // 提示下拉状态;        	topPadding(topPadding);  //不断设置上边距        	if(sapce > headerHeight+30         			&& scrollState == SCROLL_STATE_TOUCH_SCROLL){				state = RELESE;  // 提示释放状态;				reflashViewByState();			}						break;        case RELESE:    // 提示释放状态;        	topPadding(topPadding);        	if(sapce

  适配器:

package com.example.listviewrefreshdemo;import java.util.ArrayList;import android.content.Context;import android.view.LayoutInflater;import android.view.View;import android.view.ViewGroup;import android.widget.BaseAdapter;import android.widget.TextView;/** * @author 超超boy */public class MyAdapter extends BaseAdapter {	ArrayList
apk_list; LayoutInflater inflater; public MyAdapter(Context context, ArrayList
apk_list) { this.apk_list = apk_list; this.inflater = LayoutInflater.from(context); } public void onDateChange(ArrayList
apk_list) { this.apk_list = apk_list; this.notifyDataSetChanged(); //更新数据 } @Override public int getCount() { // TODO Auto-generated method stub return apk_list.size(); } @Override public Object getItem(int position) { // TODO Auto-generated method stub return apk_list.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 ApkEntity entity = apk_list.get(position); ViewHolder holder; if (convertView == null) { holder = new ViewHolder(); convertView = inflater.inflate(R.layout.item_layout, null); holder.name_tv = (TextView) convertView .findViewById(R.id.item3_apkname); holder.des_tv = (TextView) convertView .findViewById(R.id.item3_apkdes); holder.info_tv = (TextView) convertView .findViewById(R.id.item3_apkinfo); convertView.setTag(holder); }else{ holder = (ViewHolder) convertView.getTag(); } holder.name_tv.setText(entity.getName()); holder.des_tv.setText(entity.getDes()); holder.info_tv.setText(entity.getInfo()); return convertView; } class ViewHolder { TextView name_tv; TextView des_tv; TextView info_tv; }}

  activity_main.xml:

  布局文件还有header.xml和item_layout.xml,就不粘贴了,想看的可以去下我的源代码,下边有下载链接。。

二、代码逻辑

    1.自定义状态:PULL下拉状态,RELESE释放状态,REFLASHING刷新状态

    2. AbsListView的触摸事件:

      下拉的时候设置startY(开始滑动时的位置),之后就是不断的滑动过程,滑动的过程中,用自定义的onMove方法改变状态和header界面(下拉刷新,释放刷新,刷新中);

       刷新:

       case MotionEvent.ACTION_UP: //抬起

       if (state == RELESE) { //释放
         state = REFLASHING; //正在刷新
        reflashViewByState();// 加载最新数据;

         reflashListener.onReflash(); //在回调接口刷新  }

    3.自定义的move时判断状态信息:

    下拉->释放:sapce > headerHeight+30 判断距离,距离够了就改变状态:释放状态,释放更新

int sapce = tempY-startY;  //移动的距离	int topPadding = sapce - headerHeight; //移动过程中不断设置topPadding		switch (state) {		case NONE:   // 正常状态;			if(sapce>0){				state = PULL; // 提示下拉状态				reflashViewByState();			}			break;        case PULL:   // 提示下拉状态;        	topPadding(topPadding);  //不断设置上边距        	if(sapce > headerHeight+30         			&& scrollState == SCROLL_STATE_TOUCH_SCROLL){				state = RELESE;  // 提示释放状态;				reflashViewByState();			}						break;        case RELESE:    // 提示释放状态;        	topPadding(topPadding);        	if(sapce

 

    ok。。代码很简单。。。

Demo源代码下载:

附一篇很好的博文::http://blog.csdn.net/leehong2005/article/details/12567757

 转发请注明出处:

你可能感兴趣的文章
英国乐购网上银行2000个账户遭窃 现已暂停服务
查看>>
陈旭东用暴雨搞借势营销:工厂被淹 ZUK线上缺货
查看>>
中国第一家大数据资产评估实验室揭牌
查看>>
Fortinet: 全球2016年第四季度全球医疗行业威胁分析与报告
查看>>
深度剖析堆栈
查看>>
零售行业RFID应用解析
查看>>
金风科技澳洲首座20兆瓦光伏电站将于2017年投产
查看>>
Java 代理
查看>>
《Effective Debugging:软件和系统调试的66个有效方法》——第12条:将复杂的测试场景自动化...
查看>>
企业物联网安全的四个关键步骤
查看>>
盗版的软件更易被攻击 勒索钱财是黑客惯用形式
查看>>
SPI绿能宝与金沙江资本签署5亿美元可转债协议
查看>>
中英专家建言:未来城市发展要智慧化“留白”
查看>>
象棋中马行走路线的测试用例设计
查看>>
乌当区前三季度大数据产业实现产值60亿元
查看>>
微软推出新工具 可以识别恶意图片和视频
查看>>
selenium技巧——通过js来控制滚动条  业务流程:
查看>>
《软件建模与设计: UML、用例、模式和软件体系结构》一一1.3 软件体系结构设计...
查看>>
《Greenplum企业应用实战》一3.5 索引
查看>>
转:ibatis动态sql
查看>>