大屏计划进度图表修改
parent
546b375ed0
commit
78e6b33e6b
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,332 @@
|
|||
function aggregateDataByDate(executionData) {
|
||||
const dateMap = new Map();
|
||||
// 按start排序,相同时按end排序
|
||||
executionData.sort((a, b) => {
|
||||
const startA = new Date(a.start);
|
||||
const startB = new Date(b.start);
|
||||
if (startA.getTime() !== startB.getTime()) {
|
||||
return startA - startB;
|
||||
}
|
||||
const endA = new Date(a.end);
|
||||
const endB = new Date(b.end);
|
||||
return endA - endB;
|
||||
});
|
||||
// 获取整个时间范围
|
||||
let minDate = new Date(executionData[0].start);
|
||||
let maxDate = new Date(executionData[0].end);
|
||||
|
||||
// 遍历所有任务,找到最小和最大日期
|
||||
executionData.forEach((task) => {
|
||||
const startDate = new Date(task.start);
|
||||
const endDate = new Date(task.end);
|
||||
|
||||
if (startDate < minDate) minDate = startDate;
|
||||
if (endDate > maxDate) maxDate = endDate;
|
||||
});
|
||||
|
||||
// 初始化每一天的数据
|
||||
const currentDate = new Date(minDate);
|
||||
while (currentDate <= maxDate) {
|
||||
const dateStr = currentDate.toISOString().split("T")[0];
|
||||
dateMap.set(dateStr, {
|
||||
date: dateStr,
|
||||
planned: 0,
|
||||
completed: 0,
|
||||
progressSum: 0,
|
||||
progressCount: 0,
|
||||
});
|
||||
currentDate.setDate(currentDate.getDate() + 1);
|
||||
}
|
||||
|
||||
// 为每个任务创建日期范围
|
||||
executionData.forEach((task) => {
|
||||
const startDate = new Date(task.start);
|
||||
const endDate = new Date(task.end);
|
||||
|
||||
// 遍历任务的每一天
|
||||
const currentTaskDate = new Date(startDate);
|
||||
while (currentTaskDate <= endDate) {
|
||||
const dateStr = currentTaskDate.toISOString().split("T")[0];
|
||||
|
||||
if (dateMap.has(dateStr)) {
|
||||
// 增加计划任务数
|
||||
dateMap.get(dateStr).planned += 1;
|
||||
}
|
||||
|
||||
// 移动到下一天
|
||||
currentTaskDate.setDate(currentTaskDate.getDate() + 1);
|
||||
}
|
||||
});
|
||||
|
||||
// 统计完成任务(基于开始日期)
|
||||
executionData.forEach((task) => {
|
||||
if (task.process !== null) {
|
||||
const startDate = task.start;
|
||||
|
||||
if (dateMap.has(startDate)) {
|
||||
dateMap.get(startDate).completed += 1;
|
||||
dateMap.get(startDate).progressSum += task.process;
|
||||
dateMap.get(startDate).progressCount += 1;
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
// 转换为数组并按日期排序
|
||||
const result = Array.from(dateMap.values()).sort((a, b) => {
|
||||
return new Date(a.date) - new Date(b.date);
|
||||
});
|
||||
|
||||
// 获取今天的日期
|
||||
const today = new Date();
|
||||
today.setHours(0, 0, 0, 0);
|
||||
|
||||
// 计算累积进度
|
||||
let totalPlanned = 0;
|
||||
let totalCompleted = 0;
|
||||
let totalProgressSum = 0;
|
||||
let totalProgressCount = 0;
|
||||
|
||||
result.forEach((item) => {
|
||||
totalPlanned += item.planned;
|
||||
// 检查日期是否在今天之后
|
||||
const itemDate = new Date(item.date);
|
||||
if (itemDate > today) {
|
||||
// 今日之后的数据设置为null
|
||||
item.completed = null;
|
||||
item.progressSum = null;
|
||||
item.progressCount = null;
|
||||
} else {
|
||||
totalCompleted += item.completed || 0;
|
||||
totalProgressSum += item.progressSum || 0;
|
||||
totalProgressCount += item.progressCount || 0;
|
||||
}
|
||||
|
||||
// 添加累积数据
|
||||
item.cumulativePlanned = totalPlanned;
|
||||
// 对于今日之后的数据,cumulativeCompleted也设置为null
|
||||
if (new Date(item.date) > today) {
|
||||
item.cumulativeCompleted = null;
|
||||
} else {
|
||||
item.cumulativeCompleted = totalCompleted;
|
||||
}
|
||||
item.cumulativeProgress =
|
||||
totalProgressCount > 0 ? totalProgressSum / totalProgressCount : 0;
|
||||
});
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
function makeTaskTrendOptions(that, datas) {
|
||||
// 填充统计数据表格
|
||||
const summaryData = aggregateDataByDate(datas);
|
||||
// 准备图表数据
|
||||
const dates = summaryData.map((item) => item.date);
|
||||
const cumulativePlanned = summaryData.map((item) => {
|
||||
const totalTasks = summaryData[summaryData.length - 1].cumulativePlanned;
|
||||
return totalTasks > 0 ? (item.cumulativePlanned / totalTasks) * 100 : 0;
|
||||
});
|
||||
|
||||
const cumulativeCompleted = summaryData.map((item) => {
|
||||
// 如果completed为null,表示该日期在今日之后,返回null
|
||||
if (item.cumulativeCompleted === null) {
|
||||
return null;
|
||||
}
|
||||
const totalTasks = summaryData[summaryData.length - 1].cumulativePlanned;
|
||||
return totalTasks > 0 ? (item.cumulativeCompleted / totalTasks) * 100 : 0;
|
||||
});
|
||||
let is1K = that.$dpi() == "1K";
|
||||
let is2K = that.$dpi() == "2K";
|
||||
// 配置图表选项
|
||||
const option = {
|
||||
tooltip: {
|
||||
trigger: "axis",
|
||||
formatter: function (params) {
|
||||
let result = params[0].name + "<br/>";
|
||||
// 查找当前日期的数据
|
||||
const currentItem = summaryData.find(
|
||||
(item) => item.date === params[0].name
|
||||
);
|
||||
if (currentItem) {
|
||||
// 计算统计数据
|
||||
const totalDays = summaryData.length; // 总天数
|
||||
// 计划完成天数(有计划任务的天数)
|
||||
const plannedDays = summaryData.filter(
|
||||
(item) => item.planned > 0
|
||||
).length;
|
||||
|
||||
// 实际完成天数处理
|
||||
let actualCompletedDays = 0;
|
||||
const currentDate = new Date(currentItem.date);
|
||||
const today = new Date();
|
||||
today.setHours(0, 0, 0, 0);
|
||||
|
||||
if (currentDate > today) {
|
||||
// 今日之后的日期,使用之前最大的完成天数值
|
||||
const pastData = summaryData.filter((item) => {
|
||||
const itemDate = new Date(item.date);
|
||||
return itemDate <= today && item.completed > 0;
|
||||
});
|
||||
actualCompletedDays = pastData.length;
|
||||
} else {
|
||||
// 今日及之前的日期,使用当前的实际完成天数
|
||||
actualCompletedDays = summaryData.filter((item) => {
|
||||
const itemDate = new Date(item.date);
|
||||
return itemDate <= currentDate && item.completed > 0;
|
||||
}).length;
|
||||
}
|
||||
|
||||
result += "总天数: " + totalDays + " 天<br/>";
|
||||
result += "计划天数: " + plannedDays + " 天<br/>";
|
||||
result += "完成天数: " + actualCompletedDays + " 天<br/>";
|
||||
}
|
||||
|
||||
params.forEach((param) => {
|
||||
// 处理null值和undefined的情况
|
||||
if (param.value === null || param.value === undefined) {
|
||||
result += param.marker + param.seriesName + ": 无数据<br/>";
|
||||
} else {
|
||||
result +=
|
||||
param.marker +
|
||||
param.seriesName +
|
||||
": " +
|
||||
param.value.toFixed(2) +
|
||||
"%<br/>";
|
||||
}
|
||||
});
|
||||
return result;
|
||||
},
|
||||
axisPointer: {
|
||||
lineStyle: {
|
||||
color: "#57617B",
|
||||
},
|
||||
},
|
||||
textStyle: {
|
||||
fontSize: is1K ? 12 : is2K ? 18 : 20,
|
||||
},
|
||||
},
|
||||
legend: {
|
||||
icon: "rect",
|
||||
itemWidth: 14,
|
||||
itemHeight: 10,
|
||||
itemGap: 15,
|
||||
data: ["计划任务累积进度", "已完成任务累积进度"],
|
||||
top: -5,
|
||||
textStyle: {
|
||||
fontSize: is1K ? 12 : is2K ? 20 : 30,
|
||||
color: "#c8dbfc",
|
||||
},
|
||||
},
|
||||
grid: {
|
||||
top: "10%",
|
||||
left: "2%",
|
||||
right: "3%",
|
||||
bottom: "5%",
|
||||
containLabel: true,
|
||||
},
|
||||
xAxis: {
|
||||
boundaryGap: false,
|
||||
type: "category",
|
||||
data: dates,
|
||||
axisLine: {
|
||||
//坐标轴轴线相关设置。数学上的x轴
|
||||
show: true,
|
||||
lineStyle: {
|
||||
color: "#25597e",
|
||||
type: "dashed",
|
||||
},
|
||||
},
|
||||
axisTick: {
|
||||
show: false,
|
||||
},
|
||||
|
||||
axisLabel: {
|
||||
//坐标轴刻度标签的相关设置
|
||||
textStyle: {
|
||||
color: "#c5d9fc",
|
||||
margin: 20,
|
||||
fontSize: 12,
|
||||
},
|
||||
},
|
||||
},
|
||||
yAxis: {
|
||||
type: "value",
|
||||
name: "累积进度 (%)",
|
||||
axisLabel: {
|
||||
formatter: "{value} %",
|
||||
//坐标轴刻度标签的相关设置
|
||||
textStyle: {
|
||||
color: "#c5d9fc",
|
||||
margin: 20,
|
||||
fontSize: is1K ? 12 : is2K ? 16 : 20,
|
||||
},
|
||||
},
|
||||
nameTextStyle: {
|
||||
color: "#c5d9fc",
|
||||
fontSize: is1K ? 12 : is2K ? 18 : 24,
|
||||
},
|
||||
axisLine: {
|
||||
//坐标轴轴线相关设置。数学上的x轴
|
||||
show: false,
|
||||
lineStyle: {
|
||||
color: "#c5d9fc",
|
||||
type: "dashed",
|
||||
},
|
||||
},
|
||||
axisTick: {
|
||||
show: false,
|
||||
},
|
||||
splitLine: {
|
||||
show: true,
|
||||
lineStyle: {
|
||||
color: "#25597e",
|
||||
type: "dashed",
|
||||
},
|
||||
},
|
||||
},
|
||||
dataZoom: [
|
||||
{
|
||||
type: "inside",
|
||||
start: 0,
|
||||
end: 100,
|
||||
},
|
||||
{
|
||||
start: 0,
|
||||
end: 100,
|
||||
},
|
||||
],
|
||||
series: [
|
||||
{
|
||||
name: "计划任务累积进度",
|
||||
type: "line",
|
||||
data: cumulativePlanned,
|
||||
smooth: true,
|
||||
itemStyle: {
|
||||
color: "#36A2EB",
|
||||
},
|
||||
areaStyle: {
|
||||
color: "#36A2EB",
|
||||
opacity: 0.2,
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "已完成任务累积进度",
|
||||
type: "line",
|
||||
data: cumulativeCompleted,
|
||||
connectNulls: false, // 不连接null值
|
||||
smooth: true,
|
||||
itemStyle: {
|
||||
color: "#FF6384",
|
||||
},
|
||||
areaStyle: {
|
||||
color: "#FF6384",
|
||||
opacity: 0.2,
|
||||
},
|
||||
},
|
||||
],
|
||||
};
|
||||
return option;
|
||||
}
|
||||
|
||||
export default {
|
||||
makeTaskTrendOptions,
|
||||
};
|
Loading…
Reference in New Issue