2015-05-06 69 views
5

滾動後滾動RecyclerView時出現問題。這個想法是改變元素的顏色,但是當我向下滾動時,一切都很好,當滾動上升時 - 不應着色的元素正在改變顏色。RecyclerView滾動時滾動數據

這裏是我的適配器:

public class NotificationsAdapter extends RecyclerView.Adapter<NotificationsAdapter.ViewHolder> { 

private NotificationData notificationData; 
private Context mContext; 
private ArrayList<NotificationData> infromationList = new ArrayList<>(); 


public NotificationsAdapter(Context context, ArrayList<NotificationData> infromationList) { 
    this.infromationList = infromationList; 
    this.mContext = context; 
} 


@Override 
public NotificationsAdapter.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { 

    View itemLayoutView; 
    ViewHolder viewHolder; 

    itemLayoutView = LayoutInflater.from(parent.getContext()) 
      .inflate(R.layout.notification_single_item, parent, false); 
    viewHolder = new ViewHolder(itemLayoutView, viewType); 

    return viewHolder; 
} 

@Override 
public void onBindViewHolder(NotificationsAdapter.ViewHolder holder, int position) { 

    notificationData = infromationList.get(position); 
    holder.notificationDate.setText(convertDate(notificationData.getDate())); 
    holder.notificationStatus.setText(notificationData.getNotificationStatus()); 
    holder.orderDescription.setText(notificationData.getNotificationLabel()); 

    if ("true".equals(notificationData.getReadStatus())) { 
     holder.root.setBackgroundColor(mContext.getResources().getColor(R.color.white)); 
     holder.notificationStatus.setTypeface(Typeface.create("sans-serif-light", Typeface.NORMAL)); 
    } 

} 

@Override 
public int getItemCount() { 
    return (null != infromationList ? infromationList.size() : 0); 
} 

public static class ViewHolder extends RecyclerView.ViewHolder { 

    public TextView notificationDate; 
    public TextView notificationStatus; 
    public TextView orderDescription; 
    public LinearLayout root; 

    public ViewHolder(View itemView, int position) { 
     super(itemView); 

     notificationDate = (TextView) itemView.findViewById(R.id.notificationDate); 
     notificationStatus = (TextView) itemView.findViewById(R.id.notificationStatus); 
     orderDescription = (TextView) itemView.findViewById(R.id.orderDescription); 
     root = (LinearLayout) itemView.findViewById(R.id.root); 
    } 

} 

private String convertDate(String date) { 
    String convertedDate; 

    String[] parts = new String[2]; 
    parts = date.split("T"); 
    date = parts[0]; 

    SimpleDateFormat sdf = new SimpleDateFormat("yyyy-mm-dd"); 
    Date testDate = null; 
    try { 
     testDate = sdf.parse(date); 
    }catch(Exception ex){ 
     ex.printStackTrace(); 
    } 
    SimpleDateFormat formatter = new SimpleDateFormat("dd.mm.yyyy"); 
    convertedDate = formatter.format(testDate); 

    return convertedDate; 
} 
} 

回答

2

有問題,你onBindViewHolder(...),應該是:

if ("true".equals(notificationData.getReadStatus())) { 
    holder.root.setBackgroundColor(mContext.getResources().getColor(R.color.white)); 
    holder.notificationStatus.setTypeface(Typeface.create("sans-serif-light", Typeface.NORMAL)); 
} 
else { 
    holder.root.setBackgroundColor(yourDefaultColor); 
    holder.notificationStatus.setTypeface(yourDefaultTypeface); 

} 
+0

這對我有效。我以爲默認值是按defauf設定的,但是完全是誤解。 – MeLine

26

我有同樣的問題,我發現這樣做的唯一的解決辦法是:

holder.setIsRecyclable(false); 

您的回收商不會再回收,因此當您滾動時,這些項目將保持不變,如果要刪除某個項目,請不要使用notifyitemRemoved(position),而應使用notifyDataSetChanged()

+2

以上對我有幫助謝謝..... – Dilip

+5

請注意:您不應該使用這些建議中的任何一個。正如Jhonatan自己所說,這些意見將不再被回收,這完全喪失了回收者的目的,並且會導致表現不佳。同樣,使用蠻力notifyDataSetChanged()應該始終是最後的手段 - 如果可能的話,嘗試讓適配器準確知道刪除或添加數據時更新了哪些項目 - 這不僅可以提高性能,還可以讓它適當地執行動畫。 – jhm

+0

thanx man我最近3天被發現這個問題.. –

0

onBindHolder多次調用Recycler View需要一個視圖,除非是新視圖。所以每次你在子視圖中設置平衡時,其他視圖狀態也是變化。

無論何時上下滾動,這些視圖都會被重新繪製爲具有錯誤的可見性選項,因此始終指定這兩個條件會導致回收視圖不知道我們小組件的先前狀態/條件/值。

解決方案:

如果如果你塊中的其他塊中設置任何Android widget.setVisibility(View.Gone)的知名度,那麼你必須設置它就像widget.setVisibility(View.Visible)的知名度相對值克服了上述問題。

@Override 
public void onBindViewHolder(ViewHolder viewHolder, int i) { 

    viewHolder.tvName.setText(ModelCategoryProducts.name.get(i)); 
    viewHolder.tvPrice.setText("Rs."+String.format("%.2f", Float.parseFloat(ModelCategoryProducts.price.get(i)))); 
    if(ModelCategoryProducts.special_price.get(i).equals("null")) { 
     viewHolder.tvSpecialPrice.setVisibility(View.GONE); // here visibility is gone and in else it's opposite visibility i set. 
     viewHolder.tvPrice.setTextColor(Color.parseColor("#ff0000")); 
     viewHolder.tvPrice.setPaintFlags(0);// here paint flag is 0 and in else it's opposite flag that i want is set. 
    }else if(!ModelCategoryProducts.special_price.get(i).equals("null")){ 
     viewHolder.tvPrice.setTextColor(Color.parseColor("#E0E0E0")); 
     viewHolder.tvSpecialPrice.setVisibility(View.VISIBLE); 
     viewHolder.tvSpecialPrice.setText("Rs." + String.format("%.2f", Float.parseFloat(ModelCategoryProducts.special_price.get(i)))); 
     viewHolder.tvPrice.setPaintFlags(viewHolder.tvPrice.getPaintFlags() | Paint.STRIKE_THRU_TEXT_FLAG); 
    } 
    if (!ModelCategoryProducts.image_url.get(i).isEmpty()) { 
     Picasso.with(context) 
       .load(ModelCategoryProducts.image_url.get(i)) 
       .into(viewHolder.ivProduct); 
    } 

    viewHolder.setClickListener(new ItemClickListener() { 
     @Override 
     public void onClick(View view, int position, boolean isLongClick) { 
      if (isLongClick) { 
//     Toast.makeText(context, "#" + position + " - " + ModelCategoryProducts.name.get(position) + " (Long click)", Toast.LENGTH_SHORT).show(); 
      } else { 
       Toast.makeText(context, "#" + position + " - " + ModelCategoryProducts.name.get(position), Toast.LENGTH_SHORT).show(); 
       Intent i = new Intent(context, ProductDetail.class); 
       i.putExtra("position",position); 
       i.putExtra("flagHlvCheck", 5); 
       context.startActivity(i); 
      } 
     } 
    }); 
} 
0
@Override 
public DataObjectHolder onCreateViewHolder(ViewGroup parent, 
              int viewType) { 
    View view = LayoutInflater.from(parent.getContext()) 
      .inflate(R.layout.custom_layout, parent, false); 

    DataObjectHolder dataObjectHolder = new DataObjectHolder(view); 
    dataObjectHolder.setIsRecyclable(false); 

    return dataObjectHolder; 
} 
8

在適配器構造函數添加setHasStableIds(true);和 覆蓋適配器這兩個methodes。

@Override 
public long getItemId(int position) { 
      return position; 
} 

@Override 
public int getItemViewType(int position) { 
     return position; 
} 
+1

這對我有用。你能否提供更多的解釋,爲什麼這有效? –

+0

你能提供更多解釋嗎? – Rino