CNCEC_SUBQHSE_WUHUAN/SGGL/FineUIPro.Web/JDGL/SGManPower/ManPowerStat.aspx

721 lines
24 KiB
Plaintext
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="ManPowerStat.aspx.cs" Inherits="FineUIPro.Web.JDGL.SGManPower.ManPowerStat" %>
<!DOCTYPE html>
<html>
<head id="Head1" runat="server">
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>人力统计</title>
<link href="../../res/index/css/reset.css" rel="stylesheet" />
<link href="../../res/index/css/home.css" rel="stylesheet" />
<link href="../../res/index/css/swiper-3.4.2.min.css" rel="stylesheet" />
<style type="text/css">
* {
box-sizing: border-box;
}
.flexV {
flex-direction: column;
}
.wrap {
height: 100%;
padding: 15px;
background-color: #FFFFFF;
}
.iteml {
margin-left: 5px;
}
.itemb {
margin-bottom: 5px;
}
.bottom-wrap {
padding: 0;
margin-bottom: 5px;
}
.bottom-wrap:last-child {
margin-bottom: 0;
}
.bw-b-bottom {
width: 100%;
height: 100%;
}
.bw-b-bottom-up {
border-radius: 0;
height: 100%;
margin: 0;
box-shadow: none;
}
.bw-item-content {
padding: 5px;
}
.top {
width: 100%;
}
.bw-b {
width: 50%;
}
.tab-wrap {
left: auto;
right: 15px;
top: 5px;
font-size: 12px;
}
.tab .t-item {
width: auto;
padding: 5px 10px;
color: #363636;
}
.tit-item {
padding: 0 10px;
justify-content: space-between;
font-size: 12px;
}
.tab-wrap .tab .t-item {
color: #1C1C1C;
}
.tip-item {
margin-left: 10px;
align-items: center;
font-size: 10px;
}
.tip {
width: 25px;
height: 13px;
background-color: #258F76;
border-radius: 2px;
margin-right: 5px;
}
.tip-next {
background-color: #4F4F4F;
}
.myTableClass {
width: 100%;
height: 100%;
overflow: auto;
margin: 2px 1px;
border-collapse: collapse;
border: 1px solid #BEBEBE;
background: #ffffff;
color: #8B8989;
text-align: center;
font-size: 14px;
}
.tab-title {
height: 48px;
color: #3CB371;
font-size: 16px;
font-weight: 700;
}
.tab-header {
height: 36px;
color: #1C86EE;
font-size: 14px;
font-weight: 600;
}
td, th {
border: 1px solid #BEBEBE;
}
.container {
display: flex;
flex-direction: column;
height: 100%;
}
.filter-options {
justify-content: flex-end;
padding: 10px;
background-color: #f8f8f8;
border-bottom: 1px solid #ddd;
}
.filter-options label {
margin-left: 10px;
font-size: 14px;
color: #333;
}
.filter-options input[type="radio"] {
margin-right: 5px;
}
.loading-overlay {
position: fixed;
top: 0;
left: 0;
width: 100%;
height: 100%;
background: rgba(0, 0, 0, 0.5);
display: none;
justify-content: center;
align-items: center;
z-index: 9999;
}
.loading-spinner {
width: 50px;
height: 50px;
border: 5px solid #f3f3f3;
border-top: 5px solid #3498db;
border-radius: 50%;
animation: spin 1s linear infinite;
}
@keyframes spin {
0% { transform: rotate(0deg); }
100% { transform: rotate(360deg); }
}
.chart-container {
width: 100%;
height: 100%;
min-height: 300px;
}
.error-message {
color: red;
text-align: center;
padding: 20px;
display: none;
}
</style>
</head>
<body>
<div class="container">
<div class="filter-options">
<label>
<input type="radio" name="data-filter" value="total" checked> 总数
</label>
<label>
<input type="radio" name="data-filter" value="annual"> 年度
</label>
<select id="year-select" style="display: none; margin-left: 10px; padding: 2px; font-size: 14px;">
<!-- 年份选项将通过JavaScript动态填充 -->
</select>
<label>
<input type="radio" name="data-filter" value="monthly"> 月度
</label>
<select id="month-select" style="display: none; margin-left: 10px; padding: 2px; font-size: 14px;">
<option value="1">1月</option>
<option value="2">2月</option>
<option value="3">3月</option>
<option value="4">4月</option>
<option value="5">5月</option>
<option value="6">6月</option>
<option value="7">7月</option>
<option value="8">8月</option>
<option value="9">9月</option>
<option value="10">10月</option>
<option value="11">11月</option>
<option value="12">12月</option>
</select>
</div>
<div class="wrap flex flexV">
<div class="bottom-wrap flex1">
<div class="top flex">
<div class="item flex2 iteml">
<div class="bw-b-bottom">
<div class="bw-b-bottom-up">
<div class="bw-item-content">
<div id='one' class="chart-container"></div>
<div id='one-error' class="error-message"></div>
</div>
</div>
</div>
</div>
<div class="item flex2 iteml">
<div class="bw-b-bottom">
<div class="bw-b-bottom-up">
<div class="bw-item-content">
<div id='two' class="chart-container"></div>
<div id='two-error' class="error-message"></div>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="bottom-wrap flex1">
<div class="top flex">
<div class="item flex2 iteml">
<div class="bw-b-bottom">
<div class="bw-b-bottom-up">
<div class="bw-item-content">
<div id='three' class="chart-container"></div>
<div id='three-error' class="error-message"></div>
</div>
</div>
</div>
</div>
<div class="item flex2 iteml">
<div class="bw-b-bottom">
<div class="bw-b-bottom-up">
<div class="bw-item-content">
<div id='four' class="chart-container"></div>
<div id='four-error' class="error-message"></div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- 加载动画 -->
<div id="loadingOverlay" class="loading-overlay">
<div class="loading-spinner"></div>
</div>
</body>
<script type="text/javascript" src="../../res/index/js/jquery-3.4.1.min.js"></script>
<script type="text/javascript" src="../../res/index/js/swiper-3.4.2.jquery.min.js"></script>
<script type="text/javascript" src="../../res/index/js/echarts.min.js"></script>
<script type="text/javascript">
// 存储各图表的实例
var chartInstances = {};
// 页面加载完成后初始化图表
$(document).ready(function() {
// 填充年份下拉框
populateYearSelect();
// 获取当前URL中的type参数如果没有则默认为total
var urlParams = new URLSearchParams(window.location.search);
var currentType = urlParams.get('type') || 'total';
// 设置对应的单选按钮为选中状态
$('input[name="data-filter"][value="' + currentType + '"]').prop('checked', true);
// 根据选中的类型显示/隐藏年份下拉框
toggleYearSelect(currentType);
// 初始化图表
loadAndRenderCharts(currentType);
// 监听单选按钮变化事件
$('input[name="data-filter"]').change(function() {
var dataType = $(this).val();
toggleYearSelect(dataType);
});
// 监听年份下拉框变化事件
$('#year-select').change(function() {
var dataType = $('input[name="data-filter"]:checked').val();
if (dataType === 'annual' || dataType === 'monthly') {
loadAndRenderCharts(dataType);
}
});
// 监听月份下拉框变化事件
$('#month-select').change(function() {
var dataType = $('input[name="data-filter"]:checked').val();
if (dataType === 'monthly') {
loadAndRenderCharts(dataType);
}
});
});
// 填充年份下拉框
function populateYearSelect() {
var currentYear = new Date().getFullYear();
var yearSelect = $('#year-select');
// 添加最近10年的选项
for (var i = currentYear; i >= currentYear - 10; i--) {
yearSelect.append($('<option></option>').attr('value', i).text(i));
}
// 默认选中当前年份
yearSelect.val(currentYear);
}
// 根据选中的数据类型显示/隐藏年份下拉框
function toggleYearSelect(dataType) {
if (dataType === 'annual') {
$('#year-select').show();
$('#month-select').hide();
// 不再立即触发数据查询,只显示年份选择框
} else if (dataType === 'monthly') {
$('#year-select').show();
$('#month-select').show();
// 不再立即触发数据查询,只显示年份和月份选择框
} else {
$('#year-select').hide();
$('#month-select').hide();
}
}
// 通过Ajax加载数据并渲染图表
function loadAndRenderCharts(type) {
// 显示加载状态
showLoading();
// 隐藏所有错误信息
$('.error-message').hide();
// 获取选中的年份或月份
var selectedYear = $('#year-select').val();
var selectedMonth = $('#month-select').val();
// 使用Ajax并行获取四个图表的数据
$.when(
$.ajax({
url: 'ManPowerStat.aspx/GetChartData',
type: 'POST',
data: JSON.stringify(createParams(type, 'One', selectedYear, selectedMonth)),
contentType: 'application/json; charset=utf-8',
dataType: 'json',
timeout: 30000 // 30秒超时
}),
$.ajax({
url: 'ManPowerStat.aspx/GetChartData',
type: 'POST',
data: JSON.stringify(createParams(type, 'Two', selectedYear, selectedMonth)),
contentType: 'application/json; charset=utf-8',
dataType: 'json',
timeout: 30000
}),
$.ajax({
url: 'ManPowerStat.aspx/GetChartData',
type: 'POST',
data: JSON.stringify(createParams(type, 'Three', selectedYear, selectedMonth)),
contentType: 'application/json; charset=utf-8',
dataType: 'json',
timeout: 30000
}),
$.ajax({
url: 'ManPowerStat.aspx/GetChartData',
type: 'POST',
data: JSON.stringify(createParams(type, 'Four', selectedYear, selectedMonth)),
contentType: 'application/json; charset=utf-8',
dataType: 'json',
timeout: 30000
})
).done(function(oneResult, twoResult, threeResult, fourResult) {
try {
// 渲染四个图表
renderChart('one', oneResult[0].d, '五环管理人员统计分析');
renderChart('two', twoResult[0].d, '施工单位管理人员统计分析');
renderChart('three', threeResult[0].d, '作业人员统计分析');
renderChart('four', fourResult[0].d, '过程人力统计分析');
} catch (e) {
console.error('图表渲染错误:', e);
showError('图表渲染失败,请重试');
}
// 隐藏加载状态
hideLoading();
}).fail(function(jqXHR, textStatus, errorThrown) {
// 处理错误情况
console.error('Ajax请求失败:', textStatus, errorThrown);
console.error('响应内容:', jqXHR.responseText);
var errorMessage = '数据加载失败';
if (textStatus === 'timeout') {
errorMessage = '请求超时,请重试';
} else if (jqXHR.responseText) {
try {
var errorResponse = JSON.parse(jqXHR.responseText);
if (errorResponse.Message) {
errorMessage = errorResponse.Message;
}
} catch (e) {
errorMessage = jqXHR.responseText;
}
}
showError(errorMessage);
hideLoading();
});
}
// 创建传递给后端的参数对象
function createParams(type, chart, year, month) {
debugger
var params = {
type: type,
chart: chart ,
year:null,
month:null,
};
// 只有在需要时才添加year和month参数
if (type === 'annual' && year) {
params.year = year;
} else if (type === 'monthly' && year && month) {
params.year = year;
params.month = month;
}
// 确保参数对象中不包含值为undefined的属性
for (var key in params) {
if (params[key] === undefined) {
delete params[key];
}
}
return params;
}
// 渲染单个图表的通用方法
function renderChart(chartId, data, title) {
try {
// 隐藏错误信息
$('#' + chartId + '-error').hide();
// 解析数据
var chartData;
if (typeof data === 'string') {
chartData = JSON.parse(data);
} else {
chartData = data;
}
// 验证数据
if (!chartData || !chartData.categories || !chartData.series) {
throw new Error('数据格式不正确');
}
// 如果图表实例已存在,先销毁
if (chartInstances[chartId]) {
chartInstances[chartId].dispose();
}
var chartContainer = document.getElementById(chartId);
if (!chartContainer) {
throw new Error('找不到图表容器: ' + chartId);
}
var myChart = echarts.init(chartContainer);
var xArr = chartData.categories;
var num = chartData.xFontNum || 6;
// 确保series数据存在
var seriesData = [];
if (chartData.series && chartData.series.length >= 2) {
seriesData = [
{
name: '计划',
type: 'line',
data: chartData.series[1].data || [],
label: {
show: true,
position: 'top',
textStyle: {
fontSize: '12px',
color: '#363636'
},
formatter: function (params) {
return params.value === 0 ? '' : params.value;
},
},
itemStyle: { normal: { color: 'rgba(255,0,0, 0.5)' } },
smooth: true
},
{
name: '实际',
type: 'line',
data: chartData.series[0].data || [],
label: {
show: true,
position: 'top',
textStyle: {
fontSize: '12px',
color: '#363636'
},
formatter: function (params) {
return params.value === 0 ? '' : params.value;
},
},
itemStyle: { normal: { color: 'rgba(0,100,0,0.8)' } },
smooth: true
}
];
}
var option = {
title: {
text: title,
textStyle: {
color: '#1C1C1C',
fontSize: 16,
fontWeight: 700
},
show: true
},
tooltip: {},
legend: {
left: '80%',
show: true,
textStyle: {
color: '#363636',
fontSize: 12,
}
},
dataZoom: [
{
type: 'slider',
maxValueSpan: 6,
show: xArr && xArr.length > 6, // 只有数据超过6个才显示缩放
xAxisIndex: [0],
bottom: 0, height: 10,
backgroundColor: 'rgba(0,0,0,0)',
borderColor: 'none',
brushSelect: false,
textStyle: {
color: 'rgba(0,0,0,0)'
},
selectedDataBackground: {
areaStyle: {
color: 'red',
borderWidth: 0
}
},
handleStyle: {
color: "#0a1449"
},
moveHandleStyle: {
color: '#0a1449'
}
}
],
xAxis: {
axisTick: {
show: false
},
axisLine: {
lineStyle: {
color: 'rgba(0,0,0, 0.3)',
}
},
axisLabel: {
show: true,
textStyle: {
color: 'rgba(0,0,0, 0.8)'
},
interval: 0,
rotate: -15,
formatter: function (value) {
if (!value) return '';
var ret = "";
var maxLength = num;
var valLength = value.length;
var rowN = Math.ceil(valLength / maxLength);
if (rowN > 1) {
for (var i = 0; i < rowN; i++) {
var temp = "";
var start = i * maxLength;
var end = start + maxLength;
temp = value.substring(start, end) + (i == rowN - 1 ? "" : "\n");
ret += temp;
}
return ret;
} else {
return value;
}
}
},
type: 'category',
data: xArr || [],
boundaryGap: [0, 0.01],
},
yAxis: {
axisTick: {
show: false
},
axisLine: {
show: false,
lineStyle: {
color: 'rgba(0,0,0, 0.3)'
}
},
axisLabel: {
show: true,
textStyle: {
color: 'rgba(0,0,0, 0.8)'
}
},
},
series: seriesData,
grid: {
top: '20%',
left: '0%',
right: '0%',
bottom: 40,
containLabel: true,
backgroundColor: 'rgba(0,162,233, 0.01)',
},
backgroundColor: 'rgba(0,162,233, 0.01)',
textStyle: {
color: 'rgba(0,0,0, 0.3)'
}
};
myChart.setOption(option);
chartInstances[chartId] = myChart;
// 监听窗口大小变化,重新调整图表大小
var resizeHandler = function() {
if (chartInstances[chartId]) {
chartInstances[chartId].resize();
}
};
// 避免重复绑定事件
if (window.addEventListener) {
window.removeEventListener('resize', resizeHandler);
window.addEventListener('resize', resizeHandler);
}
} catch (e) {
console.error('渲染图表失败 [' + chartId + ']:', e);
showError('图表渲染失败: ' + e.message, chartId);
}
}
// 显示错误信息
function showError(message, chartId) {
if (chartId) {
$('#' + chartId + '-error').text(message).show();
} else {
// 全局错误显示
alert(message);
}
}
// 显示加载状态
function showLoading() {
document.getElementById('loadingOverlay').style.display = 'flex';
}
// 隐藏加载状态
function hideLoading() {
document.getElementById('loadingOverlay').style.display = 'none';
}
</script>
</html>