如何在Ag-Grid中实现按行格式化(转置表格效果)?
解决方案:转置数据+动态列配置+行级条件判断
核心思路是先转置时间序列数据,让原时间点行变成表格列,再通过AgGrid列配置中的函数式属性(如valueFormatter、cellStyle),根据每行的维度标识来应用对应的渲染、格式和样式,完美替代“先配置行再转置”的思路。
1. 数据转置处理
先把原始时间序列数据(每行对应一个时间点的多维度指标)转置为“维度为行、时间为列”的结构。示例代码:
// 原始时间序列数据 const rawData = [ { time: '2024-01-01', temperature: 20, humidity: 60, pm25: 35 }, { time: '2024-01-02', temperature: 22, humidity: 58, pm25: 42 }, { time: '2024-01-03', temperature: 19, humidity: 65, pm25: 28 } ]; // 数据转置函数 function transposeTimeSeries(data) { // 提取所有维度字段(排除time) const metrics = Object.keys(data[0]).filter(key => key !== 'time'); // 提取所有时间点 const times = data.map(item => item.time); // 构建转置后的数据(优化版:用Map减少查找次数) const timeDataMap = new Map(); data.forEach(item => timeDataMap.set(item.time, item)); return metrics.map(metric => { const row = { metric: metric }; times.forEach(time => { row[time] = timeDataMap.get(time)[metric]; }); return row; }); } const transposedData = transposeTimeSeries(rawData);
转置后的数据结构:
[ { metric: 'temperature', '2024-01-01': 20, '2024-01-02': 22, '2024-01-03': 19 }, { metric: 'humidity', '2024-01-01': 60, '2024-01-02': 58, '2024-01-03': 65 }, { metric: 'pm25', '2024-01-01': 35, '2024-01-02': 42, '2024-01-03': 28 } ]
2. 动态生成AgGrid列配置
针对转置后的结构,生成列配置:固定一个metric列展示维度名称,然后为每个时间点生成对应列,并通过函数式配置实现行级的渲染、格式和样式控制。
示例代码(React环境):
import { AgGridReact } from 'ag-grid-react'; import 'ag-grid-community/styles/ag-grid.css'; import 'ag-grid-community/styles/ag-theme-alpine.css'; function TimeSeriesGrid() { const transposedData = transposeTimeSeries(rawData); const times = rawData.map(item => item.time); // 动态生成列配置 const columnDefs = [ { headerName: '指标', field: 'metric', width: 120, cellStyle: { fontWeight: 'bold', textAlign: 'center' } }, // 为每个时间点生成列 ...times.map(time => ({ headerName: time, field: time, width: 150, // 按行(维度)设置值格式化器 valueFormatter: (params) => { switch(params.data.metric) { case 'temperature': return `${params.value} ℃`; case 'humidity': return `${params.value} %`; case 'pm25': return `${params.value} μg/m³`; default: return params.value; } }, // 按行(维度)设置单元格样式 cellStyle: (params) => { if (params.data.metric === 'temperature') { return { backgroundColor: params.value > 20 ? '#ffebee' : '#e8f5e9' }; } else if (params.data.metric === 'humidity') { return { backgroundColor: params.value > 60 ? '#e3f2fd' : '#fff3e0' }; } return {}; }, // 按行(维度)设置自定义渲染器(示例:给PM2.5加图标) cellRenderer: (params) => { if (params.data.metric === 'pm25') { return `<span>${params.valueFormatted} <i class="fas fa-smog"></i></span>`; } return params.valueFormatted; } })) ]; return ( <div className="ag-theme-alpine" style={{ height: 400, width: '100%' }}> <AgGridReact rowData={transposedData} columnDefs={columnDefs} enableCellTextSelection={true} suppressMenuHide={true} /> </div> ); }
3. 关键技巧说明
- 函数式配置的核心作用:AgGrid的
valueFormatter、cellStyle、cellRenderer都支持传入函数,通过params.data.metric可以判断当前行对应的原始维度,从而精准应用不同的规则,实现“按原行设置属性”的需求。 - 动态列适配性:通过遍历时间点数组生成列配置,适配任意数量的时间序列数据,无需硬编码。
- 性能优化:转置函数中用
Map存储时间到数据的映射,避免多次find操作,在大数据量场景下提升效率。
内容的提问来源于stack exchange,提问作者MYK
相关产品推荐
相关产品推荐

