javascriptreactjsinfinite-scrollreact-infinite-scroll-component

“react-infinite-scroll-component” not firing next function


I'm using the react-infinite-scroll-component to implement the infinite scroll component. The configuration of the component is:

<div id="scrollableDiv" style={{ height: 300, overflow: "auto" }}>
       <InfiniteScroll
         dataLength={texts.length}
         next={getText}
         hasMore={true}
         loader={<h5>Loading...</h5>}
         endMessage={<p style={{textAlign:'center'}}><b>Yay! You've seen it all!</b></p>}
         scrollableTarget="scrollableDiv"
         >
         {<Texts texts = {texts}/>}
         </InfiniteScroll>
</div>

where texts is simply a state array of some text objects; const [texts, setTexts] = useState([])
This is the getText method to be called in next :

const getText = async ()=>{

        const res = await axios.get("http://localhost:3001/api/sth",{
            params: {
                ids: followings.map(i => i.id),
                str_ids: followings.map(i => i.str_id)
              },
              paramsSerializer: params => {
                return qs.stringify(params)
              }
        });

        let str_ids_res = res.data.map(i => i.string_id)
        let texts_res = res.data.map(i => i.texts)
        console.log(texts_res)

        const filtered_res = //some processing here on texts_res
        /* eslint eqeqeq: 0 */
        if(!arrayIsEqual(filtered_res,texts)){
            console.log("Not equal")
            // append arrays to a array state
            setTexts((prevtexts) => prevtexts.concat([...filtered_res]))
        }

    }

await axios.get("http://localhost:3001/api/sth")

always return two different texts from DB so setTexts should always get called.

component is a card component from semantic UI tho.

const Texts = ({texts}) =>{
    return (
        <>
            {texts.map(text =>(
                <div key={text.id}>
                    <Card>
                        <Card.Content>
                            <Card.Description>
                            {text.full_text}
                            </Card.Description>
                        </Card.Content>
                    </Card>
                </div>
            ))}
        </>
    );
}

InfiniteScroll component only fires Next once even though my datalength variable is setting correctly.
PS. the texts is empty initially so when I start the app, only 'Loading....' is called


Solution

  • After some experiments, passing height = {some height} as props to InfiniteScroll does the trick..

    <div id="scrollableDiv" style={{ height: 300, overflow: "auto" }}>
                                        <InfiniteScroll
                                        dataLength={tweets.length}
                                        next={handleScrolling}
                                        hasMore={!isEnd}
                                        loader={<h5>Loading...</h5>}
                                        scrollThreshold={1}
                                        height={300}
                                        endMessage={
                                            <p style={{textAlign:'center'}}><b>Yay! You've seen it all!</b></p>
                                        }
                                        scrollableTarget="scrollableDiv"
                                        >
                                        {<Tweets tweets = {tweets}/>}
                                        </InfiniteScroll>
    </div>