Using The MSChart Control in VB 6

Download as doc, pdf, or txt
Download as doc, pdf, or txt
You are on page 1of 12

Using the MSChart Control

The MSChart control allows you to plot data in charts according to your specifications. You can
create a chart by setting data in the controls properties page, or by retrieving data to be plotted
from another source, such as a Microsoft Excel spreadsheet. The information in this topic focuses
on using an Excel worksheet as a data source.

Possible Uses
To chart dynamic data, such as current prices of selected commodities.

To plot stored data, such as product prices, for graphic analysis of trends.

Plot Data Using Arrays and the ChartData Property


The simplest way of plotting a chart is to create an array of numeric values, and then set the
ChartData property to the array, as shown in the following example:

' This code might be pasted into the Load event


' of a Form that has an MSChart control named
' "MSChart1".
Dim arrPrices(1 to 10)
Dim i As Integer
For i = 1 to 10
arrPrices(i)= i * 2
Next i
MSChart1.ChartData = arrPrices

The code above produces a simple, single-series chart. A series in a chart, is set of related data
points. For example, a typical series might be the prices of a commodity over the course of a year.
The chart below shows a single-series chart.

To create a more complex, multi-series chart, you must create a multi-dimensioned array, as shown
in the following example:

' The number of series are determined by the second


' dimension. In this example, the chart will have two
' series, with five data points in each series.

1
Dim arrPriceQuantity(1 to 5, 1 to 2)
Dim i as Integer
For i = 1 to 5
arrPriceQuantity(i, 1) = i ' Series 1
arrPriceQuantity(i, 2) = 0 - i ' Series 2
Next i
MsChart1.ChartData = arrPriceQuantity

This will produce the following chart:

Adding Labels to the Chart

When you create a multi-dimensioned array, the first series can be assigned a string; when the
array is assigned to the ChartData property, the strings become the labels for the rows. The
following code shows this feature.

Dim arrValues(1 to 5, 1 to 3)
Dim i as Integer
For i = 1 to 5
arrValues(i, 1) = "Label " & i ' Labels
arrValues(i, 2) = 0 + i ' Series 1 values.
arrValues(i, 3) = 2 * i ' Series 2 values.
Next i
MsChart1.ChartData = arrValues

The above code produces the chart shown below:

As you can see, creating a chart using the ChartData property can be quick and simple. However,
the problem with using an array is getting the data into the array. Most users of this kind of data
will probably prefer to use a spreadsheet program, such as Microsoft Excel, or perhaps a database
program, such as Microsoft Access, to store and retrieve the data.
2
Setting or Returning a Data Point
Once you have created a chart, using an array from a spreadsheet or other data source, you may
also want to set or return the value of a particular data point. This can be done by first setting the
Row and (if applicable) Column properties, then setting or returning the Data property. For
example, in a simple (single-series) chart, the following code would change the third data point.

With MSChart1
' Change third data point to 50.
.Row = 3
.Data = 50
End With

If the chart has more than one series use the Column property to designate the series, then set the
Row and Data properties as above.

With MSChart1
' Set the second data point of the fourth series
' to 42.
.Column = 4
.Row = 2
.Data = 42
End With

Using the PointActivated Event to Change a Data Point

If you've started to explore the MSChart control, you will notice that it has a large number of
events. These events allow you to program the chart to respond to practically any action of the
user. As an example of this programmability, the PointActivated event is used in the following
example to show how a data point can be changed using the Series and DataPoint parameters. (The
PointActivated event occurs whenever a data point is double-clicked.) The Series and DataPoint
parameters correspond to the Column and Row properties, and can thus be used to set the Data
property:

Private Sub MSChart1_PointActivated(Series As _


Integer, DataPoint As Integer, MouseFlags As _
Integer, Cancel As Integer)
With MSChart1
.Column = Series
.Row = DataPoint
.Data = InputBox _
("Change the data point:", , .Data)
End With
End Sub

Manipulating the Chart Appearance


The MSChart control has many visible parts, all of which can be programmed. To get a grasp on
how this is accomplished, it's useful to examine the following figure pointing out the parts of a
chart.

3
Each of these parts has a corresponding object in the MSChart control which can be used to change
the format of practically any element of the chart. For example, the code below dramatically
changes the look of a chart by changing the colors of the Plot object.

Private Sub cmdFormat_Click()


' First, change the chart type to a 3D chart to
' see all the parts of the plot.
MSChart1.chartType = VtChChartType3dArea

' Color the backdrop light blue using


' the Plot object.
With MSChart1.Plot.Backdrop
' No color will appear unless you set the style
' property to VtFillStyleBrush.
.Fill.Style = VtFillStyleBrush
.Fill.Brush.FillColor.Set 100, 255, 200
' Add a border.
.Frame.Style = VtFrameStyleThickInner
' Set style to show a shadow.
.Shadow.Style = VtShadowStyleDrop
End With

' Color the wall of the plot yellow.


With MSChart1.Plot
' Set the style to solid.
.Wall.Brush.Style = VtBrushStyleSolid
' Set the color to yellow.
.Wall.Brush.FillColor.Set 255, 255, 0
End With

With MSChart1.Plot ' Color the plot base blue.


.PlotBase.BaseHeight = 200
.PlotBase.Brush.Style = VtBrushStyleSolid
.PlotBase.Brush.FillColor.Set 0, 0, 255
End With
End Sub

Formatting Fonts

A very basic task with fonts might be to set the text of the chart's title. In order to do this, use the
Title object's Text property:

MSChart1.Title.Text = "Year End Summary"

4
This is simple enough. The next question is how to change the font's attributes.

In order to format any text attribute on the chart, you must use the VtFont object. For example, to
format the title, the following code will work:

With MSChart1.Title.VtFont
.Name = "Algerian"
.Style = VtFontStyleBold
.Effect = VtFontEffectUnderline
.Size = 14
.VtColor.Set 255, 0, 255
End With

You can use the same technique with other parts of chart. The only difference lies in the object
model. For example, to format the text attributes of the Legend area use the following code:

MSChart1.Legend.VtFont.Size = 18

Change the Scale Using the Type Property

To change the scale of the plot, you must specify that the y axis of the chart is going to be changed
(changing the x axis has no visible effect). A convenient way to change the scale is to use a
ComboBox control, as shown in the following code:

Private Sub Form_Load()


' Configure a ComboBox control named cmbScale.
With cmbScale
.AddItem "Log"
.AddItem "Percent"
.AddItem "Linear"
.ListIndex = 0
End With
End Sub

Private Sub cmbScale_Click()


' The ComboBox has three items: Log, Percent,
' and Linear (the default scale).

Select Case cmbScale.Text


Case "Log"
MSChart1.Plot.Axis(VtChAxisIdY) _
.AxisScale.Type = VtChScaleTypeLogarithmic

' You must specify a LogBase to be used when


' switching the scale to Log. The base can be
' set to any value between 2 and 200.
MSChart1.Plot.Axis(VtChAxisIdY).AxisScale _
.LogBase = 10

Case "Percent"
MSChart1.Plot.Axis(VtChAxisIdY).AxisScale _
.Type = VtChScaleTypePercent
' Set the PercentBasis to one of six types. For
' the sake of expediency, only one is shown.
MSChart1.Plot.Axis(VtChAxisIdY).AxisScale _
.PercentBasis = VtChPercentAxisBasisMaxChart

Case "Linear"
MSChart1.Plot.Axis(VtChAxisIdY).AxisScale _
.Type = VtChScaleTypeLinear
5
End Select
End Sub

Change the Color of MSChart Objects Using the


CommonDialog Control
You may wish to allow the user to pick the colors assigned to chart elements (such as the color of
series) using the CommonDialog control. In that case, you can use the following functions that
mask the bytes returned by the CommonDialog control's Color property to return individual red,
green, and blue values required by the Set method.

' Paste these functions into the Declarations section


' of the Form or Code Module.
Public Function RedFromRGB(ByVal rgb As Long) _
As Integer
' The ampersand after &HFF coerces the number as a
' long, preventing Visual Basic from evaluating the
' number as a negative value. The logical And is
' used to return bit values.
RedFromRGB = &HFF& And rgb
End Function

Public Function GreenFromRGB(ByVal rgb As Long) _


As Integer
' The result of the And operation is divided by
' 256, to return the value of the middle bytes.
' Note the use of the Integer divisor.
GreenFromRGB = (&HFF00& And rgb) \ 256
End Function

Public Function BlueFromRGB(ByVal rgb As Long) _


As Integer
' This function works like the GreenFromRGB above,
' except you don't need the ampersand. The
' number is already a long. The result divided by
' 65536 to obtain the highest bytes.
BlueFromRGB = (&HFF0000 And rgb) \ 65536
End Function

Using the functions in the preceding examples, you can take the Long value returned by the
CommonDialog object, and set the color of MSChart objects. The example below allows the user
to change the color of a Series by double-clicking it:

Private Sub MSChart1_SeriesActivated(Series As _


Integer, MouseFlags As Integer, Cancel As Integer)
' The CommonDialog control is named dlgChart.
Dim red, green, blue As Integer
With dlgChart ' CommonDialog object
.ShowColor
red = RedFromRGB(.Color)
green = GreenFromRGB(.Color)
blue = BlueFromRGB(.Color)
End With

' NOTE: Only the 2D and 3D line charts use the


' Pen object. All other types use the Brush.

If MSChart1.chartType <> VtChChartType2dLine Or _


MSChart1.chartType <> VtChChartType3dLine Then
6
MSChart1.Plot.SeriesCollection(Series). _
DataPoints(-1).Brush.FillColor. _
Set red, green, blue
Else
MSChart1.Plot.SeriesCollection(Series).Pen. _
VtColor.Set red, green, blue
End If
End Sub

Three-Dimensional Features of the MSChart


Control
You can use the MSChart control's three-dimensional chart features to lend a certain sparkle to a
report.

Rotate the Chart


You can manually rotate a 3D chart by using the CTRL key and the mouse. To do this, hold down
the CTRL key, click on the chart, then hold down the mouse as you drag across the chart image.
The following figures show the same chart, before and after rotation.

Before Rotation

7
After Rotation

Rotating the Chart Programmatically

You can also rotate a 3D chart by using the Set method of the View3D object.

MSChart1.Plot.View3D.Set 10,100

Seeing the Light


In addition to rotating a 3D chart, you can also use the Light feature to control how a virtual light
shines on the chart. In practice, the appearance of a chart changes as it rotates because its surfaces
reflect steady light in continually changing angles.

By default, the chart comes with one LightSource. The following code will set the four parameters
that affect the LightSource. These will be explained later. In the meantime, paste the code into a
standard EXE project, and run it.

Private Sub Form_Load()


With MSChart1
.chartType = VtChChartType3dArea
.Plot.Light.LightSources(1).Set 10, 10, 10, 1
End With
End Sub

This code results in a chart that appears to have a light source shining on it from the lower left of
the screen. As the chart is rotated, surfaces which face the light directly get brighter.

8
Light Basics
The LightSource feature is comprised of two parts:

Ambient light: As its name suggests, this is light that has no specific source and thus no
directionality.

LightSources: a directional light that can be shone on the chart from any angle, with
variable intensity. More than one light source can be created.

Ambient Light

Ambient light has a noticeable effect when you are using the LightSources. Ambient light simply
bathes the chart evenly in a light that comes from no particular direction. You can set the
AmbientIntensity property to any value between 0 and 1, with 0 turning off the light, and 1
increasing it to its maximum. For instance, to turn the ambient on to one quarter of its brightness,
set the AmbientIntensity property to .25.

Tip As you experiment with the LightSources, it is useful to set the property to 0. With no
ambient light, the effect of the LightSource is accentuated.

The EdgeVisible and EdgeIntensity properties work together to highlight the edges of the chart.
When the AmbientIntensity is set to a low value, you can set the EdgeIntensity property to a high
value. The result is that the edges seem to glow, as shown in the following figure:

LightSources

Each LightSource in the LightSources collection has an Intensity property which like the
AmbientIntensity property you can set to a value between 0 and 1. This property sets the
brightness of the individual LightSource.

Each LightSource also can be positioned in the virtual space that surrounds the chart by setting the
X, Y, and Z properties. By varying these properties, you can specify the direction from which the
light will shine on the chart.

9
Using the Add Method to Add a LightSource
By default, the MSChart contains one LightSource member in the LightSources collection. You
can, however, add LightSource members using the Add method, as shown below:

MSChart1.Plot.Light.LightSources.Add 10, 10, 10, 1

The parameters for the Add method include values for X, Y, and Z, which allow you to specify
exactly the angle from which the light will shine, and a value for Intensity of the light.

Data Binding the MSChart Control


The Microsoft Chart control is a data bound control, and allows you to graphically represent
numeric data. Unlike other data bound controls, however, the Chart control cannot be used with the
Remote Data Control, or the Data control. It can be used with the ADO Data Control, an ADO
Recordset, and the Data Environment. This example will show how to open an ADO Recordset
that contains the fields you want to display, and set the Chart control's DataSource property to the
Recordset object. If the first field contains string data, that data will be used as the X axis labels.

The example below shows three series of data by first creating a Recordset object that has four
fields; the first field contains the labels for the X axis, and remaining fields are displayed as series
data.

Option Explicit
' Be sure to set a reference to the Microsoft ActiveX Data
' Objects 2.0 Library.
Private rsProducts As New ADODB.Recordset
Private cn As New ADODB.Connection

Private Sub Form_Load()


Dim strQuery As String ' SQL query string.

' First change the path to a valid path for your machine.
cn.ConnectionString = _
"Provider=Microsoft.Jet.OLEDB.3.51;Data Source=" & _
"C:\Program Files\Microsoft Visual Studio\VB98\nwind.mdb" ' <-Change this
path.

' Open the connection.


cn.Open

' Create a query that retrieves only four fields.


strQuery = "SELECT ProductName, UnitPrice, " & _
"UnitsInStock, UnitsOnOrder FROM Products WHERE SupplierID = 1"
' Open the recordset.
rsProducts.Open strQuery, cn, adOpenKeyset
' Set the DataSource to the recordset.
With MSChart1
.ShowLegend = True
Set .DataSource = rsProducts
End With
End Sub

10
Using an Excel Worksheet to Populate an
Array
If you have data stored in an Excel worksheet, you can use the GetObject method to get a reference
to the workbook that contains the worksheet, then retrieve the values using the reference. To first
get the reference, the only argument needed is the path to the workbook, as shown below:

' Place this code in the Declarations section.


Option Explicit
' If you are using Office 97, be sure to set a
' reference to Microsoft Excel 8.0 Object Library.
' If you are using Office 95, set a reference to
' Microsoft Excel 5.0 Object Library, and declare
' the variable as a Worksheet.
Dim wkbObj As WorkBook ' Declare an object variable.

Private Sub Form_Load()


' Then set the variable with the GetObject method.
Set wkbObj = GetObject _
("C:\My Documents\MySpread.xls")
End Sub

Note In order to use Excel objects, you must set a reference to the Excel Objects library. To do
this, click the Project menu, then click References. Search for the Excel Objects library and
double-click it. Click OK. Also, note that if you're using GetObject with the Excel 5.0 Object
Library, you must declare the variable as a WorkSheet; if you are using the Excel 8.0 Object
Library, declare the variable as a WorkBook.

After setting a reference to the Excel object library, you can use the reference to walk through the
Excel object model, populating the array with data from the worksheet. To do this, use the Range
method in conjunction with the Value property to get the data from any single cell in a spreadsheet.

Dim arrPrices (1 to 7)
Dim i As Integer
For i = 1 to 7
' Fill the array with seven values from column B of
' the worksheet.
arrPrices(i) = wkbObj.Worksheets(1) _
.Range("B" & i + 1).Value
Next i

If you're not familiar with Excel spreadsheets, the following figure shows where the values are
coming from.

Typical Excel Spreadsheet

11
The layout of a spreadsheet, and the method used to refer to its cells, also maps conveniently to the
method of referring to data points in the MSChart control. For example, a "column" in a
spreadsheet (as in column "B" in the preceding illustration) corresponds to a "column" in the
MSChart. And when you create a multi-series chart, each column corresponds to a series.
Similarly, the "row" of a spreadsheet corresponds to the "row" in a "column" in the MSChart. For
this reason, it helps to engineer a chart with a spreadsheet in mind.

For example, just as we first created a multi-series chart by increasing the dimensions of the array,
we can now fill the array by using more than one column of the worksheet. In other words, to
create a multi-series chart, we fill two (or more) columns of the spreadsheet with numbers, and use
the columns to fill an array, as illustrated in the following code:

Dim arrData (1 to 7, 1 to 2)
Dim i As Integer
For i = 1 to 7
' Values from column A fill the first series of the
' array. If these values are strings, they become
' the labels for the rows.
arrData(i, 1) = wkbObj.Worksheets(1) _
.Range("A" & i + 1).Value

' Then values from column B fill the second.


arrData(i, 2) = wkbObj.Worksheets(1) _
.Range("B" & i + 1).Value
Next i

Tip Use the CurrentRegion property to return the number of rows in an Excel column. You can
then use this number to specify the upper bound of the array's first dimension.

The preceding code, used in conjunction with the spreadsheet shown in the figure above, will
produce a chart that has each row labeled with the appropriate day of the week.

12

You might also like