自定义适配器的 getView returns 错误位置
getView of custom adapter returns wrong Position
我已经为 gridview 编写了自定义适配器。网格视图中的每个项目都有其他子视图。其中之一是textView,它实现了点击监听器。
当用户单击 TextView 时,我会显示一个 Toast,它显示项目在 gridView 中的位置。
现在进入问题:
每次调用 getView() 时,我将 getView() 返回的 "position" 作为标记分配给 TextView。当我滚动时,getView() 提供的 "position" 是正确的值,但是一旦滚动停止,getView() 提供的位置变为 0,除非我在网格视图的顶部。但是,保存在 TextView 标记中的值始终是正确的值。这是为什么?
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder viewHolder;
if(convertView == null){
convertView = mLayoutIflater.inflate(R.layout.grid_item, null);
viewHolder = new ViewHolder();
…..
viewHolder.playButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.e(“test”, "myPos: "+ (Integer) viewHolder.mTextView.getTag()); // always returns correct position value
}
});
convertView.setTag(viewHolder);
}
else
viewHolder = (ViewHolder) convertView.getTag();
Log.e(“test”, "GETVIEW: "+ position); // position is zero when scrolling stops & correct value when scrolling
viewHolder.mTextView.setTag(position);
return convertView;
}
此致
试试这个。
convertView = mLayoutIflater.inflate(R.layout.grid_item, parent, false);
将代码修改成这样,
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder viewHolder;
if(convertView == null){
convertView = mLayoutIflater.inflate(R.layout.grid_item, null);
viewHolder = new ViewHolder();
…..
convertView.setTag(viewHolder);
}
else
viewHolder = (ViewHolder) convertView.getTag();
Log.e(“test”, "GETVIEW: "+ position); // position is zero when scrolling stops & correct value when scrolling
viewHolder.mTextView.setTag(position);
viewHolder.playButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.e(“test”, "myPos: "+ (Integer) viewHolder.mTextView.getTag()); // always returns correct position value
}
});
return convertView;
}
AdapterView 可以在其 Adapter 上任意调用 getView()
。没有保证这样做的顺序或时间。滚动完成时,它调用该方法的最后一个位置可能是 0
位置是无关紧要的。使用相应的视图(或其子视图)缓存传递的位置值是跟踪它的正确方法。调用 getView()
的最后一个位置不会告诉您任何与 AdapterView 的行为相关的信息,您不应该依赖它。
适配器并不是真正定义onClickListener 的地方。尝试在主 Activity 或任何已定义的地方为 GridView 使用 onItemClickListener()
。这是更简单的方法以及应该如何完成。
始终更喜欢 Android 的推荐做法,而不是在 类.
中进行试验
我已经为 gridview 编写了自定义适配器。网格视图中的每个项目都有其他子视图。其中之一是textView,它实现了点击监听器。
当用户单击 TextView 时,我会显示一个 Toast,它显示项目在 gridView 中的位置。
现在进入问题:
每次调用 getView() 时,我将 getView() 返回的 "position" 作为标记分配给 TextView。当我滚动时,getView() 提供的 "position" 是正确的值,但是一旦滚动停止,getView() 提供的位置变为 0,除非我在网格视图的顶部。但是,保存在 TextView 标记中的值始终是正确的值。这是为什么?
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder viewHolder;
if(convertView == null){
convertView = mLayoutIflater.inflate(R.layout.grid_item, null);
viewHolder = new ViewHolder();
…..
viewHolder.playButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.e(“test”, "myPos: "+ (Integer) viewHolder.mTextView.getTag()); // always returns correct position value
}
});
convertView.setTag(viewHolder);
}
else
viewHolder = (ViewHolder) convertView.getTag();
Log.e(“test”, "GETVIEW: "+ position); // position is zero when scrolling stops & correct value when scrolling
viewHolder.mTextView.setTag(position);
return convertView;
}
此致
试试这个。
convertView = mLayoutIflater.inflate(R.layout.grid_item, parent, false);
将代码修改成这样,
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final ViewHolder viewHolder;
if(convertView == null){
convertView = mLayoutIflater.inflate(R.layout.grid_item, null);
viewHolder = new ViewHolder();
…..
convertView.setTag(viewHolder);
}
else
viewHolder = (ViewHolder) convertView.getTag();
Log.e(“test”, "GETVIEW: "+ position); // position is zero when scrolling stops & correct value when scrolling
viewHolder.mTextView.setTag(position);
viewHolder.playButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Log.e(“test”, "myPos: "+ (Integer) viewHolder.mTextView.getTag()); // always returns correct position value
}
});
return convertView;
}
AdapterView 可以在其 Adapter 上任意调用 getView()
。没有保证这样做的顺序或时间。滚动完成时,它调用该方法的最后一个位置可能是 0
位置是无关紧要的。使用相应的视图(或其子视图)缓存传递的位置值是跟踪它的正确方法。调用 getView()
的最后一个位置不会告诉您任何与 AdapterView 的行为相关的信息,您不应该依赖它。
适配器并不是真正定义onClickListener 的地方。尝试在主 Activity 或任何已定义的地方为 GridView 使用 onItemClickListener()
。这是更简单的方法以及应该如何完成。
始终更喜欢 Android 的推荐做法,而不是在 类.