React window 如何迭代你的数据?

React window how to iterate your data?

import { FixedSizeList as List } from 'react-window'
import AutoSizer from 'react-virtualized-auto-sizer'
const TrackTable = ({ tracks }) => {
    const Row = ({ index, style }) => (
        <div
            className={index % 2 ? 'ListItemOdd' : 'ListItemEven'}
            style={style}>
            Row {index}
        </div>
    )
    const AllRows = () => {
        const arr = [
            { code: '12H', id: '1' },
            { code: '4gf', id: '2' },
        ]
        return arr.map((i, index) => {
            return <div key={index}>{i.code}</div>
        })
    }
    return (
        <AutoSizer>
            {({ height, width }) => (
                <List
                    className="List"
                    height={height}
                    itemCount={tracks.length}
                    itemSize={35}
                    width={width}>
                    {AllRows()}
                </List>
            )}
        </AutoSizer>
    )
}

如果我把 Row 放在 <List /> 中,就像作者的例子一样,它有效,

但是如果我将我的数据 AllRows 放在 <List /> 中,我会得到错误 Error: Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: object.。我检查了我的数据是好的。那么我在这里做错了什么?

这里是沙箱: https://codesandbox.io/s/bvaughn-react-window-fixed-size-list-vertical-forked-jqmyx?file=/index.js

你调用 AllRows 没有适当的,在这种情况下 tracksundefined ==> 你会得到错误 tracks.map is not a function

为避免这种情况,请使用数组调用 AllRows

        <List
            className="List"
            height={height}
            itemCount={tracks.length}
            itemSize={35}
            width={width}>
            {AllRows(yourArray)}
        </List>

编辑:

AllRows定义如下,return一个数组,去掉tracks.map之前的return

const AllRows = () => {
        if (tracks.length == 0) return ''
        return tracks.map((i, index) => {
            return <div key={i.index}>{i.code}</div>
        })
    }

改用它:

const AllRows = () => {
        if (tracks.length == 0) return <></>
        tracks.map((i, index) => {
            return <div key={i.index}>{i.code}</div>
        })
    }

或:

const AllRows = () => {
   if (tracks.length == 0) return <></>
   return (
   {
    tracks.map((i, index) => {
            return <div key={i.index}>{i.code}</div>
        })
   }
          ) 
    }

除了上面的答案,你也可以使用这个:

const AllRows = () => {
    (tracks || []).map((i, index) => {
        return <div key={i.index}>{i.code}</div>
    })
}

这是工作示例。请检查

const arr = [
  { code: "12H", id: "1" },
  { code: "4gf", id: "2" }
];
const AllRows = () => arr.map((i, index) => <div key={index}>{i.code}</div>);

const Example = () => (
  <AutoSizer>
    {({ height, width }) => (
      <List
        className="List"
        height={height}
        itemCount={1000}
        itemSize={35}
        width={width}
      >
        {AllRows}
      </List>
    )}
  </AutoSizer>
);

您提到的第一个错误是 tracks.map 未定义。这表明 List 组件调用它的子组件。从文档中,第一个参数有索引和样式变量。所以你可以使用:

// arr is defined up here
const AllRows = ({ index, style }) => {
  return <div key={index}>{arr[index].code}</div>;
};

或者作为使用闭包的更通用的方法:

const AllRows2 = (arr2) => {
  return ({ index, style }) => {
    return <div key={index}>{arr2[index].code}</div>;
  };
};

然后在列表组件中使用AllRows2(arr)。这可能不需要。 Here 是一个工作示例。