WeatherActivity.java:
package com.<span style="font-family: Arial, Helvetica, sans-serif;">modongyelang.</span><span style="font-family: Arial, Helvetica, sans-serif;">weather;</span>
import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.text.DecimalFormat;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.util.EncodingUtils;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import org.json.JSONTokener;
import com.modongyelang.weather.R;
import android.app.AlertDialog;
import android.app.AlertDialog.Builder;
import android.app.Dialog;
import android.content.Context;
import android.content.DialogInterface;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.support.v7.app.ActionBarActivity;
import android.util.Log;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.Window;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.RelativeLayout;
import android.widget.TextView;
public class WeatherActivity extends ActionBarActivity {
private final String TAG = "Weather";
private final String sGetAddrUrl = "http://ip-api.com/json/";
private final String fileName = "/data/data/com.skyworth.weather/files/cityname.db";
private TextView mWeatherTemperature;
private ImageView mWeatherIcon;
private String iTemp = "";
private String cityName = "";
private String countryCode = "";
private Bitmap bitmap = null;
private Context context = null;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_weather);
context = this;
mWeatherTemperature = (TextView)findViewById(R.id.weathertemperature);
mWeatherIcon = (ImageView)findViewById(R.id.weathericon);
mWeatherTemperature.setOnClickListener(listener);
getLocateCityName();
}
/**
* 刷新天气信息
**/
private void refreshWeatherInfo(){
new Thread() {
@Override
public void run() {
try {
Log.i(TAG, "MyThread run");
//查看是否已经保存了城市名,如果已保存,则使用保存的城市名
File file = new File(fileName);
if(file.exists() && file.isFile()){
FileInputStream fis = new FileInputStream(file);
int length = fis.available();
byte[] content = new byte[length];
fis.read(content);
String res = EncodingUtils.getString(content, "UTF-8");
String[] contenArray = res.split(";");
cityName = contenArray[0];
countryCode = contenArray[1];
Log.i(TAG,"city : " + cityName + ",county : " + countryCode);
fis.close();
}
//通过城市名和国家编号来获取天气信息,使用JSON格式传递数据,此处并没有设置语言和温度单位选项
URL url = new URL("http://api.openweathermap.org/data/2.5/weather?q=" + cityName + "," + countryCode);
BufferedReader br = new BufferedReader(new InputStreamReader(url.openStream()));
String s = "";
StringBuffer sb = new StringBuffer("");
while ((s = br.readLine()) != null) {
sb.append(s + "\r\n");
}
br.close();
//获取到的JSON数据存到weatherContent字符串中
String weatherContent = "";
weatherContent = sb.toString();
Log.i(TAG, "weatherContent : " + weatherContent);
//解析JSON数据,先得到城市名
JSONTokener jsonParser = new JSONTokener(weatherContent);
JSONObject person = (JSONObject) jsonParser.nextValue();
Log.i(TAG,"weather : " + person.getString("name"));
cityName = person.getString("name");
//获取到天气信息的具体内容,主要是为了获取天气图标icon
JSONTokener weatherTokener = new JSONTokener(person.getString("weather"));
JSONArray weatherArray = (JSONArray)weatherTokener.nextValue();
JSONObject weather = (JSONObject)weatherArray.get(0);
Log.i(TAG,"weather : " + person.getString("weather"));
//main中存放的是温度值
JSONTokener mainTokener = new JSONTokener(person.getString("main"));
JSONObject main = (JSONObject)mainTokener.nextValue();
Log.i(TAG,"main : " + person.getString("main"));
//设置温度显示格式,默认获取到的是开氏温度,将其转换为摄氏温度
DecimalFormat fnum = new DecimalFormat("##0.0");
iTemp = fnum.format(Float.parseFloat(main.getString("temp")) - 273);
//获取天气图标
URL url1 = new URL("http://openweathermap.org/img/w/" + weather.getString("icon") + ".png");
HttpURLConnection conn = (HttpURLConnection)url1.openConnection();
conn.setConnectTimeout(10*1000);
conn.setDoInput(true);
conn.connect();
InputStream inputStream=conn.getInputStream();
Log.i(TAG,"start download image");
bitmap = BitmapFactory.decodeStream(inputStream);
inputStream.close();
conn.disconnect();
Message msg = new Message();
msg.what = 1;
mHandler.sendMessage(msg);
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
} catch (Exception e) {
e.printStackTrace();
}
}
}
}.start();
}
/**
* 通过Handler机制进行UI刷新
**/
private Handler mHandler = new Handler(){
@Override
public void handleMessage(Message msg) {
if(msg.what == 1){
if(!cityName.equals("") && !iTemp.equals(""))
mWeatherTemperature.setText(cityName + " " + iTemp + "°C");
else
mWeatherTemperature.setText("");
mWeatherIcon.setImageBitmap(bitmap);
}
};
};
/***
* 通过IP获取当前城市名
***/
private void getLocateCityName() {
new Thread() {
public void run() {
try {
Log.i(TAG, "getLocateCityName");
URL url = new URL(sGetAddrUrl);
BufferedReader br = new BufferedReader(new InputStreamReader(url.openStream()));
String s = "";
StringBuffer sb = new StringBuffer("");
while ((s = br.readLine()) != null) {
sb.append(s + "\r\n");
}
br.close();
String webContent = "";
webContent = sb.toString();
Log.i(TAG, "webContent : " + webContent);
JSONTokener jsonParser = new JSONTokener(webContent);
JSONObject person = (JSONObject) jsonParser.nextValue();
cityName = person.getString("city");
countryCode = person.getString("countryCode");
Log.i(TAG, "city Name : " + cityName);
Log.i(TAG, "query : " + person.getString("query"));
refreshWeatherInfo();
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
};
}.start();
}
/**
* 由外部来设置城市名
* @param city 要设置的城市名
*/
public void setCityName(String city){
this.cityName = city;
}
/**
* 监听WeatherTextView,弹出设置城市对话框
*/
private OnClickListener listener = new OnClickListener() {
@Override
public void onClick(View arg0) {
// TODO Auto-generated method stub
AlertDialog.Builder builder = new Builder(context);
builder.setTitle("Set City Name");
LayoutInflater inflater = getLayoutInflater();
RelativeLayout layout = (RelativeLayout) inflater.inflate(R.layout.dialog, (RelativeLayout)findViewById(R.id.dialog));
builder.setView(layout);
final EditText cityText = (EditText)layout.findViewById(R.id.cityedittext);
final EditText countryText = (EditText)layout.findViewById(R.id.countryedittext);
builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
String text = cityText.getText().toString();
if(!text.equals(null))
cityName = text;
text = countryText.getText().toString();
if(text.equals(null))
countryCode = text;
File file = new File(fileName);
if(!file.exists())
try {
file.createNewFile();
} catch (IOException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
FileOutputStream fos = null;
String content = cityName + ";" + countryCode;
Log.i(TAG, "content : " + content);
try {
fos = new FileOutputStream(file);
fos.write(content.getBytes());
fos.close();
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
refreshWeatherInfo();
dialog.dismiss();
}
});
builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
// TODO Auto-generated method stub
dialog.dismiss();
}
});
Dialog dialog = builder.create();
Window dialogWindow = dialog.getWindow();
dialogWindow.setGravity(Gravity.LEFT | Gravity.TOP);
dialog.show();
}
};
}
activity_weather.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"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.skyworth.weather.WeatherActivity$PlaceholderFragment" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world"
android:layout_alignParentLeft="true"
android:id="@+id/weathertemperature"
android:focusable="true"/>
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toRightOf="@id/weathertemperature"
android:id="@+id/weathericon"/>
</RelativeLayout>
dialog.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="@+id/dialog" >
<TextView
android:id="@+id/citytextview"
android:layout_width="70dp"
android:layout_height="40dp"
android:gravity="center"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:text="@string/city" />
<EditText
android:id="@+id/cityedittext"
android:layout_width="match_parent"
android:layout_height="40dp"
android:gravity="center"
android:hint="Shenzhen"
android:layout_toRightOf="@id/citytextview"
android:layout_alignBaseline="@id/citytextview"/>
<TextView
android:id="@+id/countrytextview"
android:layout_width="70dp"
android:layout_height="40dp"
android:gravity="center"
android:layout_below="@id/citytextview"
android:text="@string/country" />
<EditText
android:id="@+id/countryedittext"
android:layout_width="match_parent"
android:layout_height="40dp"
android:gravity="center"
android:hint="CN"
android:layout_toRightOf="@id/countrytextview"
android:layout_alignBaseline="@id/countrytextview"/>
</RelativeLayout>