プログラムでAndroidアプリを「再起動」するにはどうすればよいですか?


231

まず、Androidでアプリケーションを強制終了/再起動してはいけないことを知っています。私の使用例では、サーバーが特定の情報をクライアントに送信する特定のケースでアプリケーションを出荷時設定にリセットしたいと思います。

ユーザーは、アプリケーションの1つのインスタンスを使用してサーバーにログインすることしかできません(つまり、複数のデバイスは許可されません)。別のインスタンスがその「ログイン済み」ロックを取得した場合、そのユーザーの他のすべてのインスタンスは、一貫性を維持するためにデータを削除(ファクトリーリセット)する必要があります。

ユーザーがアプリを削除して再インストールすると、異なるインスタンスIDが生成され、ユーザーがロックを解放できなくなるため、強制的にロックを取得することが可能です。そのため、強制的にロックを取得することが可能です。

その力の可能性のために、私たちは常に具体的なインスタンスでそれがロックを持っていることをチェックする必要があります。これは、サーバーへの(ほぼ)各要求に対して行われます。サーバーは「間違ったロックID」を送信する可能性があります。それが検出された場合、クライアントアプリケーションはすべてを削除する必要があります。


それがユースケースでした。

sharedPrefsの値に応じてActivity、Login ActivityLまたはアプリのメインActivityB を開始するAがあります。LまたはBを開始した後、LまたはBのみが実行されるように自身を閉じます。したがって、ユーザーがすでにログインしている場合、Bは現在実行中です。

BがCを開始します。C startServiceIntentServiceDを呼び出します。その結果、次のスタックになります。

(A)> B> C> D

DのonHandleIntentメソッドから、イベントがResultReceiver Rに送信されます

Rは、ユーザーにアプリケーションを工場出荷時の状態にリセットする(データベースやsharedPrefsなどを削除する)ことを選択できるダイアログを提供することにより、このイベントを処理します。

出荷時設定にリセットした後、アプリケーションを再起動し(すべてのアクティビティを閉じるため)、Aのみを再起動します。これにより、ログインActivityL が起動され、それ自体が終了します。

(A)> L

ダイアログのonClickメソッドは次のようになります。

@Override
public void onClick(DialogInterface dialog, int which) {

    // Will call onCancelListener
    MyApplication.factoryReset(); // (Deletes the database, clears sharedPrefs, etc.)
    Intent i = new Intent(MyApp.getContext(), A.class);
    i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
    i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    MyApp.getContext().startActivity(i);
}

そしてそれがMyAppクラスです:

public class MyApp extends Application {
    private static Context context;

    @Override
    public void onCreate() {
        super.onCreate();
        context = getApplicationContext();
    }

    public static Context getContext() {
        return context;
    }

    public static void factoryReset() {
        // ...
    }
}

問題はFLAG_ACTIVITY_NEW_TASK、アクティビティBとCをまだ使用している場合です。ログイン時Activityに戻るボタンを押すとCが表示されますが、ホーム画面に戻りたいのですが。

設定しないとFLAG_ACTIVITY_NEW_TASK、エラーが発生します。

07-07 12:27:12.272: ERROR/AndroidRuntime(9512): android.util.AndroidRuntimeException: Calling startActivity() from outside of an Activity  context requires the FLAG_ACTIVITY_NEW_TASK flag. Is this really what you want?

Dはによって開始されたバックグラウンドタスクからも呼び出される可能性があるContextため、アクティビティを使用できません。ServiceIntentAlarmManager

では、これをアクティビティスタックが(A)> Lになるように解決するにはどうすればよいですか?

回答:


284

を使用PendingIntentして、将来の開始アクティビティの起動を設定し、アプリケーションを閉じることができます

Intent mStartActivity = new Intent(context, StartActivity.class);
int mPendingIntentId = 123456;
PendingIntent mPendingIntent = PendingIntent.getActivity(context, mPendingIntentId,    mStartActivity, PendingIntent.FLAG_CANCEL_CURRENT);
AlarmManager mgr = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
mgr.set(AlarmManager.RTC, System.currentTimeMillis() + 100, mPendingIntent);
System.exit(0);

5
これは完璧に機能しました!私はちょうどandroid.os.Process.killProcess(android.os.Process.myPid());を使用しました。System.exit();
FDIM 2014

29
4.3および4.4デバイス(私がテストしたすべて)では、これにより現在のアクティビティが強制終了され、古いアクティビティの上に新しいアクティビティが起動されます。私は2つのアクティビティの深さです(メイン->設定)。戻るボタンを押すと、1つ前の画面の古いアプリに戻ります。
Mgamerz 2014

5
私の場合、トランザクションがロールバックしていたため、System.exit(0)は機能しませんでした。代わりに、activity.finish();を使用しました。そしてそれはうまく働きます。
2014年

6
@Qulin、みんな!真面目じゃない!この例は、実際の例よりも方向に似ています。開始アクティビティ名、インテントIDを使用してこのスニペットを変更し、何を使ってもメカニズムを終了する必要があります。盲目的にコピーして貼り付けないでください。
Oleg Koshkin

19
これは、バックグラウンドの活動に新たな制限にAndroidのQでもう動作しませんdeveloper.android.com/preview/privacy/...
マルコRighini

103

あなたは単に呼び出すことができます:

public static void triggerRebirth(Context context, Intent nextIntent) {
    Intent intent = new Intent(context, YourClass.class);
    intent.addFlags(FLAG_ACTIVITY_NEW_TASK);
    intent.putExtra(KEY_RESTART_INTENT, nextIntent);
    context.startActivity(intent);
    if (context instanceof Activity) {
      ((Activity) context).finish();
    }

    Runtime.getRuntime().exit(0);
}

これはProcessPhoenixライブラリで使用されます


別の方法として:

@Oleg Koshkinの回答を少し改善したバージョンを以下に示します。

現在のプロセスの強制終了を含めてアクティビティを再開したい場合は、次のコードを試してください。HelperClassまたは必要な場所に配置します。

public static void doRestart(Context c) {
        try {
            //check if the context is given
            if (c != null) {
                //fetch the packagemanager so we can get the default launch activity 
                // (you can replace this intent with any other activity if you want
                PackageManager pm = c.getPackageManager();
                //check if we got the PackageManager
                if (pm != null) {
                    //create the intent with the default start activity for your application
                    Intent mStartActivity = pm.getLaunchIntentForPackage(
                            c.getPackageName()
                    );
                    if (mStartActivity != null) {
                        mStartActivity.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
                        //create a pending intent so the application is restarted after System.exit(0) was called. 
                        // We use an AlarmManager to call this intent in 100ms
                        int mPendingIntentId = 223344;
                        PendingIntent mPendingIntent = PendingIntent
                                .getActivity(c, mPendingIntentId, mStartActivity,
                                        PendingIntent.FLAG_CANCEL_CURRENT);
                        AlarmManager mgr = (AlarmManager) c.getSystemService(Context.ALARM_SERVICE);
                        mgr.set(AlarmManager.RTC, System.currentTimeMillis() + 100, mPendingIntent);
                        //kill the application
                        System.exit(0);
                    } else {
                        Log.e(TAG, "Was not able to restart application, mStartActivity null");
                    }
                } else {
                    Log.e(TAG, "Was not able to restart application, PM null");
                }
            } else {
                Log.e(TAG, "Was not able to restart application, Context null");
            }
        } catch (Exception ex) {
            Log.e(TAG, "Was not able to restart application");
        }
    }

これにより、jniクラスとすべての静的インスタンスも再初期化されます。


1
このソリューションは優れていますが、100ミリを減らしても、アプリケーションが再起動するまで数秒間遅延します。ただし、Jack WhartonによるこのライブラリProcessPhoenixは、より優れた迅速な処理を実現しますが、アプリ内でこの関数のみのライブラリを追加する価値はありません。
ブルーウェア

@blueware回答を更新し、ProcessPhonix内で使用されるコードを追加しました
mikepenz

@mikepenz、この男「Ilya_Gazman」は、そのようなライブラリを使用せずにはるかに優れていました。
ブルーウェア

3
@blueware-Ilyaのソリューションがプロセスを再起動しないことを除いて、静的データまたは読み込まれたNDKライブラリは正しく再初期化されません。
テッドホップ2016

一部のHuaweiおよびSamsungデバイスにはAlarmManager、このソリューションを使用すると制限があり、正しく動作しません。
ブルーウェア2017

69

Jake Whartonは最近、これを信頼できる方法で実行するProcessPhoenixライブラリを公開しました。あなたは基本的に呼び出すだけです:

ProcessPhoenix.triggerRebirth(context);

ライブラリは自動的に呼び出しアクティビティを終了し、アプリケーションプロセスを強制終了して、デフォルトのアプリケーションアクティビティを後で再開します。


これは機能しているようですが、クラッシュします(報告されます)。これが理想的かどうかはわかりません。
BK- 2015年

1
libで問題が発生したことはありませんが、github.com
JakeWharton /

ああ、私はメッセージを十分に近く見ていなかったので、コメントを撤回しました。デフォルトの起動アクティビティにインテントフィルターがありませんでした。必要な正確なインテントフィルターに注目する価値があります。
BK- 2015年

1
これはこれまでのところ最良の解決策です。
yongsunCN 2016

1
@Shambhu <category android:name="android.intent.category.DEFAULT" />では、アプリマニフェストのデフォルトアクティビティ<intent-filter>にタグを追加する必要があります。
Muhammed Refaat

57

新しいAPIを使用するようにIlya_Gazmanの回答を少し変更しました(API 26以降、IntentCompatは非推奨です)。Runtime.getRuntime()。exit(0)はSystem.exit(0)よりも優れているようです。

 public static void triggerRebirth(Context context) {
    PackageManager packageManager = context.getPackageManager();
    Intent intent = packageManager.getLaunchIntentForPackage(context.getPackageName());
    ComponentName componentName = intent.getComponent();
    Intent mainIntent = Intent.makeRestartActivityTask(componentName);
    context.startActivity(mainIntent);
    Runtime.getRuntime().exit(0);
}

8
ドキュメントから直接:「呼び出し System.exit(n) は実質的に 呼び出しと同等Runtime.getRuntime().exit(n)です」。内部的には、System.exit()向きを変えて電話をかけるだけRuntime.getRuntime().exit()です。どちらかについて「より良い」ものは何もありません(タイプすることの量や、メソッド呼び出しの1つの追加のレイヤーについて心配している場合を除きます)。
Ted Hopp、2017年

上記のメソッドをどこでいつ呼び出すか?
Makvin 2018

1
@Makvinあなたはそれをどこに呼び出すかを決めます。私の場合は、言語の変更後にアプリを再起動しました。
android_dev 2018

@TedHoppはすべての回答に「良くない」とコメントしていますが、実行可能な解決策はありますか?皮肉ではなく、本当に痕跡を残さずにアプリケーションを再作成する必要がある。静的変数からクラスインスタンスへ。
ファリッド

1
@FARID-呼び出しRuntime.getRuntime().exit(0)(またはSystem.exit(0))を含むソリューションはおそらく機能します。私の「良くない」コメントの一部は、回答のためのものです(Ilya Gazmanによるコメントなど、後でこのような呼び出しを組み込むように編集されています。)
Ted Hopp

37

IntentCompat.makeRestartActivityTask

これを行う新しい方法は、IntentCompat.makeRestartActivityTaskを使用することです。

アプリケーションのタスクを基本状態で再起動するために使用できるインテントを作成します。これはmakeMainActivity(ComponentName)に似ていますが、フラグIntent.FLAG_ACTIVITY_NEW_TASKおよびFLAG_ACTIVITY_CLEAR_TASKも設定します。

PackageManager packageManager = context.getPackageManager();
Intent intent = packageManager.getLaunchIntentForPackage(context.getPackageName());
ComponentName componentName = intent.getComponent();
Intent mainIntent = IntentCompat.makeRestartActivityTask(componentName);
context.startActivity(mainIntent);
System.exit(0);

6
これによりタスクが再起動されますが、プロセスやApplicationオブジェクトは再起動されません。したがって、staticデータ、の作成中に初期化されたデータApplication、またはjniクラスは現在の状態のままであり、再初期化されません。
テッドホップ2016年

2
@TedHoppああ、私はその部分を逃した。System.exit(0);を追加しました。しかし、100%動作するかどうかはわかりません。私はそれを
後で

1
それを行うためにオープンソースライブラリを使用しない最高のソリューション。この回答を提供してくれてありがとう、+ 1
ブルーウェア

4
残念ながら、IntentCompat.makeRestartActivityTaskは現在非推奨ですソースコード調べれば、フラグを追加するだけで簡単Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASKです。
ポールランメルツマ2017

IntentCompat.makeRestartActivityTaskが削除されました
luckyhandler 2018

28

本当にいいトリックがあります。私の問題は、いくつかの本当に古いC ++ jniライブラリがリソースをリークしたことでした。ある時点で、機能が停止しました。ユーザーがアプリを終了して再起動しようとしましたが、結果はありませんでした。アクティビティの終了は、プロセスの終了(または終了)と同じではないためです。(ちなみに、ユーザーは実行中のアプリケーションのリストに移動してそこから停止することができます-これは機能しますが、ユーザーはアプリケーションを終了する方法を知りません。)

この機能の効果を観察する場合はstatic、アクティビティに変数を追加し、ボタンを押すなどして変数を1つずつ増やします。アプリケーションアクティビティを終了してから再度アプリケーションを呼び出すと、この静的変数はその値を保持します。(アプリケーションが実際に終了した場合、変数には初期値が割り当てられます。)

(そして、なぜ私は代わりにバグを修正したくなかったのかについてコメントする必要があります。ライブラリは数十年前に作成され、それ以来リソースがリークしました。管理者はそれが常に機能すると信じてます。回避策の代わりに修正を提供するコスト ...私は、あなたが考えを理解すると思います。)

さて、どうすればjni共有(動的、.so)ライブラリを初期状態にリセットできますか?新しいプロセスとしてアプリケーションを再起動することを選択しました。

コツは、System.exit()が現在のアクティビティを閉じ、Androidが1つ少ないアクティビティでアプリケーションを再作成することです。

したがって、コードは次のとおりです。

/** This activity shows nothing; instead, it restarts the android process */
public class MagicAppRestart extends Activity {
    // Do not forget to add it to AndroidManifest.xml
    // <activity android:name="your.package.name.MagicAppRestart"/>
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        System.exit(0);
    }
    public static void doRestart(Activity anyActivity) {
        anyActivity.startActivity(new Intent(anyActivity.getApplicationContext(), MagicAppRestart.class));
    }
}

呼び出しアクティビティは単にコードを実行しMagicAppRestart.doRestart(this);、呼び出しアクティビティonPause()が実行されてから、プロセスが再作成されます。そして、AndroidManifest.xmlでこのアクティビティに言及することを忘れないでください

この方法の利点は、遅延がないことです。

UPD:Android 2.xでは機能しましたが、Android 4では何かが変更されました。


3
私はactivity.startActivity(i);を使用しました System.exit(0); 天才ソリューション
max4ever

5
このソリューションはアプリを閉じますが、再起動しません。少なくともAndroid 4.3。
Kirill Rakhman 2013年

1
samsung galaxy mega android 4.2.2では、再起動の無限ループが発生します。したがって、アプリは再び起動しません。
Gunhan 2013年

@Gunhan 1)あなたは置き換えるとどうなるかSystem.exit(0)android.os.Process.killProcess(android.os.Process.myPid());?2)無限ループは、アプリを再起動したときに最上位のアクティビティを削除しないことを意味します。原則として、静的なブール変数を追加し、再起動アクティビティを呼び出す前にtrueに設定し、再起動後にfalseにすることができます。したがって、アクティビティーは、再始動がすでに発生したかどうかを確認できます(再始動が発生した場合は、単にfinish()を実行します)。OTOH、あなたのレポートは、トリックがすべてのデバイスで同じように機能するわけではないことを意味します。
18446744073709551615 2013年

@Gunham再起動を引き起こしている同じアクティビティを開始している場合、どのデバイスでも無限ループになります。
Lukas Hanacek 2014

23

私のソリューションはプロセス/アプリケーションを再起動しません。アプリがホームアクティビティを「再開」するだけです(他のすべてのアクティビティを却下します)。ユーザーにとっては再起動のように見えますが、プロセスは同じです。場合によってはこの効果を望んでいると思うので、ここではそのままにしておきます。

public void restart(){
    Intent intent = new Intent(this, YourHomeActivity.class);
    this.startActivity(intent);
    this.finishAffinity();
}

15

はい、アプリをリファクタリングしました。Aを自動的に終了しません。私はこれを常に実行させて、onActivityResultイベントを終了します。このようにして、FLAG_ACTIVITY_CLEAR_TOP+ FLAG_ACTIVITY_NEW_TASKフラグを使用して必要なものを取得できます。

public class A extends Activity {

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        finish();
    }

    protected void onResume() {
        super.onResume();
        // ...
        if (loggedIn) {
            startActivityForResult(new Intent(this, MainActivity.class), 0);
        } else {
            startActivityForResult(new Intent(this, LoginActivity.class), 0);
        }
    }
}

そして、 ResultReceiver

@Override
public void onClick(DialogInterface dialog, int which) {
    MyApp.factoryReset();
    Intent i = new Intent(MyApp.getContext(), A.class);
    i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
    i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    MyApp.getContext().startActivity(i);
}

とにかくありがとう!


23
これはアプリケーションを再起動せ、クラスを再作成するだけです。したがって、クラス内のすべての静的変数は、以前の実行からの値を保持します。
ブライアンホワイト

14
Intent i = getBaseContext().getPackageManager().getLaunchIntentForPackage( getBaseContext().getPackageName() );
i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(i);

24
これはアプリケーションを再起動せ、クラスを再作成するだけです。したがって、クラス内のすべての静的変数は、以前の実行からの値を保持します。
ブライアンホワイト

14

「アプリが突然終了しました」をトリガーしなかった唯一のコードは次のとおりです。また、外部ライブラリを必要としない非推奨のコードでもあります。また、タイマーは必要ありません。

public static void triggerRebirth(Context context, Class myClass) {
    Intent intent = new Intent(context, myClass);
    intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
    context.startActivity(intent);
    Runtime.getRuntime().exit(0);
}

8

これはAPI 29以降で機能することがわかりました-ユーザーが実行していないときにユーザーがアプリを起動したかのように、アプリを強制終了して再起動するためです。

public void restartApplication(final @NonNull Activity activity) {
   // Systems at 29/Q and later don't allow relaunch, but System.exit(0) on
   // all supported systems will relaunch ... but by killing the process, then
   // restarting the process with the back stack intact. We must make sure that
   // the launch activity is the only thing in the back stack before exiting.
   final PackageManager pm = activity.getPackageManager();
   final Intent intent = pm.getLaunchIntentForPackage(activity.getPackageName());
   activity.finishAffinity(); // Finishes all activities.
   activity.startActivity(intent);    // Start the launch activity
   System.exit(0);    // System finishes and automatically relaunches us.
}

これは、アプリのランチャーアクティビティに次のような場合に行われました。

<intent-filter>
    <action android:name="android.intent.action.VIEW"/>
    <action android:name="android.intent.action.MAIN" />
    <category android:name="android.intent.category.LAUNCHER" />
</intent-filter>

DEFAULTのカテゴリが必要であると主張するコメントを見たことがありますが、そうであるとは知りませんでした。アプリのApplicationオブジェクトが再作成されることを確認したので、プロセスが本当に強制終了され、再起動されたと思います。

これを使用する唯一の目的は、ユーザーがFirebase Crashlyticsのクラッシュレポートを有効または無効にした後にアプリを再起動することです。彼らのドキュメントによると、その変更を有効にするには、アプリを再起動する必要があります(プロセスが強制終了され、再作成されます)。


7

完全にアプリを再起動するための最良の方法は、それを再起動するだけではなくて活動にジャンプすることであるFLAG_ACTIVITY_CLEAR_TOPFLAG_ACTIVITY_NEW_TASK。だから私の解決策はあなたのアプリから、または別のアプリからそれを行うことです、唯一の条件はアプリのパッケージ名を知ることです(例: ' com.example.myProject ')

 public static void forceRunApp(Context context, String packageApp){
    Intent launchIntent = context.getPackageManager().getLaunchIntentForPackage(packageApp);
    launchIntent.setFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS | Intent.FLAG_ACTIVITY_NEW_TASK);
    context.startActivity(launchIntent);
}

appBからappAを再起動または起動する使用例:

forceRunApp(mContext, "com.example.myProject.appA");

アプリが実行されているかどうかを確認できます。

 public static boolean isAppRunning(Context context, String packageApp){
    ActivityManager activityManager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
    List<ActivityManager.RunningAppProcessInfo> procInfos = activityManager.getRunningAppProcesses();
    for (int i = 0; i < procInfos.size(); i++) {
        if (procInfos.get(i).processName.equals(packageApp)) {
           return true;
        }
    }
    return false;
}

:この回答は少し話題から外れていることはわかっていますが、誰かにとって非常に役立つ場合があります。


5

アプリケーションを再起動するfinishAffinity();
ための私の最善の方法は、を使用するfinishAffinity();ことです。JELLYBEANバージョンでのみ使用できるためActivityCompat.finishAffinity(YourCurrentActivity.this);、下位バージョンで使用できます。

次に、を使用Intentして最初のアクティビティを起動すると、コードは次のようになります。

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
    finishAffinity();
    Intent intent = new Intent(getApplicationContext(), YourFirstActivity.class);
    startActivity(intent);
} else {
    ActivityCompat.finishAffinity(YourCurrentActivity.this);
    Intent intent = new Intent(getApplicationContext(), YourFirstActivity.class);
    startActivity(intent);
}

それが役に立てば幸い。


1
これにより、現在のタスクのすべてのアクティビティが終了しますが、プロセスは再開されず、アプリケーションオブジェクトも再作成されません。したがって、静的データ、アプリケーションの作成中に初期化されたデータ、またはjniクラスによって初期化されたデータは、現在の状態のままになり、再初期化されません。
テッドホップ


3

PackageManagerを使用して一般的な方法でアプリを再起動する例を次に示します。

Intent i = getBaseContext().getPackageManager()
             .getLaunchIntentForPackage( getBaseContext().getPackageName() );
i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(i);

これによりタスクが再起動されますが、プロセスやApplicationオブジェクトは再起動されません。したがって、静的データ、の作成中に初期化されたデータApplication、またはjniクラスは現在の状態のままであり、再初期化されません。
テッドホップ

3

これを試して:

Intent intent = getPackageManager().getLaunchIntentForPackage(getPackageName());
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);

1
ここですでに他のすべての回答が同じことを示唆しているように、これはアプリケーションを再起動せず、クラスを再作成するだけです。したがって、プロセス内の静的データはリセットされません。
テッドホップ2017


2

終了を遅らせるためにハンドラを追加する必要がありました:

 mgr.set(AlarmManager.RTC, System.currentTimeMillis() + 200, mPendingIntent);
        final Handler handler = new Handler();
        handler.postDelayed(new Runnable() {
            @Override
            public void run() {
                Runtime.getRuntime().exit(0);
            }
        }, 100);


1

startInstrumentationメソッドを使用できますActivity。空Instrumentationで指摘されたマニフェストを実装する必要があります。その後、このメソッドを呼び出してアプリを再起動できます。このような:

try {           
    InstrumentationInfo info = getPackageManager().queryInstrumentation(getPackageName(), 0).get(0);
    ComponentName component = new ComponentName(this, Class.forName(info.name));
    startInstrumentation(component, null, null);
} catch (Throwable e) {             
    new RuntimeException("Failed restart with Instrumentation", e);
}

Instrumentationクラス名を動的に取得しますが、ハードコーディングできます。このようなもの:

try {           
    startInstrumentation(new ComponentName(this, RebootInstrumentation.class), null, null); 
} catch (Throwable e) {             
    new RuntimeException("Failed restart with Instrumentation", e);
}

startInstrumentationアプリのmake reloadを呼び出します。このメソッドの説明を読んでください。しかし、kill appのように振る舞う場合は安全ではありません。


1

私が取り組んでいるアプリケーションでは、表示するフラグメントを選択できるようにする必要があります(フラグメントは実行時に動的に変更されます)。私にとって最良の解決策は、アプリケーションを完全再起動することでした。

だから私はたくさんの解決策を試してみましたが、どれも私にとってうまくいきませんでしたが、これは:

final Intent mStartActivity = new Intent(SettingsActivity.this, Splash.class);
final int mPendingIntentId = 123456;
final PendingIntent mPendingIntent = PendingIntent.getActivity(SettingsActivity.this, mPendingIntentId, mStartActivity,
                    PendingIntent.FLAG_CANCEL_CURRENT);
final AlarmManager mgr = (AlarmManager) SettingsActivity.this.getSystemService(Context.ALARM_SERVICE);
mgr.set(AlarmManager.RTC, System.currentTimeMillis() + 100, mPendingIntent);
this.finishAffinity(); //notice here
Runtime.getRuntime().exit(0); //notice here

それが他の誰かを助けることを願っています!


0

これを試して:

private void restartApp() {
    Intent intent = new Intent(getApplicationContext(), YourStarterActivity.class);
    int mPendingIntentId = MAGICAL_NUMBER;
    PendingIntent mPendingIntent = PendingIntent.getActivity(getApplicationContext(), mPendingIntentId, intent, PendingIntent.FLAG_CANCEL_CURRENT);
    AlarmManager mgr = (AlarmManager) getApplicationContext().getSystemService(Context.ALARM_SERVICE);
    mgr.set(AlarmManager.RTC, System.currentTimeMillis() + 100, mPendingIntent);
    System.exit(0);
}


-3

次のように現在のアクティビティを再開できます。

フラグメント:

activity?.recreate()

活動:

recreate()

3
これは、OPがやりたいことではありません。
テッドホップ2018
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.