1、需要在AndroidManifest.xml清单文件中获取InterNet权限
2、重写ListView控件(创建RefreshListView.java,继承自ListView)
package com.t20.weather.view;
import com.t20.weather.R;
import android.content.Context;
import android.util.AttributeSet;
import android.view.View;
import android.widget.AbsListView;
import android.widget.ListView;
public class RefreshListView extends ListView {
private int mHeight;
private View footview;
public RefreshListView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
// TODO Auto-generated constructor stub
//加载初始化布局
intiRefreshListView();
}
public RefreshListView(Context context, AttributeSet attrs) {
super(context, attrs);
// TODO Auto-generated constructor stub
//加载初始化布局
intiRefreshListView();
}
public RefreshListView(Context context) {
super(context);
// TODO Auto-generated constructor stub
//加载初始化布局
intiRefreshListView();
}
/**
* 初始化布局
*/
public void intiRefreshListView(){
//加载布局(用于显示加载的图标 )
footview=View.inflate(getContext(),R.layout.refresh_foot_view, null);
//将布局追加到ListView底部
addFooterView(footview);
//用尺子量高度(低版本安卓有严重的Bug,不支持相对布局,在Level 17版本后得到修复)
footview.measure(0, 0);
//-------宽偏移量---高偏移量
//获取测量过后的高度
mHeight=footview.getMeasuredHeight();
//通过设置内边距,隐藏refresh_foot_view.xml布局
footview.setPadding(0, -mHeight, 0, 0);
//设置监听ListView的滚动事件
this.setOnScrollListener(new OnScrollListener() {
/**
* 滚动状态改变
*/
@Override
public void onScrollStateChanged(AbsListView view, int scrollState) {
// TODO Auto-generated method stub
}
/**
* 滚动中
*/
@Override
public void onScroll(AbsListView view, int firstVisibleItem,
int visibleItemCount, int totalItemCount) {
// TODO Auto-generated method stub
//当ListView滚动到最底部时
if(getLastVisiblePosition()==getCount()-1){
//让refresh_foot_view.xml布局显示出来(显示加载中)
footview.setPadding(0, 0, 0, 0);
//判断是否在请求网络数据
if(loadingFlag==false){
if(onRefreshListener!=null){
onRefreshListener.RefeshData();
loadingFlag=true;//正在请求
}
}
}
}
});
}
//是否正在请求网络,防止出现重复请求的情况(true表示正在请求,false不请求)
private boolean loadingFlag=false;
/**
* 数据加载完毕要执行的方法
*/
public void loadFinish(){
//通过设置内边距,隐藏refresh_foot_view.xml布局
footview.setPadding(0, -mHeight, 0, 0);
//请求完毕
loadingFlag=false;
}
private OnRefreshListener onRefreshListener;
/**
* @param onRefreshListener the onRefreshListener to set
*/
public void setOnRefreshListener(OnRefreshListener onRefreshListener) {
this.onRefreshListener = onRefreshListener;
}
/**
* 自定义一个接口,用来刷新网络数据
* @author Administrator
*
*/
public interface OnRefreshListener{
void RefeshData();
}
}
3、创建天气实体类Weather.java(主要用于封装服务端获取到的天气信息)
package com.t20.weather.entity;
import java.io.Serializable;
/**
* 天气实体类
* @author admin
*
*/
public class Weather implements Serializable {
private Integer id; //城市编码
private String city; //城市名
private String tianqi; //天气
private double temp; //温度
private String img; //天气图标
public Weather() {
super();
}
public Weather(Integer id, String city, String tianqi, double temp,
String img) {
super();
this.id = id;
this.city = city;
this.tianqi = tianqi;
this.temp = temp;
this.img = img;
}
/**
* @return the id
*/
public Integer getId() {
return id;
}
/**
* @param id the id to set
*/
public void setId(Integer id) {
this.id = id;
}
/**
* @return the city
*/
public String getCity() {
return city;
}
/**
* @param city the city to set
*/
public void setCity(String city) {
this.city = city;
}
/**
* @return the tianqi
*/
public String getTianqi() {
return tianqi;
}
/**
* @param tianqi the tianqi to set
*/
public void setTianqi(String tianqi) {
this.tianqi = tianqi;
}
/**
* @return the temp
*/
public double getTemp() {
return temp;
}
/**
* @param temp the temp to set
*/
public void setTemp(double temp) {
this.temp = temp;
}
/**
* @return the img
*/
public String getImg() {
return img;
}
/**
* @param img the img to set
*/
public void setImg(String img) {
this.img = img;
}
}
4、MainActivity.java
package com.t20.weather;
import java.util.List;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.lidroid.xutils.BitmapUtils;
import com.lidroid.xutils.HttpUtils;
import com.lidroid.xutils.exception.HttpException;
import com.lidroid.xutils.http.ResponseInfo;
import com.lidroid.xutils.http.callback.RequestCallBack;
import com.lidroid.xutils.http.client.HttpRequest.HttpMethod;
import com.t20.weather.entity.Weather;
import com.t20.weather.view.RefreshListView;
import com.t20.weather.view.RefreshListView.OnRefreshListener;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends Activity {
private RefreshListView lvWeather;
private List<Weather> weaList;
private MyAdapter myAdapter;
private int pageIndex=1;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
lvWeather=(RefreshListView) findViewById(R.id.lvWeather);
//使用xUtils框架的HttpUtils加载后台数据到列表集合里
final HttpUtils hu=new HttpUtils();
String url="http://172.168.40.97:8088/android0/WeatherServlet?pageIndex="+pageIndex;
hu.send(HttpMethod.GET, url, new RequestCallBack<String>(){
@Override
public void onFailure(HttpException error, String msg) {
// TODO Auto-generated method stub
Log.e("xUtils错误信息", msg);
}
@Override
public void onSuccess(ResponseInfo<String> responseInfo) {
// TODO Auto-generated method stub
String json=responseInfo.result;
//使用gson读取json中的内容
Gson gson=new Gson();
weaList=gson.fromJson(json, new TypeToken<List<Weather>>(){}.getType());
//设置适配器
myAdapter=new MyAdapter();
lvWeather.setAdapter(myAdapter);
pageIndex++;
//监听RefreshListView控件
lvWeather.setOnRefreshListener(new OnRefreshListener() {
@Override
public void RefeshData() {
// TODO Auto-generated method stub
//使用xUtils框架的HttpUtils加载后台数据到列表集合里
String url="http://172.168.40.97:8088/android0/WeatherServlet?pageIndex="+pageIndex;
hu.send(HttpMethod.GET, url, new RequestCallBack<String>(){
@Override
public void onFailure(HttpException error,
String msg) {
// TODO Auto-generated method stub
Log.e("xUtils错误信息", msg);
Toast.makeText(MainActivity.this, "网络异常",Toast.LENGTH_SHORT).show();
lvWeather.loadFinish();
}
@Override
public void onSuccess(ResponseInfo<String> responseInfo) {
// TODO Auto-generated method stub
String ret=responseInfo.result;
//先判断是否还有数据
if(ret.equals("no")){
Toast.makeText(MainActivity.this, "没有更多数据了",Toast.LENGTH_SHORT).show();
}else{
//使用gson读取json中的内容
Gson gson=new Gson();
//用临时集合接收数据
List<Weather> tempList=gson.fromJson(ret, new TypeToken<List<Weather>>(){}.getType());
//把临时集合的数据加到天气集合中
weaList.addAll(tempList);
//让适配器通知ListView刷新数据
myAdapter.notifyDataSetChanged();
pageIndex++;
}
lvWeather.loadFinish();
}
});
}
});
}
});
}
class MyAdapter extends BaseAdapter{
@Override
public int getCount() {
// TODO Auto-generated method stub
return weaList.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 view, ViewGroup parent) {
// TODO Auto-generated method stub
//1.加载list_item.xml布局文件
view=View.inflate(MainActivity.this, R.layout.list_item, null);
//------------------上下文-------------需要加载的布局----一般用null
//2.获取list_item.xml布局文件中的控件
/*TextView tvId=(TextView) view.findViewById(R.id.tvId);*/
TextView tvCity=(TextView) view.findViewById(R.id.tvCity);
TextView tvTianqi=(TextView) view.findViewById(R.id.tvTianqi);
TextView tvTemp=(TextView) view.findViewById(R.id.tvTemp);
ImageView ivImg=(ImageView) view.findViewById(R.id.ivImg);
//3.设置控件值
Weather weather=weaList.get(position);
/*tvId.setText(weather.getId()+"");*/
tvCity.setText(weather.getCity());
tvTianqi.setText(weather.getTianqi());
tvTemp.setText(weather.getTemp()+"");
//显示网络图片
BitmapUtils bu=new BitmapUtils(MainActivity.this);
String uri=weather.getImg();
bu.display(ivImg, uri);
return view;
}
}
}