【问题标题】:Random behavior with Android BaseAdapter for NavigationDrawer用于 NavigationDrawer 的 Android BaseAdapter 的随机行为
【发布时间】:2015-11-27 06:59:02
【问题描述】:

我已经实现了一个 NavigationDrawer。它使用从 BaseAdapter 扩展而来的 NavigationDrawerListAdapter。我在 NavigationDrawer 中有 10 个列表项。我想将 3 个项目设置为绿色字体,其余为黑色字体。它“禁用”configureEnabledDisabledNavDrawItems() 中的列表项。然后,在 NavDrawerListAdapter 的 renderNavDrawerItemByPos() 中,如果列表项“禁用”,它会将字体颜色设置为绿色。

但是,我的问题是导航抽屉中的每个列表项似乎都是随机绘制的。例如,当我上下滑动导航抽屉时,随机列表项变为绿色。我完全不知道为什么。有什么想法吗?

NavigationDrawerActivity

public class NavigationDrawerActivity extends ActionBarActivity {
    public DrawerLayout mDrawerLayout;
    public ListView mDrawerList;
    public TypedArray navMenuIcons; // menu item icons
    public String[] navMenuTitles; // menu item titles
    public ArrayList<NavDrawerItem> navDrawerItems; // each drawer item
    public NavDrawerListAdapter adapter; // nav drawer adapter

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        mDrawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
        mDrawerList = (ListView) findViewById(R.id.list_slidermenu);
        navDrawerItems = new ArrayList<NavDrawerItem>();
        addNavDrawerItems(); 
        adapter = new NavDrawerListAdapter(this.getApplicationContext(), navDrawerItems);
        mDrawerList.setAdapter(adapter);

        configureEnabledDisabledNavDrawItems()
    }

    private void configureEnabledDisabledNavDrawItems() {
        for(int i=1; i < navDrawerItems.size(); i++){
            adapter.setNavigationDrawerItem(i, true);
        }

        adapter.setNavigationDrawerItem(2, false); 
        adapter.setNavigationDrawerItem(3, false); 
        adapter.setNavigationDrawerItem(6, false);
    }
}

NavigationDrawerListAdapter

public class NavDrawerListAdapter extends BaseAdapter {
    private ArrayList<NavDrawerItem> navDrawerItems;
    private List<Boolean> enabledDrawerItems;
    private LayoutInflater mInflater;

    public NavDrawerListAdapter(Context context,
            ArrayList<NavDrawerItem> navDrawerItems)    {
        super();
        this.context = context;
        this.navDrawerItems = navDrawerItems;
        this.mInflater = (LayoutInflater) context.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
        this.headerView = null;

        // Toggle enabled/disabled navigation drawer items
        enabledDrawerItems = new ArrayList<Boolean>(Arrays.asList(new Boolean[navDrawerItems.size()]));
        Collections.fill(enabledDrawerItems, new Boolean(true));
    }

    @Override
    public int getCount() {
        return navDrawerItems.size();
    }

    @Override
    public Object getItem(int position) {
        return navDrawerItems.get(position);
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent)   {
        if(position == 0) {
            if(convertView == null){
                convertView = mInflater.inflate(R.layout.header_view, null);
                headerView = convertView;
            }
            return convertView;
        }

        if(convertView == null) { // Use the drawer list item view
            convertView = mInflater.inflate(R.layout.drawer_list_item, null);
        }

        renderNavDrawerItemByPos(position, convertView);

        return convertView;
    }

    private void renderNavDrawerItemByPos(int position, View convertView)   {
        TextView txtTitle = (TextView) convertView.findViewById(R.id.title);
        txtTitle.setText("test");

        if(enabledDrawerItems.get(position) == false) {
            txtTitle.setTextColor(ColorStateList.valueOf(Color.GREEN));
            convertView.setEnabled(enabledDrawerItems.get(position));
        }
    }

    @Override
    public boolean areAllItemsEnabled()     {
        return false;
    }

    @Override
    public boolean isEnabled(int position)  {
        return enabledDrawerItems.get(position);
    }

    public void setNavigationDrawerItem(int pos, boolean enabled)   {
        enabledDrawerItems.set(pos, enabled);
    }

    @Override
    public int getItemViewType (int position) {
        if(position == 0)
            return 0;
        else
            return 1;
    }

    @Override
    public int getViewTypeCount () {
        return 2;
    }
}

【问题讨论】:

  • 据我所知,您只有两种类型的项目。为第一个列表项键入 0,为其他列表项键入 1。你确定你正确地实现了这个适配器吗?

标签: android listview android-listview navigation-drawer baseadapter


【解决方案1】:

如果 getView() 传递了一个回收的 convertView,该 convertView 之前的标题为绿色,即使当前位置已启用,它将继续为绿色。这是因为renderNavDrawerItemByPos() 只设置禁用位置的颜色。

一般来说,每当您收到一个回收的View 时,您需要确保它的整个状态都针对新位置正确设置。

如果默认标题颜色为黑色,则可能会这样:

private void renderNavDrawerItemByPos(int position, View convertView)   {
    TextView txtTitle = (TextView) convertView.findViewById(R.id.title);
    txtTitle.setText("test");

    boolean enabled = enabledDrawerItems.get(position);
    txtTitle.setTextColor(ColorStateList.valueOf(
      enabled ? Color.BLACK : Color.GREEN));
    convertView.setEnabled(enabled);
} 

【讨论】:

  • 谢谢!这完美!您对 getView() 提出了一个很好的观点,以及它是如何通过以前被涂成绿色的回收视图传递的。我需要确保将启用的项目重新着色为黑色。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多