import React, { PureComponent } from 'react'; import { Chart } from '@antv/g2'; import DataSet from '@antv/data-set'; import Debounce from 'lodash-decorators/debounce'; import Bind from 'lodash-decorators/bind'; import equal from '../equal'; class ColumnarStack extends PureComponent { componentDidMount() { this.renderChart(this.props.data); window.addEventListener('resize', this.resize); } componentWillReceiveProps(nextProps) { if (!equal(this.props, nextProps)) { this.renderChart(nextProps.data); } } componentWillUnmount() { window.removeEventListener('resize', this.resize); if (this.chart) { this.chart.destroy(); } this.resize.cancel(); } @Bind() @Debounce(200) resize() { if (!this.node) { return; } this.renderChart([]); } handleRef = (n) => { this.node = n; }; renderChart(data) { const { xUnit = '', yUnit = '', height } = this.props; if (!data || (data && data.length < 1)) return; // clean if (this.chart) { this.chart.destroy(); } this.node.innerHTML = ''; const chart = new Chart({ container: this.node, autoFit: true, /* 图标自适应 */ height, padding: 'auto', }); // 计算每个柱子的占比 const ds = new DataSet(); const dv = ds.createView().source(data).transform({ type: 'percent', field: 'y', // 统计销量 dimension: 'type', // 每年的占比 groupBy: ['x'], // 以不同产品类别为分组 as: 'percent', }); chart.data(dv.rows, { percent: { min: 0, formatter: (val) => { return `${(val * 100).toFixed(2)}${yUnit}`; }, }, }); chart.axis('x', { label: { formatter: (val) => { return `${val}${xUnit}`; }, }, }); chart.interval().adjust('stack').position('x*percent').color('type') .tooltip('x*y*type', (name, value, type) => { return { title: `${name}${xUnit}`, name: type, value: `${value}`, }; }); chart.render(); this.chart = chart; } render() { return (
); } } export default ColumnarStack;