2026-01-31 09:14:24 +08:00
|
|
|
|
using DevExpress.Xpf.Charts;
|
|
|
|
|
|
using DevExpress.Xpf.Core;
|
|
|
|
|
|
using DevExpress.Xpf.Core.Native;
|
|
|
|
|
|
using System;
|
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
|
|
using System.Diagnostics;
|
|
|
|
|
|
using System.Linq;
|
|
|
|
|
|
using System.Text;
|
|
|
|
|
|
using System.Threading.Tasks;
|
|
|
|
|
|
using System.Windows;
|
|
|
|
|
|
using System.Windows.Controls;
|
|
|
|
|
|
using System.Windows.Data;
|
|
|
|
|
|
using System.Windows.Documents;
|
|
|
|
|
|
using System.Windows.Input;
|
|
|
|
|
|
using System.Windows.Media;
|
|
|
|
|
|
using System.Windows.Media.Imaging;
|
|
|
|
|
|
using System.Windows.Shapes;
|
|
|
|
|
|
using System.Windows.Threading;
|
|
|
|
|
|
|
|
|
|
|
|
namespace jiancaiburanxing
|
|
|
|
|
|
{
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
|
/// BalanceChartWindow.xaml 的交互逻辑
|
|
|
|
|
|
/// </summary>
|
|
|
|
|
|
public partial class BalanceChartWindow : ThemedWindow
|
|
|
|
|
|
{
|
|
|
|
|
|
// 存储温度数据
|
|
|
|
|
|
private List<Tuple<double, double>> temperatureData = new List<Tuple<double, double>>();
|
|
|
|
|
|
|
|
|
|
|
|
// 温度获取函数
|
|
|
|
|
|
private Func<double> _getFurnaceTemperature;
|
|
|
|
|
|
|
|
|
|
|
|
// 定时器用于实时更新
|
|
|
|
|
|
private DispatcherTimer _updateTimer;
|
|
|
|
|
|
|
|
|
|
|
|
// 已运行时间(秒)
|
|
|
|
|
|
private int _elapsedSeconds = 0;
|
|
|
|
|
|
|
|
|
|
|
|
// 开始时间戳
|
|
|
|
|
|
private DateTime _startTime;
|
|
|
|
|
|
|
|
|
|
|
|
public BalanceChartWindow(Func<double> getFurnaceTemperature)
|
|
|
|
|
|
{
|
|
|
|
|
|
InitializeComponent();
|
|
|
|
|
|
Loaded += BalanceChartWindow_Loaded;
|
|
|
|
|
|
Unloaded += BalanceChartWindow_Unloaded;
|
|
|
|
|
|
_getFurnaceTemperature = getFurnaceTemperature;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void BalanceChartWindow_Loaded(object sender, RoutedEventArgs e)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
InitializeChart();
|
|
|
|
|
|
StartDataCollection();
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"初始化图表时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void BalanceChartWindow_Unloaded(object sender, RoutedEventArgs e)
|
|
|
|
|
|
{
|
|
|
|
|
|
StopDataCollection();
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
private void InitializeChart()
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
try
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 初始化图表配置
|
|
|
|
|
|
if (temperatureChart.Diagram is XYDiagram2D diagram)
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 设置X轴 - 时间(秒)
|
|
|
|
|
|
if (diagram.AxisX is AxisX2D axisX)
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 清除可能在XAML中设置的范围
|
|
|
|
|
|
axisX.WholeRange = null;
|
|
|
|
|
|
axisX.VisualRange = null;
|
2026-01-31 09:14:24 +08:00
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 设置标题
|
|
|
|
|
|
if (axisX.Title == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
axisX.Title = new AxisTitle();
|
|
|
|
|
|
}
|
|
|
|
|
|
axisX.Title.Content = "时间 (秒)";
|
2026-01-31 09:14:24 +08:00
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 使用正确的 Range 类
|
|
|
|
|
|
axisX.WholeRange = new DevExpress.Xpf.Charts.Range
|
|
|
|
|
|
{
|
|
|
|
|
|
MinValue = 0,
|
|
|
|
|
|
MaxValue = 600 // 默认显示10分钟(600秒)
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
// 设置可视范围(可选)
|
|
|
|
|
|
axisX.VisualRange = new DevExpress.Xpf.Charts.Range
|
|
|
|
|
|
{
|
|
|
|
|
|
MinValue = 0,
|
|
|
|
|
|
MaxValue = 600
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
// 设置网格线
|
|
|
|
|
|
axisX.GridLinesVisible = true;
|
|
|
|
|
|
axisX.GridLinesMinorVisible = false;
|
|
|
|
|
|
|
|
|
|
|
|
// 设置标签格式 - 修正这里
|
2026-02-02 10:30:12 +08:00
|
|
|
|
//axisX.Label = new AxisLabel
|
|
|
|
|
|
//{
|
|
|
|
|
|
// TextPattern = "{V:F0}秒" // 添加格式化,显示整数
|
|
|
|
|
|
//};
|
|
|
|
|
|
axisX.Label = new AxisLabel();
|
|
|
|
|
|
axisX.Label.TextPattern = "{V:F0}秒";
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 设置Y轴 - 温度
|
|
|
|
|
|
if (diagram.AxisY is AxisY2D axisY)
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 清除可能在XAML中设置的范围
|
|
|
|
|
|
axisY.WholeRange = null;
|
|
|
|
|
|
axisY.VisualRange = null;
|
|
|
|
|
|
|
|
|
|
|
|
// 设置标题
|
|
|
|
|
|
if (axisY.Title == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
axisY.Title = new AxisTitle();
|
|
|
|
|
|
}
|
|
|
|
|
|
axisY.Title.Content = "温度 (°C)";
|
|
|
|
|
|
|
|
|
|
|
|
// 设置范围
|
|
|
|
|
|
axisY.WholeRange = new DevExpress.Xpf.Charts.Range
|
|
|
|
|
|
{
|
|
|
|
|
|
MinValue = 0,
|
|
|
|
|
|
MaxValue = 800
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
axisY.VisualRange = new DevExpress.Xpf.Charts.Range
|
|
|
|
|
|
{
|
|
|
|
|
|
MinValue = 0,
|
|
|
|
|
|
MaxValue = 800
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
// 设置网格线
|
|
|
|
|
|
axisY.GridLinesVisible = true;
|
|
|
|
|
|
axisY.GridLinesMinorVisible = false;
|
|
|
|
|
|
|
|
|
|
|
|
// 设置标签格式
|
2026-02-02 10:30:12 +08:00
|
|
|
|
//axisY.Label = new AxisLabel
|
|
|
|
|
|
//{
|
|
|
|
|
|
// TextPattern = "{V:F0}°C"
|
|
|
|
|
|
//};
|
|
|
|
|
|
axisY.Label = new AxisLabel();
|
|
|
|
|
|
axisY.Label.TextPattern = "{V:F0}°C";
|
2026-01-31 13:55:00 +08:00
|
|
|
|
}
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
2026-01-31 13:55:00 +08:00
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"配置图表时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
private void StartDataCollection()
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
// 清空现有数据
|
|
|
|
|
|
temperatureData.Clear();
|
|
|
|
|
|
ClearAllSeries();
|
|
|
|
|
|
|
|
|
|
|
|
// 重置时间
|
|
|
|
|
|
_elapsedSeconds = 0;
|
|
|
|
|
|
_startTime = DateTime.Now;
|
|
|
|
|
|
txtElapsedTime.Text = "0秒";
|
|
|
|
|
|
|
|
|
|
|
|
// 添加750°C参考线
|
|
|
|
|
|
AddReferenceLine();
|
|
|
|
|
|
|
|
|
|
|
|
// 设置温度曲线样式
|
|
|
|
|
|
InitializeTemperatureSeries();
|
|
|
|
|
|
|
|
|
|
|
|
// 初始化定时器
|
|
|
|
|
|
InitializeUpdateTimer();
|
|
|
|
|
|
|
|
|
|
|
|
// 添加第一个数据点
|
|
|
|
|
|
AddInitialDataPoint();
|
|
|
|
|
|
|
|
|
|
|
|
// 更新统计信息
|
|
|
|
|
|
UpdateStatistics();
|
|
|
|
|
|
|
|
|
|
|
|
// 启动定时器
|
|
|
|
|
|
_updateTimer?.Start();
|
|
|
|
|
|
|
|
|
|
|
|
UpdateStatus("数据收集已开始");
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"开始数据收集时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void StopDataCollection()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
_updateTimer?.Stop();
|
|
|
|
|
|
_updateTimer = null;
|
|
|
|
|
|
UpdateStatus("数据收集已停止");
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"停止数据收集时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void InitializeUpdateTimer()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
_updateTimer = new DispatcherTimer();
|
|
|
|
|
|
_updateTimer.Interval = TimeSpan.FromSeconds(1); // 每秒更新一次
|
|
|
|
|
|
_updateTimer.Tick += UpdateTimer_Tick;
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"设置定时器时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void UpdateTimer_Tick(object sender, EventArgs e)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
// 更新时间
|
|
|
|
|
|
_elapsedSeconds++;
|
2026-01-31 13:55:00 +08:00
|
|
|
|
//TimeSpan elapsedTimeSpan = DateTime.Now - _startTime;
|
|
|
|
|
|
txtElapsedTime.Text = $"{_elapsedSeconds}秒 ";
|
2026-01-31 09:14:24 +08:00
|
|
|
|
|
|
|
|
|
|
// 获取当前温度
|
|
|
|
|
|
if (_getFurnaceTemperature != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
double currentTemp = _getFurnaceTemperature();
|
|
|
|
|
|
|
|
|
|
|
|
// 如果温度有效(大于0),则添加到图表
|
|
|
|
|
|
if (currentTemp > 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
AddTemperatureDataPoint(_elapsedSeconds, currentTemp);
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"获取的温度无效: {currentTemp}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine("温度获取函数为空");
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 如果需要,调整X轴范围
|
|
|
|
|
|
AdjustXAxisRange();
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"更新图表数据时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void AddInitialDataPoint()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (_getFurnaceTemperature != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
double initialTemp = _getFurnaceTemperature();
|
|
|
|
|
|
if (initialTemp > 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
AddTemperatureDataPoint(0, initialTemp);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"添加初始数据点时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void AddTemperatureDataPoint(double timeInSeconds, double temperature)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
// 确保temperatureSeries存在
|
|
|
|
|
|
if (temperatureSeries == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine("temperatureSeries为空,无法添加数据点");
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 添加数据点到图表
|
|
|
|
|
|
AddDataPoint(temperatureSeries, timeInSeconds, temperature);
|
|
|
|
|
|
|
|
|
|
|
|
// 保存到数据列表用于统计
|
|
|
|
|
|
temperatureData.Add(new Tuple<double, double>(timeInSeconds, temperature));
|
|
|
|
|
|
|
|
|
|
|
|
// 更新统计信息
|
|
|
|
|
|
UpdateStatistics();
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"添加温度数据点时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void AddReferenceLine()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
// 确保targetSeries存在
|
|
|
|
|
|
if (targetSeries == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine("targetSeries为空,无法添加参考线");
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 清除现有数据点
|
|
|
|
|
|
ClearSeriesPoints(targetSeries);
|
|
|
|
|
|
|
|
|
|
|
|
// 添加750°C参考线
|
|
|
|
|
|
// 起点:时间0秒,温度750°C
|
|
|
|
|
|
// 终点:当前最大时间或预设值,温度750°C
|
|
|
|
|
|
double xMax = _elapsedSeconds > 0 ? _elapsedSeconds : 600;
|
|
|
|
|
|
AddDataPoint(targetSeries, 0, 750);
|
|
|
|
|
|
AddDataPoint(targetSeries, xMax, 750);
|
|
|
|
|
|
|
|
|
|
|
|
// 设置参考线样式
|
|
|
|
|
|
targetSeries.Brush = new SolidColorBrush(Color.FromRgb(231, 76, 60)); // 红色
|
|
|
|
|
|
if (targetSeries.LineStyle == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
targetSeries.LineStyle = new LineStyle();
|
|
|
|
|
|
}
|
|
|
|
|
|
targetSeries.LineStyle.Thickness = 2;
|
|
|
|
|
|
targetSeries.LineStyle.DashStyle = new DashStyle(new double[] { 4, 2 }, 0);
|
|
|
|
|
|
|
|
|
|
|
|
// 设置参考线标签
|
|
|
|
|
|
targetSeries.DisplayName = "目标温度 (750°C)";
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"添加参考线时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void InitializeTemperatureSeries()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (temperatureSeries == null) return;
|
|
|
|
|
|
|
|
|
|
|
|
// 设置温度曲线样式
|
|
|
|
|
|
temperatureSeries.Brush = new SolidColorBrush(Color.FromRgb(52, 152, 219)); // 蓝色
|
|
|
|
|
|
if (temperatureSeries.LineStyle == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
temperatureSeries.LineStyle = new LineStyle();
|
|
|
|
|
|
}
|
|
|
|
|
|
temperatureSeries.LineStyle.Thickness = 2;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// 设置显示名称
|
|
|
|
|
|
temperatureSeries.DisplayName = "炉内温度";
|
|
|
|
|
|
|
|
|
|
|
|
// 设置悬停提示
|
|
|
|
|
|
temperatureSeries.CrosshairLabelPattern = "时间: {A}秒\n温度: {V}°C";
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"初始化温度曲线时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void AdjustXAxisRange()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (temperatureChart.Diagram is XYDiagram2D diagram &&
|
|
|
|
|
|
diagram.AxisX is AxisX2D axisX)
|
|
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 获取当前X轴最大值
|
|
|
|
|
|
double currentMaxValue = 600; // 默认值
|
2026-01-31 09:14:24 +08:00
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
if (axisX.WholeRange != null)
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
try
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 直接使用 MinValue 和 MaxValue 属性
|
|
|
|
|
|
currentMaxValue = (double)axisX.WholeRange.MaxValue;
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
2026-01-31 13:55:00 +08:00
|
|
|
|
catch
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 如果获取失败,使用默认值
|
|
|
|
|
|
currentMaxValue = 600;
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 如果时间超过了当前X轴范围的80%,自动扩展
|
|
|
|
|
|
if (_elapsedSeconds > currentMaxValue * 0.8)
|
|
|
|
|
|
{
|
|
|
|
|
|
// 每次扩展300秒(5分钟)
|
|
|
|
|
|
double newMax = currentMaxValue + 300;
|
2026-01-31 13:55:00 +08:00
|
|
|
|
|
|
|
|
|
|
// 更新 WholeRange
|
2026-01-31 09:14:24 +08:00
|
|
|
|
axisX.WholeRange = new DevExpress.Xpf.Charts.Range
|
|
|
|
|
|
{
|
|
|
|
|
|
MinValue = 0,
|
|
|
|
|
|
MaxValue = newMax
|
|
|
|
|
|
};
|
|
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 同时更新 VisualRange 以保持显示一致
|
|
|
|
|
|
axisX.VisualRange = new DevExpress.Xpf.Charts.Range
|
|
|
|
|
|
{
|
|
|
|
|
|
MinValue = 0,
|
|
|
|
|
|
MaxValue = newMax
|
|
|
|
|
|
};
|
|
|
|
|
|
|
2026-01-31 09:14:24 +08:00
|
|
|
|
// 同时更新参考线
|
|
|
|
|
|
UpdateReferenceLine(newMax);
|
2026-01-31 13:55:00 +08:00
|
|
|
|
|
|
|
|
|
|
Debug.WriteLine($"X轴范围已扩展到: 0 - {newMax}秒");
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"调整X轴范围时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void UpdateReferenceLine(double xMax)
|
|
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
try
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
if (targetSeries != null)
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
2026-01-31 13:55:00 +08:00
|
|
|
|
// 清除现有数据点
|
|
|
|
|
|
targetSeries.Points.Clear();
|
|
|
|
|
|
|
|
|
|
|
|
// 添加新的参考线点
|
2026-01-31 09:14:24 +08:00
|
|
|
|
AddDataPoint(targetSeries, 0, 750);
|
|
|
|
|
|
AddDataPoint(targetSeries, xMax, 750);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
2026-01-31 13:55:00 +08:00
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"更新参考线时出错: {ex.Message}");
|
|
|
|
|
|
}
|
2026-01-31 09:14:24 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2026-01-31 13:55:00 +08:00
|
|
|
|
private void ClearAllSeries()
|
2026-01-31 09:14:24 +08:00
|
|
|
|
{
|
|
|
|
|
|
ClearSeriesPoints(temperatureSeries);
|
|
|
|
|
|
ClearSeriesPoints(targetSeries);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void ClearSeriesPoints(LineSeries2D series)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (series != null && series.Points != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
series.Points.Clear();
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"清除数据点时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void AddDataPoint(LineSeries2D series, double time, double temperature)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (series == null || series.Points == null)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine("series或series.Points为空");
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// 添加数据点
|
|
|
|
|
|
series.Points.Add(new SeriesPoint(time, temperature));
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"添加数据点时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void UpdateStatistics()
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (temperatureData == null || temperatureData.Count == 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
txtMaxTemp.Text = "0°C";
|
|
|
|
|
|
txtAvgTemp.Text = "0°C";
|
|
|
|
|
|
txtCurrentTemp.Text = "0°C";
|
|
|
|
|
|
txtDataPoints.Text = "0";
|
|
|
|
|
|
txtTempDifference.Text = "0°C";
|
|
|
|
|
|
return;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
double maxTemp = 0;
|
|
|
|
|
|
double sumTemp = 0;
|
|
|
|
|
|
int validPoints = 0;
|
|
|
|
|
|
double currentTemp = 0;
|
|
|
|
|
|
double minTemp = double.MaxValue;
|
|
|
|
|
|
|
|
|
|
|
|
foreach (var point in temperatureData)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
double temp = point.Item2;
|
|
|
|
|
|
if (temp > maxTemp) maxTemp = temp;
|
|
|
|
|
|
if (temp < minTemp) minTemp = temp;
|
|
|
|
|
|
sumTemp += temp;
|
|
|
|
|
|
validPoints++;
|
|
|
|
|
|
|
|
|
|
|
|
// 最后一个数据点是当前温度
|
|
|
|
|
|
if (point == temperatureData.Last())
|
|
|
|
|
|
{
|
|
|
|
|
|
currentTemp = temp;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch
|
|
|
|
|
|
{
|
|
|
|
|
|
// 忽略错误的数据点
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
if (validPoints > 0)
|
|
|
|
|
|
{
|
|
|
|
|
|
double avgTemp = sumTemp / validPoints;
|
|
|
|
|
|
double temperatureRange = maxTemp - minTemp;
|
|
|
|
|
|
|
|
|
|
|
|
// 更新显示
|
|
|
|
|
|
txtMaxTemp.Text = $"{maxTemp:F1}°C";
|
|
|
|
|
|
txtMinTemp.Text = $"{minTemp:F1}°C";
|
|
|
|
|
|
txtAvgTemp.Text = $"{avgTemp:F1}°C";
|
|
|
|
|
|
txtCurrentTemp.Text = $"{currentTemp:F1}°C";
|
|
|
|
|
|
txtDataPoints.Text = validPoints.ToString();
|
|
|
|
|
|
txtTempRange.Text = $"{temperatureRange:F1}°C";
|
|
|
|
|
|
|
|
|
|
|
|
// 显示与目标温度的差值
|
|
|
|
|
|
double difference = currentTemp - 750;
|
|
|
|
|
|
txtTempDifference.Text = $"{(difference >= 0 ? "+" : "")}{difference:F1}°C";
|
|
|
|
|
|
|
|
|
|
|
|
// 根据差值设置颜色
|
|
|
|
|
|
if (Math.Abs(difference) <= 5)
|
|
|
|
|
|
{
|
|
|
|
|
|
txtTempDifference.Foreground = Brushes.Green;
|
|
|
|
|
|
}
|
|
|
|
|
|
else if (Math.Abs(difference) <= 15)
|
|
|
|
|
|
{
|
|
|
|
|
|
txtTempDifference.Foreground = Brushes.Orange;
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
txtTempDifference.Foreground = Brushes.Red;
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
else
|
|
|
|
|
|
{
|
|
|
|
|
|
ResetStatistics();
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"更新统计信息时出错: {ex.Message}");
|
|
|
|
|
|
ResetStatistics();
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void ResetStatistics()
|
|
|
|
|
|
{
|
|
|
|
|
|
txtMaxTemp.Text = "0°C";
|
|
|
|
|
|
txtMinTemp.Text = "0°C";
|
|
|
|
|
|
txtAvgTemp.Text = "0°C";
|
|
|
|
|
|
txtCurrentTemp.Text = "0°C";
|
|
|
|
|
|
txtDataPoints.Text = "0";
|
|
|
|
|
|
txtTempRange.Text = "0°C";
|
|
|
|
|
|
txtTempDifference.Text = "0°C";
|
|
|
|
|
|
txtTempDifference.Foreground = Brushes.Black;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void UpdateStatus(string message)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
if (txtStatus != null)
|
|
|
|
|
|
{
|
|
|
|
|
|
txtStatus.Text = $"{DateTime.Now:HH:mm:ss} - {message}";
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
Debug.WriteLine($"更新状态时出错: {ex.Message}");
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
#region 按钮事件处理
|
|
|
|
|
|
|
|
|
|
|
|
private void btnClearData_Click(object sender, RoutedEventArgs e)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
var result = MessageBox.Show("确定要清空所有数据吗?", "确认",
|
|
|
|
|
|
MessageBoxButton.YesNo, MessageBoxImage.Question);
|
|
|
|
|
|
|
|
|
|
|
|
if (result == MessageBoxResult.Yes)
|
|
|
|
|
|
{
|
|
|
|
|
|
// 停止定时器
|
|
|
|
|
|
StopDataCollection();
|
|
|
|
|
|
|
|
|
|
|
|
// 清空数据
|
|
|
|
|
|
temperatureData.Clear();
|
|
|
|
|
|
ClearAllSeries();
|
|
|
|
|
|
|
|
|
|
|
|
// 重置统计信息
|
|
|
|
|
|
ResetStatistics();
|
|
|
|
|
|
|
|
|
|
|
|
// 重置时间和按钮状态
|
|
|
|
|
|
_elapsedSeconds = 0;
|
|
|
|
|
|
txtElapsedTime.Text = "0秒";
|
|
|
|
|
|
UpdateStatus("数据已清空");
|
|
|
|
|
|
MessageBox.Show("数据已清空", "提示", MessageBoxButton.OK, MessageBoxImage.Information);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"清空数据时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
private void btnClose_Click(object sender, RoutedEventArgs e)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
StopDataCollection();
|
|
|
|
|
|
this.Close();
|
|
|
|
|
|
}
|
|
|
|
|
|
catch (Exception ex)
|
|
|
|
|
|
{
|
|
|
|
|
|
MessageBox.Show($"关闭窗口时出错: {ex.Message}", "错误", MessageBoxButton.OK, MessageBoxImage.Error);
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
|
|
|
|
#region 窗口关闭
|
|
|
|
|
|
// 窗口关闭时清理资源
|
|
|
|
|
|
protected override void OnClosed(EventArgs e)
|
|
|
|
|
|
{
|
|
|
|
|
|
try
|
|
|
|
|
|
{
|
|
|
|
|
|
StopDataCollection();
|
|
|
|
|
|
temperatureData.Clear();
|
|
|
|
|
|
_getFurnaceTemperature = null;
|
|
|
|
|
|
}
|
|
|
|
|
|
catch
|
|
|
|
|
|
{
|
|
|
|
|
|
// 忽略清理时的错误
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
base.OnClosed(e);
|
|
|
|
|
|
}
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|