java - NullPointerException in NavDrawerListAdapter for NavigationDrawer in Android -
i having strange problem. using navdrawerlistadapter navigationdrawer in android app. if list has 13 items (navdraweritem), works ok. however, when add 14th element, app appears crash , give nullpointerexception. checked resources,strings,etc , appears correct. stacktrace pointing @ class inside getview() on following line:
imgicon.setimageresource(navdraweritems.get(position).geticon());
for reason, imgicon null.
public class navdrawerlistadapter extends baseadapter { private static final string tag = "navdrawerlistadapter"; private context context; 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); // 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) { convertview = minflater.inflate(r.layout.header_view, null); return convertview; } if(convertview == null) { // use drawer list item view convertview = minflater.inflate(r.layout.drawer_list_item, null); } imageview imgicon = (imageview) convertview.findviewbyid(r.id.icon); textview txttitle = (textview) convertview.findviewbyid(r.id.title); textview txtcounter = (textview) convertview.findviewbyid(r.id.counter); log.d(tag, "position: " + position + ", icon resource: " + navdraweritems.get(position).geticon()); log.d(tag, "navdraweritems: " + navdraweritems.size()); if(imgicon == null){ log.d(tag, "imgicon null"); } else{ log.d(tag, "imgicon not null"); } imgicon.setimageresource(navdraweritems.get(position).geticon()); txttitle.settext(navdraweritems.get(position).gettitle()); if(navdraweritems.get(position).iscountervisible()){ txtcounter.settext(navdraweritems.get(position).getcount()); } else{ txtcounter.setvisibility(view.gone); } if(enableddraweritems.get(position) == false) { txttitle.settextcolor(color.ltgray); convertview.setenabled(enableddraweritems.get(position)); } return convertview; } @override public boolean areallitemsenabled() { return false; } @override public boolean isenabled(int position) { return enableddraweritems.get(position); } // set state of navigation drawer item public void setnavigationdraweritem(int pos, boolean enabled) { enableddraweritems.set(pos, enabled); } }
strings.xml
<array name="nav_drawer_icons"> <item>@drawable/ic_home</item> <item>@drawable/ic_people</item> <item>@drawable/ic_photos</item> <item>@drawable/ic_communities</item> <item>@drawable/ic_pages</item> <item>@drawable/ic_whats_hot</item> </array>
navigationdraweractivity
public class navigationdraweractivity extends actionbaractivity { public drawerlayout mdrawerlayout; public listview mdrawerlist; private actionbardrawertoggle mdrawertoggle; public charsequence mdrawertitle; // nav drawer title public charsequence mtitle; // store app title 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 // static settings/configuration private static final int navigation_drawer_width_percent = 85; // in percentage private static final string tag = "mainactivity"; public static final string intent_extra_position = "navigationdrawerposition"; @override protected void oncreate(bundle savedinstancestate) { super.oncreate(savedinstancestate); // use toolbar , set actionbar toolbar toolbar = (toolbar) findviewbyid(r.id.my_awesome_toolbar); setsupportactionbar(toolbar); // nav menu icons , titles navmenuicons = getresources().obtaintypedarray(r.array.nav_drawer_icons); navmenutitles = getresources().getstringarray(r.array.nav_drawer_items); // drawerlayout , listview mdrawerlayout = (drawerlayout) findviewbyid(r.id.drawer_layout); mdrawerlist = (listview) findviewbyid(r.id.list_slidermenu); navdraweritems = new arraylist<navdraweritem>(); addnavdraweritems(); // add each navigation drawer item // recycle array navmenuicons.recycle(); // setup nav drawer list adapter adapter = new navdrawerlistadapter(this.getapplicationcontext(), navdraweritems); mdrawerlist.setadapter(adapter); mdrawerlist.setonitemclicklistener(new slidemenuclicklistener()); // enabling action bar app icon , behaving toggle button getsupportactionbar().setdisplayhomeasupenabled(true); getsupportactionbar().sethomebuttonenabled(true); mdrawertoggle = new actionbardrawertoggle(this, mdrawerlayout, // r.drawable.ic_drawer, r.string.app_name, r.string.app_name) { public void ondrawerclosed(view view){ getsupportactionbar().settitle(mtitle); invalidateoptionsmenu(); } public void ondraweropened(view drawerview){ getsupportactionbar().settitle(mtitle); invalidateoptionsmenu(); } }; mdrawerlayout.setdrawerlistener(mdrawertoggle); intent intent = getintent(); if(intent != null && intent.getextras() != null) { int drawerposition = intent.getextras().getint(intent_extra_position); if(drawerposition != 0) { // update selected item, title, , close drawer mdrawerlist.setitemchecked(drawerposition, true); mdrawerlist.setselection(drawerposition); settitle(navmenutitles[drawerposition-1]); } else { log.w(tag, "drawerposition 0"); } } mdrawertitle = gettitle(); mtitle = mdrawertitle; configurenavigationdrawer(); configureenableddisablednavdrawitems(); } private void configureenableddisablednavdrawitems() { // check if device connected (no: disable list item, yes: enable list item) if(secondscreeniab.getinstance().getdevice() == null) { getadapter().setnavigationdraweritem(2, false); getadapter().setnavigationdraweritem(3, false); } else { getadapter().setnavigationdraweritem(2, true); getadapter().setnavigationdraweritem(3, true); } } private void addnavdraweritems() { navdraweritems.add(new navdraweritem(0, "")); // drawer cover image navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(0, -1), navmenutitles[0])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(1, -1), navmenutitles[1])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(2, -1), navmenutitles[2])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(3, -1), navmenutitles[3])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(4, -1), navmenutitles[4], "23", false)); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(5, -1), navmenutitles[5])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(0, -1), navmenutitles[6], "5", false)); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(1, -1), navmenutitles[7])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(2, -1), navmenutitles[8])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(3, -1), navmenutitles[9])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(4, -1), navmenutitles[10])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(5, -1), navmenutitles[11])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(0, -1), navmenutitles[12])); navdraweritems.add(new navdraweritem(navmenuicons.getresourceid(1, -1), navmenutitles[13])); } public void configureactionbar() { spannablestring s = new spannablestring("test"); s.setspan(new typefacespan(this, "roboto-regular.ttf"), 0, s.length(), spannable.span_exclusive_exclusive); // update action bar title typefacespan instance android.support.v7.app.actionbar actionbar = this.getsupportactionbar(); actionbar.settitle(s); } private void configurenavigationdrawer() { // configure navigation drawer width drawerlayout.layoutparams params = (android.support.v4.widget.drawerlayout.layoutparams) mdrawerlist.getlayoutparams(); params.width = (int) (getresources().getdisplaymetrics().widthpixels * (navigation_drawer_width_percent/100.0)); mdrawerlist.setlayoutparams(params); } @override public boolean oncreateoptionsmenu(menu menu) { getmenuinflater().inflate(r.menu.main, menu); return true; } @override public boolean onoptionsitemselected(menuitem item) { if(mdrawertoggle.onoptionsitemselected(item)){ return true; } int id = item.getitemid(); if (id == r.id.action_settings) { return true; } return super.onoptionsitemselected(item); } @override public boolean onprepareoptionsmenu(menu menu){ boolean draweropen = mdrawerlayout.isdraweropen(mdrawerlist); menu.finditem(r.id.action_settings).setvisible(!draweropen); return super.onprepareoptionsmenu(menu); } @override public void settitle(charsequence title) { mtitle = title; getsupportactionbar().settitle(mtitle); } @override protected void onpostcreate(bundle savedinstancestate) { super.onpostcreate(savedinstancestate); mdrawertoggle.syncstate(); } @override public void onconfigurationchanged(configuration newconfig) { super.onconfigurationchanged(newconfig); mdrawertoggle.onconfigurationchanged(newconfig); } public listview getmdrawerlist() { return mdrawerlist; } public void setmdrawerlist(listview mdrawerlist) { this.mdrawerlist = mdrawerlist; } public navdrawerlistadapter getadapter() { return adapter; } public void setadapter(navdrawerlistadapter adapter) { this.adapter = adapter; } }
you seem using 2 different layouts:
- r.layout.header_view
- r.layout.drawer_list_item
i'm guessing "r.layout.header_view" doesn't have "r.id.icon". when tries reuse it, imgicon null.
base adapter has methods
public int getitemviewtype (int position) public int getviewtypecount ()
you have 2 types of views. need make sure item @ position 0 has different type rest.
you need add these 2 methods adapter:
@override public int getitemviewtype (int position) { if(position == 0) return 0; else return 1; } @override public int getviewtypecount () { return 2; }
and update first if statement in getview to:
if(position == 0) { if(convertview == null) convertview = minflater.inflate(r.layout.header_view, null); return convertview; }
Comments
Post a Comment