我正在利用虚拟化列表 ( react-virtualized ),其中需要我的列表项的高度并且可能会有很大差异。由于变化很大,我给库的任何高度估计都会产生糟糕的体验。
高度计算的常用方法是这样的:
const containerStyle = {
display: "inline-block",
position: "absolute",
visibility: "hidden",
zIndex: -1,
};
export const measureText = (text) => {
const container = document.createElement("div");
container.style = containerStyle;
container.appendChild(text);
document.body.appendChild(container);
const height = container.clientHeight;
const width = container.clientWidth;
container.parentNode.removeChild(container);
return { height, width };
};
Run Code Online (Sandbox Code Playgroud)
不幸的是,当您处理包含不同大小项目的超大列表时,这不是高效的。虽然可以利用缓存,但当您需要在一开始就知道总高度(所有项目组合的高度)时,即使这样做也不会很好。
经常使用的第二种解决方案是通过 HTML canvas' measureText。性能类似于上面的 DOM 操作。
就我而言,我知道以下几点:
我正在寻找的是一个数学解决方案,它可以计算高度(或非常接近的估计),这样我就不必依赖任何 DOM 操作,而且我可以随时获得高度。
我想它是这样的:
const measureText = (text, options) => {
const { …Run Code Online (Sandbox Code Playgroud) 我对我的桌子有以下要求:
我的假设如下:
我能够实现的目标可以在这个沙箱中看到 https://codesandbox.io/s/react-table-infinite-mzkkp?file=/src/MuiTable.js (我无法在这里提供代码,因为它很大)
因此,一般来说,我可以使 Autosizer、CellMeasurer 和 List 组件从反应虚拟化中正常工作。我被困在无限滚动部分。我在官方文档上看到了这个例子,但似乎有点反模式(直接突变状态根本不是一件好事)
所以我试图达到类似的结果,但是如果你能看到,我的 loadMore 函数由于某种原因触发得太早了。它导致几乎每个滚动事件都发送请求。
任何帮助深表感谢。
我已经尝试过的:
<TableRow
{...row.getRowProps({
style
})}
component="div"
>
{row.cells.map((cell) => {
return (
<TableCell {...cell.getCellProps()} component="div">
{cell.render("Cell")}
</TableCell>
);
})}
</TableRow>
Run Code Online (Sandbox Code Playgroud)
此外,尚不清楚如何以这种方式呈现自定义过滤器。
reactjs react-virtualized react-infinite-scroll react-table-v7
我使用的是material-ui的List和ListItem组件.具体来说,我使用的是嵌套项功能.请参阅http://www.material-ui.com/#/components/list ,在页面的下半部分,您将看到嵌套列表.重点是:material-ui负责"嵌套"问题,例如缩进以及扩展/收缩箭头.
一旦我添加了很多项目,我意识到列表非常慢.所以我偶然发现了AutoSizer的反应虚拟化.问题是:在反应虚拟化中,我的代码需要为每一行提供rowRenderer函数.我不想丢失内置的材料-ui功能,可以找出嵌套项目的缩进.然而,使用AutoSizer似乎我的代码需要做自定义工作来找出缩进.我的代码也将提供扩展/合同箭头.目前它是免费的材料-ui的List/ListItem.
任何提示或建议?
谢谢
我正在使用react-virualized 9与Autosizer,List和CellMeasurer组件.我需要在列表数据发生变化时更新行高.看来,自从版本9中支持React Fiber的更改以来,CellMeasurer的唯一公共方法现在是measure().大多数示例使用以前的resetMeasurementForRow()方法.当前的CellMeasurer doc似乎没有关于新公共方法的任何信息.不确定我是否忽略了某些东西,但感谢任何帮助.
const cache = new CellMeasurerCache({
defaultHeight: 60,
fixedWidth: true
});
<AutoSizer>
{({ width, height }) => (
<List
deferredMeasurementCache={cache}
height={height}
ref={element => { this.list = element; }}
rowCount={list.length}
rowHeight={cache.rowHeight}
rowRenderer={this.rowRenderer}
width={width}
/>
)}
</AutoSizer>
rowRenderer({ index, key, parent, style }) {
return (
<CellMeasurer
cache={cache}
columnIndex={0}
key={key}
overscanRowCount={10}
parent={parent}
ref={element => { this.cellMeasurer = element; }}
rowIndex={index}
>
{({ measure }) => {
this.measure = measure.bind(this);
return <MyList index={index} data={list[index]} style={style} />;
}}
</CellMeasurer> …Run Code Online (Sandbox Code Playgroud) 我需要打开/关闭其他行详细信息.
有没有人实现或有想法如何为每一行实现扩展/折叠功能?
当我滚动浏览列表时,我遇到了一些问题.还要注意底部的巨大空间.观看视频:https://vimeo.com/215349521
据我所知,我没有犯任何重大错误.但我确实相信问题是由于CellMeasurer.
Chrome版本:58.0.3029.81
class PromotionList extends Component {
constructor(props) {
super(props);
this.cache = new CellMeasurerCache({
defaultHeight: 100,
fixedWidth: true,
});
this.rowRenderer = this.rowRenderer.bind(this);
}
componentWillMount() {
this.props.fetchPromotionsIfNeeded();
}
rowRenderer({ index, parent }) {
const { promotions } = this.props;
const data = promotions.list[index];
return (
<CellMeasurer
cache={this.cache}
columnIndex={0}
key={uuid.v1()}
parent={parent}
rowIndex={index}
>
<BlobItem
key={uuid.v1()}
type={BlobTypes.promotion}
data={data}
onClick={this.props.onItemClick}
index={index}
/>
</CellMeasurer>
);
}
render() {
const { promotions, previewSize } = this.props;
return (
<List
height={300}
width={previewSize.width}
rowCount={promotions.list.length} …Run Code Online (Sandbox Code Playgroud) 我正在尝试创建一个8列的表,每列包含一个<input />元素。由于某些原因,我在文本输入的on change事件中遇到了延迟。将列数减少到4以下可改善体验。这可能是有道理的,但是我也尝试增加列的数量,结果发现对于10个或更多的列,体验还是很棒的。您可以检查我的超级简单React应用程序,在其中可以动态更改列数-http://com.react.table-with-inputs.s3-website.eu-central-1.amazonaws.com/。
这是我的代码:
import React from 'react';
import { AutoSizer, Table, Column } from 'react-virtualized';
class App extends React.Component {
constructor(props) {
super(props);
this.state = {
numOfCols: '8',
};
}
rowGetter = ({ index }) => {
return { index };
};
renderHeaderCell = ({ label }) => {
return (
<span>{label}</span>
);
};
renderCell = ({ rowIndex, columnIndex }) => {
return (
<input key={`input-${rowIndex}-${columnIndex}`} />
);
};
render() {
return (
<div style={{ …Run Code Online (Sandbox Code Playgroud) 如何在窗口滚动条中创建无限滚动列表?(与Facebook时间线相同 - 模拟)?
下面是我尝试过的代码,但它没有按预期工作.它只显示第一个项目,之后不显示任何内容.
<div className={styles.WindowScrollerWrapper}>
<InfiniteLoader
isRowLoaded={this._isRowLoaded}
loadMoreRows={this._loadMoreRows}
rowCount={list.size}
threshold={10}>
{({ onRowsRendered, registerChild }) => (
<WindowScroller>
{({ height, isScrolling, scrollTop }) => (
<AutoSizer disableHeight>
{({ width }) => (
<List
ref={registerChild}
className={styles.List}
autoHeight
height={height}
width={width}
onRowsRendered={onRowsRendered}
rowCount={list.size}
rowHeight={30}
rowRenderer={this._rowRenderer}
scrollToIndex={randomScrollToIndex}
/>
)}
</AutoSizer>
)}
</WindowScroller>
)}
</InfiniteLoader>
</div>
Run Code Online (Sandbox Code Playgroud)
提前谢谢了.
更新
以下是演示的URL:https://plnkr.co/edit/akyEpZ0cXhfs2jtZgQmN
AutoSizer的宽度给我一个合适的值,我一直得到Autosizer高度为0,这导致VirtualScroll组件不显示.但是,如果我使用disableHeight prop并为VirtualScroll提供固定的高度值(即200px),VirtualScroll会按预期显示行.谁能看到什么错了?
最终,Autosizer意味着生活在Material-ui Dialog组件中,但我也试过将autosizer简单地渲染成div.同样的问题.
render() {
return (
<Dialog
modal={false}
open={this.state.open}
onRequestClose={this.handleClose}
contentStyle={pageOptionsDialog.body}
>
<div>
<AutoSizer>
{({ width, height }) => (
<VirtualScroll
id="virtualScroll"
onRowsRendered={this.props.loadNextPage}
rowRenderer={this.rowRenderer}
height={height}
rowCount={this.props.rowCount}
rowHeight={30}
width={width}
/>
)}
</AutoSizer>
</div>
</dialog>
)}
Run Code Online (Sandbox Code Playgroud) 我使用angular-ui-grid(http://ui-grid.info/)来显示表格数据.总的来说,它很慢,所以我们决定使用ag-grid(https://www.ag-grid.com/).这对于常规大小的数据集来说,性能更高,更好.
但是,现在我们正在处理一些大小为100列×10,000行(~1M单元)的表格数据,并且网格的性能似乎相当慢.
我想知道是否有人使用过hypergrid(https://fin-hypergrid.github.io/core/2.0.2/) - 它似乎'解决'大cols x 大行的问题,在他们的演示中似乎在大型数据集上更快(几乎一个数量级).
javascript performance ag-grid react-virtualized fin-hypergrid