popBackStack导致一次又一次地调用片段的oncreateView

Ans*_*hul 10 android fragment android-fragments back-stack fragmentmanager

我有3个片段A,B,CI写了一段代码来替换它们并维护backstack:

 public void addFragment(Fragment fragmentToAdd, String fragmentTag) {
        FragmentManager supportFragmentManager = getSupportFragmentManager();
        Fragment activeFragment = getActiveFragment();
        FragmentTransaction fragmentTransaction = supportFragmentManager
                .beginTransaction();
        if (null != activeFragment) {
            fragmentTransaction.hide(activeFragment);
        }
        fragmentTransaction.replace(R.id.layout_child_activity, fragmentToAdd,
                fragmentTag);

       if (supportFragmentManager.getBackStackEntryCount() > 1) {
            supportFragmentManager.popBackStack();
        }
        fragmentTransaction.addToBackStack(fragmentTag);
        fragmentTransaction.commit();
    }
Run Code Online (Sandbox Code Playgroud)

在这段代码中

if (supportFragmentManager.getBackStackEntryCount() > 1) {
    supportFragmentManager.popBackStack();
}
Run Code Online (Sandbox Code Playgroud)

如果堆栈长度大于1,我使用pop来获取最新的片段.现在由于这个,当长度大于1时,它会一次又一次地调用onCreate视图.喜欢 :

  1. 打开A.
  2. 开放B.
  3. 打开C. (如果打开C. onCreateView的A被调用.)

为什么我会遇到这种行为?当我删除斜体代码时,它没有发生.

小智 7

正如文档所说,异常行为是正常的,来自后台堆栈事务。Backstack从不保存Fragments,而仅保存事务

在此处输入图片说明

http://developer.android.com/intl/es/guide/components/fragments.html

我不确定(如果不确定)这是最好的方法,但是当我想清除所有交易时,我会这样做

1)在您的活动中检查是否在后台堆栈中有任何事务,并在片段中添加一个标志,如果您是A

       int backStackCount = getSupportFragmentManager().getBackStackEntryCount();

       if(backStackCount > 0) {
           Transactions.MUST_DETACH_FROM_BACKSTACK = true;
           getSupportFragmentManager().popBackStackImmediate(null, FragmentManager.POP_BACK_STACK_INCLUSIVE);
       }
Run Code Online (Sandbox Code Playgroud)

2)在片段A内,获取标志并删除片段,onCreateView然后返回null

public class Transactions extends android.support.v4.app.Fragment{

public static boolean MUST_DETACH_FROM_BACKSTACK = false;

public Transactions() {
    // Required empty public constructor
}


@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    Log.i("FRAGMENT", "onCreateView "+MUST_DETACH_FROM_BACKSTACK);
    // Inflate the layout for this fragment
    if (MUST_DETACH_FROM_BACKSTACK) {
        MUST_DETACH_FROM_BACKSTACK = false;
        getActivity().getSupportFragmentManager().beginTransaction().remove(this).commit();
        return null;
    }
    return inflater.inflate(R.layout.fragment_transactions, container, false);
}

@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);


    Log.i("FRAGMENT", "onViewCreated");
    if(view != null){

        Log.i("FRAGMENT", "ThreadStarted");
        startThread(view);
    }
}
Run Code Online (Sandbox Code Playgroud)

但是请小心,我得到onResume()之后

OnCreateView()
Run Code Online (Sandbox Code Playgroud)

即使使用getActivity()。getSupportFragmentManager()。beginTransaction()。remove(this).commit();

因此,如果您有任何conde onResume方法,则应正确处理它