自定义ArrayAdapter + ListView,某些行未正确处理

时间:2012-04-03 12:57:28

标签: android listview android-arrayadapter

这篇文章对图像很重要。

我创建了一个自定义ArrayAdapter并在Listview上使用它。我在适配器上遗漏了什么吗?

   @Override
   public View getView(int position, View convertView, ViewGroup parent) {
      View row = convertView;
      ArrayHolder holder = null;

      if(row == null)
      {
        LayoutInflater inflater = ((Activity)context).getLayoutInflater();
        row = inflater.inflate(layoutResourceId, parent, false);
        holder = new ArrayHolder();
        holder.txtTitle = (TextView)row.findViewById(R.id.txtTitle);
        row.setTag(holder);
     }
     else
     {
        if(position % 2 == 0){row.setBackgroundColor(Color.DKGRAY);}
        else{row.setBackgroundColor(Color.BLACK);}

        Typeface font1 =Typeface.createFromAsset(context.getAssets(),"fonts/kingrich.ttf");
        ((TextView)row.findViewById(R.id.txtTitle)).setTypeface(font1);
        ((TextView)row.findViewById(R.id.txtTitle)).setTextColor(Color.rgb(153, 255, 102));

        holder = (ArrayHolder)row.getTag();

    }

    String array = data.get(position);
    holder.txtTitle.setText(array);
    return row;
  }

首次启动应用程序时,将显示以下屏幕: (屏幕形成一个实际的设备,而不是模拟器)

After app is initialized

现在,如果我使用后退按钮关闭虚拟键盘,我可以看到一行现在被错误地着色,当我向下滚动一点时:

Scroll down a little to see the "bad" row

如果我向上和向下滚动,该行将使着色正确。

提前致谢

2 个答案:

答案 0 :(得分:1)

在我看来,您没有正确处理新视图的创建。

文本显示为白色,这告诉我们跳过了else块(因此convertView参数为null,或者没有要回收的视图(这是公平的,因为当软键盘消失时你会看到更多的视图)

向上/向下滚动后,行会正确显示,因为您现在有了回收的视图,因此您将进入else块。

Imho你应该完全删除else关键字。 这样,只有在确实需要的情况下才会输入if(创建新视图的地方),否则即使视图是新的也不会被回收,您将始终使用正确的颜色。

尝试一下,告诉我它是否有效

@Override
public View getView(int position, View convertView, ViewGroup parent) {
  View row = convertView;
  ArrayHolder holder = null;

  if(row == null)
  {
    LayoutInflater inflater = ((Activity)context).getLayoutInflater();
    row = inflater.inflate(layoutResourceId, parent, false);
    holder = new ArrayHolder();
    holder.txtTitle = (TextView)row.findViewById(R.id.txtTitle);
    row.setTag(holder);
 }
//this part must be executed every time, not only for recycled views
  if(position % 2 == 0){row.setBackgroundColor(Color.DKGRAY);}
  else{row.setBackgroundColor(Color.BLACK);}

  Typeface font1 = Typeface.createFromAsset(context.getAssets(),   "fonts/kingrich.ttf");
  ((TextView)row.findViewById(R.id.txtTitle)).setTypeface(font1);
  ((TextView)row.findViewById(R.id.txtTitle)).setTextColor(Color.rgb(153, 255, 102));

  holder = (ArrayHolder)row.getTag();



  String array = data.get(position);
  holder.txtTitle.setText(array);
  return row;
}

答案 1 :(得分:0)

不要将其余代码放在if(row == null)的else部分中:

 @Override
   public View getView(int position, View convertView, ViewGroup parent) {
      View row = convertView;
      ArrayHolder holder = null;

      if(row == null)
      {
        LayoutInflater inflater = ((Activity)context).getLayoutInflater();
        row = inflater.inflate(layoutResourceId, parent, false);
        holder = new ArrayHolder();
        holder.txtTitle = (TextView)row.findViewById(R.id.txtTitle);
        row.setTag(holder);
     }

        if(position % 2 == 0){row.setBackgroundColor(Color.DKGRAY);}
        else{row.setBackgroundColor(Color.BLACK);}

        Typeface font1 = Typeface.createFromAsset(context.getAssets(),   "fonts/kingrich.ttf");
        ((TextView)row.findViewById(R.id.txtTitle)).setTypeface(font1);
        ((TextView)row.findViewById(R.id.txtTitle)).setTextColor(Color.rgb(153, 255, 102));

        holder = (ArrayHolder)row.getTag();



    String array = data.get(position);
    holder.txtTitle.setText(array);
    return row;
  }

textView txtTitle没有变色,因为跳过了else块,因为listview没有回收的视图。

当您向上/向下滚动时,回收视图开始,您就可以进入其他部分了。最好完全删除sle部分,因为你想要将textview变为彩色,无论convertview是否为null。