ZedGraph控件生成饼图、拆线图和柱状图例程

这几天做了个自己觉得还蛮NB的功能,在GRID中选中一块数据,然后右键菜单即可生成三种图形,还可以互相切换,对了,饼图还添加了鼠标点击分离的处理,大致如图:

用的控件就是ZedGraph,我把它继承封装了一下,方便调用:

  1 Imports ZedGraph
  2 
  3 Public Class MyGraph
  4     '用于切换图型的
  5     Private dtSource As DataTable
  6 
  7     Private Function MyGraph_MouseDownEvent(ByVal sender As ZedGraph.ZedGraphControl, ByVal e As System.Windows.Forms.MouseEventArgs) As System.Boolean Handles MyBase.MouseDownEvent
  8 
  9         If e.Button = Windows.Forms.MouseButtons.Left Then
 10             Dim pane As GraphPane = sender.GraphPane
 11             Dim pt As New PointF(e.X, e.Y)
 12             Dim curve As CurveItem = Nothing
 13             Dim i%
 14             If pane.FindNearestPoint(pt, curve, i) Then
 15                 If curve.IsPie Then
 16                     Dim pi As PieItem = CType(curve, PieItem)
 17                     If pi.Displacement > 0 Then
 18                         pi.Displacement = 0
 19                     Else
 20                         pi.Displacement = 0.3
 21                     End If
 22                     sender.Refresh()
 23                 End If
 24             End If
 25         End If
 26         Return True
 27 
 28     End Function
 29 
 30     Public Sub SetTitle(ByVal title As String)
 31         '' Set the pane title
 32         GraphPane.Title.Text = title
 33     End Sub
 34 
 35     Public Sub SetPieDataB(ByVal dt As DataTable, ByVal title As String)
 36 
 37         '为多列一行的数据,按列分块,不支持切换,不推荐使用
 38 
 39         Dim ds As New DataSet
 40         Dim i, j As Integer
 41         Dim cc, rc As Integer
 42 
 43         rc = dt.Rows.Count
 44         cc = dt.Columns.Count
 45         If rc = 0 Or cc = 0 Then Return
 46 
 47         GraphPane.CurveList.Clear()
 48         GraphPane.GraphObjList.Clear()
 49         GraphPane.Legend.IsVisible = True
 50         GraphPane.Legend.Position = LegendPos.Right
 51         GraphPane.Legend.FontSpec.Size = 7
 52         If String.IsNullOrEmpty(title) = False Then
 53             GraphPane.Title.Text = title
 54         End If
 55 
 56         Dim labels(cc - 1) As String
 57         Dim values(cc - 1) As Double
 58 
 59         For i = 0 To cc - 1
 60             labels(i) = dt.Columns(i).ColumnName
 61             values(i) = dt.Rows(0).Item(i)
 62         Next
 63         'Dim colors() As Color = {Color.Red, Color.Blue, Color.Green, Color.Yellow, Color.Purple, Color.Brown, Color.Coral, Color.ForestGreen}
 64         Dim slices() As PieItem = GraphPane.AddPieSlices(values, labels)
 65         GraphPane.Fill = New Fill(Color.Cornsilk)
 66         GraphPane.Chart.Fill = New Fill(Color.Cornsilk)
 67         'GraphPane.Fill = New Fill(Color.White, Color.Goldenrod, 45.0F)
 68 
 69         For i = 0 To cc - 1
 70             slices(i).LabelType = PieLabelType.Name_Value_Percent
 71         Next
 72 
 73         GraphPane.AxisChange()
 74         Refresh()
 75         dtSource = Nothing
 76         FlowLayoutPanel1.Controls.Clear()
 77 
 78     End Sub
 79 
 80     Public Sub SetPieData(ByVal dt As DataTable, ByVal title As String)
 81 
 82         'TABLE内容应为第一列为各块名称,第二列为各块的值,不能只有一列
 83 
 84         Dim ds As New DataSet
 85         Dim i, j As Integer
 86         Dim cc, rc As Integer
 87 
 88         rc = dt.Rows.Count
 89         cc = dt.Columns.Count
 90         If rc = 0 Or cc <= 1 Then Return
 91 
 92         GraphPane.CurveList.Clear()
 93         GraphPane.GraphObjList.Clear()
 94         GraphPane.Legend.IsVisible = True
 95         GraphPane.Legend.Position = LegendPos.Right
 96         GraphPane.Legend.FontSpec.Size = 7
 97         If String.IsNullOrEmpty(title) = False Then
 98             GraphPane.Title.Text = title
 99         End If
100 
101         Dim labels(rc - 1) As String
102         Dim values(rc - 1) As Double
103 
104         For j = 1 To cc - 1
105             For i = 0 To rc - 1
106                 labels(i) = dt.Rows(i).Item(0)
107                 values(i) = dt.Rows(i).Item(j)
108             Next
109             'Dim colors() As Color = {Color.Red, Color.Blue, Color.Green, Color.Yellow, Color.Purple, Color.Brown, Color.Coral, Color.ForestGreen}
110             Dim slices() As PieItem = GraphPane.AddPieSlices(values, labels)
111             GraphPane.Fill = New Fill(Color.Cornsilk)
112             GraphPane.Chart.Fill = New Fill(Color.Cornsilk)
113             'GraphPane.Fill = New Fill(Color.White, Color.Goldenrod, 45.0F)
114 
115             For i = 0 To rc - 1
116                 slices(i).LabelType = PieLabelType.Name_Value_Percent
117             Next
118         Next
119 
120         GraphPane.AxisChange()
121         Refresh()
122         dtSource = dt
123 
124         FlowLayoutPanel1.Controls.Clear()
125         AddButton("Curve", AddressOf btnCurve_Click)
126         AddButton("Bar", AddressOf btnBar_Click)
127 
128     End Sub
129 
130     Public Sub SetPieData(ByVal dt As DataTable)
131 
132         SetPieData(dt, "")
133 
134     End Sub
135 
136     Public Sub SetCurveData(ByVal dt As DataTable)
137         SetCurveData(dt, "", "", "")
138     End Sub
139 
140     Public Sub SetCurveData(ByVal dt As DataTable, ByVal title As String)
141         SetCurveData(dt, title, "", "")
142     End Sub
143 
144     Public Sub SetCurveData(ByVal dt As DataTable, ByVal title As String, ByVal xAxisTitle As String, ByVal yAxisTitle As String)
145 
146         'TABLE内容应为第一列为X轴值,第二列开始为Y轴数值,除非只有一列
147 
148         If dt Is Nothing Then Return
149 
150         Dim cc As Integer = dt.Columns.Count
151         Dim rc As Integer = dt.Rows.Count
152 
153         If rc = 0 Or cc = 0 Then Return
154 
155         GraphPane.CurveList.Clear()
156         GraphPane.GraphObjList.Clear()
157 
158         If String.IsNullOrEmpty(title) = False Then
159             GraphPane.Title.Text = title
160         End If
161         If String.IsNullOrEmpty(xAxisTitle) Then
162             GraphPane.XAxis.Title.Text = xAxisTitle
163         End If
164         If String.IsNullOrEmpty(yAxisTitle) Then
165             GraphPane.YAxis.Title.Text = yAxisTitle
166         End If
167 
168         GraphPane.Legend.IsVisible = cc > 1
169         GraphPane.Legend.Position = LegendPos.Top
170 
171         Dim values(rc - 1) As Double
172         Dim labels(rc - 1) As String
173 
174         Dim i%, j%, k%, b%
175         Dim alone As Boolean = cc = 1
176         '只有一列的情况下,X轴为序号
177         For i = 0 To rc - 1
178             If alone Then
179                 labels(i) = i + 1
180             Else
181                 labels(i) = dt.Rows(i).Item(0)
182             End If
183         Next
184 
185         Dim colors() As Color = {Color.Red, Color.Green, Color.Blue, Color.Orange, Color.Purple, Color.Pink}
186         Dim curve As LineItem
187         b = IIf(alone, 0, 1)
188         For j = b To dt.Columns.Count - 1
189             For i = 0 To dt.Rows.Count - 1
190                 values(i) = dt.Rows(i).Item(j)
191             Next
192             k = j - b
193             If k >= colors.Length Then
194                 k = j - b - colors.Length
195             End If
196             curve = GraphPane.AddCurve(dt.Columns(j).ColumnName, Nothing, values, colors(k), SymbolType.Circle)
197             curve.Line.Width = 2.5
198             curve.Line.IsAntiAlias = True
199             curve.Symbol.Fill = New Fill(Color.White)
200             curve.Symbol.Size = 8
201 
202             For i = 0 To curve.Points.Count - 1
203                 Dim pt As PointPair = curve.Points(i)
204                 Dim text As New TextObj(pt.Y.ToString("f2"), pt.X, pt.Y + GraphPane.YAxis.Scale.Max * 0.02, CoordType.AxisXYScale, AlignH.Left, AlignV.Center)
205                 text.ZOrder = ZOrder.A_InFront
206                 text.FontSpec.Size = 9
207                 text.FontSpec.Border.IsVisible = False
208                 text.FontSpec.Fill.IsVisible = False
209                 'text.FontSpec.Fill = new Fill( Color.FromArgb( 100, Color.White ) )
210                 text.FontSpec.IsItalic = True
211                 'text.FontSpec.Angle = 30  '字体倾斜度
212                 GraphPane.GraphObjList.Add(text)
213             Next
214 
215         Next
216         GraphPane.Chart.Fill = New Fill(Color.White, Color.FromArgb(255, Color.ForestGreen), 45.0F)
217 
218         GraphPane.XAxis.Scale.TextLabels = labels
219         GraphPane.XAxis.Type = AxisType.Text
220         GraphPane.XAxis.Scale.FontSpec.Size = 9
221         If labels.Length > 4 And labels(0).Length > 4 Then
222             GraphPane.XAxis.Scale.FontSpec.Angle = 30
223         End If
224         GraphPane.XAxis.IsVisible = True
225         GraphPane.YAxis.IsVisible = True
226         GraphPane.YAxis.MajorGrid.IsVisible = True
227 
228         GraphPane.AxisChange()
229         Refresh()
230         dtSource = dt
231 
232         FlowLayoutPanel1.Controls.Clear()
233         AddButton("Pie", AddressOf btnPie_Click)
234         AddButton("Bar", AddressOf btnBar_Click)
235 
236     End Sub
237 
238     Public Sub SetBarData(ByVal dt As DataTable)
239         SetBarData(dt, Nothing, Nothing, Nothing)
240     End Sub
241 
242     Public Sub SetBarData(ByVal dt As DataTable, ByVal title As String)
243         SetBarData(dt, title, Nothing, Nothing)
244     End Sub
245 
246     Public Sub SetBarData(ByVal dt As DataTable, ByVal title As String, ByVal xAxisTitle As String, ByVal yAxisTitle As String)
247 
248         'TABLE内容应为第一列为X轴值,第二列开始为Y轴数值,除非只有一列
249 
250         Dim cc As Integer = dt.Columns.Count
251         Dim rc As Integer = dt.Rows.Count
252 
253         If cc = 0 Or rc = 0 Then Return
254 
255         Dim x(rc - 1) As Double
256         Dim values(rc - 1) As Double
257         Dim labels(rc - 1) As String
258 
259         GraphPane.CurveList.Clear()
260         GraphPane.GraphObjList.Clear()
261         If String.IsNullOrEmpty(title) = False Then
262             GraphPane.Title.Text = title
263         End If
264         If String.IsNullOrEmpty(xAxisTitle) Then
265             GraphPane.XAxis.Title.Text = xAxisTitle
266         End If
267         If String.IsNullOrEmpty(yAxisTitle) Then
268             GraphPane.YAxis.Title.Text = yAxisTitle
269         End If
270         GraphPane.Legend.IsVisible = cc > 1
271         GraphPane.Legend.Position = LegendPos.Top
272 
273         Dim i%, j%, k%, b%
274         Dim alone As Boolean = cc = 1
275         Dim bi As BarItem
276 
277         '只有一列的情况下,X轴为序号
278         For i = 0 To rc - 1
279             If alone Then
280                 labels(i) = i + 1
281             Else
282                 labels(i) = dt.Rows(i).Item(0)
283             End If
284         Next
285 
286         If alone Then
287             For i = 0 To rc - 1
288                 x(i) = i + 1
289                 values(i) = dt.Rows(i).Item(0)
290             Next
291             bi = GraphPane.AddBar(dt.Columns(0).ColumnName, x, values, Color.Blue)
292             bi.Bar.Fill = New Fill(Color.Blue, Color.White, Color.Green)
293         Else
294             Dim colors() As Color = {Color.Red, Color.Green, Color.Blue, Color.Orange, Color.Purple, Color.Pink}
295 
296             For j = 1 To dt.Columns.Count - 1
297                 For i = 0 To rc - 1
298                     values(i) = dt.Rows(i).Item(j)
299                 Next
300                 k = j - 1
301                 If k >= colors.Length Then
302                     k = j - 1 - colors.Length
303                 End If
304                 bi = GraphPane.AddBar(dt.Columns(j).ColumnName, Nothing, values, colors(k))
305                 bi.Bar.Fill = New Fill(colors(k), Color.White, colors(k))
306             Next
307 
308             For i = 0 To bi.Points.Count - 1
309                 Dim pt As PointPair = bi.Points(i)
310                 Dim text As New TextObj(pt.Y.ToString("f2"), pt.X, pt.Y + GraphPane.YAxis.Scale.Max * 0.02, CoordType.AxisXYScale, AlignH.Left, AlignV.Center)
311                 text.ZOrder = ZOrder.A_InFront
312                 text.FontSpec.Size = 9
313                 text.FontSpec.Border.IsVisible = False
314                 text.FontSpec.Fill.IsVisible = False
315                 text.FontSpec.IsItalic = True
316                 GraphPane.GraphObjList.Add(text)
317             Next
318 
319         End If
320 
321         GraphPane.Chart.Fill = New Fill(Color.White, Color.FromArgb(255, Color.ForestGreen), 45.0F)
322 
323         'GraphPane.XAxis.Scale.TextLabels = labels
324         GraphPane.XAxis.Type = AxisType.Text
325         GraphPane.XAxis.Scale.FontSpec.Size = 9
326         If labels.Length > 4 And labels(0).Length > 4 Then
327             GraphPane.XAxis.Scale.FontSpec.Angle = 30
328         End If
329         GraphPane.XAxis.IsVisible = True
330         GraphPane.YAxis.IsVisible = True
331         GraphPane.YAxis.MajorGrid.IsVisible = True
332 
333         GraphPane.AxisChange()
334         Refresh()
335         dtSource = dt
336 
337         FlowLayoutPanel1.Controls.Clear()
338         AddButton("Pie", AddressOf btnPie_Click)
339         AddButton("Curve", AddressOf btnCurve_Click)
340 
341     End Sub
342 
343     Private Sub AddButton(ByVal text As String, ByVal clickEvent As EventHandler)
344         Dim btn As New Button
345         btn.Text = text
346         AddHandler btn.Click, clickEvent
347         FlowLayoutPanel1.Controls.Add(btn)
348     End Sub
349 
350     Private Sub btnPie_Click(ByVal sender As Object, ByVal e As System.EventArgs)
351         If dtSource Is Nothing Then Return
352 
353         SetPieData(dtSource, CType(sender, Button).Text)
354     End Sub
355 
356     Private Sub btnCurve_Click(ByVal sender As Object, ByVal e As System.EventArgs)
357         If dtSource Is Nothing Then Return
358 
359         SetCurveData(dtSource, CType(sender, Button).Text)
360     End Sub
361 
362     Private Sub btnBar_Click(ByVal sender As Object, ByVal e As System.EventArgs)
363         If dtSource Is Nothing Then Return
364 
365         SetBarData(dtSource, CType(sender, Button).Text)
366     End Sub
367 
368     Private Sub FinexGraph_Resize(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Resize
369         GraphPane.AxisChange()
370         Refresh()
371     End Sub
372 End Class

注意,我拖了个FlowLayoutPanel1放在控件最上面,放切换图型按钮的

调用方法很简单,把它拖到FORM上,然后准备好数据源(datatable),完了调用控件的setxxxdata()方法即可,当然我这里是在GRID的菜单点击后弹出个窗口来显示的

原文地址:https://www.cnblogs.com/RobertTsing/p/ZadGraph_UserControl.html