feat(图表): 新增矩阵热力图

This commit is contained in:
jianneng-fit2cloud 2024-08-21 20:19:41 +08:00
parent dc8879dacb
commit 432ebf627a
14 changed files with 478 additions and 5 deletions

View File

@ -0,0 +1,18 @@
<svg width="80" height="56" viewBox="0 0 80 56" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M13 6C13 5.44772 13.4477 5 14 5H24C24.5523 5 25 5.44772 25 6V14C25 14.5523 24.5523 15 24 15H14C13.4477 15 13 14.5523 13 14V6Z" fill="#244EB3"/>
<path d="M13 18C13 17.4477 13.4477 17 14 17H24C24.5523 17 25 17.4477 25 18V26C25 26.5523 24.5523 27 24 27H14C13.4477 27 13 26.5523 13 26V18Z" fill="#3370FF"/>
<path d="M13 30C13 29.4477 13.4477 29 14 29H24C24.5523 29 25 29.4477 25 30V38C25 38.5523 24.5523 39 24 39H14C13.4477 39 13 38.5523 13 38V30Z" fill="#244EB3"/>
<path d="M13 42C13 41.4477 13.4477 41 14 41H24C24.5523 41 25 41.4477 25 42V50C25 50.5523 24.5523 51 24 51H14C13.4477 51 13 50.5523 13 50V42Z" fill="#244EB3"/>
<path d="M27 6C27 5.44772 27.4477 5 28 5H38C38.5523 5 39 5.44772 39 6V14C39 14.5523 38.5523 15 38 15H28C27.4477 15 27 14.5523 27 14V6Z" fill="#142D66"/>
<path d="M27 18C27 17.4477 27.4477 17 28 17H38C38.5523 17 39 17.4477 39 18V26C39 26.5523 38.5523 27 38 27H28C27.4477 27 27 26.5523 27 26V18Z" fill="#244EB3"/>
<path d="M27 30C27 29.4477 27.4477 29 28 29H38C38.5523 29 39 29.4477 39 30V38C39 38.5523 38.5523 39 38 39H28C27.4477 39 27 38.5523 27 38V30Z" fill="#142D66"/>
<path d="M27 42C27 41.4477 27.4477 41 28 41H38C38.5523 41 39 41.4477 39 42V50C39 50.5523 38.5523 51 38 51H28C27.4477 51 27 50.5523 27 50V42Z" fill="#3370FF"/>
<path d="M41 6C41 5.44772 41.4477 5 42 5H52C52.5523 5 53 5.44772 53 6V14C53 14.5523 52.5523 15 52 15H42C41.4477 15 41 14.5523 41 14V6Z" fill="#244EB3"/>
<path d="M41 18C41 17.4477 41.4477 17 42 17H52C52.5523 17 53 17.4477 53 18V26C53 26.5523 52.5523 27 52 27H42C41.4477 27 41 26.5523 41 26V18Z" fill="#3370FF"/>
<path d="M41 30C41 29.4477 41.4477 29 42 29H52C52.5523 29 53 29.4477 53 30V38C53 38.5523 52.5523 39 52 39H42C41.4477 39 41 38.5523 41 38V30Z" fill="#244EB3"/>
<path d="M41 42C41 41.4477 41.4477 41 42 41H52C52.5523 41 53 41.4477 53 42V50C53 50.5523 52.5523 51 52 51H42C41.4477 51 41 50.5523 41 50V42Z" fill="#142D66"/>
<path d="M55 6C55 5.44772 55.4477 5 56 5H66C66.5523 5 67 5.44772 67 6V14C67 14.5523 66.5523 15 66 15H56C55.4477 15 55 14.5523 55 14V6Z" fill="#244EB3"/>
<path d="M55 18C55 17.4477 55.4477 17 56 17H66C66.5523 17 67 17.4477 67 18V26C67 26.5523 66.5523 27 66 27H56C55.4477 27 55 26.5523 55 26V18Z" fill="#142D66"/>
<path d="M55 30C55 29.4477 55.4477 29 56 29H66C66.5523 29 67 29.4477 67 30V38C67 38.5523 66.5523 39 66 39H56C55.4477 39 55 38.5523 55 38V30Z" fill="#244EB3"/>
<path d="M55 42C55 41.4477 55.4477 41 56 41H66C66.5523 41 67 41.4477 67 42V50C67 50.5523 66.5523 51 66 51H56C55.4477 51 55 50.5523 55 50V42Z" fill="#244EB3"/>
</svg>

After

Width:  |  Height:  |  Size: 2.6 KiB

View File

@ -0,0 +1,18 @@
<svg width="80" height="56" viewBox="0 0 80 56" xmlns="http://www.w3.org/2000/svg">
<path d="M13 6C13 5.44772 13.4477 5 14 5H24C24.5523 5 25 5.44772 25 6V14C25 14.5523 24.5523 15 24 15H14C13.4477 15 13 14.5523 13 14V6Z"/>
<path d="M13 18C13 17.4477 13.4477 17 14 17H24C24.5523 17 25 17.4477 25 18V26C25 26.5523 24.5523 27 24 27H14C13.4477 27 13 26.5523 13 26V18Z"/>
<path d="M13 30C13 29.4477 13.4477 29 14 29H24C24.5523 29 25 29.4477 25 30V38C25 38.5523 24.5523 39 24 39H14C13.4477 39 13 38.5523 13 38V30Z"/>
<path d="M13 42C13 41.4477 13.4477 41 14 41H24C24.5523 41 25 41.4477 25 42V50C25 50.5523 24.5523 51 24 51H14C13.4477 51 13 50.5523 13 50V42Z"/>
<path d="M27 6C27 5.44772 27.4477 5 28 5H38C38.5523 5 39 5.44772 39 6V14C39 14.5523 38.5523 15 38 15H28C27.4477 15 27 14.5523 27 14V6Z"/>
<path d="M27 18C27 17.4477 27.4477 17 28 17H38C38.5523 17 39 17.4477 39 18V26C39 26.5523 38.5523 27 38 27H28C27.4477 27 27 26.5523 27 26V18Z"/>
<path d="M27 30C27 29.4477 27.4477 29 28 29H38C38.5523 29 39 29.4477 39 30V38C39 38.5523 38.5523 39 38 39H28C27.4477 39 27 38.5523 27 38V30Z"/>
<path d="M27 42C27 41.4477 27.4477 41 28 41H38C38.5523 41 39 41.4477 39 42V50C39 50.5523 38.5523 51 38 51H28C27.4477 51 27 50.5523 27 50V42Z"/>
<path d="M41 6C41 5.44772 41.4477 5 42 5H52C52.5523 5 53 5.44772 53 6V14C53 14.5523 52.5523 15 52 15H42C41.4477 15 41 14.5523 41 14V6Z"/>
<path d="M41 18C41 17.4477 41.4477 17 42 17H52C52.5523 17 53 17.4477 53 18V26C53 26.5523 52.5523 27 52 27H42C41.4477 27 41 26.5523 41 26V18Z"/>
<path d="M41 30C41 29.4477 41.4477 29 42 29H52C52.5523 29 53 29.4477 53 30V38C53 38.5523 52.5523 39 52 39H42C41.4477 39 41 38.5523 41 38V30Z"/>
<path d="M41 42C41 41.4477 41.4477 41 42 41H52C52.5523 41 53 41.4477 53 42V50C53 50.5523 52.5523 51 52 51H42C41.4477 51 41 50.5523 41 50V42Z"/>
<path d="M55 6C55 5.44772 55.4477 5 56 5H66C66.5523 5 67 5.44772 67 6V14C67 14.5523 66.5523 15 66 15H56C55.4477 15 55 14.5523 55 14V6Z"/>
<path d="M55 18C55 17.4477 55.4477 17 56 17H66C66.5523 17 67 17.4477 67 18V26C67 26.5523 66.5523 27 66 27H56C55.4477 27 55 26.5523 55 26V18Z"/>
<path d="M55 30C55 29.4477 55.4477 29 56 29H66C66.5523 29 67 29.4477 67 30V38C67 38.5523 66.5523 39 66 39H56C55.4477 39 55 38.5523 55 38V30Z"/>
<path d="M55 42C55 41.4477 55.4477 41 56 41H66C66.5523 41 67 41.4477 67 42V50C67 50.5523 66.5523 51 66 51H56C55.4477 51 55 50.5523 55 50V42Z"/>
</svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@ -0,0 +1,18 @@
<svg width="80" height="56" viewBox="0 0 80 56" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M13 6C13 5.44772 13.4477 5 14 5H24C24.5523 5 25 5.44772 25 6V14C25 14.5523 24.5523 15 24 15H14C13.4477 15 13 14.5523 13 14V6Z" fill="#85A9FF"/>
<path d="M13 18C13 17.4477 13.4477 17 14 17H24C24.5523 17 25 17.4477 25 18V26C25 26.5523 24.5523 27 24 27H14C13.4477 27 13 26.5523 13 26V18Z" fill="#3370FF"/>
<path d="M13 30C13 29.4477 13.4477 29 14 29H24C24.5523 29 25 29.4477 25 30V38C25 38.5523 24.5523 39 24 39H14C13.4477 39 13 38.5523 13 38V30Z" fill="#85A9FF"/>
<path d="M13 42C13 41.4477 13.4477 41 14 41H24C24.5523 41 25 41.4477 25 42V50C25 50.5523 24.5523 51 24 51H14C13.4477 51 13 50.5523 13 50V42Z" fill="#85A9FF"/>
<path d="M27 6C27 5.44772 27.4477 5 28 5H38C38.5523 5 39 5.44772 39 6V14C39 14.5523 38.5523 15 38 15H28C27.4477 15 27 14.5523 27 14V6Z" fill="#D6E2FF"/>
<path d="M27 18C27 17.4477 27.4477 17 28 17H38C38.5523 17 39 17.4477 39 18V26C39 26.5523 38.5523 27 38 27H28C27.4477 27 27 26.5523 27 26V18Z" fill="#85A9FF"/>
<path d="M27 30C27 29.4477 27.4477 29 28 29H38C38.5523 29 39 29.4477 39 30V38C39 38.5523 38.5523 39 38 39H28C27.4477 39 27 38.5523 27 38V30Z" fill="#D6E2FF"/>
<path d="M27 42C27 41.4477 27.4477 41 28 41H38C38.5523 41 39 41.4477 39 42V50C39 50.5523 38.5523 51 38 51H28C27.4477 51 27 50.5523 27 50V42Z" fill="#3370FF"/>
<path d="M41 6C41 5.44772 41.4477 5 42 5H52C52.5523 5 53 5.44772 53 6V14C53 14.5523 52.5523 15 52 15H42C41.4477 15 41 14.5523 41 14V6Z" fill="#85A9FF"/>
<path d="M41 18C41 17.4477 41.4477 17 42 17H52C52.5523 17 53 17.4477 53 18V26C53 26.5523 52.5523 27 52 27H42C41.4477 27 41 26.5523 41 26V18Z" fill="#3370FF"/>
<path d="M41 30C41 29.4477 41.4477 29 42 29H52C52.5523 29 53 29.4477 53 30V38C53 38.5523 52.5523 39 52 39H42C41.4477 39 41 38.5523 41 38V30Z" fill="#85A9FF"/>
<path d="M41 42C41 41.4477 41.4477 41 42 41H52C52.5523 41 53 41.4477 53 42V50C53 50.5523 52.5523 51 52 51H42C41.4477 51 41 50.5523 41 50V42Z" fill="#D6E2FF"/>
<path d="M55 6C55 5.44772 55.4477 5 56 5H66C66.5523 5 67 5.44772 67 6V14C67 14.5523 66.5523 15 66 15H56C55.4477 15 55 14.5523 55 14V6Z" fill="#85A9FF"/>
<path d="M55 18C55 17.4477 55.4477 17 56 17H66C66.5523 17 67 17.4477 67 18V26C67 26.5523 66.5523 27 66 27H56C55.4477 27 55 26.5523 55 26V18Z" fill="#D6E2FF"/>
<path d="M55 30C55 29.4477 55.4477 29 56 29H66C66.5523 29 67 29.4477 67 30V38C67 38.5523 66.5523 39 66 39H56C55.4477 39 55 38.5523 55 38V30Z" fill="#85A9FF"/>
<path d="M55 42C55 41.4477 55.4477 41 56 41H66C66.5523 41 67 41.4477 67 42V50C67 50.5523 66.5523 51 66 51H56C55.4477 51 55 50.5523 55 50V42Z" fill="#85A9FF"/>
</svg>

After

Width:  |  Height:  |  Size: 2.6 KiB

View File

@ -316,7 +316,8 @@ const boardMoveActive = computed(() => {
'table-normal',
'table-pivot',
'symbolic-map',
'heat-map'
'heat-map',
't-heatmap'
]
return element.value.isPlugin || CHARTS.includes(element.value.innerType)
})

View File

@ -679,6 +679,9 @@ import icon_single_line_outlined from '@/assets/svg/icon_single-line_outlined.sv
import icon_todo_outlined from '@/assets/svg/icon_todo_outlined.svg'
import icon_file_doc_colorful from '@/assets/svg/icon_file-doc_colorful.svg'
import icon_font from '@/assets/svg/icon_font.svg'
import tHeatmap from '@/assets/svg/t-heatmap.svg'
import tHeatmapDark from '@/assets/svg/t-heatmap-dark.svg'
import tHeatmapOrigin from '@/assets/svg/t-heatmap-origin.svg'
const iconMap = {
'401': _401,
icon_adjustment_outlined,
@ -1356,7 +1359,10 @@ const iconMap = {
calculate,
'icon_file-doc_colorful': icon_file_doc_colorful,
icon_font,
clock
clock,
't-heatmap': tHeatmap,
't-heatmap-dark': tHeatmapDark,
't-heatmap-origin': tHeatmapOrigin
}
const props = defineProps({

View File

@ -1116,6 +1116,7 @@ export default {
table_column_fixed: '固定列宽',
table_column_custom: '自定义',
chart_table_pivot: '透视表',
chart_table_heatmap: '热力图',
table_pivot_row: '数据行',
field_error_tips:
'该字段所对应的数据集原始字段发生变更包括维度指标字段类型字段被删除等建议重新编辑',

View File

@ -68,6 +68,8 @@ declare interface Chart {
flowMapStartName?: Axis[]
flowMapEndName?: Axis[]
showPosition: string
extColor: Axis[]
}
declare type CustomAttr = DeepPartial<ChartAttr> | JSONString<DeepPartial<ChartAttr>>
declare type CustomStyle = DeepPartial<ChartStyle> | JSONString<DeepPartial<ChartStyle>>

View File

@ -57,7 +57,7 @@ declare type AxisType =
| 'area'
| 'flowMapStartName'
| 'flowMapEndName'
| 'flowMapColor'
| 'extColor'
/**
* 轴配置
*/

View File

@ -144,7 +144,7 @@ const getTimeValue = dynamicTimeSetting => {
label: '年初',
value: 'yearBeginning'
}
].find(ele => ele.value === relativeToCurrent).label
].find(ele => ele.value === relativeToCurrent)?.label
return timeValue
}
timeValue = `${timeNum}${relativeToCurrentTypeMap[relativeToCurrentType]}${

View File

@ -413,6 +413,8 @@ const dimensionItemRemove = item => {
view.value.flowMapStartName.splice(item.index, 1)
} else if (item.removeType === 'flowMapEndName') {
view.value.flowMapEndName.splice(item.index, 1)
} else if (item.removeType === 'extColor') {
view.value.extColor.splice(item.index, 1)
}
}
@ -524,7 +526,12 @@ const onCustomFlowMapEndNameSort = item => {
customSortAxis.value = 'flowMapEndName'
customSort()
}
const onCustomExtColorSort = item => {
recordSnapshotInfo('render')
state.customSortField = view.value.extColor[item.index]
customSortAxis.value = 'extColor'
customSort()
}
const onMove = e => {
recordSnapshotInfo('calcData')
state.moveId = e.draggedContext.element.id
@ -798,6 +805,10 @@ const addFlowMapEndName = e => {
addAxis(e, 'flowMapEndName')
}
const addExtColor = e => {
addAxis(e, 'extColor')
}
const onAxisChange = (e, axis: AxisType) => {
if (e.removed) {
const { element } = e.removed
@ -1110,6 +1121,11 @@ const onChangeFlowMapPointForm = val => {
renderChart(view.value)
}
const onChangExtColorForm = val => {
view.value.extColor = val
renderChart(view.value)
}
const showRename = val => {
recordSnapshotInfo('render')
state.itemForm = JSON.parse(JSON.stringify(val))
@ -1135,6 +1151,7 @@ const removeItems = (
| 'drillFields'
| 'flowMapStartName'
| 'flowMapEndName'
| 'extColor'
) => {
recordSnapshotInfo('calcData')
let axis = []
@ -1170,6 +1187,9 @@ const removeItems = (
case 'flowMapEndName':
axis = view.value.flowMapEndName?.splice(0)
break
case 'extColor':
axis = view.value.extColor?.splice(0)
break
}
axis?.length && emitter.emit('removeAxis', { axisType: _type, axis, editType: 'remove' })
}
@ -1223,6 +1243,11 @@ const saveRename = ref => {
axis = view.value.flowMapEndName[index]
view.value.flowMapEndName[index].chartShowName = chartShowName
break
case 'extColor':
axisType = 'extColor'
axis = view.value.extColor[index]
view.value.extColor[index].chartShowName = chartShowName
break
default:
break
}
@ -2131,6 +2156,64 @@ const deleteChartFieldItem = id => {
</div>
</el-row>
<el-row v-if="showAxis('extColor')" class="padding-lr drag-data">
<div class="form-draggable-title">
<span>
{{ chartViewInstance.axisConfig.extColor.name }}
</span>
<el-tooltip
:effect="toolTip"
placement="top"
:content="t('common.delete')"
>
<el-icon
class="remove-icon"
:class="{ 'remove-icon--dark': themes === 'dark' }"
size="14px"
@click="removeItems('extColor')"
>
<Icon class-name="inner-class" name="icon_delete-trash_outlined" />
</el-icon>
</el-tooltip>
</div>
<div
class="qw"
@drop="$event => drop($event, 'extColor')"
@dragenter="dragEnter"
@dragover="$event => dragOver($event)"
>
<draggable
:list="view.extColor"
:move="onMove"
item-key="id"
group="drag"
animation="300"
class="drag-block-style"
:class="{ dark: themes === 'dark' }"
@add="addExtColor"
@change="e => onAxisChange(e, 'extColor')"
>
<template #item="{ element, index }">
<dimension-item
:dimension-data="state.dimension"
:quota-data="state.quota"
:chart="view"
:item="element"
:index="index"
:themes="props.themes"
type="extColor"
@onDimensionItemChange="dimensionItemChange"
@onDimensionItemRemove="dimensionItemRemove"
@onNameEdit="showRename"
@onCustomSort="onCustomExtColorSort"
@valueFormatter="valueFormatter"
/>
</template>
</draggable>
<drag-placeholder :themes="themes" :drag-list="view.extColor" />
</div>
</el-row>
<template v-if="view.type !== 'bar-range'">
<!--yAxis-->
<el-row v-if="showAxis('yAxis')" class="padding-lr drag-data">

View File

@ -1183,6 +1183,13 @@ export const CHART_TYPE_CONFIGS = [
value: 'table-pivot',
title: t('chart.chart_table_pivot'),
icon: 'table-pivot'
},
{
render: 'antv',
category: 'table',
value: 't-heatmap',
title: t('chart.chart_table_heatmap'),
icon: 't-heatmap'
}
]
},

View File

@ -0,0 +1,316 @@
import {
G2PlotChartView,
G2PlotDrawOptions
} from '@/views/chart/components/js/panel/types/impl/g2plot'
import type { Heatmap, HeatmapOptions } from '@antv/g2plot/esm/plots/heatmap'
import { flow, hexColorToRGBA, parseJson } from '@/views/chart/components/js/util'
import { useI18n } from '@/hooks/web/useI18n'
import { deepCopy } from '@/utils/utils'
import { cloneDeep } from 'lodash-es'
import {
getLegend,
getPadding,
getXAxis,
getYAxis
} from '@/views/chart/components/js/panel/common/common_antv'
import { valueFormatter } from '@/views/chart/components/js/formatter'
import { Datum } from '@antv/g2plot/esm/types/common'
const { t } = useI18n()
const DEFAULT_DATA = []
/**
* 热力图
*/
export class TableHeatmap extends G2PlotChartView<HeatmapOptions, Heatmap> {
properties: EditorProperty[] = [
'basic-style-selector',
'background-overall-component',
'label-selector',
'legend-selector',
'x-axis-selector',
'y-axis-selector',
'title-selector',
'tooltip-selector',
'jump-set',
'linkage'
]
propertyInner: EditorPropertyInner = {
'background-overall-component': ['all'],
'basic-style-selector': ['colors'],
'label-selector': ['fontSize', 'color'],
'x-axis-selector': ['name', 'color', 'fontSize', 'position', 'axisLabel', 'axisLine'],
'y-axis-selector': ['name', 'color', 'fontSize', 'position', 'axisLabel', 'axisLine'],
'title-selector': [
'title',
'fontSize',
'color',
'hPosition',
'isItalic',
'isBolder',
'remarkShow',
'fontFamily',
'letterSpace',
'fontShadow'
],
'legend-selector': ['orient', 'color', 'fontSize', 'hPosition', 'vPosition'],
'tooltip-selector': ['color', 'fontSize', 'backgroundColor']
}
axis: AxisType[] = ['xAxis', 'xAxisExt', 'extColor', 'filter']
axisConfig: AxisConfig = {
xAxis: {
name: `横轴 / ${t('chart.dimension')}`,
type: 'd',
limit: 1
},
xAxisExt: {
name: `纵轴 / ${t('chart.dimension')}`,
type: 'd',
limit: 1
},
extColor: {
name: `${t('chart.color')} / ${t('chart.dimension_or_quota')}`,
limit: 1
}
}
async drawChart(drawOptions: G2PlotDrawOptions<Heatmap>): Promise<Heatmap> {
const { chart, container, action } = drawOptions
const xAxis = deepCopy(chart.xAxis)
const xAxisExt = deepCopy(chart.xAxisExt)
const extColor = deepCopy(chart.extColor)
if (!xAxis?.length || !xAxisExt?.length || !extColor?.length) {
return
}
const xField = xAxis[0].dataeaseName
const xFieldExt = xAxisExt[0].dataeaseName
const extColorField = extColor[0].dataeaseName
const containerDom = document.getElementById(container)
const containerHeight = containerDom?.clientHeight || 100
// data
const data = cloneDeep(chart.data.tableRow)
data.forEach(i => {
Object.keys(i).forEach(key => {
if (key === '*') {
i['@'] = i[key]
}
})
})
// options
const initOptions: HeatmapOptions = {
data: data,
xField: xField,
yField: xFieldExt,
colorField: extColorField === '*' ? '@' : extColorField,
appendPadding: getPadding(chart),
meta: {
[xField]: {
type: 'cat'
},
[xFieldExt]: {
type: 'cat'
}
},
legend: {
layout: 'vertical',
position: 'right',
slidable: true,
maxHeight: containerHeight - containerHeight * 0.2,
label: {
align: 'left',
spacing: 10
}
}
}
const options = this.setupOptions(chart, initOptions)
const { Heatmap } = await import('@antv/g2plot/esm/plots/heatmap')
const newChart = new Heatmap(container, options)
newChart.on('plot:click', param => {
if (!param.data?.data) {
return
}
const pointData = param.data.data
const dimensionList = []
const quotaList = []
chart.data.fields.forEach((item, index) => {
Object.keys(pointData).forEach(key => {
if (key.startsWith('f_') && item.dataeaseName === key) {
dimensionList.push({
id: item.id,
dataeaseName: item.dataeaseName,
value: pointData[key]
})
}
if (!key.startsWith('f_')) {
quotaList.push({
id: item.id,
dataeaseName: item.dataeaseName,
value: pointData[key]
})
}
})
})
action({
x: param.data.x,
y: param.data.y,
data: {
data: {
...param.data.data,
value: quotaList[0].value,
name: dimensionList[0].id,
dimensionList: dimensionList,
quotaList: quotaList
}
}
})
})
newChart.on('afterrender', ev => {
const l = JSON.parse(JSON.stringify(parseJson(chart.customStyle).legend))
if (l.show) {
const extColor = deepCopy(chart.extColor)
const containerDom = document.getElementById(container)
const containerHeight = containerDom?.clientHeight || 100
const containerWidth = containerDom?.clientWidth || 100
let defaultLength = getLegend(chart)
if (l.orient === 'vertical') {
defaultLength = containerHeight - containerHeight * 0.5
} else {
defaultLength = containerWidth - containerWidth * 0.5
}
ev.view.getController('legend').option[extColor[0].dataeaseName]['rail'].defaultLength =
defaultLength
}
})
return newChart
}
protected configBasicStyle(chart: Chart, options: HeatmapOptions): HeatmapOptions {
const basicStyle = parseJson(chart.customAttr).basicStyle
const color = basicStyle.colors?.map((ele, index) => {
return hexColorToRGBA(ele, basicStyle.alpha)
})
return {
...options,
color
}
}
protected configTooltip(chart: Chart, options: HeatmapOptions): HeatmapOptions {
let tooltip
let customAttr: DeepPartial<ChartAttr>
if (chart.customAttr) {
customAttr = parseJson(chart.customAttr)
// tooltip
if (customAttr.tooltip) {
const extColor = deepCopy(chart.extColor)
const t = JSON.parse(JSON.stringify(customAttr.tooltip))
if (t.show) {
tooltip = {
showTitle: true,
customItems(originalItems) {
const name = extColor[0]?.chartShowName
? extColor[0]?.chartShowName
: extColor[0]?.name
let value = originalItems[0].value
if (!isNaN(Number(value))) {
value = valueFormatter(originalItems[0].value, extColor[0]?.formatterCfg)
}
const newItems = {
...originalItems[0],
name: name,
value: value
}
return [newItems]
}
}
} else {
tooltip = false
}
}
}
return {
...options,
tooltip
}
}
protected configXAxis(chart: Chart, options: HeatmapOptions): HeatmapOptions {
const xAxis = getXAxis(chart, options)
return { ...options, xAxis: { ...xAxis, grid: null } }
}
protected configYAxis(chart: Chart, options: HeatmapOptions): HeatmapOptions {
const yAxis = getYAxis(chart)
return { ...options, yAxis: { ...yAxis, grid: null } }
}
protected configLegend(chart: Chart, options: HeatmapOptions): HeatmapOptions {
const tmpOptions = super.configLegend(chart, options)
if (tmpOptions.legend) {
const l = JSON.parse(JSON.stringify(parseJson(chart.customStyle).legend))
tmpOptions.legend.slidable = true
tmpOptions.legend.minHeight = 10
tmpOptions.legend.minWidth = 10
tmpOptions.legend.maxHeight = 600
tmpOptions.legend.maxWidth = 600
if (l.orient === 'vertical') {
tmpOptions.legend.offsetY = -5
}
tmpOptions.legend.rail = {
defaultLength: 100
}
tmpOptions.legend.label = {
spacing: 10,
style: {
fill: l.color,
fontSize: l.fontSize
}
}
}
return tmpOptions
}
setupDefaultOptions(chart: ChartObj): ChartObj {
chart.customStyle.legend.orient = 'vertical'
chart.customStyle.legend.vPosition = 'center'
chart.customStyle.legend.hPosition = 'right'
return chart
}
protected configLabel(chart: Chart, options: HeatmapOptions): HeatmapOptions {
const tmpOptions = super.configLabel(chart, options)
if (tmpOptions.label) {
const extColor = deepCopy(chart.extColor)
const label = {
...tmpOptions.label,
position: 'middle',
layout: [{ type: 'hide-overlap' }, { type: 'limit-in-canvas' }],
formatter: data => {
const value = data[extColor[0]?.dataeaseName]
if (!isNaN(Number(value))) {
return valueFormatter(value, extColor[0]?.formatterCfg)
}
return value
}
}
return {
...tmpOptions,
label
}
}
return tmpOptions
}
protected setupOptions(chart: Chart, options: HeatmapOptions): HeatmapOptions {
return flow(
this.configXAxis,
this.configYAxis,
this.configBasicStyle,
this.configLegend,
this.configTooltip,
this.configLabel
)(chart, options)
}
constructor() {
super('t-heatmap', DEFAULT_DATA)
}
}

View File

@ -9,5 +9,6 @@ public enum ChartAxis {
yAxis,
yAxisExt,
drill,
extColor,
extBubble;
}

View File

@ -224,4 +224,6 @@ public class ChartViewBaseDTO implements Serializable {
*/
private List<CalParam> calParams;
private List<ChartViewFieldDTO> extColor;
}