Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Clear Android Fragment back stack without popping?

We have an Activity that contains a SlidingMenu (https://github.com/jfeinstein10/SlidingMenu) in which there's three options, let's call them A, B1, C1. These correspond to Fragments that we show in the Activity. When you select a different option from the SlidingMenu I replace the current fragment with the new one via the FragmentManager.

From Fragment B1 you can go to two others, let's call them B2 and B3. Here we want the Back key to take you from B2 -> B1 or from B3 -> B1, so I call transaction.addToBackStack(null). If we select an option from the SlidingMenu when you're on B2 or B3 we want to clear the back stack, so I use code as suggested in this question Clear back stack using fragments which calls popBackStack() until it's clear.

So far so good.

From Fragment C1 you can go to Fragment C2. As C1/C2 are more of a Master/Detail design I use

fragmentTransaction.setCustomAnimations(R.animator.slide_in_from_right,
    R.animator.slide_out_to_left, R.animator.slide_in_from_left,
    R.animator.slide_out_to_right);

to add a slide animation where C1 slides out to the left as C2 slides in from the right, and vice versa. Pressing the Back key while on C2 takes us back to C1, with the reverse animation, and all is good.

BUT

If you select A or B1 from the SlidingMenu and we popBackStack() to get rid of C1 from the back stack, then it slides C2 out to the right, which looks weird. What I'd like to do is clear the back stack without running the animation, but I can't find a way to do that. I've tried calling popBackStackImmediate() instead, but that doesn't seem to make any difference.

As an alternative I guess I could avoid calling addToBackStack at all, and instead manually handle the user pressing the Back key via Activity.onBackPressed(), but perhaps there's a solution I just can't see?

like image 238
Jonathan Caryl Avatar asked Apr 26 '13 12:04

Jonathan Caryl


People also ask

What is Addtobackstack null?

This means that the transaction will be remembered after it is committed, and will reverse its operation when later popped off the stack. Parameters name An optional name for this back stack state, or null.

What is PopBackStack?

public abstract void popBackStack () Pop the top state off the back stack. This function is asynchronous -- it enqueues the request to pop, but the action will not be performed until the application returns to its event loop.

How add and remove fragments?

Use replace() to replace an existing fragment in a container with an instance of a new fragment class that you provide. Calling replace() is equivalent to calling remove() with a fragment in a container and adding a new fragment to that same container. transaction. commit();


2 Answers

You could try the follow, though I am unfamiliar with .remove() it seems that it should do what you want:

myFragmentClass myFragC1 = (myFragmentClass) getFragmentManager().findFragmentByTag("theTagYouUsedWhenAddingToBackStack");
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.remove(myFragC1);
transaction.commit();
like image 69
TronicZomB Avatar answered Sep 28 '22 01:09

TronicZomB


Sadly, I don't know how to make it correctly so here is my solution (actually I've quite modified other stackoverflow answer)

In base fragment class which is extended by all other fragments):

public static boolean sDisableExitAnimation = false;

@Override
public Animation onCreateAnimation(int transit, boolean enter, int nextAnim) {
    if (sDisableExitAnimation && !enter) {
        return AnimationUtils.loadAnimation(getActivity(), R.anim.clear_stack_exit);
    }
    return super.onCreateAnimation(transit, enter, nextAnim);
}

To clear stack you need to call:

ScreenFragment.sDisableExitAnimation = true;
manager.popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);
transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);

And finally clear_stack_exit animation itself (I didn't find a way to get it from FragmentManager itself):

<?xml version="1.0" encoding="utf-8"?>
<set xmlns:android="http://schemas.android.com/apk/res/android">

    <alpha
        android:fromAlpha="1"
        android:toAlpha="0"
        android:duration="220"
        />

    <scale
        android:fromXScale="1"
        android:toXScale="0.975"
        android:fromYScale="1"
        android:toYScale="0.975"
        android:pivotX="50%"
        android:pivotY="50%"
        android:duration="220"
        />

</set>

This way you'll have correct clear stack animation. Just dodn't forget to clear sDisableExitAnimation variable before starting next transition.

like image 44
MatrixDev Avatar answered Sep 28 '22 02:09

MatrixDev