Android-app-DwWeather天气预报

这个Demo可以从全国天气预报网上获取实时天气信息,能够显示省、市、县级的天气情况。主要涉及的知识点有数据库的使用、JSON数据的解析、Service、广播的使用以及MVC设计模式的应用,详情见源码。
一、布局文件

1.weather_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" >

    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="50dp"
        android:background="#484E61" >
        <Button
            android:id="@+id/switch_city"
            android:layout_width="30dp"
            android:layout_height="30dp"
            android:layout_centerVertical="true"
            android:layout_marginLeft="10dp"
            android:background="@android:drawable/ic_input_get"
            ></Button>

        <TextView
            android:id="@+id/city_name"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true"
            android:textColor="#fff"
            android:textSize="24sp" />

        <Button
            android:id="@+id/refresh_weather"
            android:layout_width="30dp"
            android:layout_height="30dp"
            android:layout_centerVertical="true"
            android:layout_alignParentRight="true"
            android:layout_marginRight="10dp"
            android:background="@android:drawable/ic_menu_rotate"
            ></Button>
    </RelativeLayout>

    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1"
        android:background="#27A5F9" >

        <TextView
            android:id="@+id/publish_text"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_alignParentRight="true"
            android:layout_marginRight="10dp"
            android:layout_marginTop="10dp"
            android:textColor="#FFF"
            android:textSize="18sp" />

        <LinearLayout
            android:id="@+id/weather_info_layout"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true"
            android:orientation="vertical" >

            <TextView
                android:id="@+id/current_date"
                android:layout_width="wrap_content"
                android:layout_height="40dp"
                android:gravity="center"
                android:textColor="#FFF"
                android:textSize="18sp" />

            <TextView
                android:id="@+id/weather_desp"
                android:layout_width="wrap_content"
                android:layout_height="60dp"
                android:layout_gravity="center_horizontal"
                android:gravity="center"
                android:textColor="#FFF"
                android:textSize="40sp" />

            <LinearLayout
                android:layout_width="wrap_content"
                android:layout_height="60dp"
                android:layout_gravity="center_horizontal"
                android:orientation="horizontal" >

                <TextView
                    android:id="@+id/temp1"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:layout_gravity="center_vertical"
                    android:textColor="#FFF"
                    android:textSize="40sp" />
                <TextView
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:layout_gravity="center_vertical"
                    android:layout_marginLeft="10dp"
                    android:layout_marginRight="10dp"
                    android:text="~"
                    android:textColor="#FFF"
                    android:textSize="40sp" />
                <TextView
                    android:id="@+id/temp2"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:layout_gravity="center_vertical"
                    android:textColor="#FFF"
                    android:textSize="40sp" />
            </LinearLayout>
        </LinearLayout>
    </RelativeLayout>

</LinearLayout>

2.choose_area.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" >
    <RelativeLayout 
        android:layout_width="match_parent"
        android:layout_height="50dp"
        android:background="#484E61">
        <TextView 
            android:id="@+id/title_text"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true"
            android:textColor="#fff"
            android:textSize="24sp"/>
    </RelativeLayout>
    <ListView 
        android:id="@+id/list_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent">
    </ListView>

</LinearLayout>

二、界面

1.ChooseAreaActivity.java

package com.dw.dwweather.activity;

import java.util.ArrayList;
import java.util.List;

import com.dw.dwweather.db.DwWeatherDB;
import com.dw.dwweather.model.City;
import com.dw.dwweather.model.County;
import com.dw.dwweather.model.Province;
import com.dw.dwweather.util.HttpCallbackListener;
import com.dw.dwweather.util.HttpUtil;
import com.dw.dwweather.util.Utility;

import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.preference.PreferenceManager;
import android.text.TextUtils;
import android.view.View;
import android.view.Window;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;

public class ChooseAreaActivity extends Activity {
    public static final int LEVEL_PROVINCE = 0;
    public static final int LEVEL_CITY = 1;
    public static final int LEVEL_COUNTY = 2;

    private ProgressDialog progressDialog;
    private TextView titleText;
    private ListView listView;
    private ArrayAdapter<String> adapter;
    private DwWeatherDB dwWeatherDB;
    private List<String> dataList = new ArrayList<String>();

    private List<Province> provinceList;
    private List<City> cityList;
    private List<County> countyList;

    private Province selectedProvince;
    private City selectedCity;

    private int currentLevel;

    private boolean isFromWeatherActivity;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);

        isFromWeatherActivity=getIntent().getBooleanExtra("from_weather_activity", false);

        SharedPreferences prefs=PreferenceManager.getDefaultSharedPreferences(this);
        //已经选择了城市而且不是从weatherActivity跳转过来,才会直接跳转到Weather、Activity
        if(prefs.getBoolean("city_selected", false)&&!isFromWeatherActivity){
            Intent intent=new Intent(this, WeatherActivity.class);
            startActivity(intent);
            finish();
            return;
        }
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        setContentView(R.layout.choose_area);
        listView = (ListView) findViewById(R.id.list_view);
        titleText = (TextView) findViewById(R.id.title_text);
        adapter = new ArrayAdapter<String>(this,
                android.R.layout.simple_list_item_1, dataList);
        listView.setAdapter(adapter);

        dwWeatherDB=DwWeatherDB.getInstance(this);

        listView.setOnItemClickListener(new OnItemClickListener() {

            @Override
            public void onItemClick(AdapterView<?> arg0, View view, int index,
                    long arg3) {
                // TODO Auto-generated met
                if (currentLevel == LEVEL_PROVINCE) {
                    selectedProvince = provinceList.get(index);
                    queryCities();
                } else if (currentLevel == LEVEL_CITY) {
                    selectedCity = cityList.get(index);
                    queryCounties();
                }else if(currentLevel == LEVEL_COUNTY){
                    String countyCode=countyList.get(index).getCountyCode();
                    Intent intent=new Intent(ChooseAreaActivity.this, WeatherActivity.class);
                    intent.putExtra("county_code", countyCode);
                    startActivity(intent);
                    finish();
                }
            }
        });
        queryProvinces();//加载省级数据
    }

    /**
     * 查询全国所有的省份,优先从数据库查询,如果数据库上没有查询到再去服务器上查询
     */
    private void queryProvinces() {
        // TODO Auto-generated method stub
        System.out.println("进入queryProvince方法");
        provinceList = dwWeatherDB.loadProvinces();
        System.out.println(provinceList.size()+"----------");
        if (provinceList.size() > 0) {
            dataList.clear();
            for (Province province : provinceList) {
                dataList.add(province.getProvinceName());
                System.out.println(dataList.toString());
            }
            adapter.notifyDataSetChanged();// 刷新
            listView.setSelection(0);
            titleText.setText("中国");
            currentLevel = LEVEL_PROVINCE;
        } else {
            queryFromServer(null, "province");
            System.out.println("服务器查询方法执行完毕");
        }
        System.out.println("queryProvince方法执行完毕");
    }

    /**
     * 查询全国所有的市,优先从数据库查询,如果数据库上没有查询到再去服务器上查询
     */

    private void queryCities() {
        // TODO Auto-generated method stub
        cityList = dwWeatherDB.loadCities(selectedProvince.getId());
        if (cityList.size() > 0) {
            dataList.clear();
            for (City city : cityList) {
                dataList.add(city.getCityName());
            }
            adapter.notifyDataSetChanged();// 刷新
            listView.setSelection(0);
            titleText.setText(selectedProvince.getProvinceName());
            currentLevel = LEVEL_CITY;
        } else {
            queryFromServer(selectedProvince.getProvinceCode(), "city");
        }

    }

    private void queryCounties() {
        // TODO Auto-generated method stub
        countyList = dwWeatherDB.loadCounties(selectedCity.getId());
        if (countyList.size() > 0) {
            dataList.clear();
            for (County county : countyList) {
                dataList.add(county.getCountyName());
            }
            adapter.notifyDataSetChanged();// 刷新
            listView.setSelection(0);
            titleText.setText(selectedProvince.getProvinceName());
            currentLevel = LEVEL_CITY;
        } else {
            queryFromServer(selectedCity.getCityCode(), "county");
        }
    }

    /**
     * 根据传入的代号和类型从服务器上查询市县数据
     * 
     * @param object
     * @param string
     */
    private void queryFromServer(final String code, final String type) {
        // TODO Auto-generated method stub
        String address;
        if (!TextUtils.isEmpty(code)) {
            address = "http://www.weather.com.cn/data/list3/city" + code
                    + ".xml";
        } else {
            address = "http://www.weather.com.cn/data/list3/city.xml";
        }
        showProgressDialog();

        HttpUtil.sendHttpRequest(address, new HttpCallbackListener() {

            @Override
            public void onFinish(String response) {
                // TODO Auto-generated method stub
                boolean result = false;
                if ("province".equals(type)) {
                    result = Utility.handleProvincesResponse(dwWeatherDB,
                            response);
                } else if ("city".equals(type)) {
                    result = Utility.handleCitiesResponse(dwWeatherDB,
                            response, selectedProvince.getId());
                } else if ("county".equals(type)) {
                    result = Utility.handleCountiesResponse(dwWeatherDB,
                            response, selectedCity.getId());
                }
                if (result) {
                    // 通过runOnUiThread方法回到主线程处理逻辑
                    runOnUiThread(new Runnable() {

                        @Override
                        public void run() {
                            // TODO Auto-generated method stub
                            closeProgressDialog();
                            if ("province".equals(type)) {
                                queryProvinces();
                            } else if ("city".equals(type)) {
                                queryCities();
                            } else if ("county".equals(type)) {
                                queryCounties();
                            }
                        }
                    });
                }
            }

            @Override
            public void onError(Exception e) {
                // TODO Auto-generated method stub
                runOnUiThread(new Runnable() {

                    @Override
                    public void run() {
                        // TODO Auto-generated method stub
                        closeProgressDialog();
                        Toast.makeText(ChooseAreaActivity.this, "加载失败!",
                                Toast.LENGTH_SHORT).show();
                    }
                });
            }
        });
    }

    /**
     * 显示加载进度
     */
    private void showProgressDialog() {
        // TODO Auto-generated method stub
        if (progressDialog == null) {
            progressDialog = new ProgressDialog(this);
            progressDialog.setMessage("正在玩命加载...");
            progressDialog.setCanceledOnTouchOutside(false);
        }
        progressDialog.show();

    }

    private void closeProgressDialog() {
        if (progressDialog != null) {
            progressDialog.dismiss();
        }
    }

    /**
     * 根据当前的级别来判断是返回市列表、省列表还是直接退出
     */
    @Override
    public void onBackPressed() {
        // TODO Auto-generated method stub
        if (currentLevel == LEVEL_COUNTY) {
            queryCities();
        } else if (currentLevel == LEVEL_CITY) {
            queryProvinces();
        } else {
            if(isFromWeatherActivity){
                Intent intent=new Intent(this, WeatherActivity.class);
                startActivity(intent);
            }
            finish();
        }
    }
}

2.WeatherActivity.java

package com.dw.dwweather.activity;

import com.dw.dwweather.service.AutoUpdateService;
import com.dw.dwweather.util.HttpCallbackListener;
import com.dw.dwweather.util.HttpUtil;
import com.dw.dwweather.util.Utility;

import android.app.Activity;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Bundle;
import android.preference.PreferenceManager;
import android.text.TextUtils;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.Window;
import android.widget.Button;
import android.widget.LinearLayout;
import android.widget.TextView;

public class WeatherActivity extends Activity implements OnClickListener {
    private LinearLayout weatherInfoLayout;
    private TextView cityNameText;
    private TextView publishText;
    private TextView weatherDespText;
    private TextView temp1Text;
    private TextView temp2Text;
    private TextView curretnDateText;
    private Button switchCity;
    private Button refreshWeather;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        setContentView(R.layout.weather_layout);
        weatherInfoLayout=(LinearLayout) findViewById(R.id.weather_info_layout);
        cityNameText=(TextView) findViewById(R.id.city_name);
        publishText=(TextView) findViewById(R.id.publish_text);
        weatherDespText=(TextView) findViewById(R.id.weather_desp);
        temp1Text=(TextView) findViewById(R.id.temp1);
        temp2Text=(TextView) findViewById(R.id.temp2);
        curretnDateText=(TextView) findViewById(R.id.current_date);
        switchCity=(Button) findViewById(R.id.switch_city);
        refreshWeather=(Button) findViewById(R.id.refresh_weather);

        String countyCode=getIntent().getStringExtra("county_code");
        if(!TextUtils.isEmpty(countyCode)){
            publishText.setText("同步中...");
            weatherInfoLayout.setVisibility(View.INVISIBLE);
            cityNameText.setVisibility(View.INVISIBLE);
            queryWeatherCode(countyCode);
        }
        switchCity.setOnClickListener(this);
        refreshWeather.setOnClickListener(this);

    }

    @Override
    public void onClick(View v) {
        // TODO Auto-generated method stub
        switch(v.getId()){
        case R.id.switch_city:
            Intent intent=new Intent(this, ChooseAreaActivity.class);
            intent.putExtra("from_weather_activity", true);
            startActivity(intent);
            finish();
            break;
        case R.id.refresh_weather:
            publishText.setText("同步中...");
            SharedPreferences prefs=PreferenceManager.getDefaultSharedPreferences(this);
            String weatherCode=prefs.getString("weather_code", "");
            if(!TextUtils.isEmpty(weatherCode)){
                queryWeatherInfo(weatherCode);
            }
            break;
        default:
            break;
        }

    }
    /**
     * 查询天气代号所对应的天气
     * @param countyCode
     */
    private void queryWeatherCode(String countyCode) {
        // TODO Auto-generated method stub
        String address="http://www.weather.com.cn/data/list3/city"+countyCode+".xml";
        queryFromServer(address,"countyCode");

    }

    /**
     * 查询县级代号对应的天气
     * @param weatherCode
     */
    private void queryWeatherInfo(String weatherCode) {
        // TODO Auto-generated method stub
        String address="http://www.weather.com.cn/data/cityinfo"+weatherCode+".html";
        queryFromServer(address,"weatherCode");


    }
    /**
     * 根据传入的地址和类型向服务器查询天气代号或者天气信息
     * @param address
     * @param string
     */
    private void queryFromServer(final String address, final String type) {
        // TODO Auto-generated method stub
        HttpUtil.sendHttpRequest(address, new HttpCallbackListener() {

            @Override
            public void onFinish(final String response) {
                // TODO Auto-generated method stub
                if("countyCode".equals(type)){
                    if(!TextUtils.isEmpty(response)){
                        String[] array=response.split("\\|");
                        if(array!=null&&array.length==2){
                            String weatherCode=array[1];
                            queryWeatherInfo(weatherCode);
                        }
                    }
                }else if("weatherCode".equals(type)){
                    //处理从服务器返回的天气信息
                    Utility.handleWeatherResponse(WeatherActivity.this, response);
                    runOnUiThread(new Runnable() {

                        @Override
                        public void run() {
                            // TODO Auto-generated method stub
                            showWeather();

                        }

                    });
                }

            }

            @Override
            public void onError(Exception e) {
                // TODO Auto-generated method stub
                runOnUiThread(new Runnable() {

                    @Override
                    public void run() {
                        // TODO Auto-generated method stub
                        publishText.setText("同步失败");

                    }
                });

            }
        });

    }
    /**
     * 从sharedPreferences中读取存储的天气信息,并显示到界面上
     */
    private void showWeather() {
        // TODO Auto-generated method stub
        SharedPreferences prefs=PreferenceManager.getDefaultSharedPreferences(this);
        cityNameText.setText(prefs.getString("city_name", ""));
        temp1Text.setText(prefs.getString("temp1", ""));
        temp2Text.setText(prefs.getString("temp2", ""));
        weatherDespText.setText(prefs.getString("weather_desp", ""));
        publishText.setText(prefs.getString("publish_time", "")+"发布");
        curretnDateText.setText(prefs.getString("current_date", ""));
        weatherInfoLayout.setVisibility(View.INVISIBLE);
        cityNameText.setVisibility(View.INVISIBLE);

        Intent intent=new Intent(this, AutoUpdateService.class);
        startService(intent);
    }
}

三、数据库操作

1.DwWeatherOpenHelper.java

package com.dw.dwweather.db;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteDatabase.CursorFactory;
import android.database.sqlite.SQLiteOpenHelper;

public class DwWeatherOpenHelper extends SQLiteOpenHelper {
    public DwWeatherOpenHelper(Context context, String name,
            CursorFactory factory, int version) {
        super(context, name, factory, version);
        // TODO Auto-generated constructor stub
    }

    public static final String CREATE_PROVINCE="create table Province ("
            +"id integer primary key autoincrement,"
            +"province_name text,"
            +"province_code text)";

    public static final String CREATE_CITY="create table City ("
            +"id integer primary key autoincrement,"
            +"city_name text,"
            +"city_code text"
            +"city_id integer)";

    public static final String CREATE_COUNTY="create table County ("
            +"id integer primary key autoincrement,"
            +"county_name text,"
            +"county_code text"
            +"city_id integer)";

    @Override
    public void onCreate(SQLiteDatabase db) {
        // TODO Auto-generated method stub
        db.execSQL(CREATE_PROVINCE);
        db.execSQL(CREATE_CITY);
        db.execSQL(CREATE_COUNTY);
    }

    @Override
    public void onUpgrade(SQLiteDatabase arg0, int arg1, int arg2) {
        // TODO Auto-generated method stub

    }}

2.DwWeatherDB.java

package com.dw.dwweather.db;

import java.util.ArrayList;
import java.util.List;

import com.dw.dwweather.model.City;
import com.dw.dwweather.model.County;
import com.dw.dwweather.model.Province;

import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;

public class DwWeatherDB {
    public static final String DB_NAME="dw_weather";
    public static final int VERSION=1;
    private static DwWeatherDB dwWeatherDB;
    private SQLiteDatabase db;
    /**
     * 构造方法私有化
     * @param context
     */
    private DwWeatherDB(Context context) {
        // TODO Auto-generated constructor stub
        DwWeatherOpenHelper dbHelper=new DwWeatherOpenHelper(context, DB_NAME, null, VERSION);
        db=dbHelper.getWritableDatabase();
    }
    /**
     * 获取DwWeatherDB实例
     * @param context
     * @return
     */
    public synchronized static DwWeatherDB getInstance(Context context){
        if(dwWeatherDB==null){
            dwWeatherDB=new DwWeatherDB(context);
        }
        return dwWeatherDB;
    }
    /**
     * 将Province实例存储到数据库
     * @param province
     */
    public void saveProvince(Province province){
        if(province!=null){
            ContentValues values=new ContentValues();
            values.put("province_name", province.getProvinceName());
            values.put("province_code", province.getProvinceCode());
            db.insert("Province", null, values);
        }
    }
    /**
     * 从数据库获取全国所有的省份信息
     * @return
     */
    public List<Province> loadProvinces(){
        System.out.println("进入loadProvinces方法");
        List<Province> list=new ArrayList<Province>();
        Cursor cursor=db.query("Province", null, null, null, null, null, null);
        if(cursor.moveToFirst()){
            do {
                Province province=new Province();
                province.setId(cursor.getInt(cursor.getColumnIndex("id")));
                province.setProvinceName(cursor.getString(cursor.getColumnIndex("province_name")));
                province.setProvinceCode(cursor.getString(cursor.getColumnIndex("province_code")));
                list.add(province);
            } while (cursor.moveToNext());
        }
        System.out.println("loadProvinces方法执行完毕");
        return list;
    }
    /**
     * 将City实例存储到数据库
     * @param province
     */
    public void saveCity(City city){
        if(city!=null){
            ContentValues values=new ContentValues();
            values.put("city_name", city.getCityName());
            values.put("city_code", city.getCityCode());
            values.put("province_id", city.getProvinceId());
            db.insert("City", null, values);
        }
    }
    /**
     * 从数据库读取某省份下所有的城市信息
     * @param provinceId
     * @return
     */
    public List<City> loadCities(int provinceId){
        List<City> list=new ArrayList<City>();
        Cursor cursor=db.query("City", null, "province_id=?", 
                new String[]{String.valueOf(provinceId)}, null,null,null);
        if(cursor.moveToFirst()){
            do {
                City city=new City();
                city.setId(cursor.getInt(cursor.getColumnIndex("id")));
                city.setCityName(cursor.getString(cursor.getColumnIndex("city_name")));
                city.setCityCode(cursor.getString(cursor.getColumnIndex("city_code")));
                city.setProvinceId(provinceId);
                list.add(city);
            } while (cursor.moveToNext());
        }
        return list;

    }
    /**
     * 将County实例存储到数据库
     * @param province
     */
    public void saveCounty(County county){
        if(county!=null){
            ContentValues values=new ContentValues();
            values.put("county_name", county.getCountyName());
            values.put("county_code", county.getCountyCode());
            values.put("city_id", county.getCityId());
            db.insert("County", null, values);
        }
    }
    /**
     * 从数据库读取某省份下某城市下所有县城信息
     * @param provinceId
     * @return
     */
    public List<County> loadCounties(int cityId){
        List<County> list=new ArrayList<County>();
        Cursor cursor=db.query("County", null, "city_id=?", 
                new String[]{String.valueOf(cityId)}, null,null,null);
        if(cursor.moveToFirst()){
            do {
                County county=new County();
                county.setId(cursor.getInt(cursor.getColumnIndex("id")));
                county.setCountyName(cursor.getString(cursor.getColumnIndex("county_name")));
                county.setCountyCode(cursor.getString(cursor.getColumnIndex("county_code")));
                county.setCityId(cityId);
                list.add(county);
            } while (cursor.moveToNext());
        }
        return list;

    }

}

四、地区模型层
1.City.java

package com.dw.dwweather.model;

public class City {
    private int id;
    private String cityName;
    private String cityCode;
    private int provinceId;
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public String getCityName() {
        return cityName;
    }
    public void setCityName(String cityName) {
        this.cityName = cityName;
    }
    public String getCityCode() {
        return cityCode;
    }
    public void setCityCode(String cityCode) {
        this.cityCode = cityCode;
    }
    public int getProvinceId() {
        return provinceId;
    }
    public void setProvinceId(int provinceId) {
        this.provinceId = provinceId;
    }

}

2.County.java

package com.dw.dwweather.model;

public class County {
    private int id;
    private int cityId;
    private String countyName;
    private String countyCode;
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public int getCityId() {
        return cityId;
    }
    public void setCityId(int cityId) {
        this.cityId = cityId;
    }
    public String getCountyName() {
        return countyName;
    }
    public void setCountyName(String countyName) {
        this.countyName = countyName;
    }
    public String getCountyCode() {
        return countyCode;
    }
    public void setCountyCode(String countyCode) {
        this.countyCode = countyCode;
    }


}

3.Province.java

package com.dw.dwweather.model;

public class Province {
    private int id;
    private String provinceName;
    private String provinceCode;
    public int getId() {
        return id;
    }
    public void setId(int id) {
        this.id = id;
    }
    public String getProvinceName() {
        return provinceName;
    }
    public void setProvinceName(String provinceName) {
        this.provinceName = provinceName;
    }
    public String getProvinceCode() {
        return provinceCode;
    }
    public void setProvinceCode(String provinceCode) {
        this.provinceCode = provinceCode;
    }


}

五、更新广播与更新服务
1.AutoUpdateReceiver.java

package com.dw.dwweather.receiver;

import com.dw.dwweather.service.AutoUpdateService;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;

public class AutoUpdateReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        // TODO Auto-generated method stub
        Intent i=new Intent(context, AutoUpdateService.class);
        context.startService(i);

    }

}

2.AutoUpdateService.java

package com.dw.dwweather.service;

import com.dw.dwweather.receiver.AutoUpdateReceiver;
import com.dw.dwweather.util.HttpCallbackListener;
import com.dw.dwweather.util.HttpUtil;
import com.dw.dwweather.util.Utility;

import android.app.AlarmManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.IBinder;
import android.os.SystemClock;
import android.preference.PreferenceManager;

public class AutoUpdateService extends Service {

    @Override
    public IBinder onBind(Intent arg0) {
        // TODO Auto-generated method stub
        return null;
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        // TODO Auto-generated method stub
        new Thread(new Runnable() {

            @Override
            public void run() {
                // TODO Auto-generated method stub
                updateWeather();
            }
        }).start();
        AlarmManager manager=(AlarmManager) getSystemService(ALARM_SERVICE);
        int time=8*60*60*1000;
        long triggerAtTime=SystemClock.elapsedRealtime()+time;
        Intent i=new Intent(this, AutoUpdateReceiver.class);
        PendingIntent pi=PendingIntent.getBroadcast(this, 0, i, 0);
        manager.set(AlarmManager.ELAPSED_REALTIME_WAKEUP, triggerAtTime, pi);

        return super.onStartCommand(intent, flags, startId);
    }
/**
 * 更新天气信息
 */
    private void updateWeather() {
        // TODO Auto-generated method stub
        SharedPreferences prefs=PreferenceManager.getDefaultSharedPreferences(this);
        String weatherCode=prefs.getString("weather_code", "");
        String address="http://www.weather.com.cn/data/cityinfo/"+weatherCode+".html";
        HttpUtil.sendHttpRequest(address, new HttpCallbackListener() {

            @Override
            public void onFinish(String response) {
                // TODO Auto-generated method stub
                Utility.handleWeatherResponse(AutoUpdateService.this, response);
            }

            @Override
            public void onError(Exception e) {
                // TODO Auto-generated method stub
                e.printStackTrace();

            }
        });
    }
}

六、工具类
1.HttpCallbackListener.java

package com.dw.dwweather.util;

public interface HttpCallbackListener {

    void onFinish(String response);

    void onError(Exception e);

}

2.HttpUtil.java

package com.dw.dwweather.util;

import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;

public class HttpUtil {
    public static void sendHttpRequest(final String address,final HttpCallbackListener listener){
        new Thread(new Runnable() {

            @Override
            public void run() {
                // TODO Auto-generated method stub
                HttpURLConnection connection=null;
                try {
                    URL url=new URL(address);
                    connection=(HttpURLConnection) url.openConnection();
                    connection.setRequestMethod("GET");
                    connection.setConnectTimeout(8000);
                    connection.setReadTimeout(8000);
                    InputStream in=connection.getInputStream();
                    BufferedReader reader=new BufferedReader(new InputStreamReader(in));
                    StringBuilder response=new StringBuilder();
                    String line;
                    while (listener!=null) {
                        //回调onFinish方法
                        listener.onFinish(response.toString());
                    }
                } catch (Exception e) {
                    // TODO: handle exception
                    if(listener!=null){
                        listener.onError(e);
                    }
                }finally{
                    if(connection!=null){
                        connection.disconnect();
                    }
                }
            }
        }).start();
    }

}

3.Utility.java

package com.dw.dwweather.util;

import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;

import org.json.JSONException;
import org.json.JSONObject;

import android.content.Context;
import android.content.SharedPreferences;
import android.preference.PreferenceManager;
import android.text.TextUtils;

import com.dw.dwweather.db.DwWeatherDB;
import com.dw.dwweather.model.City;
import com.dw.dwweather.model.County;
import com.dw.dwweather.model.Province;

public class Utility {
    /**
     * 解析和处理服务器返回的省级数据
     */
    public synchronized static boolean handleProvincesResponse(
            DwWeatherDB dwWeatherDB, String response) {
        if (!TextUtils.isEmpty(response)) {
            String[] allProvinces = response.split(",");
            if (allProvinces != null && allProvinces.length > 0) {
                for (String p : allProvinces) {
                    String[] array = p.split("\\|");
                    Province province = new Province();
                    province.setProvinceCode(array[0]);
                    province.setProvinceName(array[1]);
                    // 将解析处理的数据存储到Procince表
                    dwWeatherDB.saveProvince(province);
                }
                return true;
            }
        }
        return false;
    }

    /**
     * 解析和处理服务器返回的市级数据
     */
    public synchronized static boolean handleCitiesResponse(
            DwWeatherDB dwWeatherDB, String response, int provinceId) {
        if (!TextUtils.isEmpty(response)) {
            String[] allCities = response.split(",");
            if (allCities != null && allCities.length > 0) {
                for (String c : allCities) {
                    String[] array = c.split("\\|");
                    City city = new City();
                    city.setCityCode(array[0]);
                    city.setCityName(array[1]);
                    city.setProvinceId(provinceId);
                    // 将解析处理的数据存储到Procince表
                    dwWeatherDB.saveCity(city);
                }
                return true;
            }
        }
        return false;
    }

    /**
     * 解析和处理服务器返回的级数据
     */
    public synchronized static boolean handleCountiesResponse(
            DwWeatherDB dwWeatherDB, String response, int cityId) {
        if (!TextUtils.isEmpty(response)) {
            String[] allCounties = response.split(",");
            if (allCounties != null && allCounties.length > 0) {
                for (String c : allCounties) {
                    String[] array = c.split("\\|");
                    County county = new County();
                    county.setCountyCode(array[0]);
                    county.setCountyName(array[1]);
                    county.setCityId(cityId);

                    // 将解析处理的数据存储到Procince表
                    dwWeatherDB.saveCounty(county);
                }
                return true;
            }
        }
        return false;
    }

    /**
     * 解析服务器返回的json数据,并将解析处理的数据存储到本地
     */
    public static void handleWeatherResponse(Context context, String response) {
        try {
            JSONObject jsonObject = new JSONObject(response);
            JSONObject weatherInfo = jsonObject.getJSONObject("weatherinfo");
            String cityName = weatherInfo.getString("city");
            String weatherCode = weatherInfo.getString("cityid");
            String temp1 = weatherInfo.getString("temp1");
            String temp2 = weatherInfo.getString("temp2");
            String weatherDesp = weatherInfo.getString("weather");
            String publishTime = weatherInfo.getString("ptime");
            saveWeatherInfo(context, cityName, weatherCode, temp1, temp2,
                    weatherDesp, publishTime);

        } catch (JSONException e) {
            // TODO: handle exception
            e.printStackTrace();
        }

    }

    /**
     * 将服务器返回的所有天气信息存储到sharedPreference文件
     * 
     * @param context
     * @param cityName
     * @param weatherCode
     * @param temp1
     * @param temp2
     * @param weatherDesp
     * @param publishTime
     */
    public static void saveWeatherInfo(Context context, String cityName,
            String weatherCode, String temp1, String temp2, String weatherDesp,
            String publishTime) {
        // TODO Auto-generated method stub
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy年M月d日", Locale.CHINA);
        SharedPreferences.Editor editor = PreferenceManager
                .getDefaultSharedPreferences(context).edit();
        editor.putBoolean("city_selected", true);
        editor.putString("city_name", cityName);
        editor.putString("weather_code", weatherCode);
        editor.putString("temp1", temp1);
        editor.putString("temp2", temp2);
        editor.putString("weather_desp", weatherDesp);
        editor.putString("publish_time", publishTime);
        editor.putString("current_date", sdf.format(new Date()));
        editor.commit();
    }
}

完整项目见Github (https://github.com/Arthur0213/DwWeather)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值