反应中具有子组件的路口观察员

时间:2019-06-10 11:55:25

标签: javascript reactjs

我正在尝试使用交点观察器实现无限滚动,我有一个在子组件中呈现的数据列表。

所以我在渲染时将目标元素附加到列表元素的最后。

问题出在2个api调用之后,因为我在App.js函数handleObserver中有条件,所以它未触发

if(this.state.prevY> y){

因此,在第二次api调用之后,条件未成立。因此很明显,api调用再也不会发生。

普遍性越来越强。

我如何解决此问题,每篇文章都在父级组件中显示。我正在尝试使用子组件来实现。

任何帮助表示赞赏

App.js

import React, { Component } from 'react';
import Child from './Child';
import axios from 'axios';

class App extends Component {
  state = {
    users: [],
    page: 0,
    loading: false,
    prevY: 0,
    isDataAvailable: false
  };

  componentDidMount(){
    this.getUsers(this.state.page)
  }


  getUsers = (page = this.state.page) => {
    this.setState({ loading: true });
    axios
      .get(`https://api.github.com/users?since=${page}&per_page=100`)
      .then(res => {
        this.setState({ users: [...this.state.users, ...res.data] });
        this.setState({ loading: false, isDataAvailable: true });
      });
  }

  handleObserver = (entities, observer) => {
    const y = entities[0].boundingClientRect.y;
    if (this.state.prevY > y) {
      const lastUser = this.state.users[this.state.users.length - 1];
      const curPage = lastUser.id;
      this.getUsers(curPage);
      this.setState({ page: curPage });
    }
    this.setState({ prevY: y });
  }

  render() {
    return (
      <div className="container">
        <div style={{ minHeight: '800px' }}>
          {this.state.isDataAvailable ? (
            <Child
              handleObserver={this.handleObserver}
              users={this.state.users}
            />
          ) : null}
         
        </div>
      </div>
    );
  }
}

export default App;



// Child.js
import React, { Component } from 'react';

class Child extends Component {
  componentDidMount() {
    const options = {
      root: null,
      threshold: 0,
    };
    this.observer = new IntersectionObserver(
      this._handleObserver.bind(this),
      options,
    );
    this.observer.observe(this.loadingRef);
  }

  shouldComponentUpdate(nextProps) {
    return this.props.users !== nextProps.users;
  }

  _handleObserver(entities, observer) {
    this.props.handleObserver(entities)
  }

  render() {
    return (
      <ul>
        {this.props.users.map(
          (user, index) =>
            (index ===
              this.props.users.length - 1 ? (
                <div>
                  <div ref={loadingRef => (this.loadingRef = loadingRef)} />
                  <li key={user.id}>{user.login}</li>
                </div>
              ) : (
                <li key={user.id}>{user.login}</li>
              )),
        )}
      </ul>
    );
  }
}

export default Child;

1 个答案:

答案 0 :(得分:0)

所以问题出在每次loadRef更改时,所以我们需要每次都指出ref。

componentDidUpdate(){
 this.observer.observe(this.loadingRef)
}

最初,loadingRef将指向第99个元素,之后将指向第199个元素。因此,我们需要更新loadingRef的指向。

通过在子组件中添加以上代码,我得以解决该问题。