相信很多人在剛接觸Android時都會做一個天氣預報來了解Android,今天得空整理了一個簡單Android天氣預報Demo的製作,如下:
首先我們應該做的便是搞到一個天氣預報的API以此來獲取一個Android天氣預報的數據,在這裏我推薦註冊和風天氣個人開發者,認證時間1-3天,基本一下子就可以收到了認證成功的郵件。認證開發者後可以獲得中國和海外城市的7天預報、逐3小時預報、實況天氣、空氣質量和生活指數,對比了一下其它家,和風真是算良心接口了,雖然我只需要實況天氣這一個數據。不過讀者也可以利用這個接口繼續完善這個Android天氣預報~~~~
和風天氣API網址:https://www.heweather.com/douments/api/s6/weather-forecast 各位看官可以去裏面註冊獲得key就可以繼續開發天氣預報啦
1、配置參數
既然涉及到了網絡請求,肯定應該想到的時權限所以我們先添加個權限,在AndroidManifest中添加
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
然後我這裏使用的是okhttp所以添加okhttp的依賴,在app下的build.gradle中的dependencies下添加
compile 'com.squareup.okhttp3:okhttp:3.6.0'
2、好了,該配置的都配置完了。我們接下來就製作佈局吧。佈局我就截個圖大家可以自由製作
3、製作完佈局後,我們就繼續回到Java代碼中首先先初始化各種控件這個就不過多說明
4、接下來開始請求接口了,這裏我是個按鈕添加的點擊事件然後調用的search方法如下:
public void search() {
Log.d(TAG, "search: 1111");
OkHttpClient client = new OkHttpClient();
String uri = "https://free-api.heweather.com/s6/weather?location=" + cityItem.getSelectedItem().toString() + "&key=你在和風天氣上申請的key";
Request request = new Request.Builder()
.url(uri)
.build();
final Call call = client.newCall(request);
new Thread(new Runnable() {
@Override
public void run() {
Log.d(TAG, "run: 222222");
call.enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
Log.d(TAG, "onResponse: " + e);
}
@Override
public void onResponse(Call call, Response response) throws IOException {
Message message=new Message();
message.what=1;
message.obj=response.body().string();
handler.sendMessage(message);
}
});
}
}).start();
}
這裏我們是先將城市和key拼接一個GET請求,然後封裝至okhttp的Call中開啓線程去請求,大家千萬要注意Android的禁忌那就是不能在子線程更新UI,這個是千萬不能去碰的,所以我這裏使用了handler的方法回到主線程更新UI。
5、handler的使用,首先我們需要創建一個全局的handler來接受子線程或其他地方傳來的消息
private Handler handler = new Handler() {
@Override
public void handleMessage(Message msg) {
if (msg.what==1){
String result=msg.obj.toString();
updateUI(result);
Log.d(TAG, "handleMessage: "+result);
}
}
};
這裏面的msg.what==1就是一個標識符,代表你從哪傳來的我們在請求成功後就發送消息,上面代碼子線程中便有寫到,如下:
先製作一個Message消息然後將接口請求後的數據放入message中發出,我們就可以在之前定義的全局handler中去處理這個結果,在裏面調用更新UI的方法。
6、更新UI,我們先來看一下天氣預報接口返回的數據吧
他這裏返回的JSON是一層套一層,不過我們不要着急,一步一步的來解析,在這個項目中我使用的是Android自帶的json工具來解析的,好了,我們繼續。我們就已拿 "now" 現在的數據舉例吧。
首先我們看到最外層的 "HeWeather6" ,它的後面是一個 [ ] 包含的數據,所以我們可以得知他是一個JSONArray於是外面我們先使用Android的JSONArray來獲取它裏面的數據
JSONArray jsonArray=new JSONObject(result).getJSONArray("HeWeather6");
我們進去之後呢就看到了一個 { } 的符號將所有數據都包攬起來了這就代表了只是一個JSONObject,我們再來用剛剛獲取到的jsonarray來獲取這個JSONObject,如下:
JSONObject jsonObject=jsonArray.getJSONObject(0);
好了現在我們已經到很裏面了,可以看到都是一個 " "加 { } 的結構這代表這他們都是有名字的JSONObject,我們繼續來獲取我們想要的 "now"
JSONObject now=jsonObject.getJSONObject("now");
OK,我們已經獲取到了,接下來就把它裏面的一個個數據放到頁面中吧。更新UI的詳細方法如下:
public void updateUI(String result){
try {
SimpleDateFormat simpleDateFormat=new SimpleDateFormat("yyyy-MM-dd");
timeText.setText(simpleDateFormat.format(new Date()));
JSONArray jsonArray=new JSONObject(result).getJSONArray("HeWeather6");
JSONObject jsonObject=jsonArray.getJSONObject(0);
JSONObject now=jsonObject.getJSONObject("now");
cityText.setText(cityItem.getSelectedItem().toString());
nowWeather.setText(now.get("cond_txt")+"");
nowTmp.setText(now.get("tmp")+"℃");
nowWindDir.setText(now.get("wind_dir")+"");
nowWindSc.setText(now.get("wind_sc")+"級");
JSONArray jsonArray1=jsonObject.getJSONArray("daily_forecast");
JSONObject todayJson= (JSONObject) jsonArray1.get(0);
tmpMaxText.setText(todayJson.get("tmp_max")+"℃");
tmpMinText.setText(todayJson.get("tmp_min")+"℃");
dayTimeText.setText(todayJson.get("cond_txt_d")+"");
nightText.setText(todayJson.get("cond_txt_n")+"");
windDirText.setText(todayJson.get("wind_dir")+"");
windScText.setText(todayJson.get("wind_sc")+"級");
JSONObject tomorrowJson= (JSONObject) jsonArray1.get(1);
tomorrowTmpText.setText(tomorrowJson.get("cond_txt_d")+"");
tomorrowCondText.setText(tomorrowJson.get("tmp_min")+"-"+tomorrowJson.get("tmp_max")+"℃");
Log.d(TAG, "updateUI: "+todayJson);
Log.d(TAG, "updateUI: "+jsonArray);
Log.d(TAG, "updateUI: "+now);
} catch (JSONException e) {
e.printStackTrace();
}
到這裏我們這個Android天氣預報就已經全部完成了,大家有什麼不懂的可以留言,我會及時回覆的。最後將源碼放上,以供大家參考。Android天氣預報Demo源碼