2016-05-17 39 views
1

我在其上顯示一次一個的兩個片段,我切換它們與下面的方法:RecyclerView狀態恢復未示出的物品

public void toggle() { 
    Fragment fragment = getSupportFragmentManager().findFragmentById(R.id.fragment_container); 
    if (fragment instanceof OtherFragment && null != listFragment) { 
     // Other frag is visible - we should show the list now 

     // We reuse the fragment if it was already added to the manager 
     fragment = getSupportFragmentManager().findFragmentByTag(TAG_LIST); 
     if (fragment == null) { 
      fragment = listFragment; 
     } 
     getSupportFragmentManager().beginTransaction() 
           .setCustomAnimations(R.anim.fade_in, R.anim.fade_out, R.anim.fade_in, 
                 R.anim.fade_out) 
           .replace(R.id.fragment_container, fragment, TAG_LIST) 
           .addToBackStack(TAG_LIST) 
           .commit(); 
    } else if (fragment instanceof ListFragment && null != otherFragment) { 
     // List is visible - we show show the other fragment now 

     // We reuse the fragment if it was already added to the manager 
     fragment = getSupportFragmentManager().findFragmentByTag(TAG_OTHER); 
     if (fragment == null) { 
      fragment = otherFragment; 
     } 
     getSupportFragmentManager().beginTransaction() 
           .setCustomAnimations(R.anim.fade_in, R.anim.fade_out, R.anim.fade_in, 
                 R.anim.fade_out) 
           .replace(R.id.fragment_container, fragment, TAG_OTHER) 
           .addToBackStack(TAG_OTHER) 
           .commit(); 
    } else { 
     getSupportFragmentManager().popBackStack(); 
    } 
} 

以我列表片段,在onCreateView()我確認如果recyclerView實例仍然有效(我有,一個全球性領域):

@Override 
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { 
    View view = inflater.inflate(R.layout.fragment_list, container, false); 
    ButterKnife.bind(this, view); 

    if (null != mRecyclerView) { 
     mRecyclerView.invalidate(); 
     // Skip the initialization process 
     return; 
    } else { 
     // init recycler view 
    } 

    return view; 
} 

我遇到的問題是,當我從另一個片段切換到列表中的片段,該適配器的數據視圖不再創建。永遠不會調用onBindViewHolderonCreateViewHolder

我檢查了並且getItemCount()返回有效值。 我也確保recyclerView可見。 recyclerView與他展示時似乎具有確切的狀態。

有沒有人有一個想法,爲什麼發生這種情況?有沒有人有這個解決方案?

回答

0

我會建議使用.add而不是.replace添加第二個片段,並在需要切換回的情況下使用.remove刪除第二個片段。

這將有助於保持片段1的狀態,並重新創建視圖片段2.

編輯#1

嘗試將數據設置在適配器和調用notifyDataSetChanged()內,如果1秒的延遲之後onCreateView()的聲明。

new Handler().postDelayed(new Runnable() { 
      @Override 
      public void run() { 
       \\ set adapter and call notifyDataSetChanged() here. 
      } 
     }, 1000); 
+0

的問題是不是片段的狀態,但的recyclerView和/或適配器。 正如我所提到的,片段的狀態已正確恢復,recyclerView保留了它的原始值。 另外,add方法不會改變任何東西(replace()方法的文檔:「替換已添加到容器的現有片段,這與爲所有當前添加的片段調用remove(Fragment)基本相同使用相同的containerViewId,然後添加(int,Fragment,String),這裏給出的參數相同。「) –

+0

因此,回收站視圖中的數據沒有得到更新的問題? – Swapnil

+0

是的,當我更改回列表片段時,行不再顯示。 'onBindViewHolder()'永遠不會被調用。 如果我還將recyclerView的初始化設置爲恢復狀態,則會顯示數據(將創建一個新的適配器),但會產生閃爍的效果,這是我不想避免的。 –

0

我已經設法解決了這個問題後,一些密集調試。 RecyclerView似乎有一些恢復選項,但只關於它的佈局管理器。

我已經修復了這個問題,通過使用全局變量的RecyclerViewonCreateView()我重新使用爲上,如果任何適配器:

View rootView = inflater.inflate(R.layout.fragment_list, container, false); 
ButterKnife.bind(this, rootView); 

// Try to reuse the old adapter, if any set on the recyclerView 
MyAdapter mAdapter = null != mRecyclerView ? (MyAdapter) mRecyclerView.getAdapter() : null; 

mRecyclerView = findById(rootView, android.R.id.list); 

// Setup the recycler view everytime 
... 

// If no adapter to reuse, just create a new one 
if (null == mAdapter) { 
    // create a new adapter again 
    ... 
} 

// Bind the adapter to the RecyclerView 
mRecyclerView.setAdapter(mAdapter);