一、实现效果
这是整体实现效果。
二、实现步骤
(1)实现一个简单的自定义ListView;(2)给这个ListView添加一个底部进度提示;(3)实现ListView滚动监听。
三、整个项目实现
(1)项目结构
其中ApkInfo.java是ListView Item的一个实体类,描述了Item里相关的信息。这个就不多说了,主要是get和set相关方法;
(2)看下MyAdapter.java的实现:
package com.example.listviewdemo;
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.ImageView;
import android.widget.TextView;
/**
* listView适配器
*
*
*/
public class MyAdapter extends BaseAdapter {
ArrayList<ApkInfo> apkInfos_list;
LayoutInflater inflater;
public MyAdapter(ArrayList<ApkInfo> apkInfos_list, Context context) {
this.apkInfos_list = apkInfos_list;
this.inflater = LayoutInflater.from(context);
}
public void onDataChange(ArrayList<ApkInfo> apkInfos_list) {
this.apkInfos_list = apkInfos_list;
this.notifyDataSetChanged();
}
@Override
public int getCount() {
return apkInfos_list.size();
}
@Override
public Object getItem(int position) {
return apkInfos_list.get(position);
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
ApkInfo apkInfo = apkInfos_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);
holder.item_iv = (ImageView) convertView.findViewById(R.id.item3_apkiv);
convertView.setTag(holder);
} else {
holder = (ViewHolder) convertView.getTag();
}
holder.name_tv.setText(apkInfo.getName());
holder.des_tv.setText(apkInfo.getDes());
holder.info_tv.setText(apkInfo.getInfo());
holder.item_iv.setImageResource(apkInfo.getImage());
return convertView;
}
class ViewHolder {
TextView name_tv;
TextView des_tv;
TextView info_tv;
ImageView item_iv;
}
}
这个Adapter是AdapterView视图与数据之间的桥梁,Adapter提供对数据的访问,也负责为每一项数据产生一个对应的View。
看看,其中ListView里的Item实现效果:
配置文件item_layout.xml的实现:
<?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="match_parent"
android:orientation="vertical" >
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="60dip"
android:background="@drawable/app_item_bg"
android:gravity="center_vertical"
android:orientation="horizontal" >
<ImageView
android:id="@+id/item3_apkiv"
android:layout_width="50dip"
android:layout_height="50dip"
android:layout_marginLeft="10dip" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginLeft="10dip"
android:layout_weight="1"
android:orientation="vertical" >
<TextView
android:id="@+id/item3_apkname"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="应用程序名字"
android:textColor="@color/black"
android:textSize="18dip" />
<TextView
android:id="@+id/item3_apkinfo"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="5dip"
android:text="应用程序信息"
android:textSize="14dip" />
</LinearLayout>
<Button
android:id="@+id/item3_dlbtn"
android:layout_width="60dip"
android:layout_height="30dip"
android:layout_marginRight="10dip"
android:background="@drawable/dlbtn_selector"
android:text="卸载" />
</LinearLayout>
<TextView
android:id="@+id/item3_apkdes"
android:layout_width="fill_parent"
android:layout_height="30dip"
android:layout_marginLeft="5dip"
android:layout_marginRight="5dip"
android:gravity="center_vertical"
android:text="应用程序描述"
android:textSize="14dip" />
</LinearLayout>
(3)自定义ListView实现
package com.example.listviewdemo;
import android.content.Context;
import android.util.AttributeSet;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.AbsListView;
import android.widget.AbsListView.OnScrollListener;
import android.widget.ListView;
public class LoadListView extends ListView implements OnScrollListener {
View footer;// 底部布局
int totalItemCount;// ListView加载数据总量
int lastVisibaleItem;// 底部显示的数据下标
boolean isLoading;// 是否在加载
OnLoaderListener loaderListener;// 加载监听
public LoadListView(Context context) {
super(context);
initView(context);
}
public LoadListView(Context context, AttributeSet attrs) {
super(context, attrs);
initView(context);
}
public LoadListView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
initView(context);
}
@Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
/**
* scrollState = SCROLL_STATE_TOUCH_SCROLL(1) 正在滚动 ; scrollState =
* SCROLL_STATE_FLING(2) 手指做了抛的动作(手指离开屏幕前,用力滑了一下); scrollState =
* SCROLL_STATE_IDLE(0) 停止滚动 ; 当滚动到最后一行,且停止滚动,加载数据;
*/
if (totalItemCount == lastVisibaleItem && scrollState == SCROLL_STATE_IDLE) {
if (!isLoading) {
isLoading = true;
footer.findViewById(R.id.load_layout).setVisibility(View.VISIBLE);
loaderListener.onLoad();// 加载更多
}
}
}
@Override
public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount,
int totalItemCount) {
/**
* 滚动一直回调直到停止滚动时才停止回调,单击时回调一次; 列表到达结尾之前,我们要加载数据模块;
* firstVisibleItem表示当前屏幕显示的第一个listItem在整个listView里的位置(下标从0开始);
* visibleItemCount表示当前屏幕可见的listItem(部分显示的listItem也算)总数;
* totalItemCount表示listView里listItem总数。
*/
this.lastVisibaleItem = firstVisibleItem + visibleItemCount;
this.totalItemCount = totalItemCount;
}
/**
* 底部进度调加载到listview
*
* @param context
*/
private void initView(Context context) {
LayoutInflater inflater = LayoutInflater.from(context);
footer = inflater.inflate(R.layout.footer_layout, null);
footer.findViewById(R.id.load_layout).setVisibility(View.GONE);
this.addFooterView(footer);// 加到底部
this.setOnScrollListener(this);// 监听滚动到底部
}
/**
* 加载完毕
*/
public void loadComplete() {
isLoading = false;
footer.findViewById(R.id.load_layout).setVisibility(View.GONE);
}
public void setLoaderListener(OnLoaderListener loaderListener) {
this.loaderListener = loaderListener;
}
// 加载更多回调接口
public interface OnLoaderListener {
public void onLoad();
}
}
添加底部加载进度条
footer_layout.xml实现如下:
<?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="match_parent"
android:orientation="vertical" >
<LinearLayout
android:id="@+id/load_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="horizontal"
android:paddingBottom="10dip"
android:paddingTop="10dip" >
<ProgressBar
style="?android:attr/progressBarStyleSmall"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="10条载入中..." />
</LinearLayout>
</LinearLayout>
(4)MainActivity.java里的实现:
package com.example.listviewdemo;
import java.util.ArrayList;
import com.example.listviewdemo.LoadListView.OnLoaderListener;
import android.os.Bundle;
import android.os.Handler;
import android.app.Activity;
public class MainActivity extends Activity implements OnLoaderListener {
ArrayList<ApkInfo> apkInfos_list = new ArrayList<ApkInfo>();
MyAdapter adapter;
LoadListView listview;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
getData();
showListView(apkInfos_list);
}
private void showListView(ArrayList<ApkInfo> apkInfos_list) {
if (adapter == null) {
listview = (LoadListView) findViewById(R.id.listview);
listview.setLoaderListener(this);
adapter = new MyAdapter(apkInfos_list, this);
listview.setAdapter(adapter);
} else {
adapter.onDataChange(apkInfos_list);
}
}
private void getData() {
for (int i = 0; i < 10; i++) {
ApkInfo apkInfo = new ApkInfo();
apkInfo.setName("测试程序I");
apkInfo.setInfo("50w用户");
apkInfo.setDes("这是一个神奇的应用!");
apkInfo.setImage(R.drawable.ic_launcher);
apkInfos_list.add(apkInfo);
}
}
private void loadData() {
for (int i = 0; i < 10; i++) {
ApkInfo apkInfo = new ApkInfo();
apkInfo.setName("测试程序II");
apkInfo.setInfo("50w用户");
apkInfo.setDes("这是一个更加神奇的应用!");
apkInfo.setImage(R.drawable.test_icon);
apkInfos_list.add(apkInfo);
}
}
@Override
public void onLoad() {
Handler handler = new Handler();
handler.postDelayed(new Runnable() {
@Override
public void run() {
// 获取更多数据
loadData();
// 更新listview显示;
showListView(apkInfos_list);
// 通知listview加载完毕
listview.loadComplete();
}
}, 2000);
}
}
activity_main.xml配置文件:
<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"
tools:context=".MainActivity" >
<com.example.listviewdemo.LoadListView
android:id="@+id/listview"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:background="@color/white"
android:cacheColorHint="#00000000"
android:dividerHeight="5dip" >
</com.example.listviewdemo.LoadListView>
</RelativeLayout>
到这里整个实现就算完成了,这里使用了handler.postDelayed延时两秒加载只是为了实验效果。这是在慕课网上学习时的笔记,大家要想更加深入地了解相关知识,请移步慕课网吧,感觉很实用!
源码下载猛戳:http://download.csdn.net/detail/shizhao0716/8382029