如何使用两个 Return 语句在 React Component 中设置三元运算符 "Loading" Div?

How to set Ternary Operator "Loading" Div inside React Component with Two Return statements?

我正在使用的 API 很慢。我的 React 组件使用 FetchAPI 并且有两个 return 语句。

我想合并一个三元运算符条件,在我等待数据时显示 "Loading.." div 像这样https://codesandbox.io/s/api-fetch-using-usestate-useeffect-k024k

如何在下面的代码中包含一个 "Loading" 三元和 两个 return 语句 ?注意:为了不让任何人发疯,我大幅减少了我的代码,所以我只包含了整体结构。不客气!

class App extends Component {
  constructor(props) {
    super(props);
    this.state = {
      data: []
    };
  }

  componentDidMount() {
    fetch('https.data.json')
      .then(response => response.json())
      .then(data => this.setState({ data: data}))
  }

  render() {

    let theList = this.state.map((item, id) => {

      return (
        <Card>A bunch of API Stuff </Card>
      );

    })
    return (
      <div className="search-wrap">
        <Row>
          {theList}
        </Row>
      </div>
    )
  }
}

export default App;

只需在您的状态中添加一个布尔字段,表明正在加载数据。

class App extends Component {
  constructor(props) {
    super(props);
    this.state = {
      data: [],
      loading: true, // this one
    };
  }

  componentDidMount() {
    fetch('https.data.json')
      .then(response => response.json())
      .then(data => this.setState({ data: data, loading: false }))
  }

  render() {

    if (this.state.loading)
       return <div>Loading...</div>

    let theList = this.state.map((item, id) => {

      return (
        <Card>A bunch of API Stuff </Card>
      );

    })
    return (
      <div className="search-wrap">
        <Row>
          {theList}
        </Row>
      </div>
    )
  }
}

export default App;

My React component is using FetchAPI and has two return statements.

不,不是。它有一个:

render() {

  let theList = this.state.map((item, id) => {

    return (
      <Card>A bunch of API Stuff </Card>
    );

  })
  return (                               // <========== here
    <div className="search-wrap">
      <Row>
        {theList}
      </Row>
    </div>
  )
}

另一个是 map 回调中的 return,它对 render 方法没有任何影响。

如果您想使用条件运算符来显示加载指示器,您可以在 render 的 return:

中执行此操作
render() {
  let { loading } = this.state; // *** Get the flag

  let theList = this.state.map((item, id) => {

    return (
      <Card>A bunch of API Stuff </Card>
    );

  })
  return (                          // *** Use it in the below
    <div className="search-wrap">
      <Row>
        {loading ? <p>Loading...</p> : theList}
      </Row>
    </div>
  )
}

您可能还想避免不必要的 map 调用,但如果您知道您的状态是用空数组初始化的,那么该调用是无害的。但是如果你想摆脱它:

render() {
  let { loading } = this.state; // *** Get the flag

  let theList = !loading && this.state.map((item, id) => {

    return (
      <Card>A bunch of API Stuff </Card>
    );

  })
  return (                          // *** Use it in the below
    <div className="search-wrap">
      <Row>
        {loading ? <p>Loading...</p> : theList}
      </Row>
    </div>
  )
}

如果我没理解错的话,你的代码应该如下所示:

class App extends Component {
  constructor(props) {
    super(props);
    this.state = {
      data: [],
      isLoading: false
    };
  }

  componentDidMount() {
    this.setState({ isLoading: true }); // mount the loading component when we will start the fecth
    fetch('https.data.json')
      .then(response => response.json())
      .then(data => this.setState({ data: data}))
      .then(() => this.setState({ isLoading: false })) // unmount Loading component when the fetch ends
  }

  render() {
    let theList = this.state.map((item, id) => {
      return (
        <Card>A bunch of API Stuff </Card>
      );
    })

    // Here we will return the Loading component as long as isLoading is true
    return (isLoading) ? <Loading /> : (
      <div className="search-wrap">
        <Row>
          {theList}
        </Row>
      </div>
    )
  }
}

export default App;

所以基本上我们将添加一个布尔变量 (isLoading) 来处理获取的状态,并将其添加到组件的状态中。触发提取时,此变量将为 true 否则将为 false.

那么在return语句中,我们可以根据这个新变量的值使用三元运算符。如果是 true,我们将 return 加载组件或简单的 div 语句 Loading...。否则我们将 return 加载数据的 App 组件。

希望对您有所帮助:)

你可以这样做。请注意,您可以从一开始就直接导出 class 。此外,您可以简化状态,而无需显式构造函数。 要了解获取状态,您应该在获取数据前后添加一个 isLoading 条件。然后在render里面,你可以return一个单独的节点,里面根据你的状态渲染你想要的组件。使用这种编码风格,您甚至可以在获取 return 空数组时显示。

export default class App extends Component {
  state = {
    data: [],
    isLoading: false
  }
  componentDidMount() {
    this.setState({
      isLoading: true
    }, () => {
      fetch('https.data.json')
      .then(response => response.json())
      .then(data => this.setState({
        data,false
      }))
    })
  }
  render() {
    return (
      <div>
      {
        this.state.isLoading &&
        <span>
          Loading...
        </span>
      }
      {
        !this.state.isLoading &&
        (this.state.data.length > 0) &&
        <div className="search-wrap">
          <Row>
            {
              this.state.data.map((item, id) => {
                return (
                  <Card key={id}>
                    A bunch of API Stuff
                  </Card>
                );
               })
            }
          </Row>
        </div>
      }
      {
        !this.state.isLoading &&
        (this.state.data.length === 0) &&
        <span>
          There's no data to show
        </span>
      }
      </div>
    )
  }
}

希望对您有所帮助! 丹尼