2017-08-17 63 views
1

該應用程序由一個活動(僅包含FrameLayout)和三個Fragments(所有這些結構相同,都有一個按鈕,但唯一的區別是不同的背景色)。片段管理器在方向更改後是否還原屏幕上最後顯示的片段?

當第一次創建活動時,所有片段都通過替換被放入FrameLayout中。當我們點擊屏幕上的按鈕(片段)時,它會將當前片段替換爲另一片段。

問題是,在屏幕旋轉時,該活動顯示了應用程序第一次啓動時顯示的片段,與旋轉之前剛剛顯示的片段無關。

爲什麼會發生這種情況?爲什麼屏幕上還沒有最後顯示的片段?

我知道我可以使用onSavedInstanceState,但更重要的是,我想了解FragmentManager的工作原理。

主要活動:

public class MainActivity extends AppCompatActivity implements ActivityInstance { 

    fraga a; 
    fragb b; 
    fragc c; 
    FragmentManager fm; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 
     fm = getSupportFragmentManager(); 


     if (fm.findFragmentByTag("a")!=null){ 
      a = (fraga) fm.findFragmentByTag("a"); 
     } 
     else { 
      a = new fraga(); 
      FragmentTransaction ft = fm.beginTransaction(); 
      ft.add(R.id.frame, a, "a"); 
      ft.commit(); 
     } 

     if (fm.findFragmentByTag("b")!=null){ 
      b = (fragb) fm.findFragmentByTag("b"); 
     } 
     else { 
      b = new fragb(); 
      FragmentTransaction fx = fm.beginTransaction(); 
      fx.add(R.id.frame, b, "b"); 
      fx.commit(); 
     } 

     if (fm.findFragmentByTag("c")!=null){ 
      c = (fragc) fm.findFragmentByTag("c"); 
     } 
     else { 
      c = new fragc(); 
      FragmentTransaction fl = fm.beginTransaction(); 
      fl.add(R.id.frame, c, "c"); 
      fl.commit(); 
     } 

    } 

    public void changefrag(int i) { //This method is called by the fragment 
            using the ActivityInstance interface 
     switch (i){ 
      case 1: FragmentTransaction f1 = fm.beginTransaction().replace(R.id.frame, a, "a"); 
        f1.commit(); 
        break; 
      case 2: FragmentTransaction f2 = fm.beginTransaction().replace(R.id.frame, b, "b"); 
        f2.commit(); 
        break; 
      case 3: FragmentTransaction f3 = fm.beginTransaction().replace(R.id.frame, c, "c"); 
        f3.commit(); 
        break; 
      default: 
        {Toast.makeText(this, "default", Toast.LENGTH_SHORT).show();} 
     } 
    } 
} 

回答

4

FragmentManager恢復上次方向更改後顯示fragment。看起來您在從Activity每次方向更改後都要添加新的fragment。所以一個新的片段被添加到最後一個片段上,它覆蓋了最後一個片段。

只有當savedInstanceState爲空時,您才應該在onCreate中添加您的fragmentsavedInstanceState僅在第一次爲空時,在方向更改後它不會爲空。

if (savedInstanceState == null) { 
    // add your fragment 
} 
// else - don't add fragment, because all the fragments are restored automatically 
+0

但我首先檢查如果旋轉之前存在碎片。如果沒有,那麼只有我在ELSE塊中添加片段。我對嗎? @Bob –

+0

因爲當你點擊按鈕時你正在調用replace。 Replace會刪除容器中所有添加的片段,並只添加您傳遞的最新片段。所以如果你用fragc替換,fraga和fragb都不見了。方向改變後,這些片段將再次添加。更多信息:https://developer.android.com/reference/android/app/FragmentTransaction.html#replace(int,android.app.Fragment,java.lang.String) – Bob