mirror of
https://github.com/dataease/dataease.git
synced 2025-02-24 19:42:56 +08:00
feat(图表): 明细表支持总计 #12650
This commit is contained in:
parent
7a87a511ce
commit
804e6e93ae
@ -20,7 +20,9 @@ import {
|
||||
CustomTableColCell,
|
||||
getRowIndex,
|
||||
calculateHeaderHeight,
|
||||
SortTooltip
|
||||
SortTooltip,
|
||||
configSummaryRow,
|
||||
summaryRowStyle
|
||||
} from '@/views/chart/components/js/panel/common/common_table'
|
||||
|
||||
const { t } = useI18n()
|
||||
@ -68,7 +70,9 @@ export class TableInfo extends S2ChartView<TableSheet> {
|
||||
'alpha',
|
||||
'tablePageMode',
|
||||
'showHoverStyle',
|
||||
'autoWrap'
|
||||
'autoWrap',
|
||||
'showSummary',
|
||||
'summaryLabel'
|
||||
],
|
||||
'table-cell-selector': [
|
||||
...TABLE_EDITOR_PROPERTY_INNER['table-cell-selector'],
|
||||
@ -240,8 +244,12 @@ export class TableInfo extends S2ChartView<TableSheet> {
|
||||
return new CustomTableColCell(node, sheet, config)
|
||||
}
|
||||
}
|
||||
// 总计
|
||||
configSummaryRow(chart, s2Options, newData, tableHeader, basicStyle, basicStyle.showSummary)
|
||||
// 开始渲染
|
||||
const newChart = new TableSheet(containerDom, s2DataConfig, s2Options)
|
||||
// 总计紧贴在单元格后面
|
||||
summaryRowStyle(newChart, newData, tableCell, tableHeader, basicStyle.showSummary)
|
||||
// 开启自动换行
|
||||
if (basicStyle.autoWrap) {
|
||||
// 调整表头宽度时,计算表头高度
|
||||
|
@ -1,9 +1,10 @@
|
||||
import { useI18n } from '@/hooks/web/useI18n'
|
||||
import { formatterItem, valueFormatter } from '@/views/chart/components/js/formatter'
|
||||
import {
|
||||
configSummaryRow,
|
||||
copyContent,
|
||||
CustomDataCell,
|
||||
SortTooltip
|
||||
SortTooltip,
|
||||
summaryRowStyle
|
||||
} from '@/views/chart/components/js/panel/common/common_table'
|
||||
import { S2ChartView, S2DrawOptions } from '@/views/chart/components/js/panel/types/impl/s2'
|
||||
import { parseJson } from '@/views/chart/components/js/util'
|
||||
@ -189,56 +190,11 @@ export class TableNormal extends S2ChartView<TableSheet> {
|
||||
}
|
||||
|
||||
// 总计
|
||||
if (basicStyle.showSummary) {
|
||||
// 设置汇总行高度和表头一致
|
||||
const heightByField = {}
|
||||
heightByField[newData.length] = tableHeader.tableTitleHeight
|
||||
s2Options.style.rowCfg = { heightByField }
|
||||
// 计算汇总加入到数据里,冻结最后一行
|
||||
s2Options.frozenTrailingRowCount = 1
|
||||
const yAxis = chart.yAxis
|
||||
const xAxis = chart.xAxis
|
||||
const summaryObj = newData.reduce(
|
||||
(p, n) => {
|
||||
yAxis.forEach(axis => {
|
||||
p[axis.dataeaseName] =
|
||||
(parseFloat(n[axis.dataeaseName]) || 0) + (parseFloat(p[axis.dataeaseName]) || 0)
|
||||
})
|
||||
return p
|
||||
},
|
||||
{ SUMMARY: true }
|
||||
)
|
||||
newData.push(summaryObj)
|
||||
s2Options.dataCell = viewMeta => {
|
||||
if (viewMeta.rowIndex !== newData.length - 1) {
|
||||
return new CustomDataCell(viewMeta, viewMeta.spreadsheet)
|
||||
}
|
||||
if (viewMeta.colIndex === 0) {
|
||||
if (tableHeader.showIndex) {
|
||||
viewMeta.fieldValue = basicStyle.summaryLabel ?? '总计'
|
||||
} else {
|
||||
if (xAxis.length) {
|
||||
viewMeta.fieldValue = basicStyle.summaryLabel ?? '总计'
|
||||
}
|
||||
}
|
||||
}
|
||||
return new SummaryCell(viewMeta, viewMeta.spreadsheet)
|
||||
}
|
||||
}
|
||||
configSummaryRow(chart, s2Options, newData, tableHeader, basicStyle, basicStyle.showSummary)
|
||||
// 开始渲染
|
||||
const newChart = new TableSheet(containerDom, s2DataConfig, s2Options)
|
||||
// 总计紧贴在单元格后面
|
||||
if (basicStyle.showSummary) {
|
||||
newChart.on(S2Event.LAYOUT_BEFORE_RENDER, () => {
|
||||
const totalHeight =
|
||||
tableHeader.tableTitleHeight * 2 + tableCell.tableItemHeight * (newData.length - 1)
|
||||
if (totalHeight < newChart.options.height) {
|
||||
// 6 是阴影高度
|
||||
newChart.options.height =
|
||||
totalHeight < newChart.options.height - 6 ? totalHeight + 6 : totalHeight
|
||||
}
|
||||
})
|
||||
}
|
||||
summaryRowStyle(newChart, newData, tableCell, tableHeader, basicStyle.showSummary)
|
||||
// 自适应铺满
|
||||
if (basicStyle.tableColumnMode === 'adapt') {
|
||||
newChart.on(S2Event.LAYOUT_RESIZE_COL_WIDTH, () => {
|
||||
@ -334,15 +290,3 @@ export class TableNormal extends S2ChartView<TableSheet> {
|
||||
super('table-normal', [])
|
||||
}
|
||||
}
|
||||
|
||||
class SummaryCell extends CustomDataCell {
|
||||
getTextStyle() {
|
||||
const textStyle = cloneDeep(this.theme.colCell.bolderText)
|
||||
textStyle.textAlign = this.theme.dataCell.text.textAlign
|
||||
return textStyle
|
||||
}
|
||||
getBackgroundColor() {
|
||||
const { backgroundColor, backgroundColorOpacity } = this.theme.colCell.cell
|
||||
return { backgroundColor, backgroundColorOpacity }
|
||||
}
|
||||
}
|
||||
|
@ -28,7 +28,7 @@ import {
|
||||
type PivotSheet,
|
||||
renderPolygon,
|
||||
renderText,
|
||||
S2DataConfig,
|
||||
S2DataConfig, S2Event,
|
||||
S2Options,
|
||||
S2Theme,
|
||||
SERIES_NUMBER_FIELD,
|
||||
@ -40,13 +40,15 @@ import {
|
||||
TableDataCell,
|
||||
updateShapeAttr,
|
||||
ViewMeta
|
||||
} from '@antv/s2'
|
||||
} from "@antv/s2";
|
||||
import { cloneDeep, filter, find, intersection, keys, merge, repeat } from 'lodash-es'
|
||||
import { createVNode, render } from 'vue'
|
||||
import TableTooltip from '@/views/chart/components/editor/common/TableTooltip.vue'
|
||||
import Exceljs from 'exceljs'
|
||||
import { saveAs } from 'file-saver'
|
||||
import { ElMessage } from 'element-plus-secondary'
|
||||
import { useI18n } from '@/hooks/web/useI18n'
|
||||
const { t } = useI18n()
|
||||
|
||||
export function getCustomTheme(chart: Chart): S2Theme {
|
||||
const headerColor = hexColorToRGBA(
|
||||
@ -1748,3 +1750,92 @@ const getWrapTextHeight = (wrapText, textStyle, spreadsheet, maxLines) => {
|
||||
const lines = wrapText.split('\n').length
|
||||
return Math.min(lines, maxLines) * maxHeight
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置汇总行
|
||||
* @param chart
|
||||
* @param s2Options
|
||||
* @param newData
|
||||
* @param tableHeader
|
||||
* @param basicStyle
|
||||
* @param showSummary
|
||||
*/
|
||||
export const configSummaryRow = (chart, s2Options, newData, tableHeader, basicStyle, showSummary) =>{
|
||||
if (!showSummary) return
|
||||
// 设置汇总行高度和表头一致
|
||||
const heightByField = {}
|
||||
heightByField[newData.length] = tableHeader.tableTitleHeight
|
||||
s2Options.style.rowCfg = { heightByField }
|
||||
// 计算汇总加入到数据里,冻结最后一行
|
||||
s2Options.frozenTrailingRowCount = 1
|
||||
const yAxis = chart.yAxis
|
||||
const xAxis = chart.xAxis
|
||||
const summaryObj = newData.reduce(
|
||||
(p, n) => {
|
||||
if (chart.type === 'table-info') {
|
||||
xAxis
|
||||
.filter(axis => [2, 3, 4].includes(axis.deType))
|
||||
.forEach(axis => {
|
||||
p[axis.dataeaseName] =
|
||||
(parseFloat(n[axis.dataeaseName]) || 0) + (parseFloat(p[axis.dataeaseName]) || 0)
|
||||
})
|
||||
} else {
|
||||
yAxis.forEach(axis => {
|
||||
p[axis.dataeaseName] =
|
||||
(parseFloat(n[axis.dataeaseName]) || 0) + (parseFloat(p[axis.dataeaseName]) || 0)
|
||||
})
|
||||
}
|
||||
return p
|
||||
},
|
||||
{ SUMMARY: true }
|
||||
)
|
||||
newData.push(summaryObj)
|
||||
s2Options.dataCell = viewMeta => {
|
||||
if (viewMeta.rowIndex !== newData.length - 1) {
|
||||
return new CustomDataCell(viewMeta, viewMeta.spreadsheet)
|
||||
}
|
||||
if (viewMeta.colIndex === 0) {
|
||||
if (tableHeader.showIndex) {
|
||||
viewMeta.fieldValue = basicStyle.summaryLabel ?? t('chart.total_show')
|
||||
} else {
|
||||
if (xAxis.length) {
|
||||
viewMeta.fieldValue = basicStyle.summaryLabel ?? t('chart.total_show')
|
||||
}
|
||||
}
|
||||
}
|
||||
return new SummaryCell(viewMeta, viewMeta.spreadsheet)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 汇总行样式,紧贴在单元格后面
|
||||
* @param newChart
|
||||
* @param newData
|
||||
* @param tableCell
|
||||
* @param tableHeader
|
||||
* @param showSummary
|
||||
*/
|
||||
export const summaryRowStyle = (newChart, newData, tableCell, tableHeader, showSummary) => {
|
||||
if (!showSummary) return
|
||||
newChart.on(S2Event.LAYOUT_BEFORE_RENDER, () => {
|
||||
const totalHeight =
|
||||
tableHeader.tableTitleHeight * 2 + tableCell.tableItemHeight * (newData.length - 1)
|
||||
if (totalHeight < newChart.options.height) {
|
||||
// 6 是阴影高度
|
||||
newChart.options.height =
|
||||
totalHeight < newChart.options.height - 6 ? totalHeight + 6 : totalHeight
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
export class SummaryCell extends CustomDataCell {
|
||||
getTextStyle() {
|
||||
const textStyle = cloneDeep(this.theme.colCell.bolderText)
|
||||
textStyle.textAlign = this.theme.dataCell.text.textAlign
|
||||
return textStyle
|
||||
}
|
||||
getBackgroundColor() {
|
||||
const { backgroundColor, backgroundColorOpacity } = this.theme.colCell.cell
|
||||
return { backgroundColor, backgroundColorOpacity }
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user