C#实现chart控件图表的漫游

C#中的chart控件是非常强大的,可以轻松实现数据的可视化,用于自己的数据处理是非常方便的。
在我之前的一篇文章中,我讲了如何对chart中的数据进行框选、删除、平移等功能(详细见C#实现chart控件数据点的框选、删除、平移),这次我又新添加了一个功能,chart的漫游。我就是在自己处理数据过程中慢慢摸索,慢慢增加我的程序的功能,下面就来看看如何实现chart图表的漫游。
在chart中,有时需要放大查看数据,但是很容易出现下面的情况,数据超出显示范围了。
C#实现chart控件图表的漫游
虽然有滚动条按钮,但每次都要点滚动条,感觉也挺累的,而且不是很好控制滚动大小,所以我想到了要实现一个chart图表的漫游功能。
要实现漫游功能,需要了解chart坐标轴的一个属性,它就是数据视图位置属性。
C#实现chart控件图表的漫游
这个Position表示的是滚动条左端当前的视图位置,那么就容易想到,漫游功能的实现其实就是设置这个Position的值。根据我们的习惯,以X轴方向为例,当按住鼠标从右往左拖动时,chart的视图应该是从左向右移动,也就是往X轴变大的方向显示数据。那么我们只要记住按下鼠标时刻的坐标start.X和松开鼠标时刻的坐标end.X,两者做差,再加上当前的Position,就是漫游后新的Position的位置。代码表示就是

chart1.ChartAreas[0].AxisX.ScaleView.Position += start.X - end.X;

这里要注意,虽然根据实现方法是这样列出式子,但是等式两边的坐标系不同,左边的Position的坐标系是chart数据坐标系,而右边是chart控件坐标系,关于这两个坐标系的转换,可以通过上面的链接去看我上一篇文章的介绍,这里不再赘述。所以这里我们需要把chart控件坐标系转换到chart数据坐标系。根据反算公式,可以知道

chart1.Series[0].Point.XValue = chart1.ChartAreas[0].AxisX.ScaleView.ViewMinimum +
                    (x * 100.0 / (double)chart1.Width - (double)chart1.ChartAreas[0].InnerPlotPosition.X) / xpercent;

那么只要把XValue替换成Position,x替换成start.X-end.X,就是我们要求的新的Position,代码表示就是

chart1.ChartAreas[0].AxisX.ScaleView.Position = chart1.ChartAreas[0].AxisX.ScaleView.ViewMinimum +
                    ((double)(start.X - end.X) * 100.0 / (double)chart1.Width - (double)chart1.ChartAreas[0].InnerPlotPosition.X) / xpercent;

这就是X轴方向的漫游公式。
Y轴方向的漫游,类似X轴,但是很重要一点要注意,chart控件坐标系的Y轴和chart数据点坐标系的Y轴方向是相反的,前者向下为正,后者向上为正,所以在转换前,还需要把向下的坐标系转换到向上的方向上来,这个转换很简单,设同一个点,在chart控件坐标系中Y坐标是y2,在chart数据点坐标系中Y坐标是y1,那么就有

y1 = chart1.Height - y2

而且还有一点需要注意,鼠标从上往下拖动时,Y值其实是增大的,那么这里就和X轴相反了,是

chart1.ChartAreas[0].AxisY.ScaleView.Position += chart1.Height - (end.Y - start.Y);

再考虑坐标转换,完整的代码就是

chart1.ChartAreas[0].AxisY.ScaleView.Position = chart1.ChartAreas[0].AxisY.ScaleView.ViewMaximum -
                    ((double)(chart1.Height - end.Y + start.Y) * 100.0 / (double)chart1.Height - (double)chart1.ChartAreas[0].InnerPlotPosition.Y) / ypercent;

这样我们就可以实现chart图表的漫游功能啦。
下面给出漫游功能核心代码

Point start = new Point();
Point end = new Point();
private void chart1_MouseDown(object sender, MouseEventArgs e)
        {
            start.X = e.X;
            start.Y = e.Y;
        }
        
private void chart1_MouseUp(object sender, MouseEventArgs e)
        {
                double x_min = chart1.ChartAreas[0].AxisX.Minimum;
                double y_min = chart1.ChartAreas[0].AxisY.Minimum;
                double xpercent = (double)chart1.ChartAreas[0].InnerPlotPosition.Width / (chart1.ChartAreas[0].AxisX.ScaleView.ViewMaximum - chart1.ChartAreas[0].AxisX.ScaleView.ViewMinimum);
                double ypercent = (double)chart1.ChartAreas[0].InnerPlotPosition.Height / (chart1.ChartAreas[0].AxisY.ScaleView.ViewMaximum - chart1.ChartAreas[0].AxisY.ScaleView.ViewMinimum);
                //////计算Position的位置
                chart1.ChartAreas[0].AxisX.ScaleView.Position = chart1.ChartAreas[0].AxisX.ScaleView.ViewMinimum +
                    ((double)(start.X - end.X) * 100.0 / (double)chart1.Width - (double)chart1.ChartAreas[0].InnerPlotPosition.X) / xpercent;
                if (chart1.ChartAreas[0].AxisX.ScaleView.Position < x_min)
                    chart1.ChartAreas[0].AxisX.ScaleView.Position = x_min;

                chart1.ChartAreas[0].AxisY.ScaleView.Position = chart1.ChartAreas[0].AxisY.ScaleView.ViewMaximum -
                    ((double)(chart1.Height - end.Y + start.Y) * 100.0 / (double)chart1.Height - (double)chart1.ChartAreas[0].InnerPlotPosition.Y) / ypercent;
                if(chart1.ChartAreas[0].AxisY.ScaleView.Position < y_min)
                    chart1.ChartAreas[0].AxisY.ScaleView.Position = y_min;
         }

这里我定义了两个参数,x_min和y_min,是当数据视图拖动到数据最左边甚至超过最左边的数据时,控制视图在最小值处,防止出现如下情况。
C#实现chart控件图表的漫游
但是视图最大值处还不知道如何设置该参数,想用Position+ScrollBar的长度来表示,但是发现并没有参数能表示ScrollBar的长度,因此最右边我也就没有设置了,等以后想到了怎么解决再更新上来。或者有知道的小伙伴给我留言噢,谢谢。

C#实现chart控件图表的漫游C#实现chart控件图表的漫游 海的-心 发布了4 篇原创文章 · 获赞 0 · 访问量 248 私信 关注
上一篇:C# WinForm开发系列之chart控件画折线图和柱形图并自定义鼠标移动到数据标记点显示提示信息


下一篇:asp.net微软图表控件MsChart