Android 保存片段以备以后显示的最佳做法

Android 保存片段以备以后显示的最佳做法,android,android-fragments,android-fragmentactivity,android-support-library,Android,Android Fragments,Android Fragmentactivity,Android Support Library,我有一个活动,里面有一个FrameLayout。 活动应该显示四个步骤,每个步骤都是一个片段。当我想再往回走的时候,我不希望我的片段被重新创建。我想保留它们,并在我的片段中简单地替换它们的视图 我通常先创建片段并将其添加到backbackback中,如下所示: Fragment step= new Frag1ActCompleteFragsCommTrack(); FragmentTransaction ft= getSupportFragmentManager().beginTransacti

我有一个活动,里面有一个
FrameLayout
。 活动应该显示四个步骤,每个步骤都是一个
片段
。当我想再往回走的时候,我不希望我的片段被重新创建。我想保留它们,并在我的片段中简单地替换它们的视图

我通常先创建片段并将其添加到backbackback中,如下所示:

Fragment step= new Frag1ActCompleteFragsCommTrack();
FragmentTransaction ft= getSupportFragmentManager().beginTransaction();
ft.add(step, ""+onStepNr);
ft.addToBackStack(null);
ft.commit();
注意,我没有显示它,我只是创建它并添加到backbackback

因此,一旦我需要显示一个片段,我就添加它(在本例中,我不会从
framelayout
中删除任何片段,因为这是我的第一次添加):

所以:问题是我得到了一个

原因:java.lang.IllegalStateException:已添加片段:Frag1ActCompleteFragsComTrack{410dcb20#0 id=0x7f050041-1}


但是我认为我不能第一次直接添加到框架布局中,否则下次替换它时,我可能会丢失片段。我说得对吗?所以保留可以在framelayout中相互交换的片段的最佳做法是什么?

如果我理解正确,您总是可以执行类似的操作,即尝试添加所有片段,但在准备好之前不显示它们<代码>FragmentTransaction.add()并不能完全做到这一点。它也将在其添加后显示。添加每个片段后,应该使用
hide()
,然后可以使用
show()
使其可见,然后再次使用
hide()
使其他片段不可见

像这样:

Fragment step = new Frag1ActCompleteFragsCommTrack();
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.add(step, ""+onStepNr);
ft.hide(step);
ft.commit();
随后:

Fragment step = getSupportFragmentManager().findFragmentByTag(""+onStepNr);
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.show(step);
// may want to hide other fragments here
ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
ft.commit();

女士们先生们,我做到了

如果您添加了一个
片段
,并且希望它显示在
框架布局
中,请记住将其放在片段backstack中。就这样!如果您在framelayout中用另一个替换它,不用担心:由于它的标记,您可以通过查找它来将它放回原处。 这比我想象的要容易

//step is an int describing the step associated to the fragment I wanna place
FragmentTransaction ft= getSupportFragmentManager().beginTransaction();
ft.replace(R.id.act_complete_track_frameLayout, f, ""+step);
ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
if(firstAttach)
    ft.addToBackStack(null);
ft.commit();
想象一个带有标记“1”的片段通过上面的代码被一个带有标记“2”的片段替换。如果我想回到步骤1,我通过使用
getSupportFragmentManager().findframentbytag(“1”)


简而言之,我认为,
FragmentTransaction.replace
也从backbackback中删除了
片段。似乎不是这样(幸运的)

哼,说得对!我会考虑的!我曾考虑过这个解决方案,但我不确定它是否有效:
ft.remove(fragmentoretain);ft.add(fragmentoretain,fragmentoretain.getTag());ft.addToBackStack(空);ft.add(R.id.act\u complete\u track\u frameLayout,step)//新的一步!ft.setTransition(碎片事务处理、传输、碎片淡入淡出)ft.commit()`不!我想做一些类似“一步一步”的事情。每个片段包含一个步骤。但我想增加返回的机会(即从第四步返回到第二步,反之亦然)。片段是在第一次需要时创建的。例如:如果我从第一步走到第二步,我将创建第二步片段。但无论如何,这是一个很好的建议!我也可以用那种方式!如果有人能证实我对
零碎交易的印象。替换
就好了。文档对此问题的描述有点含糊不清。我也希望findframentbytag()在替换的fragment.me上返回null,但它的行为似乎不是这样的。这可能是因为v4支持库的实现吗?我不认为。。。使用“后退”按钮导航回已删除的片段时会发生什么情况?它真的还在那里吗?暗示可能是鬼碎片?返回按钮弹出先前添加的碎片<代码>替换
并没有达到我们的预期。你是对的:正确的方法是使用
show
hide
//step is an int describing the step associated to the fragment I wanna place
FragmentTransaction ft= getSupportFragmentManager().beginTransaction();
ft.replace(R.id.act_complete_track_frameLayout, f, ""+step);
ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
if(firstAttach)
    ft.addToBackStack(null);
ft.commit();