主页: 走势: 传统+商务的总额
parent
a427a221a9
commit
be2298c5bc
@ -0,0 +1,139 @@
|
||||
import { observer } from 'mobx-react';
|
||||
import { Mix } from '@ant-design/plots';
|
||||
import { merge, isEmpty, groupBy, cloneDeep } from '../utils/commons';
|
||||
import { dataFieldAlias } from '../libs/ht';
|
||||
|
||||
const uniqueByKey = (array, key, pickLast) => {
|
||||
const seen = new Map();
|
||||
const isPickLast = pickLast === true;
|
||||
|
||||
return array.filter((item) => {
|
||||
const k = item[key];
|
||||
const storedItem = seen.get(k);
|
||||
|
||||
if (storedItem) {
|
||||
if (isPickLast) {
|
||||
seen.set(k, item); // update with last item
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
seen.set(k, item);
|
||||
return true;
|
||||
});
|
||||
};
|
||||
|
||||
export default observer((props) => {
|
||||
const { dataSource, summaryData: areaData, ...config } = props;
|
||||
const kpiKey = dataFieldAlias[config.yField]?.nestkey?.v;
|
||||
const seriesData = groupBy(dataSource, (ele) => ele[config.seriesField]);
|
||||
const pickKey4KPI = Object.keys(seriesData)[0];
|
||||
const KPIData = (seriesData?.[pickKey4KPI] || []).reduce((r, v) => {
|
||||
if (!isEmpty(v[kpiKey])) {
|
||||
// 有设目标才多显示一条虚线 颜色: #F4664A
|
||||
r.push({ ...v, [config.yField]: v[kpiKey], [config.seriesField]: dataFieldAlias[kpiKey].label, extraLine: true });
|
||||
}
|
||||
return r;
|
||||
}, []);
|
||||
const dataColors = ['#598cf3', '#69deae', '#FAAD14'];
|
||||
const colorSets = Object.keys(seriesData)
|
||||
.sort()
|
||||
.reduce((obj, k, i) => ({ ...obj, [k]: dataColors[i] }), {});
|
||||
const { xField, yField, seriesField, tooltip, ...extConfig } = config;
|
||||
const lineConfig = merge(
|
||||
{
|
||||
data: [...dataSource, ...KPIData],
|
||||
xField,
|
||||
yField,
|
||||
seriesField,
|
||||
point: {
|
||||
size: 4,
|
||||
shape: 'cicle',
|
||||
},
|
||||
xAxis: false,
|
||||
yAxis: false,
|
||||
meta: {
|
||||
[yField]: {
|
||||
sync: true,
|
||||
}
|
||||
},
|
||||
// color: ['#598cf3', '#69deae', '#F4664A', '#FAAD14'],
|
||||
color: (item) => {
|
||||
const thisSeries = item[config.seriesField];
|
||||
return thisSeries.includes('目标') ? '#F4664A' : colorSets[thisSeries];
|
||||
},
|
||||
lineStyle: (data) => {
|
||||
// console.log(data);
|
||||
if (data[config.seriesField].includes('目标')) {
|
||||
return {
|
||||
lineDash: [4, 4],
|
||||
opacity: 0.5,
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
opacity: 1,
|
||||
};
|
||||
},
|
||||
},
|
||||
extConfig
|
||||
);
|
||||
const MixConfig = {
|
||||
appendPadding: 8,
|
||||
syncViewPadding: true,
|
||||
tooltip: {
|
||||
shared: true,
|
||||
customItems: (originalItems) => {
|
||||
// process originalItems,
|
||||
const items = originalItems.map((ele) => ({ ...ele, name: ele.data?.extraLine ? ele.name : `${ele.name} ${dataFieldAlias[yField]?.alias || yField}` }));
|
||||
return items;
|
||||
},
|
||||
},
|
||||
plots: [
|
||||
{
|
||||
type: 'area',
|
||||
options: {
|
||||
data: areaData,
|
||||
xField,
|
||||
yField,
|
||||
seriesField,
|
||||
xAxis: false,
|
||||
meta: merge(
|
||||
{
|
||||
...cloneDeep(dataFieldAlias),
|
||||
},
|
||||
{ [xField]: { sync: true }, [yField]: { sync: true } }
|
||||
),
|
||||
// color: '#b32b19',
|
||||
color: '#f58269',
|
||||
smooth: true,
|
||||
areaStyle: () => {
|
||||
return {
|
||||
fill: 'l(270) 0:#ffffff 0.25:#f8e8e7 0.5:#fac9bd 0.75:#f7a593',
|
||||
};
|
||||
},
|
||||
label: {
|
||||
offsetY: -8,
|
||||
},
|
||||
annotations: areaData.map((d) => {
|
||||
return {
|
||||
type: 'dataMarker',
|
||||
position: d,
|
||||
point: {
|
||||
style: {
|
||||
stroke: '#F4664A',
|
||||
lineWidth: 1.5,
|
||||
},
|
||||
},
|
||||
};
|
||||
}),
|
||||
},
|
||||
},
|
||||
{
|
||||
type: 'line',
|
||||
options: lineConfig,
|
||||
},
|
||||
],
|
||||
};
|
||||
return <Mix {...MixConfig} />;
|
||||
});
|
Loading…
Reference in New Issue