MvvmCross / MvvmCross-AndroidSupport

Android support library packages for MvvmCross: The .NET MVVM framework for cross-platform solutions.
http://mvvmcross.com
15 stars 0 forks source link

Fragment already added Exception #204

Open sescandell opened 8 years ago

sescandell commented 8 years ago

Steps to reproduce

  1. Clone my forked repo (which is a copy of the current repo only the HomeFragment file have been modified to remove the AddToBack attribute)
  2. Navigate the following:
    1. Launch the application (HomeFragment is displayed)
    2. Open the menu, click on RecyclerView (RecyclerFragment is displayed)
    3. Open the menu, click on Home (HomeFragment is displayed)
    4. Open the menu, click on RecyclerView (RecyclerFragment is displayed)
    5. Click back device button (HomeFragment is displayed)
    6. Click back device button : Exception "Java.Lang.IllegalStateException: Fragment already added: HomeFragment{1aa2137 #0 id=0x7f060073 Example.Core.ViewModels.HomeViewModel}" is thrown.

      Expected behavior

The application should close when pressing back button when the HomeFragment is displayed.

Actual behavior

Application is crashing on call on SupportFragmentManager.PopBackStackImmediate(); in MvxCachingFragmentCompatActivity file

Configuration

Tested on Nexus 5 Android 6

Version:

master 2016-04-03.

Same behavior on 4.1.0

martijn00 commented 8 years ago

I can reproduce this. Some more info:

We should probably check for something when poping the backstack, but i am not sure what currently.

sescandell commented 8 years ago

And another one: http://stackoverflow.com/questions/6250580/fragment-already-added-illegalstateexception

I will do some tests on my side as soon as possible.

sescandell commented 8 years ago

Hi there,

I've found a workaround that is acceptable for my application. Here are the little modifications made:

public class MvxCachingFragmentCompatActivity : ....
{
    private string _firstFragmentTag;
    // ...
    protected override void ShowFragment(string tag, int contentId, Bundle bundle, bool forceAddToBackStack = false, bool forceReplaceFragment = false)
    {
        // ...
        if (fragmentReplaceMode == FragmentReplaceMode.ReplaceFragmentAndViewModel)
        {
            var cache = Mvx.GetSingleton<IMvxMultipleViewModelCache>();
            cache.GetAndClear(fragInfo.ViewModelType, GetTagFromFragment(fragInfo.CachedFragment as Fragment));
        }

        //////////////////
        // MODIFICATION
        //  Clear the backstack
        if (fragInfo.Tag == _firstFragmentTag)
        {
            SupportFragmentManager.PopBackStack(null, (int)PopBackStackFlags.Inclusive);
        }
        //////////////////
        // MODIFICATION
        //     Save the first fragment tag for further use
        if (string.IsNullOrEmpty(_firstFragmentTag))
        {
            _firstFragmentTag = fragInfo.Tag;
        }
        // ...
    }
}

I assume here the application have a "HomeFragment" and using the back button from the HomeFragment whatever the navigation have been before, the application terminates.

If this is a constraint acceptable, let me know, I'll push a PR.

martijn00 commented 8 years ago

It seems acceptable to me, but i can't oversee the issue enough to know for sure. If you submit a PR i'll test it, and merge if everything works.

ghost commented 8 years ago

@sescandell please make a pr

sescandell commented 8 years ago

@robertbaker Done, sorry for the delay

glalwani2 commented 8 years ago

Hi I am facing the same issue how can I overcome this in my application.In my application I am using a single activity and all the other screen are just fragments so when I click on one navigation drawer item and press back button and I do this twice then I get the above exception. How can I solve this since my application is crashing.

sescandell commented 8 years ago

Hi @glalwani2

You can create your own "FragmentBaseActivity" and override the ShowFragement method as proposed in this discussion or in the PR associated.