Reputation: 205
In my adapter I have three variations of view using yellow, orange and red for their different text-color. To go along with these, I'm trying to have three different images as thumbnails (hhy, hho, hhr). When it runs the images do not match with their corresponding view item, I'm getting the hho and hhy either one item too early or late in the listview. I have the imageview layout names correct so I'm unsure why they are not displaying correctly.
PostItemAdapter.java
@Override
public View getView(int position, View convertView, ViewGroup parent)
{
ViewHolder viewHolder;
int listViewItemType = getItemViewType(position);
if (convertView == null) {
convertView = inflater.inflate(R.layout.postitem, null);
viewHolder = new ViewHolder();
//viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb);
if (listViewItemType == TYPE_short) {
viewHolder.itemTitleView = (TextView) convertView.findViewById(R.id.itemTitleLabel);
viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb);
} else if (listViewItemType == TYPE_med) {
viewHolder.itemTitleView = (TextView) convertView.findViewById(R.id.itemTitleLabel1);
viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb1);
} else {
viewHolder.itemTitleView = (TextView) convertView.findViewById(R.id.itemTitleLabel2);
viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb2);
}
convertView.setTag(viewHolder);
} else {
viewHolder = (ViewHolder) convertView.getTag();
}
if (listViewItemType == TYPE_short) {
viewHolder.itemTitleView.setText(datas.get(position).itemTitle);
viewHolder.itemThumbView.setImageResource(R.drawable.hhy);
} else if (listViewItemType == TYPE_med) {
viewHolder.itemTitleView.setText(datas.get(position).itemTitle);
viewHolder.itemThumbView.setImageResource(R.drawable.hho);
} else {
viewHolder.itemTitleView.setText(datas.get(position).itemTitle);
viewHolder.itemThumbView.setImageResource(R.drawable.hhr);
}
return convertView;
}
}
and the relevant layout postitem.xml
<ImageView
android:id="@+id/itemThumb"
android:layout_width="48dp"
android:layout_height="48dp"
android:src="@drawable/hhy"
android:scaleType="centerCrop"
android:layout_marginRight="5dp"/>
<ImageView
android:id="@+id/itemThumb1"
android:layout_width="48dp"
android:layout_height="48dp"
android:src="@drawable/hho"
android:scaleType="centerCrop"
android:layout_marginRight="5dp"/>
<ImageView
android:id="@+id/itemThumb2"
android:layout_width="48dp"
android:layout_height="48dp"
android:src="@drawable/hhr"
android:scaleType="centerCrop"
android:layout_marginRight="5dp"/>
<TextView
android:id="@+id/itemTitleLabel"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignTop="@id/itemThumb"
android:layout_toRightOf="@id/itemThumb"
android:maxLines="2"
android:textIsSelectable="false"
android:textSize="16sp"
android:textStyle="bold"
android:textColor="#ffff00"
android:ellipsize="end"
/>
<TextView
android:id="@+id/itemTitleLabel1"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignTop="@id/itemThumb"
android:layout_toRightOf="@id/itemThumb"
android:maxLines="2"
android:textIsSelectable="false"
android:textSize="16sp"
android:textStyle="bold"
android:textColor="#ffa500"
android:ellipsize="end"
/>
<TextView
android:id="@+id/itemTitleLabel2"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignTop="@id/itemThumb"
android:layout_toRightOf="@id/itemThumb"
android:maxLines="2"
android:textIsSelectable="false"
android:textSize="16sp"
android:textStyle="bold"
android:textColor="#ff0000"
android:ellipsize="end"
/>
Upvotes: 0
Views: 720
Reputation: 1599
There's a few issues with what you have going on in your question. Recycled views are intended to only be inflated/created enough times to populate the visible portion of your ListView fully for the first time. They are then recycled as you scroll rather than created again.
Which means this block is only called the first few times:
if (convertView == null) {
convertView = inflater.inflate(R.layout.postitem, null);
viewHolder = new ViewHolder();
//viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb);
if (listViewItemType == TYPE_short) {
viewHolder.itemTitleView = (TextView) convertView.findViewById(R.id.itemTitleLabel);
viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb);
} else if (listViewItemType == TYPE_med) {
viewHolder.itemTitleView = (TextView) convertView.findViewById(R.id.itemTitleLabel1);
viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb1);
} else {
viewHolder.itemTitleView = (TextView) convertView.findViewById(R.id.itemTitleLabel2);
viewHolder.itemThumbView = (ImageView) convertView.findViewById(R.id.itemThumb2);
}
convertView.setTag(viewHolder);
}
For subsequent recycles your ViewHolder could be pointing at an unintended resource. If the current item is TYPE_med, the viewHolder.itemThumbView could have been created with a different resource reference (i.e. TYPE_short at the time of creation). Fixing this still won't solve your problem because you have the other two ImageViews/TextViews hanging around.
I'm not seeing any apparent need to have multiple ImageViews/TextViews so rather than setting visibility on everything the more accepted approach would be:
static class ViewHolder
{
private TextView mTextViewTitle;
private ImageView mImageViewThumb;
}
@Override
public View getView(int position, View convertView, ViewGroup parent)
{
ViewHolder viewHolder;
Item i = datas.get(position);
int listViewItemType = i.viewtype;
if (convertView == null) {
convertView = inflater.inflate(R.layout.postitem, null);
viewHolder = new ViewHolder();
viewHolder.mTextViewTitle = (TextView) convertView.findViewById(R.id.itemTitleLabel);
viewHolder.mImageViewThumb = (ImageView) convertView.findViewById(R.id.itemThumb);
convertView.setTag(viewHolder);
} else {
viewHolder = (ViewHolder) convertView.getTag();
}
viewHolder.mTextViewTitle.setText(i.itemTitle);
if (listViewItemType == TYPE_short) {
viewHolder.mTextViewTitle.setTextColor(Color.parseColor("#ffff00"));
viewHolder.mImageViewThumb.setImageResource(R.drawable.hhy);
} else if (listViewItemType == TYPE_med) {
viewHolder.mTextViewTitle.setTextColor(Color.parseColor("#ffff00"));
viewHolder.mImageViewThumb.setImageResource(R.drawable.hho);
} else {
viewHolder.mTextViewTitle.setTextColor(Color.parseColor("#ff0000"));
viewHolder.mImageViewThumb.setImageResource(R.drawable.hhr);
}
return convertView;
}
It would be better to have your colors defined in resources, but I'll save that for another discussion.
Your new XML:
<ImageView
android:id="@+id/itemThumb"
android:layout_width="48dp"
android:layout_height="48dp"
android:scaleType="centerCrop"
android:layout_marginRight="5dp" />
<TextView
android:id="@+id/itemTitleLabel"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignTop="@id/itemThumb"
android:layout_toRightOf="@id/itemThumb"
android:maxLines="2"
android:textIsSelectable="false"
android:textSize="16sp"
android:textStyle="bold"
android:ellipsize="end" />
Upvotes: 4
Reputation: 205
Okay so, my problem is that when the listview views were being recycled they were overwriting, or unable to overwrite, the pre-existing image/text. My rather hacky solution was to use the following code. If anyone knows the way you are supposed to resolve this I would be interested in hearing about it :P
PostItemAdapter.java (ViewHolder)
static class ViewHolder
{
private TextView itemTitleViewY, itemTitleViewO, itemTitleViewR;
private ImageView itemThumbViewY, itemThumbViewO, itemThumbViewR;
}
@Override
public View getView(int position, View convertView, ViewGroup parent)
{
ViewHolder viewHolder;
Item i = datas.get(position);
int listViewItemType = i.viewtype;
if (convertView == null) {
convertView = inflater.inflate(R.layout.postitem, null);
viewHolder = new ViewHolder();
viewHolder.itemTitleViewY = (TextView) convertView.findViewById(R.id.itemTitleLabel);
viewHolder.itemThumbViewY = (ImageView) convertView.findViewById(R.id.itemThumb);
viewHolder.itemTitleViewO = (TextView) convertView.findViewById(R.id.itemTitleLabel1);
viewHolder.itemThumbViewO = (ImageView) convertView.findViewById(R.id.itemThumb1);
viewHolder.itemTitleViewR = (TextView) convertView.findViewById(R.id.itemTitleLabel2);
viewHolder.itemThumbViewR = (ImageView) convertView.findViewById(R.id.itemThumb2);
convertView.setTag(viewHolder);
} else {
viewHolder = (ViewHolder) convertView.getTag();
}
switch (listViewItemType) {
case 0:
viewHolder.itemTitleViewY.setText(i.itemTitle);
viewHolder.itemTitleViewO.setText("");
viewHolder.itemTitleViewR.setText("");
viewHolder.itemThumbViewY.setVisibility(View.VISIBLE);
viewHolder.itemThumbViewO.setVisibility(View.INVISIBLE);
viewHolder.itemThumbViewR.setVisibility(View.INVISIBLE);
Log.d("DEBUG CHECKME", "getItemViewType Y: " + i.itemTitle + ", " + i.viewtype + ", " + i);
break;
case 1:
viewHolder.itemTitleViewO.setText(i.itemTitle);
viewHolder.itemTitleViewY.setText("");
viewHolder.itemTitleViewR.setText("");
viewHolder.itemThumbViewO.setVisibility(View.VISIBLE);
viewHolder.itemThumbViewY.setVisibility(View.INVISIBLE);
viewHolder.itemThumbViewR.setVisibility(View.INVISIBLE);
Log.d("DEBUG CHECKME", "getItemViewType O: " + i.itemTitle + ", " + i.viewtype + ", " + i);
break;
case 2:
viewHolder.itemTitleViewR.setText(i.itemTitle);
viewHolder.itemTitleViewO.setText("");
viewHolder.itemTitleViewY.setText("");
viewHolder.itemThumbViewR.setVisibility(View.VISIBLE);
viewHolder.itemThumbViewY.setVisibility(View.INVISIBLE);
viewHolder.itemThumbViewO.setVisibility(View.INVISIBLE);
Log.d("DEBUG CHECKME", "getItemViewType R: " + i.itemTitle + ", " + i.viewtype + ", " + i);
break;
default:
viewHolder.itemTitleViewY.setText("");
viewHolder.itemTitleViewO.setText("");
viewHolder.itemTitleViewR.setText("");
viewHolder.itemThumbViewY.setVisibility(View.INVISIBLE);
viewHolder.itemThumbViewO.setVisibility(View.INVISIBLE);
viewHolder.itemThumbViewR.setVisibility(View.INVISIBLE);
Log.d("DEBUG CHECKME", "getItemViewType D: " + i.itemTitle + ", " + i.viewtype + ", " + i);
break;
}
return convertView;
}
Upvotes: 0