yeg
4 天以前 f4d7007b89cf565746af4623623a294b82666ff1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
export const projectMetrics = [
  { key: 'finalVoltage1', title: '最终电压1', unit: 'V' },
  { key: 'finalVoltage2', title: '最终电压2', unit: 'V' },
  { key: 'dischargeCapacityF', title: '每循环放电末容量 / F', unit: 'mAh / F' },
] as const
export type ProjectMetric = typeof projectMetrics[number]
export interface ProjectPoint { position: number; source?: string; values: Partial<Record<ProjectMetric['key'], number | null>> }
export interface ProjectSeries { key: string; name: string; legendLabel?: string; points: ProjectPoint[] }
export const projectPalette = ['#3978f6', '#7d42d8', '#f08a3e', '#23a983', '#e15268', '#1b9ac8', '#b5892f', '#6957c8']
 
/** 控制台、拼接预览和打印共享图表样式;来源提示与横轴位置分开,不插值或补循环。 */
export function projectCycleChartOption(metric: ProjectMetric, series: ProjectSeries[], positions: number[], colors: string[], hidden: string[] = [], spliced = false) {
  const values = series.flatMap(item => item.points.map(point => point.values[metric.key])).filter((value): value is number => typeof value === 'number' && Number.isFinite(value))
  const low = values.length ? Math.min(...values) : undefined
  const high = values.length ? Math.max(...values) : undefined
  const margin = low === undefined || high === undefined ? undefined : Math.max((high - low) * 0.15, 0.01)
  return { animation: false, color: colors, grid: { top: 62, right: 34, bottom: 48, left: 62 },
    tooltip: { trigger: 'axis', renderMode: 'richText', formatter: (params: Array<{ seriesName: string; data: { value: [number | string, number | null]; source?: string } }>) => params.map(item => `${item.seriesName}\n${item.data.source || ''}\n${spliced ? '累计位置' : '循环'} ${item.data.value[0]}:${item.data.value[1] ?? '缺失'} ${metric.unit}`).join('\n\n') },
    legend: { top: 8, left: 12, right: 12, type: 'scroll', icon: 'roundRect', itemWidth: 14, itemHeight: 8, itemGap: 16, textStyle: { fontSize: 10, color: '#52606d' }, formatter: (name: string) => series.find(item => item.name === name)?.legendLabel ?? name, selected: Object.fromEntries(series.map(item => [item.name, !hidden.includes(item.key)])) },
    xAxis: { type: spliced ? 'value' : 'category', boundaryGap: false, data: spliced ? undefined : positions.map(String), min: spliced ? positions[0] ?? 1 : undefined, max: spliced ? (positions.at(-1) === positions[0] ? (positions[0] ?? 1) + 1 : positions.at(-1)) : undefined, minInterval: 1, name: spliced ? '累计位置' : '循环次数', nameLocation: 'middle', nameGap: 30, axisLine: { lineStyle: { color: '#cbd8e4' } }, axisLabel: { color: '#8795a3', fontSize: 10 }, nameTextStyle: { color: '#52606d', fontSize: 10 } },
    yAxis: { type: 'value', name: metric.unit, nameLocation: 'middle', nameGap: 42, min: margin === undefined ? undefined : low! - margin, max: margin === undefined ? undefined : high! + margin, axisLabel: { color: '#8795a3', fontSize: 10, formatter: (value: number) => String(Number(value.toFixed(metric.key === 'dischargeCapacityF' ? 2 : 4))) }, splitLine: { lineStyle: { color: '#e8eef4' } } },
    // 最终电压2没有确认公式,保留空图。单点保留标记,缺测空点不连线。
    series: metric.key === 'finalVoltage2' ? [] : series.map((item, index) => ({ name: item.name, type: 'line', showSymbol: item.points.length === 1, connectNulls: false, lineStyle: { width: 2 }, itemStyle: { color: colors[index] || projectPalette[index % projectPalette.length] }, data: item.points.map(point => ({ value: [spliced ? point.position : String(point.position), point.values[metric.key] ?? null], source: point.source })) })),
  }
}