2011-08-12 162 views
3

我通过教程去搜查,但我仍然无法理解,Android的自定义列表视图

getView(int position, View convertView, ViewGroup arg2) 

方法扩展BaseAdapter何时创建我的Android应用程序自定义的ListView是如何工作的。因此,我不能编辑我想要的自定义列表视图。

我需要知道这个方法调用的时间和参数的含义。

如果有人可以解释下面的方法它很棒。当你在你的代码中调用setAdapter感谢

@Override 
public View getView(int position, View convertView, ViewGroup arg2) 
{ 

    ViewHolder holder; 
    LayoutInflater inflater = context.getLayoutInflater(); 

    if (convertView == null) 
    { 
     convertView = inflater.inflate(R.layout.listitem_row, null);      
     holder = new ViewHolder(); 
     holder.txtViewTitle = (TextView) convertView.findViewById(R.id.textView1); 
     holder.txtViewDescription = (TextView) convertView.findViewById(R.id.textView2); 

     convertView.setTag(holder); 
    } 
    else 
    { 
     holder = (ViewHolder) convertView.getTag();           
    } 

    holder.txtViewTitle.setText(title[position]); 
    holder.txtViewDescription.setText(description[position]); 



    return convertView; 
} 

回答

3

getView():正如在规范中提到的getView方法在指定的位置显示数据。所以,当你设置适配器,当你滚动你的listView getView方法将被调用。

你在这里复制的方法是EfficientAdapter的一部分,以优化您的ListView性能和优化您一起使用ViewHolder模式。

从规格复制:几乎没有更多的解释

位置:该项目的适配器的数据集,我们希望其观点的项目中的位置。

convertView:旧的视图重用,如果可能的话。注意:在使用之前,您应该检查此 视图是否为非空且类型适当。如果无法将此视图转换为显示正确的数据,则此方法可以创建新视图。异构列表可以指定它们的视图类型数量,因此这个视图始终是正确的类型(请参阅getViewTypeCount()和getItemViewType(int))。

所以,在上面的方法中,当你正在做以下的事情时,你是重用你的convertView。

 if (convertView == null){ 
      .... 
      convertView.setTag(holder); 
    } else { 
      holder = (ViewHolder) convertView.getTag(); 
     } 

并通过这样你避免查找(findViewById)以后的事,那是什么好东西约ViewHolder模式

 holder.txtViewTitle = (TextView) convertView.findViewById(R.id.textView1); 

:父,这种观点最终会附加到

编辑

问题:调用getView多少次,并创建多少个convertView? 答:让我们以Efficeint Adapter from ApiDemos为例。如果你的屏幕显示10行,那么,

convertView计数:10 + 1 = 11(10行你在屏幕上看到的,一个额外的显示滚动效果)。这意味着if(convertView == null){...}块中的语句只会被调用11次。

getView计数:最初计数将为10,但是当您开始滚动时,计数会继续增加。每次调用getView来更新数据。

注意:这仅适用于问题中提到的getView方法。

+0

是的,但是当我使用此方法将项目加载到listview中时,getView()方法运行的元素数量是显示。我无法理解为什么...... – JibW

+0

并且在它第一次创建convertView = inflater.inflate(R.layout.listitem_row,null)的同时,当它加载项时,它会运行多次。你能解释一下为什么? – JibW

+0

@JibW当然,这取决于你在屏幕上可以看到多少行。假设你只看到3行,这意味着ListView只需要显示3个convertView,当你滚动它们时,这3个将被重用。因为你一次没有在屏幕上显示更多的内容。这就是为什么getView会被调用3次。尝试HierarchyViewer它将帮助你更多地了解ConvertViews的数量。希望这个回答你的问题...如果不能ping我...我会很乐意帮助你。 – Gopal

4

getView()被调用。在此之后,当您将焦点移至列表或选择任何项目或致电notifyDataSetChanged()时,您将拨打电话getView()

Position - 该项目在适配器的数据集中的位置,该项目的数据集的视图是我们想要的。

convertView - 旧的视图重用,如果可能的话。注意:你应该在使用之前检查这个视图是非空的并且是合适的类型。如果无法将此视图转换为显示正确的数据,则此方法可以创建新视图。异构列表可以指定其视图类型的数量,以便此视图始终为正确的类型

ViewGroup - 该视图最终将附加到该视图。

+0

嗨vineetska感谢您的答案。在我的代码中,当我想加载这个列表时,getView()方法调用列表视图中记录数的三倍。我通过创建一个日志检查它..不明白为什么这是如此 – JibW

+0

使用“LayoutInflater inflater =(LayoutInflater)mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);”在内部如果在getView()中代替“LayoutInflater inflater = context.getLayoutInflater(); ” –

+0

仍然是这样。使用这种方法有点混乱..无法真正找出执行次数。执行此方法的次数是记录的三倍(当列表中显示2个listview记录时,此方法运行6次) – JibW

2

这里是getView()参数的描述:

int position - 的视图中的列表中的位置;

View convertView - 恕我直言,这是理解最困难的参数。在列表工作开始时,convertView = null。但是当你开始向下滚动时,当一个列表项(它是View的实例)被隐藏时,它将被存储在内存中,如convertView。这个技巧可以让你当你将列表滚动回,但使用存储在内存中的convertView时不创建新项目。因此,成为convertView的列表中的第一项是0位置处的项目。请记住,当您向下滚动ListView(从0位置到更大)时,如果向上滚动ListView,则convertView位于顶部和底部。

ViewGroup arg2 - 这是你的ListView(这个类来源于ViewGroup)。

ViewHolder是一种模式,它可以与列表项目进行舒适的通信。您将此对象作为项目的标记,并可用于与列表项目间接交互,因为它引用了项目的字段(View.setTag(holder))。

每次Android需要绘制另一个列表项时,都会调用getView()方法。

有任何问题吗?

+0

感谢teoREtik .. 。当我使用这种方法将项目加载到listview中时,getView()方法运行三次要显示的元素数量。(例如getView()方法运行6次,如果它必须加载2个元素到列表视图),我不知道为什么........也创建convertView = inflater.inflate(R.layout.listitem_row, null),通过检查convertview == null,它在将元素加载到列表视图中时运行多次 – JibW