2012/09/26

onActivityResult が呼ばれるタイミング

@Android 2.3.7  Xperia acro HD

onActivityResult は onResume の前に呼ばれるという記述をよく見かけるのですが、実はそんな単純じゃなさそうなので、調べて見ました。
Activity の一般的なライフサイクルについては以下に書きましたので参考にしてみてください。
穀風: ホームボタン と 戻るボタン で Activity の終了処理が異なる


今回は、ボタンが一つだけある Activity を用意して、ボタンを押した時に startActivityForResult を呼ぶ単純なテストを作成してみました。
コードは最後に載せてあります。
参考: Tech Boosterさんより

まず、一般的な Gallery 等を呼び出した場合のログは以下のようになりました。
ボタンを押した直後から、別アプリでの処理が終わって、Activityが表示されるまでをとったものです。空白行は、他のアプリが起動している間を表現するために私が追加したものです。
D/LifeCycleTest(22601): onSaveInstanceState
D/LifeCycleTest(22601): onPause
D/LifeCycleTest(22601): onStop

D/LifeCycleTest(22601): onActivityResult -1
D/LifeCycleTest(22601): onRestart
D/LifeCycleTest(22601): onStart
D/LifeCycleTest(22601): onResume

他の Activity が前に表示されるので、 onStop まで呼ばれるわけです。
この時、 onActivityResult は onRestart の前で呼ばれるようですね。

これに対し、Astro file manager 等のダイアログ風インターフェースをもつアプリケーションを呼んだ場合は以下のようになります。
D/LifeCycleTest(22601): onSaveInstanceState
D/LifeCycleTest(22601): onPause

D/LifeCycleTest(22601): onActivityResult -1
D/LifeCycleTest(22601): onResume

シンプルでわかりやすいです。
呼び出したアプリケーションがダイアログ状態の場合、後ろに自分が見えているので、onPause までしか呼ばれないわけですね。

と、ここまでは良かったんですが、実はこのパターンに当てはまらないアプリを見つけてしまいました。
こちらはかなり特殊なケースだと思われるので、別に書きました。
穀風: onActivityResult が呼ばれた直後に onPause が走ることがある


以下に使用したコードを載せておきます。
レイアウトは載せていませんが、ボタンが一つあるだけの単純なActivityです。
package com.kokufu.test.lifecycletest2;

import com.kokufu.test.lifecycletest2.R;

import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;

public class MainActivity extends Activity {
    private static final String TAG = "LifeCycleTest";

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        Log.d(TAG, "onCreate");

        Button button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
                intent.addCategory(Intent.CATEGORY_OPENABLE);
                intent.setType("*/*");
                startActivityForResult(intent, 0);
            }
        });
    }

    @Override
    protected void onStart() {
        super.onStart();

        Log.d(TAG, "onStart");
    }

    @Override
    protected void onResume() {
        super.onResume();

        Log.d(TAG, "onResume");
    }

    @Override
    protected void onRestart() {
        super.onRestart();

        Log.d(TAG, "onRestart");
    }

    @Override
    protected void onRestoreInstanceState(Bundle savedInstanceState) {
        super.onRestoreInstanceState(savedInstanceState);

        Log.d(TAG, "onRestoreInstanceState");
    }

    @Override
    protected void onSaveInstanceState(Bundle outState) {
        Log.d(TAG, "onSaveInstanceState");

        super.onSaveInstanceState(outState);
    }

    @Override
    protected void onPause() {
        Log.d(TAG, "onPause");

        super.onPause();
    }

    @Override
    protected void onStop() {
        Log.d(TAG, "onStop");

        super.onStop();
    }

    @Override
    protected void onDestroy() {
        Log.d(TAG, "onDestroy");

        super.onDestroy();
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        Log.d(TAG, "onActivityResult " + resultCode);
    }
}

0 件のコメント: