背景
公司的后台产品有很多表格,UI要求表格和别的内容一屏展示,表格内容超出部分表格内滚动。antd Table支持添加scroll属性:scroll={{ y: Y }},滚动区域高度为Y,因此需要计算出Y的值,每个表格都需要,因此考虑封装普通Table组件或是使用高阶组件。
高阶组件
https://react.docschina.org/docs/higher-order-components.html
antd table自适应高度
// 高阶组件,可做装饰器
// 计算 窗口高度-WrappedComponent.tableRef距离页面顶部的距离
import React, { Component } from "react";
const TableAdaptive = WrappedComponent => {
return class extends Component {
constructor(props) {
super(props);
this.state = { y: null };
this.ref = WrappedComponent.tableRef;
this.onWindowResize = this.onWindowResize.bind(this);
}
componentDidMount() {
this.onWindowResize();
window.addEventListener("resize", this.onWindowResize);
}
componentWillUnmount() {
window.removeEventListener("resize", this.onWindowResize);
}
// 计算元素距窗口顶端的距离
getAbsTop(node) {
var top = node.offsetTop;
while (node.offsetParent != null) {
node = node.offsetParent;
top += node.offsetTop;
}
return top;
}
onWindowResize() {
if (this.ref && this.ref.current) {
const el = document.body || document.documentElement;
const top = this.getAbsTop(this.ref.current) || 0;
const y = el.clientHeight - top;
this.setState({
y
});
}
}
render() {
const { y } = this.state;
return <WrappedComponent tableData={{ y: y }} {...this.props} />;
}
};
};
export default TableAdaptive;
可直接在页面使用装饰器
@tableAdaptive
class Project extends Component {
static tableRef = React.createRef();
render(){
const {tableData:{Y}={} = this.props;
return <div ref={Project.tableRef}>
<Table
rowKey="id"
size="small"
scroll={{ y: Y - 100 }} // 100是size为small时的表头和表尾
dataSource={data}
columns={columns}
/>
</div>
}
}