using DevExpress.Utils;
|
using DevExpress.XtraCharts;
|
using NPOI.OpenXmlFormats.Dml.Diagram;
|
using NPOI.SS.Formula.Functions;
|
using System.Text;
|
using Yw.Geometry;
|
|
namespace Yw.WinFrmUI.Phart
|
{
|
/// <summary>
|
/// 泵串并联图表
|
/// </summary>
|
public partial class PumpVariableSpeedChart : DevExpress.XtraEditors.XtraUserControl
|
{
|
public PumpVariableSpeedChart()
|
{
|
InitializeComponent();
|
InitialChart();
|
this.chartControl1.RuntimeHitTesting = true;
|
//this.chartControl1.SelectionMode = ElementSelectionMode.Single;
|
//this.chartControl1.SeriesSelectionMode = SeriesSelectionMode.Series;
|
}
|
|
#region Private Variable
|
|
private List<PumpVariableSpeedInfoViewModel> _vm_list = new List<PumpVariableSpeedInfoViewModel>();
|
private readonly string _tag_qh = "CurveQH", _tag_qe = "CurveQE", _tag_qp = "CurveQP";
|
|
private XYDiagram _main_chart_diagram;
|
private XYDiagramDefaultPane _pane_qh;
|
private XYDiagramPane _pane_qe;
|
private XYDiagramPane _pane_qp;
|
private AxisX _axis_x_q;
|
private AxisY _axis_y_qh;
|
private SecondaryAxisY _axis_y_qe, _axis_y_qp;
|
private ConstantLine _work_pt_line;
|
|
private TextAnnotation _work_pt_txt_annot;
|
private PumpCoordinate _coordinate_paras;
|
|
private Series _series_eq, _series_eq_pt;
|
|
private Yw.Geometry.Point2d _design_pt;
|
|
private bool _qh_visible = true;
|
private bool _qe_visible = true;
|
private bool _qp_visible = true;
|
private bool _cubic_spline_eq_visible = true;
|
|
private bool _initialData = false;
|
|
#endregion
|
|
#region Public Variable
|
|
/// <summary>
|
/// 工作线是否可见
|
/// </summary>
|
public bool LineVisible
|
{
|
get => _line_visible;
|
set
|
{
|
_line_visible = value;
|
this.barCekLineVisible.Checked = _line_visible;
|
this.barBtnSetAxisQValue.Enabled = _line_visible;
|
}
|
}
|
private bool _line_visible = false;
|
|
/// <summary>
|
/// 曲线名是否可见
|
/// </summary>
|
public bool LineNameVisible
|
{
|
get => _line_name_visible;
|
set
|
{
|
_line_name_visible = value;
|
this.barCekCurveNameVisible.Checked = _line_name_visible;
|
}
|
}
|
private bool _line_name_visible = true;
|
|
/// <summary>
|
/// 曲线名显示频率
|
/// </summary>
|
public bool LineNameShowHz
|
{
|
get => _line_name_show_hz;
|
set
|
{
|
_line_name_show_hz = value;
|
this.barCekShowHz.Checked = _line_name_show_hz;
|
}
|
}
|
private bool _line_name_show_hz = false;
|
|
#endregion
|
|
#region Public Evnet
|
|
public event Action<PumpCoordinate> OnCurveCoordinateChanged;
|
|
public event Action<string, PumpGroupPt> OnCalcQueryPoint = null;
|
|
public event Action AddBySpeedEvent = null;
|
|
public event Action AddByHzEvent = null;
|
|
public event Action AddByPointEvent = null;
|
|
#endregion
|
|
#region Initial
|
|
/// <summary>
|
/// 初始化图表
|
/// </summary>
|
private void InitialChart()
|
{
|
this.chartControl1.SetChartDisplay();
|
this.chartControl1.Legend.Direction = DevExpress.XtraCharts.LegendDirection.TopToBottom;
|
|
_main_chart_diagram = (XYDiagram)this.chartControl1.Diagram;
|
_pane_qh = _main_chart_diagram.DefaultPane;
|
_pane_qe = (XYDiagramPane)_main_chart_diagram.FindPaneByName("PaneQE");
|
_pane_qp = (XYDiagramPane)_main_chart_diagram.FindPaneByName("PaneQP");
|
|
_axis_x_q = _main_chart_diagram.AxisX;
|
_axis_x_q.SetAxisXQDisplay();
|
_axis_y_qh = _main_chart_diagram.AxisY;
|
_axis_y_qh.SetAxisYQHDisplay();
|
_axis_y_qe = _main_chart_diagram.SecondaryAxesY.GetAxisByName("AxisYQE");
|
_axis_y_qe.SetSecondaryAxisYQEDisplay();
|
_axis_y_qe.Alignment = AxisAlignment.Near;
|
_axis_y_qp = _main_chart_diagram.SecondaryAxesY.GetAxisByName("AxisYQP");
|
_axis_y_qp.SetSecondaryAxisYQPDisplay();
|
|
_work_pt_line = (ConstantLine)_main_chart_diagram.AxisX.ConstantLines.GetElementByName("WorkPointLine");
|
_work_pt_line.SetWorkPointLineDisplay();
|
|
_work_pt_txt_annot = this.chartControl1.AnnotationRepository[0] as TextAnnotation;
|
_work_pt_txt_annot.SetTextAnnoWorkPointDisplay();
|
|
_axis_x_q.Visibility = DefaultBoolean.False;
|
_axis_x_q.GridLines.Visible = false;
|
_axis_y_qh.Visibility = DefaultBoolean.False;
|
_axis_y_qh.GridLines.Visible = false;
|
_axis_y_qe.Visibility = DefaultBoolean.False;
|
_axis_y_qe.GridLines.Visible = false;
|
_axis_y_qp.Visibility = DefaultBoolean.False;
|
_axis_y_qp.GridLines.Visible = false;
|
|
|
_work_pt_line.Visible = false;
|
_work_pt_txt_annot.Visible = false;
|
|
this.chartControl1.MouseMove += new System.Windows.Forms.MouseEventHandler(this.chartControl1_MouseMove);
|
this.chartControl1.MouseUp += new System.Windows.Forms.MouseEventHandler(this.chartControl1_MouseUp);
|
this.chartControl1.MouseDown += new System.Windows.Forms.MouseEventHandler(this.chartControl1_MouseDown);
|
this.chartControl1.Resize += new System.EventHandler(this.chartControl1_Resize);
|
}
|
|
/// <summary>
|
/// 初始化图表数据
|
/// </summary>
|
public void InitialChartData()
|
{
|
_initialData = false;
|
_coordinate_paras = null;
|
|
UpdateChart(false);
|
}
|
|
/// <summary>
|
/// 初始化图表数据
|
/// </summary>
|
public void SetEasyChart()
|
{
|
this.barSubAdd.Visibility = DevExpress.XtraBars.BarItemVisibility.Never;
|
}
|
#endregion
|
|
#region Add Set Curve
|
|
/// <summary>
|
/// 添加曲线
|
/// </summary>
|
/// <param name="vm_list"></param>
|
public void Add(List<PumpVariableSpeedInfoViewModel> vm_list, Yw.Geometry.Point2d design_pt)
|
{
|
if (vm_list == null || !vm_list.Any())
|
return;
|
_vm_list = new List<PumpVariableSpeedInfoViewModel>();
|
_design_pt = design_pt;
|
_initialData = true;
|
_vm_list.AddRange(vm_list);
|
UpdateChart(true);
|
}
|
|
/// <summary>
|
/// 添加曲线
|
/// </summary>
|
/// <param name="vm"></param>
|
public void Add(PumpVariableSpeedInfoViewModel vm, Yw.Geometry.Point2d design_pt)
|
{
|
if (vm == null)
|
return;
|
if (_vm_list == null)
|
_vm_list = new List<PumpVariableSpeedInfoViewModel>();
|
_design_pt = design_pt;
|
_initialData = true;
|
_vm_list.Add(vm);
|
UpdateChart(true);
|
}
|
|
/// <summary>
|
/// 添加曲线
|
/// </summary>
|
/// <param name="vm_list"></param>
|
public void Add(List<PumpVariableSpeedInfoViewModel> vm_list)
|
{
|
if (vm_list == null || !vm_list.Any())
|
return;
|
_vm_list = new List<PumpVariableSpeedInfoViewModel>();
|
_initialData = true;
|
_vm_list.AddRange(vm_list);
|
UpdateChart(true);
|
}
|
|
/// <summary>
|
/// 添加曲线
|
/// </summary>
|
/// <param name="vm"></param>
|
public void Add(PumpVariableSpeedInfoViewModel vm)
|
{
|
if (vm == null)
|
return;
|
if (_vm_list == null)
|
_vm_list = new List<PumpVariableSpeedInfoViewModel>();
|
_initialData = true;
|
_vm_list.Add(vm);
|
UpdateChart(true);
|
}
|
|
|
/// <summary>
|
/// 设置曲线
|
/// </summary>
|
/// <param name="id"></param>
|
/// <param name="qh"></param>
|
/// <param name="qe"></param>
|
/// <param name="qp"></param>
|
/// <param name="name"></param>
|
public void Set(string id, double hz, double ex_ratio, Yw.Geometry.CubicSpline2d qh, Yw.Geometry.CubicSpline2d qe, Yw.Geometry.CubicSpline2d qp)
|
{
|
var exist = _vm_list.FirstOrDefault(x => x.Id == id);
|
if (exist == null)
|
return;
|
exist.CurrentHz = hz;
|
exist.CurrentSpeed = Math.Round(hz / 50 * exist.RatedSpeed, 1);
|
exist.ExtendRatio = ex_ratio;
|
exist.QhCalc = qh;
|
exist.QeCalc = qe;
|
exist.QpCalc = qp;
|
foreach (Series series in this.chartControl1.Series)
|
{
|
var tag = series.Tag;
|
if (tag == null)
|
continue;
|
if (tag.ToString() != exist.Id)
|
continue;
|
exist.Name = LineNameShowHz ? exist.CurrentHz.ToString() : exist.CurrentSpeed.ToString();
|
}
|
UpdateChart(true);
|
|
}
|
|
/// <summary>
|
/// 设置曲线
|
/// </summary>
|
/// <param name="id"></param>
|
/// <param name="color"></param>
|
public void SetInfo(string id, Color color)
|
{
|
var exist = _vm_list.FirstOrDefault(x => x.Id == id);
|
if (exist == null)
|
return;
|
foreach (Series series in this.chartControl1.Series)
|
{
|
var tag = series.Tag;
|
if (tag == null)
|
continue;
|
if (tag.ToString() != exist.Id)
|
continue;
|
exist.Color = color;
|
series.View.Color = color;
|
for (int i = 0; i < this.chartControl1.AnnotationRepository.Count; i++)
|
{
|
var txt = this.chartControl1.AnnotationRepository[i];
|
if (txt.Name == _tag_qh + id)
|
{
|
(txt as TextAnnotation).Text = exist.Name;
|
(txt as TextAnnotation).TextColor = color;
|
(txt as TextAnnotation).Border.Color = color;
|
}
|
}
|
}
|
}
|
|
|
/// <summary>
|
/// 设置曲线
|
/// </summary>
|
/// <param name="id"></param>
|
/// <param name="name"></param>
|
/// <param name="color"></param>
|
public void SetInfo(string id, string name, Color color)
|
{
|
var exist = _vm_list.FirstOrDefault(x => x.Id == id);
|
if (exist == null)
|
return;
|
foreach (Series series in this.chartControl1.Series)
|
{
|
var tag = series.Tag;
|
if (tag == null)
|
continue;
|
if (tag.ToString() != exist.Id)
|
continue;
|
exist.Name = name;
|
exist.Color = color;
|
series.View.Color = color;
|
for (int i = 0; i < this.chartControl1.AnnotationRepository.Count; i++)
|
{
|
var txt = this.chartControl1.AnnotationRepository[i];
|
if (txt.Name == _tag_qh + id)
|
{
|
(txt as TextAnnotation).Text = name;
|
(txt as TextAnnotation).TextColor = color;
|
(txt as TextAnnotation).Border.Color = color;
|
}
|
}
|
}
|
}
|
|
public List<PumpVariableSpeedInfoViewModel> GetList()
|
{
|
if (_vm_list == null || !_vm_list.Any())
|
return default;
|
return _vm_list.Select(x => new PumpVariableSpeedInfoViewModel(x)).ToList();
|
}
|
|
public List<PumpSectPointViewModel> GetSectPointList()
|
{
|
if (_vm_list == null || !_vm_list.Any())
|
return default;
|
|
var list = new List<PumpSectPointViewModel>();
|
foreach (var x in _vm_list)
|
{
|
var vm = new PumpSectPointViewModel();
|
vm.Id = x.Id;
|
vm.Name = x.Name;
|
if (x.SectPoint != null)
|
{
|
var flow = x.SectPoint.X;
|
var head = x.SectPoint.Y;
|
vm.QueryQ = $"{flow:N1}";
|
vm.QueryH = $"{head:N1}";
|
if (x.QeCalc != null)
|
{
|
vm.QueryE = $"{x.QeCalc.GetPointY(flow):N1}";
|
}
|
if (x.QpCalc != null)
|
{
|
vm.QueryP = $"{x.QpCalc.GetPointY(flow):N1}";
|
}
|
}
|
list.Add(vm);
|
}
|
return list;
|
}
|
|
/// <summary>
|
/// 设置设计点
|
/// </summary>
|
/// <param name="design_pt"></param>
|
public void SetDesignPt(double x,double y)
|
{
|
_design_pt = new Point2d(x,y);
|
UpdateChart(true);
|
}
|
|
|
/// <summary>
|
/// 删除曲线
|
/// </summary>
|
public void Delete()
|
{
|
_vm_list.Clear();
|
UpdateChart(true);
|
_initialData = false;
|
}
|
|
/// <summary>
|
/// 删除曲线
|
/// </summary>
|
/// <param name="id"></param>
|
public void Delete(string id)
|
{
|
var exist = _vm_list.FirstOrDefault(x => x.Id == id);
|
if (exist == null)
|
return;
|
_vm_list.Remove(exist);
|
UpdateChart(true);
|
if (_vm_list.Count == 0)
|
{
|
_initialData = false;
|
}
|
}
|
|
/// <summary>
|
/// 更新图表
|
/// </summary>
|
/// <param name="calc_coordinate">计算坐标</param>
|
public void UpdateChart(bool calc_coordinate = false)
|
{
|
if (calc_coordinate || _coordinate_paras == null)
|
{
|
//不强迫计算,就用上次更新的坐标系
|
CalcCoordinate();
|
}
|
|
CalcSeries();
|
|
CalcChartAxis();
|
|
CalcWorkPointByQ();
|
|
CalcTextAnchorPoint();
|
|
}
|
|
#endregion
|
|
#region Calc
|
|
private double _minQ, _maxQ;
|
private double _maxH = 0, _minH = 10000;
|
private double _maxE = 0, _minE = 0;
|
private double _maxP = 0, _minP = 1000;
|
|
/// <summary>
|
/// 计算坐标
|
/// </summary>
|
private void CalcCoordinate()
|
{
|
if (_vm_list == null || !_vm_list.Any())
|
{
|
//设置成白板坐标
|
_coordinate_paras = new PumpCoordinate();
|
_coordinate_paras.GridNumberX = 30;
|
_coordinate_paras.GridNumberY = 16;
|
//显示的坐标线号
|
_coordinate_paras.StartLineNoH = 10;
|
_coordinate_paras.EndLineNoH = 15;
|
_coordinate_paras.StartLineNoE = 0;
|
_coordinate_paras.EndLineNoE = 10;
|
_coordinate_paras.StartLineNoP = 2;
|
_coordinate_paras.EndLineNoP = 9;
|
//坐标最小值和间隔
|
_coordinate_paras.CoordMinQ = 0; _coordinate_paras.CoordSpaceQ = 1000;
|
_coordinate_paras.CoordMinH = 10; _coordinate_paras.CoordSpaceH = 100;
|
_coordinate_paras.CoordMinE = 0; _coordinate_paras.CoordSpaceE = 100;
|
_coordinate_paras.CoordMinP = 10; _coordinate_paras.CoordSpaceP = 100;
|
return;
|
}
|
|
_maxQ = 0; _minQ = 10000;
|
_maxH = 0; _minH = 10000;
|
_maxE = 0; _minE = 0;
|
_maxP = 0; _minP = 1000;
|
|
double _scaleMinH = 1, _scaleMaxH = 1;
|
|
foreach (var vm in _vm_list)
|
{
|
var qh_pt_list = vm.QhCalc.GetPointList();
|
var xxx = qh_pt_list.Select(x => x.X);
|
var yyy = qh_pt_list.Select(x => x.Y);
|
|
_minQ = Math.Min(_minQ, xxx.Min());
|
_maxQ = Math.Max(_maxQ, xxx.Max());
|
|
_minH = Math.Min(_minH, yyy.Min());
|
_maxH = Math.Max(_maxH, yyy.Max());
|
}
|
|
|
foreach (var vm in _vm_list)
|
{
|
if (vm.QeCalc == null)
|
continue;
|
var qe_pt_list = vm.QeCalc.GetPointList();
|
var yyy = qe_pt_list.Select(x => x.Y);
|
_maxE = Math.Max(_maxE, yyy.Max());
|
}
|
|
foreach (var vm in _vm_list)
|
{
|
if (vm.QpCalc == null)
|
continue;
|
var yyy = vm.QpCalc.GetPointList().Select(x => x.Y);
|
_minP = Math.Min(_minP, yyy.Min());
|
_maxP = Math.Max(_maxP, yyy.Max());
|
}
|
|
_coordinate_paras = PumpCoordinate.CalcCoordinate(_minQ,
|
_maxQ,
|
_minH * _scaleMinH,
|
_maxH * _scaleMaxH,
|
_minE,
|
_maxE,
|
_minP,
|
_maxP);
|
|
if (_coordinate_paras == null)
|
return;
|
|
if (_coordinate_paras.CoordMinQ + _coordinate_paras.CoordSpaceQ * this._coordinate_paras.GridNumberX < _maxQ * 1.05)
|
{
|
_coordinate_paras.GridNumberX++;
|
}
|
}
|
|
/// <summary>
|
/// 计算图表轴
|
/// </summary>
|
private void CalcChartAxis()
|
{
|
_axis_x_q.Visibility = DefaultBoolean.False;
|
_axis_x_q.GridLines.Visible = false;
|
_axis_y_qh.Visibility = DefaultBoolean.False;
|
_axis_y_qh.GridLines.Visible = false;
|
_axis_y_qe.Visibility = DefaultBoolean.False;
|
_axis_y_qe.GridLines.Visible = false;
|
_axis_y_qp.Visibility = DefaultBoolean.False;
|
_axis_y_qp.GridLines.Visible = false;
|
|
_work_pt_line.Visible = false;
|
|
_pane_qe.Visibility = ChartElementVisibility.Hidden;
|
_pane_qp.Visibility = ChartElementVisibility.Hidden;
|
|
|
_pane_qe.Visibility = _qe_visible ? ChartElementVisibility.Visible : ChartElementVisibility.Hidden;
|
_pane_qp.Visibility = _qp_visible ? ChartElementVisibility.Visible : ChartElementVisibility.Hidden;
|
|
//计算刻度 Q
|
var axisQLabels = new List<CustomAxisLabel>();
|
var disQ = _coordinate_paras.CoordMinQ;
|
for (int i = 0; i < _coordinate_paras.GridNumberX + 1; i++)
|
{
|
axisQLabels.Add(new CustomAxisLabel(disQ.ToString("N0"), disQ));
|
disQ = disQ + _coordinate_paras.CoordSpaceQ;
|
}
|
|
_axis_x_q.CustomLabels.Clear();
|
_axis_x_q.CustomLabels.AddRange(axisQLabels.ToArray());
|
_axis_x_q.Visibility = DefaultBoolean.True;
|
_axis_x_q.GridLines.Visible = true;
|
|
|
//计算刻度
|
var axisQHLabels = new List<CustomAxisLabel>();
|
var disH = _coordinate_paras.CoordMinH + _coordinate_paras.CoordSpaceH * _coordinate_paras.StartLineNoH;
|
for (int i = _coordinate_paras.StartLineNoH; i < _coordinate_paras.EndLineNoH + 1; i++)
|
{
|
axisQHLabels.Add(new CustomAxisLabel(disH.ToString(), disH));
|
disH = disH + _coordinate_paras.CoordSpaceH;
|
}
|
|
_axis_y_qh.CustomLabels.Clear();
|
_axis_y_qh.CustomLabels.AddRange(axisQHLabels.ToArray());
|
_axis_y_qh.Visibility = DefaultBoolean.True;
|
_axis_y_qh.GridLines.Visible = true;
|
|
//效率
|
if (_maxE > _minE && _qe_visible)
|
{
|
//计算刻度
|
var axisQELabels = new List<CustomAxisLabel>();
|
var disE = _coordinate_paras.CoordMinE + _coordinate_paras.CoordSpaceE * _coordinate_paras.StartLineNoE;
|
for (int i = _coordinate_paras.StartLineNoE; i < _coordinate_paras.EndLineNoE + 1; i++)
|
{
|
axisQELabels.Add(new CustomAxisLabel(disE.ToString(), disE));
|
disE = disE + _coordinate_paras.CoordSpaceE;
|
}
|
|
_axis_y_qe.CustomLabels.Clear();
|
_axis_y_qe.CustomLabels.AddRange(axisQELabels.ToArray());
|
_axis_y_qe.Visibility = DefaultBoolean.True;
|
_axis_y_qe.GridLines.Visible = true;
|
}
|
|
//功率
|
if (_maxP > _minP)
|
{
|
//计算刻度
|
var axisQPLabels = new List<CustomAxisLabel>();
|
double disP = _coordinate_paras.CoordMinP + _coordinate_paras.CoordSpaceP * _coordinate_paras.StartLineNoP;
|
for (int i = _coordinate_paras.StartLineNoP; i < _coordinate_paras.EndLineNoP + 1; i++)
|
{
|
axisQPLabels.Add(new CustomAxisLabel(disP.ToString(), disP));
|
disP = disP + _coordinate_paras.CoordSpaceP;
|
}
|
|
_axis_y_qp.CustomLabels.Clear();
|
_axis_y_qp.CustomLabels.AddRange(axisQPLabels.ToArray());
|
_axis_y_qp.Visibility = DefaultBoolean.True;
|
_axis_y_qp.GridLines.Visible = true;
|
}
|
|
|
_axis_x_q.SetAxisRange(_coordinate_paras.CoordMinQ, _coordinate_paras.DispMaxQ());
|
_axis_y_qh.SetAxisRange(_coordinate_paras.DispMinH(), _coordinate_paras.DispMaxH());
|
_axis_y_qe.SetAxisRange(_coordinate_paras.DispMinE(), _coordinate_paras.DispMaxE());
|
_axis_y_qp.SetAxisRange(_coordinate_paras.DispMinP(), _coordinate_paras.DispMaxP());
|
}
|
|
/// <summary>
|
/// 计算系列
|
/// </summary>
|
private void CalcSeries()
|
{
|
this.chartControl1.BeginInit();
|
this.chartControl1.Series.Clear();
|
|
var annotationCount = this.chartControl1.AnnotationRepository.Count;
|
for (int i = annotationCount - 1; i > 0; i--)
|
{
|
if (i == 0)
|
break;
|
this.chartControl1.AnnotationRepository.RemoveAt(i);
|
}
|
|
this.chartControl1.Legend.CustomItems.Clear();
|
if (_vm_list.Count > 0)
|
{
|
foreach (var vm in _vm_list)
|
{
|
if (!vm.IsDefault)
|
{
|
CreateLineSeries(vm);
|
}
|
else
|
{
|
CreateLineSeries(vm);
|
CreateEqSeries(vm, _design_pt);
|
}
|
}
|
}
|
else
|
{
|
LineVisible = false;
|
}
|
this.chartControl1.EndInit();
|
}
|
|
/// <summary>
|
/// 计算注释定位
|
/// </summary>
|
private void CalcTextAnchorPoint()
|
{
|
var x = this.chartControl1.Location.X + this.chartControl1.Width - (100);
|
var y = this.chartControl1.Height - (100);
|
|
(_work_pt_txt_annot.AnchorPoint as ChartAnchorPoint).X = x;
|
(_work_pt_txt_annot.AnchorPoint as ChartAnchorPoint).Y = y;
|
}
|
|
/// <summary>
|
/// 计算工作点
|
/// </summary>
|
/// <param name="workQ"></param>
|
public void CalcWorkPointByQ(double? workQ = null)
|
{
|
if (!_line_visible)
|
{
|
_work_pt_line.Visible = false;
|
_work_pt_line.Title.Visible = false;
|
_work_pt_txt_annot.Visible = false;
|
return;
|
}
|
else
|
{
|
_work_pt_line.Visible = true;
|
_work_pt_line.Title.Visible = true;
|
_work_pt_txt_annot.Visible = true;
|
}
|
|
if (_vm_list == null || !_vm_list.Any())
|
return;
|
|
|
if (workQ == null)
|
{
|
workQ = _minQ;
|
//workQ = (_minQ + _maxQ) / 2;
|
}
|
|
if (workQ < _minQ || workQ > _maxQ)
|
return;
|
foreach (var vm in _vm_list)
|
{
|
var curveMinQ = vm.QhCalc.MinX;
|
var curveMaxQ = vm.QhCalc.MaxX;
|
|
var workPoint = new PumpGroupPt(0, 0, 0, 0, 0);
|
if (curveMinQ > workQ.Value || workQ.Value > curveMaxQ)
|
{
|
if (OnCalcQueryPoint != null)
|
{
|
OnCalcQueryPoint(vm.Id, workPoint);
|
}
|
continue;
|
}
|
|
workPoint.Q = workQ.Value;
|
workPoint.H = vm.QhCalc.GetPointY(workQ.Value);
|
|
var workInfoStringBuilder = new StringBuilder();
|
workInfoStringBuilder.Append($"流量:{workPoint.Q.ToString("N1")} ");
|
|
if (vm.QeCalc != null)
|
{
|
if (vm.QpCalc != null)
|
{
|
workPoint.P = vm.QpCalc.GetPointY(workPoint.Q);
|
workPoint.E = PumpCalcHelper.CalculateE(workPoint.Q, workPoint.H, workPoint.P);
|
}
|
else
|
{
|
workPoint.E = vm.QeCalc.GetPointY(workPoint.Q);
|
}
|
|
}
|
if (vm.QpCalc != null)
|
{
|
workPoint.P = vm.QpCalc.GetPointY(workPoint.Q);
|
}
|
_work_pt_txt_annot.Text = workInfoStringBuilder.ToString();
|
_work_pt_txt_annot.AutoSize = true;
|
|
if (OnCalcQueryPoint != null)
|
{
|
OnCalcQueryPoint(vm.Id, workPoint);
|
}
|
|
}
|
|
_work_pt_line.AxisValue = workQ;
|
_work_pt_line.Title.Text = workQ.Value.ToString("N1");
|
}
|
|
/// <summary>
|
/// 创建线系列
|
/// </summary>
|
private void CreateLineSeries(PumpVariableSpeedInfoViewModel vm)
|
{
|
var series_qh = new DevExpress.XtraCharts.Series();
|
series_qh.ArgumentScaleType = DevExpress.XtraCharts.ScaleType.Numerical;
|
series_qh.LabelsVisibility = DevExpress.Utils.DefaultBoolean.False;
|
series_qh.Name = _tag_qh + vm.Id.ToString();
|
series_qh.ShowInLegend = false;
|
series_qh.CrosshairEnabled = DefaultBoolean.False;
|
series_qh.Tag = vm.Id.ToString();
|
series_qh.ShowInLegend = true;
|
series_qh.LegendTextPattern = vm.Name;
|
|
var series_qh_view = new DevExpress.XtraCharts.SplineSeriesView();
|
series_qh_view.LineStyle.Thickness = 2;
|
series_qh_view.Color = vm.Color;
|
series_qh_view.EnableAntialiasing = DefaultBoolean.True;
|
|
series_qh.SeriesPointsSorting = SortingMode.None;
|
series_qh.SeriesPointsSortingKey = SeriesPointKey.Value_1;
|
series_qh.View = series_qh_view;
|
series_qh.Visible = _qh_visible;
|
|
var pointsQH = vm.QhCalc.GetPointList(12);
|
for (int i = 0; i < pointsQH.Count; i++)
|
{
|
series_qh.Points.Add(new SeriesPoint(pointsQH[i].X, new double[] { pointsQH[i].Y }));
|
}
|
|
var point_qh = pointsQH[pointsQH.Count() - 1];
|
var anchor_qh_pt = new DevExpress.XtraCharts.PaneAnchorPoint();
|
anchor_qh_pt.Pane = _pane_qh;
|
anchor_qh_pt.AxisXCoordinate.AxisValue = point_qh.X.ToString();
|
anchor_qh_pt.AxisYCoordinate.AxisValue = point_qh.Y.ToString();
|
|
var position_qh = new DevExpress.XtraCharts.RelativePosition();
|
position_qh.Angle = 30;
|
position_qh.ConnectorLength = 35;
|
|
var txt_qh = new TextAnnotation();
|
txt_qh.Border.Visibility = DefaultBoolean.False;
|
txt_qh.AnchorPoint = anchor_qh_pt;
|
txt_qh.AutoHeight = true;
|
txt_qh.AutoWidth = true;
|
txt_qh.BackColor = System.Drawing.Color.Transparent;
|
txt_qh.Border.Color = vm.Color;
|
txt_qh.ConnectorStyle = DevExpress.XtraCharts.AnnotationConnectorStyle.Line;
|
txt_qh.DXFont = Perform2dChartDisplay.AnnoFontQH;
|
txt_qh.Name = _tag_qh + vm.Id.ToString();
|
txt_qh.Padding.Bottom = 1;
|
txt_qh.Padding.Left = 1;
|
txt_qh.Padding.Right = 1;
|
txt_qh.Padding.Top = 1;
|
txt_qh.RuntimeAnchoring = false;
|
txt_qh.RuntimeMoving = true;
|
txt_qh.RuntimeResizing = false;
|
txt_qh.RuntimeRotation = false;
|
txt_qh.Text = LineNameShowHz ? vm.CurrentHz.ToString() : vm.CurrentSpeed.ToString(); ;
|
txt_qh.TextColor = vm.Color;
|
txt_qh.ShapePosition = position_qh;
|
txt_qh.Visible = _line_name_visible;
|
this.chartControl1.AnnotationRepository.Add(txt_qh);
|
this.chartControl1.Series.Add(series_qh);
|
|
if (vm.QeCalc != null)
|
{
|
var series_qe = new DevExpress.XtraCharts.Series();
|
series_qe.ArgumentScaleType = DevExpress.XtraCharts.ScaleType.Numerical;
|
series_qe.LabelsVisibility = DevExpress.Utils.DefaultBoolean.False;
|
series_qe.Name = _tag_qe + vm.Id.ToString();
|
series_qe.ShowInLegend = false;
|
series_qe.CrosshairEnabled = DefaultBoolean.False;
|
series_qe.Tag = vm.Id.ToString();
|
|
var series_qe_view = new DevExpress.XtraCharts.SplineSeriesView();
|
series_qe_view.LineStyle.Thickness = 2;
|
series_qe_view.Color = vm.Color;
|
series_qe_view.AxisY = _axis_y_qe;
|
series_qe_view.Pane = _pane_qe;
|
series_qe_view.EnableAntialiasing = DefaultBoolean.True;
|
|
series_qe.SeriesPointsSorting = SortingMode.None;
|
series_qe.SeriesPointsSortingKey = SeriesPointKey.Value_1;
|
series_qe.View = series_qe_view;
|
series_qe.Visible = _qe_visible;
|
|
var pointsQE = vm.QeCalc.GetPointList(12);
|
for (int i = 0; i < pointsQE.Count; i++)
|
{
|
series_qe.Points.Add(new SeriesPoint(pointsQE[i].X, new double[] { pointsQE[i].Y }));
|
}
|
|
this.chartControl1.Series.Add(series_qe);
|
}
|
|
if (vm.QpCalc != null)
|
{
|
var series_qp = new DevExpress.XtraCharts.Series();
|
series_qp.ArgumentScaleType = DevExpress.XtraCharts.ScaleType.Numerical;
|
series_qp.LabelsVisibility = DevExpress.Utils.DefaultBoolean.False;
|
series_qp.Name = _tag_qp + vm.Id.ToString();
|
series_qp.ShowInLegend = false;
|
series_qp.CrosshairEnabled = DefaultBoolean.False;
|
series_qp.Tag = vm.Id.ToString();
|
|
var series_qp_view = new DevExpress.XtraCharts.SplineSeriesView();
|
series_qp_view.LineStyle.Thickness = 2;
|
series_qp_view.Color = vm.Color;
|
series_qp_view.AxisY = _axis_y_qp;
|
series_qp_view.Pane = _pane_qp;
|
series_qp_view.EnableAntialiasing = DefaultBoolean.True;
|
|
series_qp.SeriesPointsSorting = SortingMode.None;
|
series_qp.SeriesPointsSortingKey = SeriesPointKey.Value_1;
|
series_qp.View = series_qp_view;
|
series_qp.Visible = _qp_visible;
|
|
var pointsQP = vm.QpCalc.GetPointList(12);
|
for (int i = 0; i < pointsQP.Count; i++)
|
{
|
series_qp.Points.Add(new SeriesPoint(pointsQP[i].X, new double[] { pointsQP[i].Y }));
|
}
|
|
this.chartControl1.Series.Add(series_qp);
|
}
|
|
}
|
|
/// <summary>
|
/// 创建装置系列
|
/// </summary>
|
public void CreateEqSeries(PumpVariableSpeedInfoViewModel vm, Yw.Geometry.Point2d design_pt)
|
{
|
this.chartControl1.BeginInit();
|
if (vm == null || design_pt == null)
|
{
|
ClearEqSeries();
|
return;
|
}
|
|
if (_vm_list == null || !_vm_list.Any())
|
{
|
ClearEqSeries();
|
return;
|
}
|
|
var eq_paras = EquipCurveHelper.CalcEquipCurve(vm.QhCalc, design_pt, out Yw.Geometry.Point2d sect_pt);
|
if (eq_paras == null)
|
{
|
ClearEqSeries();
|
return;
|
}
|
var eq = eq_paras.EquipCurve;
|
if (!eq.IsValid())
|
{
|
ClearEqSeries();
|
return;
|
}
|
|
vm.SectPoint = sect_pt;
|
|
_series_eq = new DevExpress.XtraCharts.Series();
|
_series_eq.ArgumentScaleType = DevExpress.XtraCharts.ScaleType.Numerical;
|
_series_eq.LabelsVisibility = DevExpress.Utils.DefaultBoolean.False;
|
_series_eq.Name = "eq";
|
_series_eq.ShowInLegend = false;
|
_series_eq.CrosshairEnabled = DefaultBoolean.False;
|
_series_eq.Tag = vm.Id.ToString();
|
|
|
var series_eq_view = new DevExpress.XtraCharts.SplineSeriesView();
|
series_eq_view.Color = vm.Color;
|
series_eq_view.AxisY = _axis_y_qh;
|
series_eq_view.Pane = _pane_qh;
|
series_eq_view.EnableAntialiasing = DefaultBoolean.True;
|
series_eq_view.LineStyle.DashStyle = DashStyle.Dash;
|
series_eq_view.LineStyle.Thickness = 2;
|
|
|
_series_eq.View = series_eq_view;
|
_series_eq.Visible = _cubic_spline_eq_visible;
|
|
var eq_pt_list = eq.GetPointList(12);
|
for (int i = 0; i < eq_pt_list.Count; i++)
|
{
|
_series_eq.Points.Add(new SeriesPoint(eq_pt_list[i].X, new double[] { eq_pt_list[i].Y }));
|
}
|
|
this.chartControl1.Series.Add(_series_eq);
|
|
_series_eq_pt = new DevExpress.XtraCharts.Series();
|
_series_eq_pt.ArgumentScaleType = DevExpress.XtraCharts.ScaleType.Numerical;
|
_series_eq_pt.LabelsVisibility = DevExpress.Utils.DefaultBoolean.False;
|
_series_eq_pt.Name = "eq_pt";
|
_series_eq_pt.ShowInLegend = false;
|
_series_eq_pt.CrosshairEnabled = DefaultBoolean.False;
|
_series_eq_pt.ShowInLegend = true;
|
_series_eq_pt.LegendTextPattern = "设计点";
|
_series_eq_pt.LabelsVisibility = DefaultBoolean.False;
|
|
|
var series_eq_pt_view = new DevExpress.XtraCharts.PointSeriesView();
|
//series_eq_pt_view.Color = vm.Color;
|
series_eq_pt_view.Pane = _pane_qh;
|
series_eq_pt_view.PointMarkerOptions.BorderColor = vm.Color;
|
series_eq_pt_view.PointMarkerOptions.Size = 15;
|
series_eq_pt_view.PointMarkerOptions.Kind = MarkerKind.ThinCross;
|
|
//_series_eq_pt.SeriesPointsSorting = SortingMode.None;
|
//_series_eq_pt.SeriesPointsSortingKey = SeriesPointKey.Value_1;
|
_series_eq_pt.View = series_eq_pt_view;
|
_series_eq_pt.Visible = _cubic_spline_eq_visible;
|
|
var series_pt = new SeriesPoint(sect_pt.X, new double[] { sect_pt.Y });
|
series_pt.Color = vm.Color;
|
_series_eq_pt.Points.Add(series_pt);
|
|
foreach (var item in _vm_list)
|
{
|
if (item.IsDefault)
|
{
|
continue;
|
}
|
var eq_paras_other = EquipCurveHelper.CalcEquipCurve(item.QhCalc, design_pt, out Yw.Geometry.Point2d sect_pt_other);
|
if (eq_paras_other == null || sect_pt_other == null)
|
{
|
continue;
|
}
|
item.SectPoint = sect_pt_other;
|
var series_pt_other = new SeriesPoint(sect_pt_other.X, new double[] { sect_pt_other.Y });
|
series_pt_other.Color = item.Color;
|
_series_eq_pt.Points.Add(series_pt_other);
|
}
|
|
this.chartControl1.Series.Add(_series_eq_pt);
|
this.chartControl1.EndInit();
|
}
|
|
|
|
|
/// <summary>
|
/// 清空装置系列
|
/// </summary>
|
private void ClearEqSeries()
|
{
|
if (_series_eq != null)
|
{
|
this.chartControl1.Series.Remove(_series_eq);
|
}
|
if (_series_eq_pt != null)
|
{
|
this.chartControl1.Series.Remove(_series_eq_pt);
|
}
|
if (_vm_list != null && _vm_list.Any())
|
{
|
_vm_list.ForEach(x => x.SectPoint = null);
|
}
|
_series_eq = null;
|
_series_eq_pt = null;
|
this.chartControl1.EndInit();
|
return;
|
}
|
|
|
#endregion
|
|
#region ChartEvent
|
|
// 右键对象
|
private object _rightClickObj = null;
|
private bool _onMoveWorkPointLine = false;
|
private void chartControl1_MouseDown(object sender, MouseEventArgs e)
|
{
|
if (!_initialData)
|
return;
|
var hitInfo = chartControl1.CalcHitInfo(e.Location);
|
if (e.Button == MouseButtons.Left)
|
{
|
if (hitInfo.InSeries)
|
{
|
_rightClickObj = hitInfo.Series;
|
|
}
|
else if (hitInfo.InAxis)
|
{
|
_rightClickObj = hitInfo.Axis;
|
}
|
else if (hitInfo.InConstantLine)
|
{
|
if (hitInfo.ConstantLine == _work_pt_line)
|
{
|
_onMoveWorkPointLine = true;
|
}
|
|
|
}
|
else if (hitInfo.InAnnotation)
|
{
|
_rightClickObj = hitInfo.Annotation;
|
}
|
else
|
{
|
_rightClickObj = null;
|
}
|
}
|
else if (e.Button == MouseButtons.Right)
|
{
|
if (hitInfo.InConstantLine)
|
{
|
this.popMenuLine.ShowPopup(MousePosition);
|
}
|
else
|
{
|
this.popMenuChart.ShowPopup(MousePosition);
|
}
|
}
|
}
|
|
private void chartControl1_MouseMove(object sender, MouseEventArgs e)
|
{
|
if (!_initialData)
|
return;
|
if (_onMoveWorkPointLine)
|
{
|
var diagramCoordinates = _main_chart_diagram.PointToDiagram(e.Location);
|
var axisValue = diagramCoordinates.GetAxisValue(_axis_x_q);
|
if (axisValue == null)
|
return;
|
double chartQ = axisValue.NumericalValue;
|
CalcWorkPointByQ(chartQ);
|
|
}
|
else
|
{
|
var hitInfo = chartControl1.CalcHitInfo(e.Location);
|
if (hitInfo.InConstantLine)
|
{
|
this.chartControl1.Cursor = Cursors.Hand;
|
}
|
else if (hitInfo.InAnnotation)
|
{
|
this.chartControl1.Cursor = Cursors.SizeAll;
|
}
|
else
|
{
|
this.chartControl1.Cursor = Cursors.Default;
|
}
|
}
|
}
|
|
private void chartControl1_MouseUp(object sender, MouseEventArgs e)
|
{
|
if (!_initialData)
|
return;
|
_onMoveWorkPointLine = false;
|
}
|
|
private void chartControl1_Resize(object sender, EventArgs e)
|
{
|
CalcTextAnchorPoint();
|
}
|
#endregion
|
|
#region Right Click Menu
|
|
#region Event
|
private void barBtnSetAxisQValue_ItemClick(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
if (_vm_list == null || !_vm_list.Any())
|
return;
|
var dlg = new PumpAxisValueDlg();
|
dlg.SetBindingData();
|
dlg.VerifyValueChanged += (value) =>
|
{
|
if (value < _minQ || value > _maxQ)
|
return false;
|
CalcWorkPointByQ(value);
|
return true;
|
};
|
dlg.ShowDialog();
|
}
|
|
private void barCekLineVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
SetLineVisible(this.barCekLineVisible.Checked);
|
}
|
|
private void barCekCurveNameVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
SetCurveNameVisible(this.barCekCurveNameVisible.Checked);
|
}
|
|
|
private void barCekLegendVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
SetLegendVisible(this.barCekLegendVisible.Checked);
|
}
|
|
private void barCekSetAxisNameVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
SetAxisNameVisible(this.barCekSetAxisNameVisible.Checked);
|
}
|
|
private void barBtnSetChartAxis_ItemClick(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
SetChartAxis();
|
}
|
|
private void barCekCurveQHVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
_pane_qh.Visibility = _pane_qh.Visibility == ChartElementVisibility.Visible ? ChartElementVisibility.Hidden : ChartElementVisibility.Visible;
|
}
|
|
private void barCekCurveQEVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
_pane_qe.Visibility = _pane_qe.Visibility == ChartElementVisibility.Visible ? ChartElementVisibility.Hidden : ChartElementVisibility.Visible;
|
}
|
|
private void barCekCurveQPVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
_pane_qp.Visibility = _pane_qp.Visibility == ChartElementVisibility.Visible ? ChartElementVisibility.Hidden : ChartElementVisibility.Visible;
|
}
|
|
private void barCekCurveEQVisible_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
_cubic_spline_eq_visible = this.barCekCurveEQVisible.Checked;
|
if (_series_eq != null && _series_eq_pt != null)
|
{
|
_series_eq.Visible = _cubic_spline_eq_visible;
|
_series_eq_pt.Visible = _cubic_spline_eq_visible;
|
}
|
}
|
|
#endregion
|
|
/// <summary>
|
/// 设置工作点显示
|
/// </summary>
|
public void SetLineVisible(bool visible)
|
{
|
if (!_initialData)
|
return;
|
LineVisible = visible;
|
CalcWorkPointByQ();
|
}
|
|
|
/// <summary>
|
/// 设置曲线名
|
/// </summary>
|
public void SetCurveNameVisible(bool visible)
|
{
|
if (!_initialData)
|
return;
|
_line_name_visible = visible;
|
for (int i = 1; i < this.chartControl1.AnnotationRepository.Count; i++)
|
{
|
var anno = this.chartControl1.AnnotationRepository[i];
|
anno.Visible = _line_name_visible;
|
}
|
}
|
|
/// <summary>
|
/// 设置图例显示
|
/// </summary>
|
public void SetLegendVisible(bool visible)
|
{
|
this.chartControl1.Legend.Visibility = visible ? DefaultBoolean.True : DefaultBoolean.False;
|
}
|
|
/// <summary>
|
/// 设置轴名称显示
|
/// </summary>
|
public void SetAxisNameVisible(bool visible)
|
{
|
_axis_x_q.Title.Visibility = visible ? DefaultBoolean.True : DefaultBoolean.False;
|
_axis_y_qh.Title.Visibility = visible ? DefaultBoolean.True : DefaultBoolean.False;
|
_axis_y_qe.Title.Visibility = visible ? DefaultBoolean.True : DefaultBoolean.False;
|
_axis_y_qp.Title.Visibility = visible ? DefaultBoolean.True : DefaultBoolean.False;
|
}
|
|
/// <summary>
|
/// 设置坐标轴
|
/// </summary>
|
public void SetChartAxis()
|
{
|
var dlg = new PumpChartCoordinateDlg();
|
dlg.SetBindingData(_coordinate_paras);
|
dlg.OnChangedCoord += (rhs) =>
|
{
|
_coordinate_paras = rhs;
|
CalcChartAxis();
|
this.OnCurveCoordinateChanged?.Invoke(_coordinate_paras);
|
};
|
dlg.ShowDialog();
|
}
|
|
/// <summary>
|
///
|
/// </summary>
|
private void SetShowHz()
|
{
|
this.LineNameShowHz = this.barCekShowHz.Checked;
|
if (_vm_list == null || !_vm_list.Any())
|
return;
|
foreach (var vm in _vm_list)
|
{
|
if (this.LineNameShowHz)
|
{
|
SetInfo(vm.Id, vm.CurrentHz.ToString(), vm.Color);
|
}
|
else
|
{
|
SetInfo(vm.Id, vm.CurrentSpeed.ToString(), vm.Color);
|
}
|
}
|
}
|
|
#endregion
|
|
#region Get
|
|
/// <summary>
|
/// 获取曲线列表
|
/// </summary>
|
public void GetCubicSplineList(out List<Tuple<Yw.Geometry.CubicSpline2d, Yw.Geometry.CubicSpline2d, Yw.Geometry.CubicSpline2d>> list)
|
{
|
list = null;
|
if (_vm_list == null || !_vm_list.Any())
|
return;
|
foreach (var item in _vm_list)
|
{
|
if (item.IsDefault)
|
continue;
|
var qh = item.QhCalc;
|
var qe = item.QeCalc;
|
var qp = item.QpCalc;
|
list.Add(new Tuple<Geometry.CubicSpline2d, Geometry.CubicSpline2d, Geometry.CubicSpline2d>(qh, qe, qp));
|
}
|
}
|
|
#endregion
|
|
#region Event
|
|
private void barBtnAddBySpeed_ItemClick(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
this.AddBySpeedEvent?.Invoke();
|
}
|
|
private void barBtnAddByHz_ItemClick(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
this.AddByHzEvent?.Invoke();
|
|
}
|
|
private void barBtnAddByPoint_ItemClick(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
this.AddByPointEvent?.Invoke();
|
}
|
|
private void barCekShowHz_CheckedChanged(object sender, DevExpress.XtraBars.ItemClickEventArgs e)
|
{
|
SetShowHz();
|
}
|
|
#endregion
|
|
|
}
|
|
}
|