17

I've got an app with nav drawer, which is switching fragments. From inside one of those fragments, I am calling a new activity. When I click back in this activity (in toolbar), I want to go back to previous selected fragment but instead it puts me back to first fragment. I am adding my fragment to back stack so this should not be a problem.

Here is what I have already tried:

I have overriden the onBackPressed method in my 2nd activity like this:

@Override
public void onBackPressed() {
    if (getFragmentManager().getBackStackEntryCount() == 0) {
        this.finish();
    } else {
        getFragmentManager().popBackStack();
    }
}

It is not working. I also saved index of current fragment inside onsaveinstancestate method and retrieve it but same result. I also tried with always putting current fragment inside variable and try to reshow it but still, it does not work. Anything else I could try?

Fun fact: if I press back inside bottom panel, it does actually goes back to previous fragment.

EDIT: Here is my code for doing this:

 private void replaceFragment(Fragment fragment)
 {
     if (fragment != null)
     {
         FragmentManager manager = getSupportFragmentManager();
         manager.beginTransaction()
                    .replace(R.id.main_content, fragment)
                    .addToBackStack(null)
                    .commit();
        }
    }

I add first fragment only, if savedInstanceState is null, like so:

if (savedInstanceState == null) {
    // first time
    mTitle = getResources().getString(R.string.home);
    replaceFragment(HomeFragment.newInstance()); 
}

And yes, all this is done inside onCreate() method.

MaTTo
  • 2,326
  • 5
  • 20
  • 24

9 Answers9

7

I had the same problem and got fixed. The only thing you need to do is to override the method "onOptionsItemSelected" in the activity:

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    if (item.getItemId() == android.R.id.home) {
        finish();
        return true;
    }
    return super.onOptionsItemSelected(item);
}

android.R.id.home is your first fragment in the menu.

L.L.
  • 679
  • 8
  • 14
4

What I tend to do is this

@Override
public void onBackPressed() {
    if (getFragmentManager().getBackStackEntryCount() == 0) {
        this.finish();
    } else {
        super.onBackPressed(); //replaced
    }
}

This way it handles the fragment stuff on its own within, but when there's no fragments left to go back to, then it finishes the activity.

EDIT: UP navigation can recreate your previous activity even if it already exists. To prevent that from happening, redefine the Up navigation's event in onOptionsItemSelected like so:

public boolean onOptionsItemSelected(MenuItem item) {
    switch (item.getItemId()) {
        case android.R.id.home:
            Intent parentIntent = NavUtils.getParentActivityIntent(this);
            if(parentIntent == null) { 
                finish();
                return true;
            } else {
                parentIntent.setFlags(Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT | Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
                startActivity(parentIntent);
                finish();
                return true;
            }
    }
    return super.onOptionsItemSelected(item);
}
EpicPandaForce
  • 79,669
  • 27
  • 256
  • 428
  • Still not working. I guess I did wrong something else. – MaTTo Jul 19 '15 at 11:38
  • When I press back inside second activity, it goes back to first one and shows up first fragment, not second one. – MaTTo Jul 19 '15 at 11:58
  • Are you also adding the first fragment to the stack, and also the second? Are you using `add` or `replace`? Are you adding the fragment only if the save instance state is null? Are you doing this in onCreate? Post the code for the first activity's relevant methods. – EpicPandaForce Jul 19 '15 at 12:02
  • 1
    Ohhhhhhhhh..... wait a second, so you're trying to use UP Navigation to go back. Hold on, I have a fix for this: http://stackoverflow.com/a/30059708/2413303 – EpicPandaForce Jul 19 '15 at 12:12
  • That's it! Thank you! – MaTTo Jul 19 '15 at 12:22
3

When you call an activity from other activity's fragment, then the previous activity's instance state that is the calling activity which was having fragment's instance state will be saved in stack...so all u need to do is finish the called activity and u will have the fragment from which you called your second activity.

@Override
public void onBackPressed() {
finish();
}
1

Try

getFragmentManager().popBackStackImmediate();

It worked for me.

Samrat Dutta
  • 1,727
  • 1
  • 11
  • 23
0

Sorry, I don't have enough reputation to leave a comment. So I have to guess. I once had the same issue. Sounds like a problem related to the activity lifecycle (http://developer.android.com/reference/android/app/Activity.html#ProcessLifecycle). Be sure to add your first fragment only once, because your activity's fragment manager is capable of the lifecycle. Thus, the statement that adds the first fragment to your fragment manager should be surrounded by if (savedInstanceState == null) { ... }.

Chris Fox
  • 76
  • 1
  • 6
  • I took care of that: `if (savedInstanceState == null) { mTitle = getResources().getString(R.string.home); replaceFragment(HomeFragment.newInstance()); ` – MaTTo Jul 18 '15 at 17:43
0

I see, that people are still trying to help me. This answer helped me fix my problem: Android - Navigation Up from Activity to Fragment

Community
  • 1
  • 1
MaTTo
  • 2,326
  • 5
  • 20
  • 24
0

Override onOptionsItemSelected method in activity as follows,

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    int id = item.getItemId();
    if (id == android.R.id.home) {
        finish();
    }
    return super.onOptionsItemSelected(item);
}
Parinda Rajapaksha
  • 2,963
  • 1
  • 36
  • 40
0

When you call new Activity from Fragment you should write :

Intent intent = new Intent(getFragment().getContext(),NewActivity.class);
getFragment().getContext().startActivity(intent);

FragmentManager fm = CurrentFragment.getActivity().getSupportFragmentManager();
FragmentTransaction ft = fm.beginTransaction();
ft.addToBackStack(CurrentFragment.class.getName()).commit();
fm.executePendingTransactions();

It Works for me.

Arjun Vyas
  • 27
  • 7
0
getSupportFragmentManager().beginTransaction()
                           .setReorderingAllowed(true)
                           .addToBackStack("home") // should not be null
                           .replace(binding.fragmentContainer.getId(), new HomeFragment())
                           .commit();

Pass name in addToBackStack(String name) method. This function add fragment into backstack if passed name is not null. App automatically start managing backstack of fragment

Remove your override onBackPressed() method. No use of it now