using DevExpress.Drawing;
using DevExpress.XtraCharts;
using System.Data;
using Yw.EPAnet;
using Yw.Hydro;
namespace Yw.WinFrmUI
{
public partial class HydroSingleWorkingLossCurveCtrl : DevExpress.XtraEditors.XtraUserControl
{
public HydroSingleWorkingLossCurveCtrl()
{
InitializeComponent();
}
///
///
///
public event Action HydroClickEvent;
///
/// 绑定数据
///
public void SetBindingData
(
Yw.Model.HydroModelInfo hydroInfo,
HydroCalcuResult calcuResult,
Yw.Model.HydroVisualInfo visual
)
{
if (hydroInfo == null)
{
return;
}
var allVisualDict = hydroInfo.GetVisualDict();
var network = hydroInfo.ToNetwork();
if (network == null)
{
return;
}
var node = network.GetAllNodes()?.Find(x => x.Id == visual.Code);
if (node == null)
{
return;
}
var allPathList1 = network.AnalyzeUpstreamPath(node, calcuResult.EPAnetCalcuResult);
var allPathList2 = network.AnalyzeDownstreamPath(node, calcuResult.EPAnetCalcuResult);
var allPathList= allPathList1.Concat(allPathList2).ToList();
var allEpaLossList = network.GetChartNodeByPathLinks(allPathList, calcuResult.EPAnetCalcuResult);
var allNodeLossList = new List();
allEpaLossList?.ForEach(x =>
{
var visualNode = allVisualDict?.GetValue(x.Id);
if (visualNode != null)
{
allNodeLossList.Add(new HydroNodeLossViewModel(x, visualNode));
}
});
SetBindingData(allNodeLossList);
}
///
/// 绑定数据
///
public void SetBindingData(List allNodeLossList)
{
AutoFitAxises(allNodeLossList);
var allElevList = allNodeLossList?.Select(x => new HydroLossCurvePointVieModel(x.Code, x.Name, x.Distance, x.Elev)).ToList();
this.elevBindingSource.DataSource = allElevList;
var allLossList = new List();
allNodeLossList?.ForEach(x =>
{
allLossList.Add(new HydroLossCurvePointVieModel(x.Code, x.Name, x.Distance, x.StartHead));
allLossList.Add(new HydroLossCurvePointVieModel(x.Code, x.Name, x.Distance, x.EndHead));
});
this.lossBindingSource.DataSource = allLossList;
if (allNodeLossList != null && allNodeLossList.Count > 0)
{
var startHead = allNodeLossList.Max(x => x.StartHead);
var endHead = allNodeLossList.Min(x => x.EndHead);
var allHeadLoss = startHead - endHead;
var allMinorLoss = allNodeLossList.Sum(x => x.MinorLoss);
var allForLoss = allHeadLoss - allMinorLoss;
var sb = new StringBuilder();
sb.AppendLine($"水头损失:{allHeadLoss:N2}m");
sb.AppendLine($"局部损失:{allMinorLoss:N2}m");
sb.AppendLine($"沿程损失:{allForLoss:N2}m");
var anno = this.chartControl1.AnnotationRepository[0] as DevExpress.XtraCharts.TextAnnotation;
anno.Text = sb.ToString();
anno.AutoSize = true;
}
}
//自动适应刻度
private void AutoFitAxises(List allNodeLossList)
{
if (allNodeLossList == null || allNodeLossList.Count < 1)
{
return;
}
var diagram = this.chartControl1.Diagram as XYDiagram;
#region X轴
var allDistances = allNodeLossList.Select(x => x.Distance).Distinct().ToList();
var distanceMax = allDistances.Max();
diagram.AxisX.Tickmarks.MinorVisible = false;
diagram.AxisX.WholeRange.SideMarginsValue = 0;
if (distanceMax <= 10)
{
var maxValue = Math.Ceiling(distanceMax);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue;
diagram.AxisX.NumericScaleOptions.GridSpacing = 1;
}
else if (distanceMax <= 50)
{
var maxValue = Math.Ceiling(distanceMax / 10);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue * 10;
diagram.AxisX.NumericScaleOptions.GridSpacing = 5;
}
else if (distanceMax <= 100)
{
var maxValue = Math.Ceiling(distanceMax / 10);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue * 10;
diagram.AxisX.NumericScaleOptions.GridSpacing = 10;
}
else if (distanceMax <= 500)
{
var maxValue = Math.Ceiling(distanceMax / 100);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue * 100;
diagram.AxisX.NumericScaleOptions.GridSpacing = 50;
}
else if (distanceMax <= 3000)
{
var maxValue = Math.Ceiling(distanceMax / 100);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue * 100;
diagram.AxisX.NumericScaleOptions.GridSpacing = 100;
}
else if (distanceMax <= 5000)
{
var maxValue = Math.Ceiling(distanceMax / 1000);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue * 1000;
diagram.AxisX.NumericScaleOptions.GridSpacing = 200;
}
else if (distanceMax <= 10000)
{
var maxValue = Math.Ceiling(distanceMax / 1000);
diagram.AxisX.WholeRange.MinValue = 0;
diagram.AxisX.WholeRange.MaxValue = maxValue * 1000;
diagram.AxisX.NumericScaleOptions.GridSpacing = 1000;
}
else
{
}
#endregion
#region 压力
var allPressMinList = allNodeLossList.Select(x => Math.Min(Math.Min(x.StartHead, x.EndHead), x.Elev)).ToList();
var allPressMaxList = allNodeLossList.Select(x => Math.Max(Math.Max(x.StartHead, x.EndHead), x.Elev)).ToList();
var pressMin = allPressMinList.Min();
var pressMax = allPressMaxList.Max();
diagram.AxisY.Tickmarks.MinorVisible = false;
diagram.AxisY.WholeRange.SideMarginsValue = 0;
diagram.AxisY.CrosshairAxisLabelOptions.EnableAntialiasing = DevExpress.Utils.DefaultBoolean.True;
if (pressMax <= 10)
{
diagram.AxisY.WholeRange.MinValue = Math.Floor(pressMin);
diagram.AxisY.WholeRange.MaxValue = 10;
diagram.AxisY.NumericScaleOptions.GridSpacing = 1;
diagram.AxisY.VisualRange.SetMinMaxValues(0, 10);
}
else if (pressMax <= 100)
{
var maxValue = Math.Ceiling(pressMax / 10);
diagram.AxisY.WholeRange.MinValue = Math.Floor(pressMin);
diagram.AxisY.WholeRange.MaxValue = maxValue * 10;
diagram.AxisY.NumericScaleOptions.GridSpacing = 5;
diagram.AxisY.VisualRange.SetMinMaxValues(0, maxValue * 10);
}
else if (pressMax <= 3000)
{
var maxValue = Math.Ceiling(pressMax / 100);
diagram.AxisY.WholeRange.MinValue = Math.Floor(pressMin);
diagram.AxisY.WholeRange.MaxValue = maxValue * 100;
diagram.AxisY.NumericScaleOptions.GridSpacing = 50;
diagram.AxisY.VisualRange.SetMinMaxValues(0, maxValue * 100);
}
else if (pressMax <= 6000)
{
var maxValue = Math.Ceiling(pressMax / 1000);
diagram.AxisY.WholeRange.MinValue = Math.Floor(pressMin);
diagram.AxisY.WholeRange.MaxValue = maxValue * 1000;
diagram.AxisY.NumericScaleOptions.GridSpacing = 100;
diagram.AxisY.VisualRange.SetMinMaxValues(0, maxValue * 1000);
}
else
{
}
#endregion
}
//提示
private void chartControl1_CustomDrawCrosshair(object sender, CustomDrawCrosshairEventArgs e)
{
// Specify the crosshair argument line color, dash style and thickness.
e.CrosshairLineElement.Color = Color.Green;
e.CrosshairLineElement.LineStyle.DashStyle = DashStyle.DashDot;
e.CrosshairLineElement.LineStyle.Thickness = 3;
// Specify the back color for the crosshair argument axis label.
foreach (CrosshairAxisLabelElement axisLabelElement in e.CrosshairAxisLabelElements)
{
axisLabelElement.BackColor = Color.Blue;
axisLabelElement.Text = $"{axisLabelElement.AxisValue:N2}";
}
foreach (CrosshairElementGroup group in e.CrosshairElementGroups)
{
CrosshairGroupHeaderElement groupHeaderElement = group.HeaderElement;
var pt = group.HeaderElement.SeriesPoints.FirstOrDefault();
if (pt != null)
{
var model = pt.Tag as HydroLossCurvePointVieModel;
if (model != null)
{
groupHeaderElement.Text = model.Name;
}
}
// Specify the text, text color and font for the crosshair group header element.
groupHeaderElement.TextColor = Color.Green;
groupHeaderElement.DXFont = new DXFont("SegoeUI", 12, DXFontStyle.Bold);
//groupHeaderElement.Text = group.CrosshairElements[0].AxisLabelElement.Text;
foreach (var ele in group.CrosshairElements)
{
ele.AxisLabelElement.Text = $"{ele.AxisLabelElement.AxisValue:N1}";
ele.AxisLabelElement.DXFont = new DXFont(this.Font.Name, 6);
//ele.AxisLabelElement.Visible = false;
}
//// Obtain the first series.
//CrosshairElement element = group.CrosshairElements[0];
//// Specify the color, dash style and thickness for the crosshair value lines.
//element.LineElement.Color = Color.DarkViolet;
//element.LineElement.LineStyle.DashStyle = DashStyle.Dash;
//element.LineElement.LineStyle.Thickness = 2;
//// Specify the text color and back color for the crosshair value labels.
//element.AxisLabelElement.TextColor = Color.Red;
//element.AxisLabelElement.BackColor = Color.Yellow;
//// Format the text shown for the series in the crosshair cursor label. Specify the text color and marker size.
//element.LabelElement.TextColor = Color.Red;
//element.LabelElement.MarkerSize = new Size(15, 15);
//element.LabelElement.Text = $"高程:{element.SeriesPoint.Values[0]}m";
}
}
//点击事件
private void chartControl1_MouseClick(object sender, MouseEventArgs e)
{
ChartHitInfo hitInfo = this.chartControl1.CalcHitInfo(e.Location);
if (hitInfo.Series != null)
{
if (hitInfo.SeriesPoint != null)
{
var vm = hitInfo.SeriesPoint.Tag as HydroLossCurvePointVieModel;
if (vm != null)
{
this.HydroClickEvent?.Invoke(vm.Code);
}
}
}
}
///
/// 导出图片
///
public void ExportToImage(string filePath)
{
this.chartControl1.ExportToImage(filePath, DXImageFormat.Png);
}
}
}