Skip to content
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

Ionic 2 beta 11 virtual scroll and infinite scroll autoscrolls up after update #8037

Closed
theromis opened this issue Sep 9, 2016 · 18 comments
Closed

Comments

@theromis
Copy link

theromis commented Sep 9, 2016

Trying to build contact list with about 10k nodes, my assumption was to combine virtualScroll and infinite-scroll controller, so my page is like below:

<ion-content>
      <ion-list [virtualScroll]="contacts">
        <ion-item *virtualItem="let contact">
....
        </ion-item>
      </ion-list>

      <ion-infinite-scroll (ionInfinite)="doInfiniteInvitation($event)">
        <ion-infinite-scroll-content></ion-infinite-scroll-content>
      </ion-infinite-scroll>
</ion-content>

and .ts controller

  doInfiniteInvitation(infiniteScroll) {
    console.log('doInfiniteInvitation');
    this.contactsService.contact_invitations()
    .then(contacts => {
      for (var i = 0; i < contacts.length; i++) {
        this.contacts.push(contacts[i]);
      }

      infiniteScroll.complete();
      console.log('doInfiniteInvitation done');
    });
  }

so after every doInfiniteInvitation call it resets to the top position, is it possible somehow avoid this "feature"?
may be [virtualTrackBy]="virtualTrack" can help with that?

@numerized
Copy link

numerized commented Sep 27, 2016

Yes I confirm, it's a bug inherited from ionic1 by the way. I've not had time to log it . In my infinite scrolls when I load a video from the (ionInfinite)="doInfinite($event)" the ion-content goes back up automatically when video is finished and comes back to the view.

thanks @theromis !!!
thanks Ionic.

@theromis
Copy link
Author

any plans to fix that?
or, may be, somebody can point me to the place and I'll try to fix it by myself?

@lujakob
Copy link
Contributor

lujakob commented Oct 4, 2016

Hi,
I am working on similar things and might have a workaround for you:
First of all, I think this is caused by node_modules/ionic-angular/components/virtual-scroll/virtual-scroll.js line 111

self._elementRef.nativeElement.parentElement.scrollTop = 0;

So you either remove this line, or you could just scroll back to the position you want after completing the reload.
infiniteScroll.complete();
this.content.scrollTo(0, scrollHeight, 200); // scrollHeigh is your scroll position (integer value)
The duration of 200 ms (3rd parameter) might be important, because the rendering of the virtual items (that happens on scrolling) happens every chunk of milliseconds. (So you might end up with a white screen, with virtual items appearing only after a slight scroll)
If this doesn't work out, try delaying this in a setTimout (100-200ms)
setTimeout(()=>{ this.content.scrollTo(0, scrollHeight, 200); }, 200);

You can play around with those values.

@ghost
Copy link

ghost commented Oct 4, 2016

Just tried the first solution by removing the scrollTop line, it does not show data until you change scroll position. And as for 2nd solution how can we get the scroll position before loading as in variable scrollHeight?

@lujakob
Copy link
Contributor

lujakob commented Oct 5, 2016

yeah correct.
first solution:
I found that whenever data is loaded, processRecords in virtual-util.js starts the first item with top:0. So currently it's not possible so easily to remove the scrollToTop after reloading (I spent hours on this).

As a workaround you could try 2nd solution:

I guess it only shows scroll items after loading when you scroll down a bit ? (if you scroll up it doesn't show)
That's because of another gotcha: after loading, only when scrolling down the content the virtual-scroll data is visible, because the VS component does the processRecords only on scrolling down. If you remove
if (data.scrollDiff > 0) {
in line 163 of node_modules/ionic-angular/components/virtual-scroll/virtual-scroll.js the processRecords is called on scrolling up and down.

To get the scroll position:
if you check the source node_modules/ionic-angular/components/content/content.d.ts you'll find
getScrollTop()

@ghost
Copy link

ghost commented Oct 5, 2016

We need to made some more changes just removing if(data.scrollDiff > 0){ is not gonna work, after scrolling down 4 or 5 times items does not even load until scrolling upwards. and anyways its still not showing items until we scroll up or down.
And thanks for the help i will give it another go do share if you find anything else.

@ghost
Copy link

ghost commented Oct 5, 2016

And i think this line has nothing to do with items not showing until you scroll down a bit after loading is done with infinite scroll. do share your thoughts on that.

@ghost
Copy link

ghost commented Oct 5, 2016

Just found the solution so it appears if(data.scrollDiff>0) has nothing to do with this problem. I guess problem was that processRecords was not being called when infinite scroll completes loading the data and when we scrolled up and down a bit updateScroll was called which than calls processRecords and we were able to see them.

Solution:
First remove
self._cells.length = 0; self._nodes.length = 0; self._itmTmp.viewContainer.clear(); self._elementRef.nativeElement.parentElement.scrollTop = 0;
and put
var data = this._data; var stopAtHeight = (data.scrollTop + data.renderHeight); virtual_util_1.processRecords(stopAtHeight, this._records, this._cells, this._hdrFn, this._ftrFn, data);

there as it was being done in updateScroll. It seems to work perfectly when i have used VirtualScroll+InfiniteScroll+PullToRefresh altogether.

Now just need someone to test it on android, and someone who can test its performance.

Thank you so much @lujakob you have been a massive help.

@rodrigopagnuzzi
Copy link

@azzamasghar I've tried your solution and unfortunately the perfomance on scrolling is really bad

@ghost
Copy link

ghost commented Oct 5, 2016

Yeah its not feasible i am also stuck here.

@gfviegas
Copy link

gfviegas commented Nov 3, 2016

Hey, lots of questions about this on forums and articles about virtual scroll. Any update on that? This is a must-have in many applications. Wonder how would be an Ionic's Twitter without infinite scrolling, loading tons of useless data, or without virtualscroll leaving tons of useless data behind as you scroll...

@lujakob
Copy link
Contributor

lujakob commented Nov 5, 2016

The current state for my application is a modified ion-infinite-scroll. I duplicated the code of the ionic component and named it my-infinite-scroll and changed the code that I basically get notified if I scroll to the bottom or top. I have a property 'arrivedAt' telling me if it's top or bottom. Also I find out about the first visible item in the list at the time of the reload. I replace my list items and scroll to the position where first visible item from before was.

@faraazc
Copy link

faraazc commented Nov 25, 2016

+1. This is a must fix defect. please ionic fix this. we desperately need an official solution on this bug.

@faraazc
Copy link

faraazc commented Nov 25, 2016

@lujakob can you please share you custom solution source code if possible

@lujakob
Copy link
Contributor

lujakob commented Nov 28, 2016

I will try to find some time in the next couple of days to set up a public repository with a simple demo of my solution.

@lujakob
Copy link
Contributor

lujakob commented Nov 30, 2016

Hey guys, I set up a repository with a simple implementation of my solution. (The solution itself is not that simple, but the demo ;-) ) It's a custom variation of the original infinite scroll component. Scrolling back and forth with a replacement of the content to prevent DOM stuffing. As well the fetched content will scroll to the correct position after loading. The original loading spinner is replaced by a Loading component, because having the spinner on top of the list won't work that easy.
https://github.com/lujakob/ionic-infinite-scroll-example

@jgw96
Copy link
Contributor

jgw96 commented Dec 28, 2016

Hello everyone! Thanks for using Ionic! We have been hard at work lately with virtualscroll. The issue here is that when you update the virtualscroll with data after it has already been rendered the measurements that virtual scroll uses to lazily render elements then become wrong. When this happens the virtual scroll has to re-render itself entirely, therefore making it look like it has jumped back to the beginning of the list. We are well aware of this issue and hope to have a solution for it soon. Also, just to keep our issues concise and not have duplicates I am going to close this one as a duplicate of #6423 . You can track the status of this issue over on that issue. Also, feel free to put any findings you may have on that issue. Thanks again everyone!

@jgw96 jgw96 closed this as completed Dec 28, 2016
@ionitron-bot
Copy link

ionitron-bot bot commented Sep 5, 2018

Thanks for the issue! This issue is being locked to prevent comments that are not relevant to the original issue. If this is still an issue with the latest version of Ionic, please create a new issue and ensure the template is fully filled out.

@ionitron-bot ionitron-bot bot locked and limited conversation to collaborators Sep 5, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

8 participants