草庐IT

android - 即使 View 存在,convertView 也会作为 null 传递

coder 2023-12-18 原文

我开发了一个 android 应用程序,其中图像和文本显示在 GridView 中,当用户向下滚动时会显示接下来的十个项目(图像和文本)。在调用 adapter.notifyDataSetChanged() 之后调用适配器的 getView 方法时会出现问题。适配器回收数据,但位置在 GridView 中重新排列和重复。在添加条件以检查 convertView 是否为 null 之前,我没有遇到过这个问题。

Activity 类:

public class DynamicListViewActivity extends Activity implements
    OnScrollListener {

int visibleElements;
int scrollState;
int count;
TextAdapter adapter = new TextAdapter();
int total=200;// total items limit in grid view


@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    setContentView(R.layout.grid);
    count=10;
    GridView grid = (GridView) findViewById(R.id.gridview);
    grid.setAdapter(adapter);
    grid.setOnScrollListener(this);

}

public void onScroll(AbsListView view, int firstVisible, int visibleCount,
        int totalCount) {
    visibleElements= visibleCount;
}

public void onScrollStateChanged(AbsListView v, int s) {
    Log.d("ScrollState", s+"");
    scrollState=s;
    isScrollStateComplete();
}

public void isScrollStateComplete(){
if(visibleElements>0 && scrollState==SCROLL_STATE_IDLE && total>count){
        int diff=total-count;
        count+=(diff>=10)?10:diff;//update count to next ten items
        adapter.notifyDataSetChanged();
    }
}


class TextAdapter extends BaseAdapter {
    public int getCount() {
        return count;
    }

    public Object getItem(int pos) {
        return pos;
    }

    public long getItemId(int pos) {
        return pos;
    }

    public View getView(int pos, View convertView, ViewGroup p) {

        View v = convertView;
        System.out.println("pos : "+pos+" boolean "+(v==null));// log to check position and convertView
                  if(v==null){
            v =((LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.textlayout,null);

            ImageView iv = (ImageView) v.findViewById(R.id.album_thumbnail);
            iv.setImageDrawable(getResources().getDrawable(R.drawable.icon));

            TextView tvAlbumName = (TextView)v.findViewById(R.id.album_name);
            tvAlbumName.setText("postion "+pos);

            TextView tvAlbumDesc = (TextView)v.findViewById(R.id.album_description);
            tvAlbumDesc.setText("");

           }

          return v;
    }
}
}

在滚动 GridView 之前正确显示。日志:

08-05 14:24:34.440: INFO/ActivityManager(58): Starting activity: Intent {  act=android.intent.action.MAIN cat=[android.intent.category.LAUNCHER] flg=0x10200000 cmp=com.mis.list.demo/.DynamicListViewActivity }
08-05 14:24:34.642: INFO/System.out(685): pos : 0 boolean true
08-05 14:24:34.710: INFO/System.out(685): pos : 0 boolean false
08-05 14:24:34.710: INFO/System.out(685): pos : 1 boolean true
08-05 14:24:34.730: INFO/System.out(685): pos : 2 boolean true
08-05 14:24:34.800: INFO/System.out(685): pos : 3 boolean true
08-05 14:24:34.860: INFO/System.out(685): pos : 4 boolean true
08-05 14:24:34.880: INFO/System.out(685): pos : 5 boolean true
08-05 14:24:34.910: INFO/System.out(685): pos : 6 boolean true
08-05 14:24:34.920: INFO/System.out(685): pos : 7 boolean true
08-05 14:24:34.960: INFO/System.out(685): pos : 0 boolean true
08-05 14:24:35.030: INFO/ActivityManager(58): Displayed activity com.mis.list.demo/.DynamicListViewActivity: 520 ms (total 520 ms)

第一次滚动结束后

08-05 14:26:15.740: DEBUG/ScrollState(685): 1
08-05 14:26:15.830: DEBUG/dalvikvm(685): GC_EXTERNAL_ALLOC freed 3624 objects / 257464 bytes in 71ms
08-05 14:26:16.210: INFO/System.out(685): pos : 8 boolean false
08-05 14:26:16.210: INFO/System.out(685): pos : 9 boolean true
08-05 14:26:16.250: DEBUG/ScrollState(685): 0
08-05 14:26:16.260: INFO/System.out(685): pos : 0 boolean true
08-05 14:26:16.271: INFO/System.out(685): pos : 0 boolean false
08-05 14:26:16.271: INFO/System.out(685): pos : 1 boolean false
08-05 14:26:16.271: INFO/System.out(685): pos : 2 boolean false
08-05 14:26:16.271: INFO/System.out(685): pos : 3 boolean false
08-05 14:26:16.271: INFO/System.out(685): pos : 4 boolean false
08-05 14:26:16.271: INFO/System.out(685): pos : 5 boolean false
08-05 14:26:16.280: INFO/System.out(685): pos : 6 boolean false
08-05 14:26:16.280: INFO/System.out(685): pos : 7 boolean false
08-05 14:26:16.280: INFO/System.out(685): pos : 8 boolean false
08-05 14:26:16.280: INFO/System.out(685): pos : 9 boolean false
08-05 14:26:16.280: INFO/System.out(685): pos : 10 boolean false
08-05 14:26:16.280: INFO/System.out(685): pos : 11 boolean true
08-05 14:26:16.371: DEBUG/dalvikvm(685): GC_EXTERNAL_ALLOC freed 644 objects / 33224 bytes in 41ms
08-05 14:26:45.270: WARN/KeyCharacterMap(685): No keyboard for id 0
08-05 14:26:45.270: WARN/KeyCharacterMap(685): Using default keymap: /system/usr/keychars/qwerty.kcm.bin
08-05 14:26:45.341: INFO/System.out(685): pos : 12 boolean true
08-05 14:26:45.351: INFO/System.out(685): pos : 13 boolean true
08-05 14:26:45.371: INFO/System.out(685): pos : 14 boolean true
08-05 14:26:45.380: INFO/System.out(685): pos : 15 boolean true
08-05 14:26:45.450: INFO/System.out(685): pos : 16 boolean false
08-05 14:26:45.450: INFO/System.out(685): pos : 17 boolean false
08-05 14:26:45.460: INFO/System.out(685): pos : 18 boolean false
08-05 14:26:45.460: INFO/System.out(685): pos : 19 boolean false

但是网格显示了重复的值,而不是按应有的顺序显示。 抱歉,我是新用户,不允许发布图片。

在日志中,我看到位置 0 convertView==null 为真。

如何设置这个权利,因为我计划下载图像来代替当前使用的 ImageView 的 android 图标。

请帮忙。

最佳答案

您对 convertView 的解释不正确。

public View getView(int position, @Nullable View convertView, ViewGroup parent) {

    View v = convertView;

    //If convertView is null create a new view, else use convert view
    if (v == null)
        v = ((LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE)).inflate(R.layout.textlayout, null);

    ImageView iv = (ImageView) v.findViewById(R.id.album_thumbnail);
    iv.setImageDrawable(getResources().getDrawable(R.drawable.icon));

    TextView tvAlbumName = (TextView)v.findViewById(R.id.album_name);
    tvAlbumName.setText("postion "+pos);

    TextView tvAlbumDesc = (TextView)v.findViewById(R.id.album_description);
    tvAlbumDesc.setText("");

    return v;
}

是你应该做的。

由于您所做的事情,在 convertView 不为 null 的情况下,您只是返回 convertView 而没有更新数据,因此您的图像被重复。仅在 convertView 为 null 的情况下才设置数据。

适配器和 ListView 系统之间的契约:如果传递的 convertView 为空,则创建一个新的,否则重新使用它。

关于android - 即使 View 存在,convertView 也会作为 null 传递,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6953866/

有关android - 即使 View 存在,convertView 也会作为 null 传递的更多相关文章

  1. ruby-on-rails - Rails - 一个 View 中的多个模型 - 2

    我需要从一个View访问多个模型。以前,我的links_controller仅用于提供以不同方式排序的链接资源。现在我想包括一个部分(我假设)显示按分数排序的顶级用户(@users=User.all.sort_by(&:score))我知道我可以将此代码插入每个链接操作并从View访问它,但这似乎不是“ruby方式”,我将需要在不久的将来访问更多模型。这可能会变得很脏,是否有针对这种情况的任何技术?注意事项:我认为我的应用程序正朝着单一格式和动态页面内容的方向发展,本质上是一个典型的网络应用程序。我知道before_filter但考虑到我希望应用程序进入的方向,这似乎很麻烦。最终从任何

  2. ruby-on-rails - 渲染另一个 Controller 的 View - 2

    我想要做的是有2个不同的Controller,client和test_client。客户端Controller已经构建,我想创建一个test_clientController,我可以使用它来玩弄客户端的UI并根据需要进行调整。我主要是想绕过我在客户端中内置的验证及其对加载数据的管理Controller的依赖。所以我希望test_clientController加载示例数据集,然后呈现客户端Controller的索引View,以便我可以调整客户端UI。就是这样。我在test_clients索引方法中试过这个:classTestClientdefindexrender:template=>

  3. ruby - RSpec - 使用测试替身作为 block 参数 - 2

    我有一些Ruby代码,如下所示:Something.createdo|x|x.foo=barend我想编写一个测试,它使用double代替block参数x,这样我就可以调用:x_double.should_receive(:foo).with("whatever").这可能吗? 最佳答案 specify'something'dox=doublex.should_receive(:foo=).with("whatever")Something.should_receive(:create).and_yield(x)#callthere

  4. ruby-on-rails - 如何在我的 Rails 应用程序 View 中打印 ruby​​ 变量的内容? - 2

    我是一个Rails初学者,但我想从我的RailsView(html.haml文件)中查看Ruby变量的内容。我试图在ruby​​中打印出变量(认为它会在终端中出现),但没有得到任何结果。有什么建议吗?我知道Rails调试器,但更喜欢使用inspect来打印我的变量。 最佳答案 您可以在View中使用puts方法将信息输出到服务器控制台。您应该能够在View中的任何位置使用Haml执行以下操作:-puts@my_variable.inspect 关于ruby-on-rails-如何在我的R

  5. ruby - 即使失败也继续进行多主机测试 - 2

    我已经构建了一些serverspec代码来在多个主机上运行一组测试。问题是当任何测试失败时,测试会在当前主机停止。即使测试失败,我也希望它继续在所有主机上运行。Rakefile:namespace:specdotask:all=>hosts.map{|h|'spec:'+h.split('.')[0]}hosts.eachdo|host|begindesc"Runserverspecto#{host}"RSpec::Core::RakeTask.new(host)do|t|ENV['TARGET_HOST']=hostt.pattern="spec/cfengine3/*_spec.r

  6. ruby-on-rails - 如何在 Rails View 上显示错误消息? - 2

    我是rails的新手,想在form字段上应用验证。myviewsnew.html.erb.....模拟.rbclassSimulation{:in=>1..25,:message=>'Therowmustbebetween1and25'}end模拟Controller.rbclassSimulationsController我想检查模型类中row字段的整数范围,如果不在范围内则返回错误信息。我可以检查上面代码的范围,但无法返回错误消息提前致谢 最佳答案 关键是您使用的是模型表单,一种显示ActiveRecord模型实例属性的表单。c

  7. ruby - rails 3 redirect_to 将参数传递给命名路由 - 2

    我没有找到太多关于如何执行此操作的信息,尽管有很多关于如何使用像这样的redirect_to将参数传递给重定向的建议:action=>'something',:controller=>'something'在我的应用程序中,我在路由文件中有以下内容match'profile'=>'User#show'我的表演Action是这样的defshow@user=User.find(params[:user])@title=@user.first_nameend重定向发生在同一个用户Controller中,就像这样defregister@title="Registration"@user=Use

  8. ruby - 字符串文字中的转义状态作为 `String#tr` 的参数 - 2

    对于作为String#tr参数的单引号字符串文字中反斜杠的转义状态,我觉得有些神秘。你能解释一下下面三个例子之间的对比吗?我特别不明白第二个。为了避免复杂化,我在这里使用了'd',在双引号中转义时不会改变含义("\d"="d")。'\\'.tr('\\','x')#=>"x"'\\'.tr('\\d','x')#=>"\\"'\\'.tr('\\\d','x')#=>"x" 最佳答案 在tr中转义tr的第一个参数非常类似于正则表达式中的括号字符分组。您可以在表达式的开头使用^来否定匹配(替换任何不匹配的内容)并使用例如a-f来匹配一

  9. ruby-on-rails - 如何生成传递一些自定义参数的 `link_to` URL? - 2

    我正在使用RubyonRails3.0.9,我想生成一个传递一些自定义参数的link_toURL。也就是说,有一个articles_path(www.my_web_site_name.com/articles)我想生成如下内容:link_to'Samplelinktitle',...#HereIshouldimplementthecode#=>'http://www.my_web_site_name.com/articles?param1=value1¶m2=value2&...我如何编写link_to语句“alàRubyonRailsWay”以实现该目的?如果我想通过传递一些

  10. ruby-on-rails - rspec - 如何检查方法是否存在? - 2

    我的模型有defself.empty_building//stuffend我怎样才能对这个现有的进行rspec?,已经尝试过:describe"empty_building"dosubject{Building.new}it{shouldrespond_to:empty_building}endbutgetting:Failure/Error:it{shouldrespond_to:empty_building}expected#torespondto:empty_building 最佳答案 你有一个类方法self.empty_bu

随机推荐