android - RecyclerView, StaggeredGridLayoutManager Refresh Bug -


i used support library v7-21 , recyclerview isn't showing correctly. gridlayoutmanager , linearlayoutmanager ok. problem occurs when in staggeredgridlayoutmanager load dataset , refresh data. data refresh working fine recyclerview's view exist out of screen.

does knows how fix it?

updated 2015-01-04 (at bottom)

i have example project demonstrate @ https://github.com/dbleicher/recyclerview-grid-quickreturn . here few more details may out.

when add/remove item recyclerview, should call notifyiteminserted/notifyitemremoved have adapter tell layout manager re-layout affected views. example, in adapter:

public void additematposition(int position, string item) {     mydataset.add(position, item);     madapter.notifyiteminserted(position);         } 

if call method add view, , view on-screen, sglm seems work expected inserting , adjusting layout. if, however, viewing top of list , add item @ position zero, view created off-screen (and won't see it). can scroll view following code:

public void additematposition(int position, string item) {     mydataset.add(position, item);     madapter.notifyiteminserted(position);     msglm.scrolltoposition(position); } 

there (imho) bug in staggeredgridlayoutmanager revealed adding items "off-screen". according comments yiğit boyar in thread https://plus.google.com/u/1/111532428576115387787/posts/6xxayubz2iv

"...if item added out of bounds, layout manager not care"

and here's bug appears. sglm, there timing issue when re-layout occurs. in example code (link above) have itemdecorator adds margin top-most item(s) aren't obscured toolbar. when using code above, layout incorrectly retains margin on item moved "down" screen when new item(s) inserted. bummer.

here's layout before adding @ top: layout before adding @ top

here's layout demonstrating bug after adding item @ top: bad layout

there workaround, defeats purpose of using recyclerview. basically, if call notifydatasetchanged after adds/removes, case sglm invalidate it's entire layout. not optimal efficiency perspective, result in proper layout. using following code:

public void additematposition(int position, string item) {     mydataset.add(position, item);     madapter.notifydatasetchanged();  // should not this, works!     msglm.scrolltoposition(position); } 

will result in proper, post-addition layout: proper layout result

hope helps.

update: 2014-01-04

as noted in comments, workaround call invalidateitemdecorations() on recyclerview after performing insert. right now, appears doing after insert ignore call (possibly because layout pass running). if 1 defers call briefly, seem work:

public void additematposition(int position, string item) {     mydataset.add(position, item);     madapter.notifyiteminserted(position);     msglm.scrolltoposition(position);      // items added top row? better invalidate decorator.     // delay ensure previous layout pass has completed.     if (position < columncount) {         new handler().postdelayed(new runnable() {             @override             public void run() {                 mrecycler.invalidateitemdecorations();             }         }, 300);     } } 

Comments

Popular posts from this blog

c++ - QTextObjectInterface with Qml TextEdit (QQuickTextEdit) -

javascript - angular ng-required radio button not toggling required off in firefox 33, OK in chrome -

xcode - Swift Playground - Files are not readable -