feat(视图): 明细表/汇总表支持按列设置宽度,拖拽调整宽度。#7707
This commit is contained in:
parent
b478a26c62
commit
3e0f51a7e6
@ -101,6 +101,7 @@
|
||||
:terminal-type="scaleCoefficientType"
|
||||
:track-menu="trackMenu"
|
||||
:search-count="searchCount"
|
||||
:in-screen="inScreen"
|
||||
@onChartClick="chartClick"
|
||||
@onJumpClick="jumpClick"
|
||||
@onPageChange="pageClick"
|
||||
|
||||
@ -1398,6 +1398,7 @@ export default {
|
||||
table_column_width_config: 'Column Width',
|
||||
table_column_adapt: 'Adapt',
|
||||
table_column_custom: 'Custom',
|
||||
table_column_fixed: 'Fixed',
|
||||
chart_table_pivot: 'Pivot Table',
|
||||
table_pivot_row: 'Data Row',
|
||||
field_error_tips: 'This field is changed(Include dimension、quota,field type,deleted),please edit again.',
|
||||
@ -1539,7 +1540,7 @@ export default {
|
||||
drill_dimension_tip: 'Only fields in the dataset can be drilled',
|
||||
table_scroll_tip: 'The detail table is only effective when the pagination mode is "Drop-down".',
|
||||
table_threshold_tip: 'Tip: Do not select fields repeatedly. If the same field is configured repeatedly, only the last field will take effect.',
|
||||
table_column_width_tip: `Column width do not always work.<br/>
|
||||
table_column_width_tip: `Fixed Column width do not always work.<br/>
|
||||
The priority of the container width is higher than the column width, <br/>
|
||||
which means if the result of dividing the width of the table container by the number of columns is greater than specified column width, <br/>
|
||||
the former will take effect.`,
|
||||
|
||||
@ -1396,6 +1396,7 @@ export default {
|
||||
table_freeze: '表格凍結',
|
||||
table_column_adapt: '自適應',
|
||||
table_column_custom: '自定義',
|
||||
table_column_fixed: '固定列寬',
|
||||
chart_table_pivot: '透視表',
|
||||
table_pivot_row: '數據行',
|
||||
field_error_tips: '該字段所對應的數據集原始字段發生變更(包括維度、指標,字段類型,字段被刪除等),建議重新編輯',
|
||||
@ -1536,7 +1537,7 @@ export default {
|
||||
drill_dimension_tip: '鑽取字段僅支持數據集中的字段',
|
||||
table_scroll_tip: '明細表僅在分頁模式為"下拉"時生效。',
|
||||
table_threshold_tip: '提示:請勿重複選擇字段,若同一字段重複配置,則只有最後的字段配置生效。',
|
||||
table_column_width_tip: '列寬並非任何時候都能生效。<br/>容器寬度優先級高於列寬。即(表格容器寬度 / 列數 > 指定列寬),則列寬優先取(容器寬度 / 列數)',
|
||||
table_column_width_tip: '固定列寬並非任何時候都能生效。<br/>容器寬度優先級高於列寬。即(表格容器寬度 / 列數 > 指定列寬),則列寬優先取(容器寬度 / 列數)',
|
||||
reference_field_tip: '引用字段以 "[" 開始,"]" 結束。請<br/>勿修改引用內容,否則將引用失敗。<br/>若輸入與引用字段相同格式的內容,將被當做引用字段處理。',
|
||||
scatter_tip: '該指標生效時,樣式大小中的氣泡大小屬性將失效',
|
||||
scatter_group_tip: '僅當橫軸內為指標時生效',
|
||||
|
||||
@ -1396,6 +1396,7 @@ export default {
|
||||
table_column_width_config: '列宽调整',
|
||||
table_column_adapt: '自适应',
|
||||
table_column_custom: '自定义',
|
||||
table_column_fixed: '固定列宽',
|
||||
chart_table_pivot: '透视表',
|
||||
table_pivot_row: '数据行',
|
||||
field_error_tips: '该字段所对应的数据集原始字段发生变更(包括维度、指标,字段类型,字段被删除等),建议重新编辑',
|
||||
@ -1536,7 +1537,7 @@ export default {
|
||||
drill_dimension_tip: '钻取字段仅支持数据集中的字段',
|
||||
table_scroll_tip: '明细表仅在分页模式为"下拉"时生效。',
|
||||
table_threshold_tip: '提示:请勿重复选择字段,若同一字段重复配置,则只有最后的字段配置生效',
|
||||
table_column_width_tip: '列宽并非任何时候都能生效。<br/>容器宽度优先级高于列宽,即(表格容器宽度 / 列数 > 指定列宽),则列宽优先取(容器宽度 / 列数)。',
|
||||
table_column_width_tip: '固定列宽并非任何时候都能生效。<br/>容器宽度优先级高于列宽,即(表格容器宽度 / 列数 > 指定列宽),则列宽优先取(容器宽度 / 列数)。',
|
||||
reference_field_tip: '引用字段以 "[" 开始, "]" 结束。<br/>请勿修改引用内容,否则将引用失败。<br/>若输入与引用字段相同格式的内容,将被当作引用字段处理。',
|
||||
scatter_tip: '该指标生效时,样式大小中的气泡大小属性将失效',
|
||||
scatter_group_tip: '仅当横轴内为指标时生效',
|
||||
|
||||
@ -103,6 +103,7 @@ export const DEFAULT_SIZE = {
|
||||
tableCellTooltip: {
|
||||
show: false
|
||||
},
|
||||
tableFieldWidth: [],
|
||||
gaugeMinType: 'fix', // fix or dynamic
|
||||
gaugeMinField: {
|
||||
id: '',
|
||||
|
||||
@ -249,12 +249,33 @@ export function getSize(chart) {
|
||||
size.cellCfg = {
|
||||
height: s.tableItemHeight
|
||||
}
|
||||
if (s.tableColumnMode && s.tableColumnMode === 'adapt') {
|
||||
delete size.cellCfg.width
|
||||
size.layoutWidthType = 'compact'
|
||||
} else {
|
||||
delete size.layoutWidthType
|
||||
size.cellCfg.width = s.tableColumnWidth
|
||||
switch (s.tableColumnMode) {
|
||||
case 'adapt': {
|
||||
delete size.cellCfg.width
|
||||
size.layoutWidthType = 'compact'
|
||||
break
|
||||
}
|
||||
case 'field': {
|
||||
delete size.layoutWidthType
|
||||
const fieldMap = s.tableFieldWidth?.reduce((p, n) => {
|
||||
p[n.fieldId] = n
|
||||
return p
|
||||
}, {}) || {}
|
||||
size.colCfg.width = node => {
|
||||
const width = node.spreadsheet.container.cfg.el.offsetWidth
|
||||
if (!s.tableFieldWidth?.length) {
|
||||
let columnCount = s.showIndex ? chart.data.fields.length + 1 : chart.data.fields.length
|
||||
return width / columnCount
|
||||
}
|
||||
const baseWidth = width / 100
|
||||
return fieldMap[node.field] ? fieldMap[node.field].width * baseWidth : baseWidth * 10
|
||||
}
|
||||
break
|
||||
}
|
||||
default: {
|
||||
delete size.layoutWidthType
|
||||
size.cellCfg.width = s.tableColumnWidth
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -75,7 +75,7 @@ class SortTooltip extends BaseTooltip {
|
||||
})
|
||||
}
|
||||
}
|
||||
export function baseTableInfo(s2, container, chart, action, tableData, pageInfo, vueCom) {
|
||||
export function baseTableInfo(s2, container, chart, action, tableData, pageInfo, vueCom, resizeFunc) {
|
||||
const containerDom = document.getElementById(container)
|
||||
|
||||
// fields
|
||||
@ -256,6 +256,10 @@ export function baseTableInfo(s2, container, chart, action, tableData, pageInfo,
|
||||
if (size.tableCellTooltip?.show) {
|
||||
s2.on(S2Event.DATA_CELL_HOVER, event => showTooltipValue(s2, event, meta))
|
||||
}
|
||||
// column resize
|
||||
if (size.tableColumnMode === 'field') {
|
||||
s2.on(S2Event.LAYOUT_RESIZE_COL_WIDTH, event => resizeFunc(event))
|
||||
}
|
||||
// theme
|
||||
const customTheme = getCustomTheme(chart)
|
||||
s2.setThemeCfg({ theme: customTheme })
|
||||
@ -263,7 +267,7 @@ export function baseTableInfo(s2, container, chart, action, tableData, pageInfo,
|
||||
return s2
|
||||
}
|
||||
|
||||
export function baseTableNormal(s2, container, chart, action, tableData, vueCom) {
|
||||
export function baseTableNormal(s2, container, chart, action, tableData, vueCom, resizeFunc) {
|
||||
const containerDom = document.getElementById(container)
|
||||
if (!containerDom) return
|
||||
|
||||
@ -490,6 +494,10 @@ export function baseTableNormal(s2, container, chart, action, tableData, vueCom)
|
||||
if (size.tableCellTooltip?.show) {
|
||||
s2.on(S2Event.DATA_CELL_HOVER, event => showTooltipValue(s2, event, meta))
|
||||
}
|
||||
// column resize
|
||||
if (size.tableColumnMode === 'field') {
|
||||
s2.on(S2Event.LAYOUT_RESIZE_COL_WIDTH, event => resizeFunc(event))
|
||||
}
|
||||
// theme
|
||||
const customTheme = getCustomTheme(chart)
|
||||
s2.setThemeCfg({ theme: customTheme })
|
||||
|
||||
@ -102,6 +102,7 @@ import { CHART_CONT_FAMILY_MAP, DEFAULT_TITLE_STYLE, NOT_SUPPORT_PAGE_DATASET }
|
||||
import ChartTitleUpdate from './ChartTitleUpdate.vue'
|
||||
import { mapState } from 'vuex'
|
||||
import DePagination from '@/components/deCustomCm/pagination.js'
|
||||
import bus from '@/utils/bus'
|
||||
|
||||
export default {
|
||||
name: 'ChartComponentS2',
|
||||
@ -133,6 +134,10 @@ export default {
|
||||
type: Number,
|
||||
required: false,
|
||||
default: 0
|
||||
},
|
||||
inScreen: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
},
|
||||
data() {
|
||||
@ -296,9 +301,9 @@ export default {
|
||||
}
|
||||
}
|
||||
if (chart.type === 'table-info') {
|
||||
this.myChart = baseTableInfo(this.myChart, this.chartId, chart, this.antVAction, this.tableData, this.currentPage, this)
|
||||
this.myChart = baseTableInfo(this.myChart, this.chartId, chart, this.antVAction, this.tableData, this.currentPage, this, this.columnResize)
|
||||
} else if (chart.type === 'table-normal') {
|
||||
this.myChart = baseTableNormal(this.myChart, this.chartId, chart, this.antVAction, this.tableData, this)
|
||||
this.myChart = baseTableNormal(this.myChart, this.chartId, chart, this.antVAction, this.tableData, this, this.columnResize)
|
||||
} else if (chart.type === 'table-pivot') {
|
||||
this.myChart = baseTablePivot(this.myChart, this.chartId, chart, this.antVAction, this.tableHeaderClick, this.tableData)
|
||||
} else {
|
||||
@ -554,6 +559,21 @@ export default {
|
||||
},
|
||||
initRemark() {
|
||||
this.remarkCfg = getRemark(this.chart)
|
||||
},
|
||||
columnResize(resizeColumn) {
|
||||
if (!this.inScreen) {
|
||||
// 预览/全屏预览不保存
|
||||
return
|
||||
}
|
||||
const fieldId = resizeColumn.info.meta.field
|
||||
const size = JSON.parse(this.chart.customAttr).size
|
||||
size.tableFieldWidth?.forEach(item => {
|
||||
if (item.fieldId === fieldId) {
|
||||
const containerWidth = document.getElementById(this.chartId).offsetWidth
|
||||
item.width = (resizeColumn.info.resizedWidth / containerWidth * 100).toFixed(2)
|
||||
}
|
||||
})
|
||||
bus.$emit('set-table-column-width', size.tableFieldWidth)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -258,10 +258,15 @@
|
||||
>
|
||||
<el-radio-group
|
||||
v-model="sizeForm.tableColumnMode"
|
||||
class="column-radio"
|
||||
@change="changeBarSizeCase('tableColumnMode')"
|
||||
>
|
||||
<el-radio label="adapt"><span>{{ $t('chart.table_column_adapt') }}</span></el-radio>
|
||||
<!--此处为了兼容原有的配置,原先的自定义效果实际为固定列宽,后续添加的按列配置才是实际的自定义列宽。-->
|
||||
<el-radio label="custom">
|
||||
<span>{{ $t('chart.table_column_fixed') }}</span>
|
||||
</el-radio>
|
||||
<el-radio v-if="equalsAny(chart.type, 'table-info', 'table-normal')" label="field">
|
||||
<span>{{ $t('chart.table_column_custom') }}</span>
|
||||
</el-radio>
|
||||
</el-radio-group>
|
||||
@ -295,6 +300,43 @@
|
||||
@change="changeBarSizeCase('tableColumnWidth')"
|
||||
/>
|
||||
</el-form-item>
|
||||
<el-form-item
|
||||
v-if="showProperty('tableColumnMode') && sizeForm.tableColumnMode === 'field'"
|
||||
label=""
|
||||
class="form-item"
|
||||
>
|
||||
<el-row>
|
||||
<el-col :span="10">
|
||||
<el-select
|
||||
v-model="fieldColumnWidth.fieldId"
|
||||
:min="10"
|
||||
:max="500"
|
||||
show-input
|
||||
:show-input-controls="false"
|
||||
input-size="mini"
|
||||
@change="changeFieldColumn()"
|
||||
>
|
||||
<el-option
|
||||
v-for="item in sizeForm.tableFieldWidth"
|
||||
:key="item.fieldId"
|
||||
:label="item.name"
|
||||
:value="item.fieldId"
|
||||
/>
|
||||
</el-select>
|
||||
</el-col>
|
||||
<el-col :span="12" :offset="2">
|
||||
<el-input
|
||||
v-model.number="fieldColumnWidth.width"
|
||||
type="number"
|
||||
:min="0"
|
||||
:max="100"
|
||||
@change="changeFieldColumnWidth()"
|
||||
>
|
||||
<template #append>%</template>
|
||||
</el-input>
|
||||
</el-col>
|
||||
</el-row>
|
||||
</el-form-item>
|
||||
<el-form-item
|
||||
v-if="showProperty('tableFreeze')"
|
||||
:label="$t('chart.table_freeze')"
|
||||
@ -1555,6 +1597,7 @@
|
||||
import { CHART_FONT_FAMILY, CHART_FONT_LETTER_SPACE, DEFAULT_SIZE } from '../../chart/chart'
|
||||
import { equalsAny, includesAny } from '@/utils/StringUtils'
|
||||
import { mapState } from 'vuex'
|
||||
import { SERIES_NUMBER_FIELD } from '@antv/s2'
|
||||
|
||||
export default {
|
||||
name: 'SizeSelectorAntV',
|
||||
@ -1618,7 +1661,11 @@ export default {
|
||||
{ name: this.$t('chart.map_line_type_line'), value: 'line' },
|
||||
{ name: this.$t('chart.map_line_type_arc'), value: 'arc' },
|
||||
{ name: this.$t('chart.map_line_type_arc_3d'), value: 'arc3d' }
|
||||
]
|
||||
],
|
||||
fieldColumnWidth: {
|
||||
fieldId: '',
|
||||
width: 10
|
||||
}
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
@ -1775,6 +1822,67 @@ export default {
|
||||
}
|
||||
this.sizeForm.wordSizeRange = this.sizeForm.wordSizeRange ?? DEFAULT_SIZE.wordSizeRange
|
||||
this.sizeForm.wordSpacing = this.sizeForm.wordSpacing ?? DEFAULT_SIZE.wordSpacing
|
||||
|
||||
if (this.chart.type !== 'table-pivot') {
|
||||
let { xaxis, xaxisExt } = this.chart
|
||||
if (!(xaxis instanceof Object)) {
|
||||
xaxis = JSON.parse(xaxis)
|
||||
}
|
||||
if (!(xaxisExt instanceof Object)) {
|
||||
xaxisExt = JSON.parse(xaxisExt)
|
||||
}
|
||||
let allAxis = xaxis
|
||||
if (this.chart.type === 'table-normal') {
|
||||
allAxis = allAxis.concat(xaxisExt)
|
||||
}
|
||||
if (allAxis.length && this.sizeForm.showIndex) {
|
||||
allAxis.unshift({
|
||||
dataeaseName: SERIES_NUMBER_FIELD,
|
||||
name: this.sizeForm.indexLabel
|
||||
})
|
||||
}
|
||||
if (!allAxis.length) {
|
||||
this.sizeForm.tableFieldWidth?.splice(0)
|
||||
this.fieldColumnWidth.fieldId = ''
|
||||
this.fieldColumnWidth.width = ''
|
||||
} else {
|
||||
if (!this.sizeForm.tableFieldWidth?.length) {
|
||||
this.sizeForm.tableFieldWidth = []
|
||||
const defaultWidth = (100 / allAxis.length).toFixed(2)
|
||||
allAxis.forEach(item => {
|
||||
this.sizeForm.tableFieldWidth.push({
|
||||
fieldId: item.dataeaseName,
|
||||
name: item.name,
|
||||
width: defaultWidth
|
||||
})
|
||||
})
|
||||
} else {
|
||||
const fieldMap = this.sizeForm.tableFieldWidth.reduce((p, n) => {
|
||||
p[n.fieldId] = n
|
||||
return p
|
||||
},{})
|
||||
this.sizeForm.tableFieldWidth.splice(0)
|
||||
allAxis.forEach(item => {
|
||||
let width = 10
|
||||
if (fieldMap[item.dataeaseName]) {
|
||||
width = fieldMap[item.dataeaseName].width
|
||||
}
|
||||
this.sizeForm.tableFieldWidth.push({
|
||||
fieldId: item.dataeaseName,
|
||||
name: item.name,
|
||||
width
|
||||
})
|
||||
})
|
||||
}
|
||||
let selectedField = this.sizeForm.tableFieldWidth[0]
|
||||
const curFieldIndex = this.sizeForm.tableFieldWidth.findIndex(i => i.fieldId === this.fieldColumnWidth.fieldId)
|
||||
if (curFieldIndex !== -1) {
|
||||
selectedField = this.sizeForm.tableFieldWidth[curFieldIndex]
|
||||
}
|
||||
this.fieldColumnWidth.fieldId = selectedField.fieldId
|
||||
this.fieldColumnWidth.width = selectedField.width
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -1905,6 +2013,19 @@ export default {
|
||||
}
|
||||
}
|
||||
return false
|
||||
},
|
||||
changeFieldColumn() {
|
||||
const fieldWidth = this.sizeForm.tableFieldWidth?.find(i => i.fieldId === this.fieldColumnWidth.fieldId)
|
||||
if (fieldWidth) {
|
||||
this.fieldColumnWidth.width = fieldWidth.width
|
||||
}
|
||||
},
|
||||
changeFieldColumnWidth() {
|
||||
const fieldWidth = this.sizeForm.tableFieldWidth?.find(i => i.fieldId === this.fieldColumnWidth.fieldId)
|
||||
if (fieldWidth) {
|
||||
fieldWidth.width = this.fieldColumnWidth.width
|
||||
this.changeBarSizeCase('tableFieldWidth')
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1965,4 +2086,17 @@ export default {
|
||||
.form-flex >>> .el-form-item__content {
|
||||
display: flex;
|
||||
}
|
||||
::v-deep input::-webkit-outer-spin-button,
|
||||
::v-deep input::-webkit-inner-spin-button {
|
||||
-webkit-appearance: none !important;
|
||||
}
|
||||
|
||||
::v-deep input[type="number"] {
|
||||
-moz-appearance: textfield !important;
|
||||
}
|
||||
.column-radio {
|
||||
label {
|
||||
margin-right: 10px;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
@ -2323,6 +2323,7 @@ export default {
|
||||
bus.$off('plugins-calc-style', this.calcStyle)
|
||||
bus.$off('plugin-chart-click', this.chartClick)
|
||||
bus.$off('set-dynamic-area-code', this.setDynamicAreaCode)
|
||||
bus.$off('set-table-column-width', this.onTableFieldWidthChange)
|
||||
},
|
||||
activated() {
|
||||
},
|
||||
@ -2413,6 +2414,7 @@ export default {
|
||||
bus.$on('plugins-calc-style', this.calcStyle)
|
||||
bus.$on('plugin-chart-click', this.chartClick)
|
||||
bus.$on('set-dynamic-area-code', this.setDynamicAreaCode)
|
||||
bus.$on('set-table-column-width', this.onTableFieldWidthChange)
|
||||
},
|
||||
initTableData(id, optType) {
|
||||
if (id != null) {
|
||||
@ -2962,7 +2964,10 @@ export default {
|
||||
this.view.customAttr.size = val
|
||||
this.calcData()
|
||||
},
|
||||
|
||||
onTableFieldWidthChange(val) {
|
||||
this.view.customAttr.size.tableFieldWidth = val
|
||||
this.calcData()
|
||||
},
|
||||
onTextChange(val) {
|
||||
this.view.customStyle.text = val
|
||||
this.view.title = val.title
|
||||
@ -3651,6 +3656,9 @@ export default {
|
||||
} else if (type === 'label-normal') {
|
||||
this.view.senior.functionCfg.emptyDataStrategy = 'breakLine'
|
||||
}
|
||||
if (type === 'table-pivot') {
|
||||
this.view.customAttr.size.tableColumnMode = 'custom'
|
||||
}
|
||||
// reset custom colors
|
||||
this.view.customAttr.color.seriesColors = []
|
||||
},
|
||||
|
||||
Loading…
Reference in New Issue
Block a user