|
|
@@ -0,0 +1,377 @@
|
|
|
+using OTSIncAReportGraph;
|
|
|
+using System;
|
|
|
+using System.Collections.Generic;
|
|
|
+using System.Drawing;
|
|
|
+using System.Linq;
|
|
|
+using System.Text;
|
|
|
+using System.Threading.Tasks;
|
|
|
+
|
|
|
+namespace OTSIncAReportGraph
|
|
|
+{
|
|
|
+ #region 颗粒分布图,排序图统一使用类
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 颗粒排序,能对颗粒进行分栏的类
|
|
|
+ /// </summary>
|
|
|
+ public class SortParticleDistribution : ICloneable
|
|
|
+ {
|
|
|
+ private List<DisplayParticle> list_dparticle = new List<DisplayParticle>();
|
|
|
+ private RectangleF m_rectf;
|
|
|
+ private string m_showstr = "";
|
|
|
+ private float m_size_min = 0;
|
|
|
+ private float m_size_max = 0;
|
|
|
+
|
|
|
+ public SortParticleDistribution()
|
|
|
+ { }
|
|
|
+
|
|
|
+ //构造函数
|
|
|
+ SortParticleDistribution(List<DisplayParticle> inlist_dparticle, SortParticleDistribution in_spd)
|
|
|
+ {
|
|
|
+ m_rectf = in_spd.m_rectf;
|
|
|
+ m_showstr = in_spd.m_showstr;
|
|
|
+ m_size_min = in_spd.m_size_min;
|
|
|
+ m_size_max = in_spd.m_size_max;
|
|
|
+
|
|
|
+ foreach (DisplayParticle e in inlist_dparticle)
|
|
|
+ {
|
|
|
+ list_dparticle.Add(e.Clone() as DisplayParticle);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 克隆方法
|
|
|
+ /// </summary>
|
|
|
+ /// <returns></returns>
|
|
|
+ public object Clone()
|
|
|
+ {
|
|
|
+ return new SortParticleDistribution(this.list_dparticle, this);
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 多边形图数组
|
|
|
+ /// </summary>
|
|
|
+ public List<DisplayParticle> List_DParticle
|
|
|
+ {
|
|
|
+ get { return list_dparticle; }
|
|
|
+ set { list_dparticle = value; }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 整个分类Grid的位置
|
|
|
+ /// </summary>
|
|
|
+ public RectangleF RectF
|
|
|
+ {
|
|
|
+ get { return m_rectf; }
|
|
|
+ set { m_rectf = value; }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 该分类Grid显示的文字
|
|
|
+ /// </summary>
|
|
|
+ public string ShowStr
|
|
|
+ {
|
|
|
+ get { return m_showstr; }
|
|
|
+ set { m_showstr = value; }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 该Grid保存多边形范围的最小值
|
|
|
+ /// </summary>
|
|
|
+ public float Size_Min
|
|
|
+ {
|
|
|
+ get { return m_size_min; }
|
|
|
+ set { m_size_min = value; }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 该Grid保存多边形范围的最大值
|
|
|
+ /// </summary>
|
|
|
+ public float Size_Max
|
|
|
+ {
|
|
|
+ get { return m_size_max; }
|
|
|
+ set { m_size_max = value; }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 获取多边形Grid内,所有多边形所占有的行数,用于其它计算使用
|
|
|
+ /// </summary>
|
|
|
+ /// <returns></returns>
|
|
|
+ public int GetDParticleRowNumber()
|
|
|
+ {
|
|
|
+ int RowsNumber = 0;
|
|
|
+
|
|
|
+ //首先获取所有多边形的宽度之和
|
|
|
+ float f_all_dparticle_widthsum = 0;
|
|
|
+ foreach (DisplayParticle dp in this.list_dparticle)
|
|
|
+ {
|
|
|
+ f_all_dparticle_widthsum = f_all_dparticle_widthsum + dp.Rect.Width;
|
|
|
+ }
|
|
|
+
|
|
|
+ //然后除以自身的宽度+1,就是所有的行数了
|
|
|
+ float f_rowsnumber = f_all_dparticle_widthsum / this.RectF.Width + 1;
|
|
|
+
|
|
|
+ RowsNumber = Convert.ToInt32(f_rowsnumber);
|
|
|
+ return RowsNumber;
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 获取多边形分栏,分栏的高度
|
|
|
+ /// </summary>
|
|
|
+ /// <returns></returns>
|
|
|
+ public float GetSortGridHeight()
|
|
|
+ {
|
|
|
+ float i_SortGridHeight = 0;
|
|
|
+ int i_RowNumber = GetDParticleRowNumber();
|
|
|
+ //再获取所有的颗粒中,最长的
|
|
|
+ float i_heightmax = 0;
|
|
|
+ float i_ls_height = 0;
|
|
|
+ foreach (DisplayParticle dp in this.list_dparticle)
|
|
|
+ {
|
|
|
+ float ls_y = 0;//用来判断y坐标是否有变化,好用来计算长度
|
|
|
+ foreach (DisplaySegment ds in dp.DSegments)
|
|
|
+ {
|
|
|
+ if (ds.Rect.Y != ls_y)
|
|
|
+ {
|
|
|
+ //i_ls_height++;
|
|
|
+ ls_y = ds.Rect.Y;
|
|
|
+
|
|
|
+ //如果需要考虑笔宽缩放的话,目前这样写,效果还没有出现问题
|
|
|
+ i_ls_height = i_ls_height + ds.Rect.Height * ds.PenWidthAndHeight;
|
|
|
+ }
|
|
|
+ if (i_heightmax < i_ls_height)
|
|
|
+ {
|
|
|
+ i_heightmax = i_ls_height;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ i_ls_height = 0;
|
|
|
+ }
|
|
|
+
|
|
|
+ //用最高的颗粒*行数,来计算整个grid的高度
|
|
|
+ i_SortGridHeight = i_RowNumber * (i_heightmax + 10) + 20;//因为每行都额外增加了10点的高度
|
|
|
+
|
|
|
+ //应该当grid最小大于=50
|
|
|
+ if (i_SortGridHeight < 50)
|
|
|
+ {
|
|
|
+ i_SortGridHeight = 50;
|
|
|
+ }
|
|
|
+
|
|
|
+ return i_SortGridHeight;
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 根据传入的2个多边形list,从大到小进行排序,两个多边形list通过guid保持一致
|
|
|
+ /// 主要用于计算list与old_list能进行相同顺序的排序
|
|
|
+ /// </summary>
|
|
|
+ /// <param name="list_dparticle"></param>
|
|
|
+ /// <param name="old_list_dparticle"></param>
|
|
|
+ public void SortDParticleBySizeFromBigToSmall(List<DisplayParticle> list_dparticle, List<DisplayParticle> old_list_dparticle)
|
|
|
+ {
|
|
|
+ //首先分别将两个多边形list保存起来
|
|
|
+ List<DisplayParticle> list_dp1 = new List<DisplayParticle>();
|
|
|
+ List<DisplayParticle> list_dp2 = new List<DisplayParticle>();
|
|
|
+ foreach (DisplayParticle ls_dp in list_dparticle)
|
|
|
+ {
|
|
|
+ DisplayParticle dp1 = ls_dp.Clone() as DisplayParticle;
|
|
|
+ list_dp1.Add(dp1);
|
|
|
+ }
|
|
|
+ foreach (DisplayParticle ls_dp in old_list_dparticle)
|
|
|
+ {
|
|
|
+ DisplayParticle dp2 = ls_dp.Clone() as DisplayParticle;
|
|
|
+ list_dp2.Add(dp2);
|
|
|
+ }
|
|
|
+
|
|
|
+ //清除原先的两个多边形list
|
|
|
+ list_dparticle.Clear();
|
|
|
+ old_list_dparticle.Clear();
|
|
|
+
|
|
|
+ //嵌套2次循环
|
|
|
+ int icount = list_dp1.Count();
|
|
|
+ for (int i = 0; i < icount; i++)
|
|
|
+ {
|
|
|
+ //找出最大的
|
|
|
+ float f_max_size = 0;
|
|
|
+ Guid str_jlguid ;
|
|
|
+ DisplayParticle ls_dp = new DisplayParticle();
|
|
|
+ foreach (DisplayParticle ls_del_dp in list_dp1)
|
|
|
+ {
|
|
|
+ //通过包含的线,获取多边形的尺寸大小
|
|
|
+ ls_del_dp.FSize = ls_del_dp.GetSizeFormSegmentsAllWidth();
|
|
|
+
|
|
|
+ if (f_max_size < ls_del_dp.FSize)
|
|
|
+ {
|
|
|
+ f_max_size = ls_del_dp.FSize;
|
|
|
+ str_jlguid = ls_del_dp.guid;
|
|
|
+ ls_dp = ls_del_dp;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ //然后分别将两个该guid的多边形从list1,2中删除
|
|
|
+ list_dp1.Remove(ls_dp);
|
|
|
+
|
|
|
+ //再分别插入到原先的list,和old_list中
|
|
|
+ ls_dp.Rect = ls_dp.GetRectFromDSegment();
|
|
|
+ list_dparticle.Add(ls_dp);
|
|
|
+ }
|
|
|
+
|
|
|
+ //换种方法,按Guid将list2中对应的再添加到old_list中
|
|
|
+ foreach (DisplayParticle ls_dp in list_dparticle)
|
|
|
+ {
|
|
|
+ foreach (DisplayParticle ls_dp2 in list_dp2)
|
|
|
+ {
|
|
|
+ if (ls_dp2.guid == ls_dp.guid)
|
|
|
+ {
|
|
|
+ ls_dp2.Rect = ls_dp2.GetRectFromDSegment();
|
|
|
+ old_list_dparticle.Add(ls_dp2);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 根据传入的2个多边形list,从小到大进行排序,两个多边形list通过guid保持一致
|
|
|
+ /// 主要用于计算list与old_list能进行相同顺序的排序
|
|
|
+ /// </summary>
|
|
|
+ /// <param name="list_dparticle"></param>
|
|
|
+ /// <param name="old_list_dparticle"></param>
|
|
|
+ public void SortDParticlesBySizeFromSmallToBig(List<DisplayParticle> list_dparticle, List<DisplayParticle> old_list_dparticles)
|
|
|
+ {
|
|
|
+ //首先分别将两个多边形list保存起来
|
|
|
+ List<DisplayParticle> list_dp1 = new List<DisplayParticle>();
|
|
|
+ List<DisplayParticle> list_dp2 = new List<DisplayParticle>();
|
|
|
+ foreach (DisplayParticle ls_dp in list_dparticle)
|
|
|
+ {
|
|
|
+ DisplayParticle dp1 = ls_dp.Clone() as DisplayParticle;
|
|
|
+ list_dp1.Add(dp1);
|
|
|
+ }
|
|
|
+ foreach (DisplayParticle ls_dp in old_list_dparticles)
|
|
|
+ {
|
|
|
+ DisplayParticle dp2 = ls_dp.Clone() as DisplayParticle;
|
|
|
+ list_dp2.Add(dp2);
|
|
|
+ }
|
|
|
+
|
|
|
+ //清除原先的两个多边形list
|
|
|
+ list_dparticle.Clear();
|
|
|
+ old_list_dparticles.Clear();
|
|
|
+
|
|
|
+ //嵌套2次循环
|
|
|
+ int icount = list_dparticle.Count();
|
|
|
+ for (int i = 0; i < icount; i++)
|
|
|
+ {
|
|
|
+ //找出最小的
|
|
|
+ float f_min_size = 10000000;
|
|
|
+ Guid str_jlguid ;
|
|
|
+ DisplayParticle ls_dp = new DisplayParticle();
|
|
|
+ foreach (DisplayParticle ls_del_dp in list_dp1)
|
|
|
+ {
|
|
|
+ //通过包含的线,获取多边形的尺寸大小
|
|
|
+ ls_del_dp.FSize = ls_del_dp.GetSizeFormSegmentsAllWidth();
|
|
|
+
|
|
|
+ if (f_min_size > ls_del_dp.FSize)
|
|
|
+ {
|
|
|
+ f_min_size = ls_del_dp.FSize;
|
|
|
+ str_jlguid = ls_del_dp.guid;
|
|
|
+ ls_dp = ls_del_dp;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ //然后分别将两个该guid的多边形从list1,2中删除
|
|
|
+ list_dp1.Remove(ls_dp);
|
|
|
+
|
|
|
+ //再分别插入到原先的list,和old_list中
|
|
|
+ list_dparticle.Add(ls_dp);
|
|
|
+ }
|
|
|
+
|
|
|
+ //换种方法,按Guid将list2中对应的再添加到old_list中
|
|
|
+ foreach (DisplayParticle ls_dp in list_dparticle)
|
|
|
+ {
|
|
|
+ foreach (DisplayParticle ls_dp2 in list_dp2)
|
|
|
+ {
|
|
|
+ if (ls_dp2.guid == ls_dp.guid)
|
|
|
+ {
|
|
|
+ old_list_dparticles.Add(ls_dp2);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 颗粒排序方法2
|
|
|
+ /// </summary>
|
|
|
+ /// <param name="in_f_zoom_record"></param>
|
|
|
+ public void SortParticle222(float in_f_zoom_record)
|
|
|
+ {
|
|
|
+ float f_ls_x = this.m_rectf.X + 3 * in_f_zoom_record;
|
|
|
+ float f_ls_y = this.m_rectf.Y + 3 * in_f_zoom_record;
|
|
|
+ foreach (DisplayParticle dp in this.list_dparticle)
|
|
|
+ {
|
|
|
+ dp.Rect = dp.GetRectFromDSegment();
|
|
|
+
|
|
|
+ if ((f_ls_x + dp.Rect.Width + 6) > this.m_rectf.Width + this.m_rectf.X)
|
|
|
+ {
|
|
|
+ f_ls_x = this.m_rectf.X + 3 * in_f_zoom_record;
|
|
|
+ f_ls_y = f_ls_y + this.GetSortGridHeight() / this.GetDParticleRowNumber() - 5;
|
|
|
+ }
|
|
|
+
|
|
|
+ float f_cz_x = f_ls_x - dp.Rect.X;
|
|
|
+ float f_cz_y = f_ls_y - dp.Rect.Y;
|
|
|
+ foreach (DisplaySegment ds in dp.DSegments)
|
|
|
+ {
|
|
|
+ ds.Rect = new RectangleF(ds.Rect.X + f_cz_x, ds.Rect.Y + f_cz_y, ds.Rect.Width, ds.Rect.Height);
|
|
|
+ }
|
|
|
+ f_ls_x = f_ls_x + dp.Rect.Width + 3 * in_f_zoom_record;
|
|
|
+
|
|
|
+ dp.Rect = dp.GetRectFromDSegment();
|
|
|
+ dp.GPath = dp.GetRegionFromDSegments();
|
|
|
+ dp.SmallRect = dp.GetSmallRectangleFromRect();
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /// <summary>
|
|
|
+ /// 对已经存入的颗粒信息,按定位好的rect位置,重新给line和各参数,重新进行计算
|
|
|
+ /// 就是在分栏的Grid中对多边形进行摆放
|
|
|
+ /// </summary>
|
|
|
+ public void SortDParticle(float in_f_zoom_record)
|
|
|
+ {
|
|
|
+ //设置增长的x,y轴值,+3是跳过边框的位置, 可能有个别情况,会在右侧突出占到边框的位置上
|
|
|
+ float f_ls_x = this.m_rectf.X + 3 * in_f_zoom_record;
|
|
|
+ float f_ls_y = this.m_rectf.Y + 3 * in_f_zoom_record;
|
|
|
+ foreach (DisplayParticle dp in this.list_dparticle)
|
|
|
+ {
|
|
|
+ //这里要对不显示的颗粒进行屏蔽,也就是进行不计算位置,不知道会不会有其它的影响
|
|
|
+ if (dp.displayState != DisplayState.NODISPLAY)
|
|
|
+ {
|
|
|
+ //首先确定各多边形的矩形位置
|
|
|
+ dp.Rect = dp.GetRectFromDSegment();
|
|
|
+
|
|
|
+ //判断是否已经达到了x的边缘,是的话,那么y轴进行增长,判断x轴+颗粒的宽度+6的相当于边框宽度的差值补值,大于grid宽度时
|
|
|
+ //在增长前就判断宽度,防止部份多边形突出到分栏外
|
|
|
+ if ((f_ls_x + dp.Rect.Width + 6) > this.m_rectf.Width + this.m_rectf.X)
|
|
|
+ {
|
|
|
+ //还原x到该分栏Grid的左边框+3的位置,并且将y轴定位到下一高度的y轴位置
|
|
|
+ f_ls_x = this.m_rectf.X + 3 * in_f_zoom_record;
|
|
|
+ f_ls_y = f_ls_y + this.GetSortGridHeight() / this.GetDParticleRowNumber() - 5;//在获取高度时,已经+10,所以这里再-5,颗粒近一些
|
|
|
+ }
|
|
|
+
|
|
|
+ //计算出与定位的Grid的差值,然后重新排序线,用分栏Grid-颗粒的外Rect,取到x,y的差值
|
|
|
+ float f_cz_x = f_ls_x - dp.Rect.X;
|
|
|
+ float f_cz_y = f_ls_y - dp.Rect.Y;
|
|
|
+ //获取到差值后,再对该多边形下面的所有线进行调整
|
|
|
+ foreach (DisplaySegment ds in dp.DSegments)
|
|
|
+ {
|
|
|
+ ds.Rect = new RectangleF(ds.Rect.X + f_cz_x, ds.Rect.Y + f_cz_y, ds.Rect.Width, ds.Rect.Height);
|
|
|
+ }
|
|
|
+ //定位好该多边形后,对x轴进行增长,为下一个多边形定位好位置
|
|
|
+ f_ls_x = f_ls_x + dp.Rect.Width + 3 * in_f_zoom_record;
|
|
|
+
|
|
|
+ //重新计算sort_ap的
|
|
|
+ dp.Rect = dp.GetRectFromDSegment();
|
|
|
+ //通过line获取路径边缘
|
|
|
+ dp.GPath = dp.GetRegionFromDSegments();
|
|
|
+ //重新计算小矩形边框
|
|
|
+ dp.SmallRect = dp.GetSmallRectangleFromRect();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+}
|
|
|
+#endregion
|