2013-02-25 82 views
4

我對此非常困惑。我有一個actionbar列表導航。我點擊列表一個接一個地打開2 fragment並顯示在同一活動中。我使用這種方法基本上替換它們:片段在活動輪轉上重疊

public void openFragment(AprilAppsFragment createdFragment){   
    if (createdFragment.getClass().isInstance(getDisplayedFragment())) 
     return; 

    FragmentManager manager = getSupportFragmentManager(); 
    FragmentTransaction transaction = manager.beginTransaction(); 
    transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN); 

    transaction.replace(R.id.main_fragment, createdFragment, "displayed fragment"); 
    transaction.addToBackStack(null); 
    transaction.commit(); 
} 

我打開片段,然後我打開片段,然後我旋轉屏幕。片段A正在重新創建崩潰我的應用程序

因爲我使用替換?我如何避免重新創建不再顯示的碎片,而不會丟失對它們進行反壓的可能性?

+0

你可以從崩潰中添加堆棧跟蹤? – ianhanniballake 2013-02-25 19:19:04

+0

這將是無關緊要的。崩潰發生時,片段試圖用數據填充其內容,但無法實例化視圖組件,因爲它甚至未顯示 – 2013-02-25 19:20:12

+0

您是否從「OnNavigationListener」調用該方法?如果是,請記住,活動創建/娛樂會觸發偵聽器。 – Luksprog 2013-03-01 14:05:10

回答

9

你的問題是,你不節能狀態的碎片,因爲你還沒有加入

android:configChanges="orientation|screenSize" 

你的第一個片段再次呼籲,既然你有沒有保存狀態你的應用程序崩潰。所以它的好,你添加行上面,你的活動申報清單,如:

<activity android:name=".yourActivity" android:configChanges="orientation|screenSize" 

並覆蓋和的onSaveInstanceState保存狀態爲您的片段。而在你的onCreate只是做此項檢查:

if(savedInstanceState != null){ 
fragmentA = (FragmentA) fragmentManager.getFragment(savedInstanceState, stringValueA); 
fragmentB = (FragmentB) fragmentManager.getFragment(savedInstanceState, stringValueB); 
} 

,然後檢查你的任何片段不爲空不是創建它的實例,並將其設置爲fragmentTransaction.relplace。或者在你的openFragment方法中做到這一點。

乾杯,

+1

它並沒有真正回答爲什麼娛樂活動重新創建所有片段,甚至是被替換的片段。 configChanges實際上停止了娛樂活動,但它不能與ActionBarSherlock一起工作,我只能在ICS後期系統上嘗試 – 2013-03-10 09:41:37

+0

閱讀本主題中的答案:http://stackoverflow.com/questions/14184182/why-wont-fragment-retain - 狀態 - 當屏幕旋轉 – AliR 2013-03-11 00:12:11

+0

完美!!!!!!!!!!!!!!!!!!!! – 2014-01-07 04:52:03

2

碎片自動保存它們的狀態(以及背堆棧上的位置)。確保你沒有重新創建你的片段,或者在onActivityCreated或onCreate方法中調用openFragment。

+0

我不是,我敢肯定 – 2013-02-25 19:18:05

+0

因此,您創建片段A和片段B(即調用此openFragment方法)的唯一位置是列表中的單擊方法嗎? – ianhanniballake 2013-02-25 19:28:07

+0

究竟,這是唯一的地方 – 2013-02-25 19:30:22

1

我有一個類似的問題,我做的是在我的 AndroidManifest.xml中添加代碼行(你的活動,美要停止重建內線):

機器人:configChanges =「方向」

還有一件事,我才知道,片段是一種子活動和不活動, 我們一定要爲獲得與片段支持延伸的活動片段,並且extands活動活動片段是持有「子活動」的實際活動那叫做碎片。

我希望我幫助ü...

1

添加到您的活動定義在AndroidManifest.xml檔案:

android:configChanges="keyboardHidden|screenLayout|orientation|screenSize" 

這將保持活動從自動重新創建重啓和FragmentManager它具有的片段。

如果您需要在循環中重新啓動活動,那麼您必須查找正在傳遞給onCreate的savedInstanceState,然後使用您提供的標記來查詢FragmentManager。

2

您的問題是您的活動正在重新創建,這會導致您重新設置列表導航,導致默認(第一個)位置被觸發。您需要在活動銷燬和活動重新消費之間保存選定的索引。這裏有一個例子:

@Override 
public void onCreate(Bundle savedInstanceState) { 

    // onCreate implementation... 

    // Must come after setListNavigationCallbacks is called 
    if (savedInstanceState != null) { 
     int index = savedInstanceState.getInt("index"); 
     getActionBar().setSelectedNavigationItem(index); 
    } 
} 

@Override 
protected void onSaveInstanceState(Bundle outState) { 

    super.onSaveInstanceState(outState); 
    outState.putInt("index", getActionBar().getSelectedNavigationIndex()); 
} 
+0

爲什麼downvote?我的答案是什麼沒有用? – 2013-03-11 07:20:57