Meteor+ React + Infinite Scroll?


#1

Hello all:

Can anyone recommend a good example of how to implement infinite scrolling (i.e. loading more results from a collection as a user hits the bottom of the page) with React as a view layer? I’ve found some good guides demonstrating how to set up the publications and subscriptions (i.e. Gentlenode, Discover Meteor), but am struggling to visualize how to construct my React components/event listeners to make it work.

Thanks!


#2

Something like this can be used to do infinite scroll:
https://github.com/seatgeek/react-infinite/blob/master/README.md

Then on the components load callback you can pass in your own function that subscribes to the feed but with a higher subscription limit.

You can call subscribe directly but the Typical way to do this is to set a session variable with the limit and pass that into an auto run. Then in your callback just change the session variable like you would in any meteor app.

Also checkout the react.parts website, they have other infinite components too.

Hope this helps!


#3

That’s super useful. Just to clarify, by “component’s load callback,” do you mean the “componentDidMount” property in the React component?

I’ve been translating this guide to React: https://gentlenode.com/journal/meteor-21-pagination-system-with-infinite-scroll/43

Here’s a Gist of what I’ve got so far:

This works great except for two things:

  1. I get these errors in the console:

    Uncaught TypeError: handlers.push is not a function jQuery.js:4403

    Warning: Don’t set .props.guid of the React component. Instead, specify the correct value when initially creating the element or use React.cloneElement to make a new element with updated props.

  2. I’m not quite sure how to implement a loading spinner that appears below the content - is that a separate component that the parent passes state to?


#4

Ah sorry I wasn’t more clear… I was on mobile at the time :frowning:

Just to clarify, by “component’s load callback,” do you mean the “componentDidMount” property in the React component?

So for this specific component it has a prop that takes a function. This function is called when you get near the end of the infinite list. Normally you would use AJAX to get more data but in Meteor we can just adjust the subscription to say ‘give me 10 additional posts’. This will make it re-render.

Actually now that i’m thinking about it… if a re-render screws up the list you could use a DDP method in place of an AJAX method. I wouldn’t do this unless you have to.

Anyhow the prop is called onInfiniteLoad and the info on that can be found here

I’ve been translating this guide to React: https://gentlenode.com/journal/meteor-21-pagination-system-with-infinite-scroll/43

Here’s a Gist of what I’ve got so far:
This works great except for two things:
I get these errors in the console:

I’m not quite sure about this one. The tutorial is using Blaze so that’s going to be different than React.

If you need an app to tinker with I have a Facebook clone on github here: http://react-ive.meteor.com/feed It has a ‘load more’ button (not infinite-scroll) that can be augmented to do infinite scroll. This may be easier to get a sample working.


#5

This is all super helpful. Thanks so much! It’s been a bit of a challenge to shift my thinking from from Blaze to React. It would be a amazing if someone wrote a post like, “This thing you used to do all of the time in Blaze, here’s how to do it in React.”, i.e. functions that run in “Template.xxx.rendered,” implementing user accounts, plugins, where to utilize session variables and where not, etc.


#6

Yep it takes a bit of time to think in “react” :smile: Most of the react tutorials are the same as Meteor except for collection data. You can also use meteor methods in place of AJAX if needed.

Have fun!


#7

Adam:

Thanks again for your help. I managed to get it working tonight following along with your example translated to watching scroll events in “componentDidMount.” I even managed to get a loading spinner to show up below the content while the subscription is refreshing. Once it’s better styled I might put it up on GitHub.

The jQuery error I’m getting seems to object to this function, which I took from Gentlenode but had to add the _.throttle method to ensure the function didn’t get called multiple times if the user kept scrolling:

$(window).scroll(
    _.throttle(function() {
        if ($(window).scrollTop() + $(window).height() > $(document).height() - 100) {
            self.props.incrementLimit();
        }
    }, 500)).bind(this);

I’ll look into that further, but at least it works. Thanks again for your help!


#8

Ah, I gut the “.bind(this)” and that eliminated the error. Success!