J'ai plusieurs activités dans mon application. et le flux est très compliqué. Lorsque je clique sur l'application Déconnexion, les navigateurs se connectent à l'écran de connexion et, à partir de là, l'utilisateur peut quitter en annulant le bouton (appeler system.exit(0)
).
quand je sors ou retourne, le système appelle une activité de la pile :( comment puis-je effacer toutes les activités de la pile quand j'atteins l'écran de connexion? appeler finish()
n'est pas pratique car il y a tellement d'activités et certaines les activités ne doivent pas être fermées lorsqu'elles sont actives, telles que l'activité d'appel de caméra native.
validateuser logoutuser = new validateuser();
logoutuser.logOut();
Intent loginscreen = new Intent(homepage.this, Login2.class);
(homepage.this).finish();
loginscreen.setFlags( Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NO_HISTORY);
startActivity(loginscreen);
La plupart d'entre vous ont tort. Si vous souhaitez fermer la pile d'activités existante indépendamment de ce qu'il y a dedans et créer une nouvelle racine, le jeu correct d'indicateurs est le suivant:
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
public static final int FLAG_ACTIVITY_CLEAR_TASK
Ajouté à l'API niveau 11S'il est défini dans une intention transmise à
Context.startActivity()
, cet indicateur effacera toute tâche existante qui serait associée à l'activité avant son démarrage. En d’autres termes, l’activité devient la nouvelle racine d’une tâche par ailleurs vide et toutes les anciennes activités sont terminées. Ceci ne peut être utilisé qu'avecFLAG_ACTIVITY_NEW_TASK
.
Lorsque vous appelez startActivity
lors de la dernière activité, vous pouvez toujours utiliser
Intent.FLAG_ACTIVITY_CLEAR_TOP
comme un drapeau sur cette intention.
En savoir plus sur le drapeau ici .
Voici une méthode d'assistance simple pour démarrer une nouvelle activité en tant que nouvelle activité principale, qui fonctionne à partir du niveau 4 de l'API jusqu'à la version 17 actuelle:
static void startNewMainActivity(Activity currentActivity, Class<? extends Activity> newTopActivityClass) {
Intent intent = new Intent(currentActivity, newTopActivityClass);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB)
intent.addFlags(0x8000); // equal to Intent.FLAG_ACTIVITY_CLEAR_TASK which is only available from API level 11
currentActivity.startActivity(intent);
}
appelez ça comme ça depuis votre activité actuelle:
startNewMainActivity(this, MainActivity.class);
Clear Activity Backstate par le code ci-dessous:
Intent intent = new Intent(Your_Current_Activity.this, Your_Destination_Activity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK |Intent.FLAG_ACTIVITY_CLEAR_TOP);
startActivity(intent);
Fait
Dans mon cas, LoginActivity était également fermé. Par conséquent,
Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_CLEAR_TASK
n'a pas aidé.
Cependant, la mise
Intent.FLAG_ACTIVITY_NEW_TASK
m'a aidé.
Intent intent = new Intent(LoginActivity.this, Home.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); //It is use to finish current activity
startActivity(intent);
this.finish();
Cette décision fonctionne bien:
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TASK);
Mais la nouvelle activité démarre longtemps et vous voyez un écran blanc un certain temps. Si cela est critique, utilisez cette solution de contournement:
public class BaseActivity extends AppCompatActivity {
private static final String ACTION_FINISH = "action_finish";
private BroadcastReceiver finisBroadcastReceiver;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
registerReceiver(finisBroadcastReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
finish();
}
}, new IntentFilter(ACTION_FINISH));
}
public void clearBackStack() {
sendBroadcast(new Intent(ACTION_FINISH));
}
@Override
protected void onDestroy() {
unregisterReceiver(finisBroadcastReceiver);
super.onDestroy();
}
}
Comment l'utiliser:
public class ActivityA extends BaseActivity {
// Click any button
public void startActivityB() {
startActivity(new Intent(this, ActivityB.class));
clearBackStack();
}
}
Inconvénient: toutes les activités qui doivent être fermées sur la pile doivent étendre BaseActivity.
J'ai remarqué que vous aviez demandé une solution qui ne repose pas sur finish()
, mais je me demande si cela peut néanmoins vous aider.
J'ai suivi si un indicateur de sortie est levé avec une variable de classe statique, qui survit à la durée de vie de l'application. Dans chaque pertinent de l'activité onResume()
, utilisez
@Override
public void onResume() {
super.onResume();
if (ExitHelper.isExitFlagRaised) {
this.finish();
}
}
La classe ExitHelper
public class ExitHelper {
public static boolean isExitFlagRaised = false;
}
Supposons que, dans mainActivity, un utilisateur appuie sur un bouton pour quitter. Vous pouvez définir ExitHelper.isExitFlagRaised = true;
Puis finish()
. Par la suite, les autres activités pertinentes qui sont automatiquement reprises seront également terminées.
Pour les développeurs Xamarin, vous pouvez utiliser:
intent.SetFlags(ActivityFlags.NewTask | ActivityFlags.ClearTask);