画像切り替え、ディレクトリの移動など動作OKなので、重い処理で待機している時の円形プログレスバーを組み込みたい。
プログレス オン()
処理()
プログレス オフ()
やっちまった。
アンドロイドプログラミング初心者あるある。だそう。
OSは、マルチで動いていてもアプリはシングルらしい。
プログレスバーもメインスレッドの一部の時間を上手く使って動いてる。
処理が長時間占有するとプログレスバーは止まるという事。
プログレスバーはUIなのでメインで使うルール。
処理を別スレッドで実行させないとグルグルが回らない。
まず、円形プログレスバー。
【activity_main.xml】
< ProgressBar
android:id="@+id/progress_circular"
style="@style/Widget.AppCompat.ProgressBar"
android:layout_width="100dp"
android:layout_height="100dp" />
大きさを変える時は、layout_width="100dp" サイズ指定。大きくしすぎるとボケる。
別デザインあり。ちょっと気に入らない。
要望などなど。
別スレッドを作る時に引数を渡して戻り値を受け取りたい。
メモリリークに注意する。
AsyncTask、Handlerは、非推奨になるらしい。
Thread、Runnableを使っての別スレッドを実行。
色々検索して、EventListener インターフェースを新設することで戻り値を受け取れると分かった。
スレッド内のメモリを解放、参照を切ること。
インターフェースは、これ。
テストでビットマップを受け取ってみる。
【MyEventListener.java】
public interface MyEventListener extends EventListener {
void onMyEvent(Bitmap bitmap);
}
スレッドでの処理。
【MyRunnable.java】
public class MyRunnable implements Runnable {
private MyMainData mainData;
private MyEventListener mEventListener = null;
private Bitmap mBitmap = null;
MyRunnable(MyMainData mainData ) {
this.mainData = mainData;
}
public void setEventListener( MyEventListener listener ) {
this.mEventListener = listener;
}
public void removeEventListener() {
this.mEventListener = null;
}
@Override
public void run() {
try {
File file = new File(mainData.getTargetFilePath());
InputStream isf1 = new FileInputStream(file);
mBitmap = BitmapFactory.decodeStream(isf1);
isf1.close();
} catch (Exception e) {
e.printStackTrace();
}
if ( this.mEventListener != null && mBitmap != null ) {
this.mEventListener.onMyEvent( mBitmap );
}
mainData = null;
mEventListener = null;
mBitmap = null;
}
}
タイミング的に後始末が良いのか不安が残る。
イベントリスナー宣言内ではUI操作はエラーとならない。
受け取ったビットマップをコピーしてImageViewに設定している。
スレッド内で確保したビットマップをrecycle()で解放。
一時的に同じビットマップを2面利用するのが気になるが今はスルー。
【MainActivity.java】
MyRunnable test = new MyRunnable( mainData );
test.setEventListener( new MyEventListener() {
@Override
public void onMyEvent(Bitmap bitmap) {
MyImageView view = mainData.getTargetImageView();
view.scrollTo(0, 0);
view.setImageBitmap( bitmap.copy( Bitmap.Config.ARGB_8888, true ) );
mainPage.setPaddingImageView(view, bitmap.getWidth(), bitmap.getHeight());
bitmap.recycle();
}
});
Thread th = new Thread( test );
th.start();
テストは動作問題なし。メモリ状況は確認できず。
どうなんだろう?