アプリケーションの次の作業フローがあります。メイン アクティビティには、クリック後に 2 番目のアクティビティを開始するボタンがあります。2 番目のアクティビティにはTextView
、指定されたジオポイントにある都市を示す があります。この都市を見つけるために、バックグラウンド スレッドで作成するGeocoderにリクエストを送信します。
私が期待すること: 2 番目のアクティビティが (ほぼ) すぐに開始され、バックグラウンド スレッドが要求を終了すると、UI スレッドがTextView
コンテンツを更新します。
何が起こるか: 2 番目のアクティビティは、そのジョブが終了したときにのみ開始されます。Geocoder
Wi-Fi をオフにしてボタンをクリックできることを明確にするために、5 ~ 6 秒Geocoder
待ち、ジオポイントを取得できなかったことを示すメッセージがログに表示された直後に、2 番目のアクティビティが起動します。
私が間違っていることは何ですか?関連するコードを以下に示します。完全なサンプル プロジェクトはgithub にあります。
public class SecondActivity extends Activity implements Handler.Callback {
private HandlerThread mHandlerThread = new HandlerThread("BackgroundThread");
private Handler mUIHandler;
private Handler mBackgroundHandler;
private TextView mLocationView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_second);
mLocationView = (TextView) findViewById(R.id.location_name);
mUIHandler = new Handler(getMainLooper(), this);
mHandlerThread.start();
mBackgroundHandler = new Handler(mHandlerThread.getLooper()) {
@Override
public void handleMessage(Message msg) {
if (msg.what == 0) {
final Geocoder geocoder = new Geocoder(SecondActivity.this);
try {
final List<Address> results = geocoder.getFromLocation(53.539316, 49.396494, 1);
if (results != null && !results.isEmpty()) {
mUIHandler.dispatchMessage(Message.obtain(mUIHandler, 1, results.get(0)));
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
};
}
@Override
protected void onResume() {
super.onResume();
mBackgroundHandler.dispatchMessage(Message.obtain(mBackgroundHandler, 0));
}
@Override
public boolean handleMessage(Message msg) {
if (msg.what == 1) {
mLocationView.setText("I live in " + ((Address) msg.obj).getLocality());
return true;
}
return false;
}
}