-
Notifications
You must be signed in to change notification settings - Fork 145
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Table view jumps when scrolling up #17
Comments
Have the same problem after navigating to another view controller and back: The iOS7 approach still works https://github.com/smileyborg/TableViewCellWithAutoLayout |
Have the same problem too |
Hey @marcelmika, @deville, & @waterlee23, Please be sure to file bug reports with Apple about this issue. As far as I know, it is a (fairly serious) bug with self-sizing cells on iOS 8. Until it's fixed by Apple, there may be nothing we can do as I am not aware of any workarounds for this issue yet. |
@smileyborg Thanks, I've got the same problem in my own project and thought it was my fault, seems like I can stop finding bugs :) |
Did anyone file a bug? It seems like one exists on Open Radar for this, but it'd be good for Apple to see a few more bugs filed on the same issue to help prioritize during triage. FWIW, I have an infinite feed scenario similar to @marcelmika, and this bug is a deal-breaker for that scenario. From what I can tell, the issue is being caused because height calculation of the new cells added to the bottom of the tableview is being deferred until the cell is about to appear on screen. So when you add 10 new cells to the bottom of the tableview, I suspect that the scrollview height, contentoffset, etc. are all adjusted by 10 * estimatedRowHeight (which is static). This in turn renders the y-positions of all the cells above that point (i.e. the point where you loaded 10 more cells) to be incorrect, and when you scroll up, the layout pass updates them as you scroll leading to lots of sad. A quick workaround that I've implemented is the age-old cell height cache workaround, and so far, I really like it because it's cell-implementation agnostic and it's very lightweight. Basically:
I'll obviously optimize things a little more, but even this rough workaround makes the tableView scroll like butter. No jittering at all. I'll report back once I've had some time to implement it properly. |
@rainypixels Not sure I understand how your solution works. After that, |
Actually, isn't it called for all cells whenever
Good question; I wasn't clear enough. The one detail I failed to mention is that I initialize the Here's code for a trivial implementation:
Yes, there's a small performance hit that grows over time and depends on the complexity of your cells. Once you have hundreds of cells, Hope that helps. Let me know if I'm missing anything or if it's still unclear. |
Thanks @rainypixels for your estimatedHeight caching solution it works like a charm. I have bumped in to a few problems though. They are both related to resizing of cells. I am using the tableview.beginUpdates() + tableview.EndUpdates() trick to animate the height change of a cell. When someone taps a cell I activate another, stronger, constraint that changes the height of the cell. Now the cache needs to be updated somehow, as it has a new height. This one I solved by also updating the cache inside the didEndDisplayingCell method so that when resizing a cell and then scrolling away from it, the new height will be in the cache. This works fine, but the second issue (that I cannot resolve) is when the cell that I am resizing is one of the last rows. When I first expand the cell its fine, but if I scroll down a little after expanding so that I am at the bottom of the tableview and then collapse the cell the animation that occurs first decreases the height of the cell from the bottom up, pulling the lower cells with it and even if there is no more cells to animate up. Then the animation ends with a big glitchy jump back so that the last row is position at the bottom of the tableview again. Maybe I need to make and example project for this to you to be able to understand :) |
Hi again. I forked this repo to showcase the problem I tried to describe in the post above. https://github.com/IMGNRY/TableViewCellWithAutoLayoutiOS8 I have implemented the estimated height cache and when tapping on a cell it will toggle between expanded and collapsed by activating/deactivating a constraint. This works great as long as you're not at the bottom of the tableview (or close to the bottom). Try scrolling down all the way and tap on last cell. It will expand to show all the text i the body label. Now tap on the same cell again to collapse it. The cell collapses, but the y position of the cell is never changed and instead it just shrinks the cell from the bottom up leaving the bottom part of the table view empty (as there are no cells there to display. When the animation is finished the tableview realises that it is scrolled outside of the bounds and snaps back with jumpy glitch. When doing this kind of collapse using the old school 7.0 style, the tableview automatically corrects itself inside the animation and everything looks smooth. Any idea of how one might solve this? I have tried updating the estimated height cache manually when collapsing but that didn't change this behaviour. |
Hmm. I think I have found a solution. If I switch the animation from UITableViewScrollPosition.None to UITableViewScrollPosition.Middle Before:
After:
The glitch goes away. 👍 |
@bobmoff Whoops! Getting to this too late. Glad I could help with the glitch. :P Seriously though, that's an elegant solution. I'll keep it in mind if I run into this. Here's to another small win for this self-sizing battle. :) |
@rainypixels Thanks a ton for your quick fix. Might have saved me hours of UI adjustments and pixel calculations which was the only other solution to avoid the jumps. I am writing this comment to share my following experience while implementing the itemHeights cache: I have 15 cells, each of them having different UI and elements. When the view loads, the service response is used to populate all the cells and the height needs to be calculated based on certain logics. (used stack views to deal with hiding of particular sections inside a cell). When I started using automatic dimensions, I got the mentioned jump issue even after I tried providing an approximate height in the estimatedHeightForRowAtIndexPath method which was close to the actual height of each cell. After implementing the above mentioned itemHeights cache, most of the jumps went away but in one particular scenario, the jump was still happening where the cell contained an imageView. While debugging I noticed that the array values are only getting updated once. When I removed the condition which checks
Thanks again. |
The solution really works, thanks for it @rainypixels . I know it is a bit old post, but I will update the solution if one has several sections instead of one.
|
UPDATE:
|
I do not have this cache solution, I tried not to use automaticDimension because I know the height of the my cell in heightRowForIndexpath I returned number 80.f, with insert sections, I continue to jerk when scrolling up tableView. How to solve? Please, help me @rainypixels, @bbbuka, @speedoholic, @bobmoff |
@smileyborg Thanks, I've got the same problem in my own project and thought it was my fault, and one more thing we are not using storyboards, we create tableview cell customized. |
How to recreate:
I have such issue in my own project. I have an infinite feed where I load data dynamically whenever the user scrolls to the bottom. However, when I want to scroll up it jumps and gives you a bad user experience.
Did you guys figured out this issue?
The text was updated successfully, but these errors were encountered: