18

onPause()現在のアクティビティを停止 ( 、その後onStop()) して再起動する Android アクティビティ インストルメンテーション テストを作成しようとしています。私は試した

activity.finish();
activity = getActivity();

...しかし、それは適切に機能していないようです。

テストの目的は、フォーム データがメソッド中に保存され、onPause()メソッド中に再読み込みされることを確認するonStart()ことです。activity.finish()手動で実行すると機能しますが、テストが失敗するため、アクティビティを停止して再開する方法が間違っていると思われるという結論を導き出します。


編集:私の主な問題は同期の問題だったようです。アクティビティを再開した後、テスト ランナーはすべてのイベント ハンドラーが終了するのを待ちませんでした。次の行は、アクティビティがアイドル状態になるまでテストの実行を停止します。

getInstrumentation().waitForIdleSync()

それに加えて、ライフサイクルに関するより価値のある情報については、受け入れられた回答をご覧ください。

4

5 に答える 5

13

呼び出す(または画面の向きの変更をトリガーする):

activity.finish(); // old activity instance is destroyed and shut down.
activity = getActivity(); // new activity instance is launched and created.

活動を引き起こすことは完全なレクリエーションライフサイクルを通過します:

onPause() -> onStop() -> onDestroy() -> onCreate()

必要なものは次のとおりです。

onPause() -> onStop() -> onRestart()

私は最近InstrumentationAPIを公開し、興味深いアクティビティライフサイクルトリガーメソッドcallActivityOnXXX()をたくさん見つけました。次の1行のコードで注意が必要です。

MyActivity myActivity = getActivity();
// make activity falling into restart phase:
getInstrumentation().callActivityOnRestart(myActivity);

公式開発ガイドから引用したアクティビティライフサイクル図: ここに画像の説明を入力してください

于 2012-04-24T22:51:27.460 に答える
10

私は .finish(), setActivity(null), getActivity() を呼び出してみましたが、アクティビティを再開しましたが、私にとっては状態を復元していませんでした。SOに関する他のすべての回答を試してみましたが、これを行うための他のすべての方法をオンラインで見つけることができましたが、どれもうまくいきませんでした。多くの実験の後、私は次の作品を見つけました(注:APIレベル11以上が必要です):

    getInstrumentation().runOnMainSync(new Runnable() {
        @Override
        public void run() {
            activity.recreate();
        }
    });
    setActivity(null);
    activity = getActivity();

これを行うと、新しい Activity インスタンスが作成され、テストの前半でアクティビティにアタッチしたフラグメントの新しいインスタンスも作成され、アクティビティとフラグメントの両方が期待どおりに状態を復元します。

これがどのように機能するのか、なぜこれが機能するのかはわかりません。試行錯誤を経てこのソリューションにたどり着きました。キットカットを実行している Nexus 4 でのみテストしました。アクティビティのレクリエーションを正しくシミュレートすることは保証できませんが、私の目的には適していました。

編集:後日、これがどのように機能するかを理解しました。getActivity() は、作成中の新しいアクティビティを受け取るフックを登録することで機能します。このフックは、activity.recreate() によって作成された新しいアクティビティをキャッチします。setActivity(null)内部キャッシュ バッキング getActivity をクリアする必要がありました。それ以外の場合は、古いものを返し、新しいものを探しません。

拡張元のさまざまなテスト ケース クラスのソース コードを調べると、これがどのように機能するかがわかります。

于 2014-01-14T11:40:06.370 に答える
2

ライフサイクルイベントをテストする良い方法は、画面の向きを変更することです。私の経験では、onPause/onStartパターンを防爆するのに便利な方法です。

于 2012-04-24T12:28:10.933 に答える
0

次のようにコードを変更します。

mActivity.finish();
    setActivity(null);
    mActivity = this.getActivity();

完全な説明はこの質問で見つけることができます

于 2013-01-22T13:08:26.360 に答える
0

おそらく、アクティビティの名前を保存して終了し、リフレクションを使用して、新しいインテントを作成するための .class の新しいインスタンスを取得することができます...

于 2012-04-24T12:20:44.083 に答える