UI部分を非同期処理させるよ
Android で UI 部分を非同期で処理させたい場合ってありますよね。
単にサービスやスレッドを利用しても可能でしょうが、もっと楽にできる方法があります。
その名も「AsyncTask」です。
AsyncTask
非同期処理を行う際の便利な API です。
冒頭でも述べましたが、これは UI の処理はさせたいけど別スレッドで処理させたい場合に便利です。
この処理の流れとしては、
「コンストラクタ(ここで View などを渡しておく)」→「バックグラウンド処理」→「UI への描画処理」
となっています。
ソースレベルで解説
Activity にて非同期処理の書かれたクラスをインスタンス化して、executeメソッドを実行します。
クラス名 task = new クラス名(view);
task.execute(何らかのデータ);
public class クラス名 extends AsyncTask<String, Integer, Drawable> { public DownloadTask(View v) { // View を受け取る処理 } protected Drawable doInBackground(String... uri) { // バックグラウンド処理。 // executeメソッドが呼ばれたら、このメソッドが初めに呼ばれる。 } protected void onPostExecute(Drawable draw) { // UIヘの描画処理。mainスレッドで実行したことになる。 // doInBackgroundメソッドの後で呼ばれる。 } }
ソース
私が書いた、画像を非同期通信で取得してくるソース。
単純にソースの一部を抽出しただけなので、おかしな点があるかもしれません。イメージを感じ取ってください。
// Activity // 画像をダウンロードして表示する private void downloadAndUpdateImage(View v, String imageStr) { DownloadTask task = new DownloadTask(v); task.execute(imageStr); }
public class DownloadTask extends AsyncTask<String, Integer, Drawable> { private View view; public DownloadTask(View v) { view = v; } public Drawable downloadImage(String uri) { URL url = null; try { url = new URL(uri); InputStream is = url.openStream(); Drawable draw = Drawable.createFromStream(is, ""); view.setTag(url.toExternalForm()); is.close(); return draw; } catch (MalformedURLException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } return null; } /** * 独自スレッドでバックグラウンド処理 * @param result */ protected Drawable doInBackground(String... uri) { return downloadImage(uri[0]); } /** * 画面描画できるmainスレッドで実行したい処理 */ protected void onPostExecute(Drawable draw) { view.setBackgroundDrawable(draw); } }
ソースはこちらに置いてます。全体を確認したい場合は参照してみてください。
まとめ
onCreateメソッド内で時間のかかる処理はできないため、一部表示させて後は非同期処理で行うのが良さそうですね。
色々と使いどころがありそうな API なので知っておいて損はないかと思います。
参考
throw Life -> 初めてのAndroid -第7章 世界との接続-
素晴らしいまとめです。私の記事なんか読むより大変参考になります。