Question

I have a Fragment that calls an asynchronous task, and when the result returns, commits a fragmentTransaction.

However, this sometimes returns an illegalState exception due to the OS calling the onStop() function of the fragment, as noted here and here.

A solution to this was to simply move the transaction into the onResume() function, where it is guaranteed that the fragment's states are restored.

Again, however, this generates another problem: when the fragment is not stopped, I have to wait for the onResume() function to be called before the new fragment is shown.

One solution I came up with was to catch the illegalState exception and commit in the onResume() function only when the one in the async function fails(as shown below) but it seems unnecessarily long and unintelligent. Any tips or ideas for a smarter code? I just started programming for Android so I very possibly am missing something..

The code looks something like this:

@Override
public void asyncTaskResult(JSONObject obj) {
    //pre-transaction instructions

    try{
        TestFragment test = new TestFragment();
        Bundle bundle = new Bundle();
        bundle.putString("testvar", obj.optString("testvar", null));
        test.setArguments(bundle);

        FragmentTransaction ft = getFragmentManager().beginTransaction();
        ft.replace(R.id.testcontainer, test);
        ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
        ft.addToBackStack(null);
        ft.commit();
    catch(illegalStateExeption e){
        //if failed, save data and turn on flag
        mCommitOnResume = true;
        mJSONObj = obj;
}

@Override
Public void onResume(){
    super.onResume();

    //if commit on asyncTaskResult fails, do it here
    if(mCommitOnResume){
        TestFragment test = new TestFragment();
        Bundle bundle = new Bundle();
        bundle.putString("testvar", mJSONObj.optString("testvar", null));
        test.setArguments(bundle);

        FragmentTransaction ft = getFragmentManager().beginTransaction();
        ft.replace(R.id.testcontainer, test);
        ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
        ft.addToBackStack(null);
        ft.commit();
    }
    mCommitOnResume = false;
}

Any ideas/tips/advices are highly appreciated.

Was it helpful?

Solution

Try this

ft.commitAllowingStateLoss() instead of ft.commit()

eg.

        TestFragment test = new TestFragment();
        Bundle bundle = new Bundle();
        bundle.putString("testvar", obj.optString("testvar", null));
        test.setArguments(bundle);

        FragmentTransaction ft = getFragmentManager().beginTransaction();
        ft.replace(R.id.testcontainer, test);
        ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
        ft.addToBackStack(null);
        ft.commitAllowingStateLoss();
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top