2016-03-01 87 views
2

我想在回收視圖中顯示不同的項目/佈局。所以這是我如何定義這些項目:RecyclerView的onBindViewHolder中的ClassCastException

public class SearchItem { 

    public static final int TYPE_DEFAULT = 0; 
    public static final int TYPE_LOADING = 1; 

    public int type; 

    public SearchItem(int type) { 
     this.type = type; 
    } 

    public static class DefaultItem extends SearchItem { 

     public String title; 

     public DefaultItem(String title) { 
      super(TYPE_DEFAULT); 
      this.title = title; 
     } 
    } 

    public static class LoadingItem extends SearchItem { 

     public String icon, title; 

     public LoadingItem(String icon, String title) { 
      super(TYPE_LOADING); 
      this.icon = icon; 
      this.title = title; 
     } 
    } 
} 

所以基本上我有兩種類型。在適配器的適當的佈局將選擇每個項目:

public class SearchAdapter extends RecyclerView.Adapter<SearchAdapter.BaseViewHolder>{ 

    public ArrayList<SearchItem> items = new ArrayList<>(); 

    @Override 
    public int getItemCount() { 
     return items.size(); 
    } 

    @Override 
    public int getItemViewType(int position) { 
     return items.get(position).type; 
    } 


    @Override 
    public BaseViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { 

     LayoutInflater mInflater = LayoutInflater.from(parent.getContext()); 

     switch (viewType) { 
      case SearchItem.TYPE_LOADING: 
       ViewGroup vLoading = (ViewGroup) mInflater.inflate(R.layout.search_item_loading, parent, false); 
       return new LoadingViewHolder(vLoading); 
      case SearchItem.TYPE_DEFAULT:default: 
       ViewGroup vDefault = (ViewGroup) mInflater.inflate(R.layout.search_item_default, parent, false); 
       return new DefaultViewHolder(vDefault); 
     } 
    } 

    @Override 
    public void onBindViewHolder(BaseViewHolder holder, int position) { 

     SearchItem item = items.get(position); 

     switch (holder.getItemViewType()) { 
      case SearchItem.TYPE_DEFAULT: 
       DefaultViewHolder defaultViewHolder = (DefaultViewHolder) holder; 
       defaultViewHolder.mTextViewTitle.setText(((SearchItem.DefaultItem)item).title); 
      case SearchItem.TYPE_LOADING: 
       LoadingViewHolder loadingViewHolder = (LoadingViewHolder) holder; 
       loadingViewHolder.mTextViewIcon.setText(((SearchItem.LoadingItem)item).icon); 
       loadingViewHolder.mTextViewTitle.setText(((SearchItem.LoadingItem)item).title); 
     } 
    } 

    /** 
    * Base view holder. 
    */ 
    public static class BaseViewHolder extends RecyclerView.ViewHolder { 
     public BaseViewHolder(View view) { 
      super(view); 
     } 
    } 

    public static class DefaultViewHolder extends BaseViewHolder { 

     @Bind(R.id.mTextViewTitle) 
     TextView mTextViewTitle; 

     public DefaultViewHolder(View mView) { 
      super(mView); 
      ButterKnife.bind(this, mView); 
     } 
    } 

    public static class LoadingViewHolder extends BaseViewHolder { 

     @Bind(R.id.mTextViewIcon) 
     TextView mTextViewIcon; 

     @Bind(R.id.mTextViewTitle) 
     TextView mTextViewTitle; 

     public LoadingViewHolder(View mView) { 
      super(mView); 
      ButterKnife.bind(this, mView); 
     } 
    } 
} 

onBindViewHolder

LoadingViewHolder loadingViewHolder = (LoadingViewHolder) holder; 

機器人工作室已經給了我鑄造holderLoadingViewHolder的時候,我可能會得到一個異常的警告。運行項目時,我得到:

SearchAdapter$DefaultViewHolder cannot be cast to SearchAdapter$LoadingViewHolder 

因此不知何故DefaultViewHolder被轉移到LoadingViewHolder,但它不應該。相反,BaseViewHolder應該被鑄造。你看到最新的錯誤?

+0

'holder.getItemViewType()'似乎不存在。 – CommonsWare

回答

1

你寫的代碼是錯誤的,因爲你的要求和你想要實現的。我所看到的實施要擴展不通用RecyclerView持有人,即這將需要在基礎視圖架爲單座

extends RecyclerView.Adapter<RecyclerView.ViewHolder> 

而不是

extends RecyclerView.Adapter<SearchAdapter.BaseViewHolder> 

在這裏,整個代碼是如何做到這一點


https://gist.github.com/umesh0492/e65d5195d8962b1a3049

+0

SearchAdapter.BaseViewHolder是RecyclerView.ViewHolder的子類,所以這不應該是問題。 –

+0

@artworkadシ這就是我所說的,如果你只擴展BaseViewHolder,那麼你只能訪問該視圖/持有者類型。您不能使用其他持有人類型的視圖進行遊戲。你必須擴展我上面提到的內容,在那裏我可以看一下如何做到這一點。 – UMESH0492

+0

我試過了你的建議,但是我得到了同樣的錯誤... –

0

這可能是LAT e但是對於得到相同錯誤的人。 在每種情況下都使用「break」,並且不會出現任何錯誤。

+0

像是換行符還是代碼執行中斷? – NickSentowski

相關問題