Peltier Tech Blog

Excel Chart Add-Ins | Training | Custom Solutions | Charts and Tutorials | PTS Blog

 

Main menu:

 
Peltier Tech
Chart Add-Ins

Peltier Tech Waterfall Chart Utility
Peltier Tech Cluster-Stack Chart Utility
Peltier Tech Box and Whisker Chart Utility
Peltier Tech Marimekko Chart Utility
Peltier Tech Dot Plot Utility
Peltier Tech Cascade Chart Utility

 
Excel Dashboards

Subscribe

Site search

Subscribe

Site search


Recent Posts

Recently Commented

Popular Posts

Archive


 

Categories


 

Privacy Policy

Creative Commons License
Licensed under a Creative Commons Attribution-Noncommercial-Share Alike 3.0 Unported License.

Build an Excel Add-In 4 – Create the Dialog

by Jon Peltier
Wednesday, January 13th, 2010
Peltier Technical Services, Inc., Copyright © 2010.
Licensed under a Creative Commons Attribution-Noncommercial-Share Alike 3.0 Unported License.

This is the fourth part of a series that shows the steps involved in building an Excel add-in. In Build an Excel Add-In 1 – Basic Routine I showed a VBA procedure that creates a regular chart from an arbitrary rectangular range, including from a pivot table. In Build an Excel Add-In 2 – Enhanced Functionality I turned modularized this routine, so it could be called from any code that passed the appropriate settings into the function as arguments. In Build an Excel Add-In 3 – Auxiliary Modular Functions I included an additional modular function which cleans up the chart created in the previous article’s code. Because this function is widely useful, it will be made more general in a future article, after this series is finished.

In this installment of the Build an Excel Add-In series, I will show how to create a custom dialog using a VBA UserForm, a set of controls, and related code.

Insert UserForm

The first step in building a dialog is to insert a UserForm. In the Visual Basic Editor (VBE) select the project in the Project Explorer pane, then from the Insert menu, choose UserForm.

Insert UserFrom from Menu

A new window is created, containing a blank UserForm.

New UserFrom

The UserForm is listed in the Project Explorer, in the Forms folder of the VB Project.

UserFrom Listed in the Project Explorer

A UserForm actually consists of two parts: the Designer window and the Code window. The code window contains all of the VBA procedures that make the dialog work. For example, in the code window you will find the code that responds to button clicks.

When the UserForm’s window is active, the Properties window can be used to edit the properties of the UserForm. For example, the name of the UserForm has been changed from UserForm1 (below left) to FPlotSetup (below right), and the caption has been changed from UserForm1 to PT Plotter.

Properties of the Original UserForm - - Properties of the Renamed UserForm

In addition to changing properties through the Properties window, the size of the dialog can be changed by dragging the white handles on the right and bottom edge of the UserForm.

Forms Controls

The blank UserForm shown above is transformed into the fully featured dialog shown below by adding and coding a set of controls. VBA offers a range of controls, and others can be used if additional capabilities are required. Care should be taken when using controls which are not built in, because of potential deployment complications.

Finished Add-In Dialog

The controls in this dialog are listed below, in top-down and left-to-right order:

  • lblChartData
  • refChartData
  • fraOrientation
    • optByRow
    • optByColumn
  • fraHeaders
    • txtHeaderRows
    • lblHeaderRows
    • txtHeaderColumns
    • lblHeaderColumns
  • fraChartType
    • optChartTypeXY
    • optChartTypeLine
    • optChartTypeBar
    • optChartTypeColumn
  • lblChartPosition
  • refChartPosition
  • lblChartPosition2
  • lblCopyright
  • btnOK
  • btnCancel

I have used a simple naming convention:

Three letter prefixes identify the type of control: lbl for label, ref for RefEdit, fra for frame, opt for option button, txt for text boxes, btn for command buttons (some developers use cmd for command button, but I think btn is more descriptive)). Not used in this dialog are chk for check box, mpg for multipage, lst for list box, cbo for combo box, scr for scroll bar, spn for spin button, img for image.

The purpose of each control is encoded into its name. For example, optChartTypeXY is for choosing the XY Chart Type option, refChartData is the RefEdit used to select the chart data, etc.

Controls Toolbox

When a UserForm is the active window, the Controls Toolbox appears. This is a toolbar-like window that contains VBA controls as well as other controls that you may have added.

Controls Toolbox

To add a control to the dialog, click on its icon in the Controls Toolbox. When the cursor is moved over the UserForm, it changes to a cross hair and the selected icon is shown below the icon to remind you what control you’re adding. Click and drag to draw a rectangle as large as the control you are adding.

Adding a Control to a UserForm

When you release the mouse, the control appears, highlighted with white resizing handles.

Control Added to a UserForm

After a control is added, its name and other properties can be set in the Property window, just as the name and caption of the UserForm itself were set.

Labels and Text Boxes

Labels simply contain text that guides the user through the dialog. The user cannot change the caption of a label, but the caption can be controlled by code in response to certain conditions.

Text boxes allow a user to specify values which can be represented as text. These values may be numerical, but it is up to the programmer to deal with number formats of entered and displayed numbers. In our dialog, text boxes are used to specify the number of header rows and columns in the chart source data.

Label and Text Box

Frames

Frames are used to give some order to the dialog, grouping together related controls. Our dialog has three frames, containing controls for selection of data orientation, header rows and columns, and chart type.

Option Buttons and Checkboxes

Option buttons are used to let a user select from among several options. All option buttons within a frame or with the same GroupName property are grouped together, such that only one can be true (selected) at once, and changing one to true automatically changes the others in its group to false. In this frame, only the XY option is selected.

Chart Type Frame with XY Option Selected

When the Line option is selected, the XY option is unselected.

Chart Type Frame with Line Option Selected

Check boxes are used to let a user set a true (checked) or false (unchecked) value. In the absence of event code in the UserForm, check box values are independent of each other.

UserForm Check Boxes

List Boxes and Combo Boxes

List boxes and combo boxes allow the user to select one or more items from a list. A list box is more user friendly because it shows the whole list (or at least a subset of the list) while the combo box only shows the selected item, unless the user clicks to expand the list.

List Box, Combo Box, and Expanded Combo Box

Command Buttons

Command Buttons allow a user to initiate an action, in our case, approving or canceling the session with the dialog. Clicking the button runs code that carries out the user’s command.

RefEdit Controls

RefEdit controls allow the user to select a range of cells with the mouse. While the user is selecting cells, the UserForm shrinks to the size of the RefEdit plus the title bar. The address of the selected range appears in the RefEdit and updates as the mouse is dragged, and the size of the selected range is displayed next to the cursor.

RefEdit in Minimized Dialog While Range is Selected

When the mouse is released, the UserForm returns to its original size, and the address remains in the RefEdit.

RefEdit Shows Address of Selected=

Read more about the RefEdit control in Using RefEdit Controls in Excel Dialogs.

Adding Code

There is a simple way to add code to the UserForm. Double click on a control, and the UserForm’s code window opens. An empty event procedure for the default method (action) of the control is added to the code window. For example, double clicking on the OK button adds the btnOK_Click event procedure stub to the code.

OK Button Click Event Procedure

You enter the code you want to run on the OK button click event into this procedure stub. The following shows a call to a function that validates the user’s selections. If selections are valid, the code hides the form, sending execution back to the procedure that showed the UserForm. If selections are invalid, the user sees a message and decides whether to continue or bail out.

OK Button Click Event Procedure

Notice the two dropdowns at the top of the code window. The selected control, btnOK, is shown in the left dropdown, and the Click event is shown in the right dropdown. You can use these dropdowns to select any event that’s available for any control. It’s a good idea to use these dropdowns to define your procedures, because some events include arguments, and the dropdowns will always get the arguments correct.

For example, the KeyDown event of a text box control includes the KeyCode (the ASCII code of the key that was pressed) and the Shift (whether Shift, Alt, and/or Ctrl were down when the key was pressed) arguments. When the procedure runs, Excel passes these values into the procedure, so the code knows which key was pressed, under which shift state.

Header Rows Textbox KeyDown Event Procedure

The UserForm code module can contain event procedures, as well as functions and subs that can be called by these event procedures. For example, the Validated function called by the btnOK_Click event is also found in the UserForm’s code. Procedures in the UserForm can also call procedures in other modules.

The Code Behind the Dialog

The complete listing of the Userform’s code is presented below.

The UserForm_Initialize event loads the selected range address into the RefEdit.

The Validated function checks the RefEdit for a valid range and the header text boxes for valid numbers of header rows and columns.

The various property procedures are used called by the main routine to extract information from the UserForm. I wrote about this technique in Property Procedures – Passing Information to and from Forms.

The mbCancel variable is True if the Cancel button is clicked. The Cancel property checks this variable and tells the main routine if the user canceled the dialog.

Option Explicit

Private mbCancel As Boolean

Private Sub btnCancel_Click()
  mbCancel = True
  Me.Hide
End Sub

Private Sub btnOK_Click()
  Dim sMessage As String
  Dim lResponse As VbMsgBoxResult

  If Validated(sMessage) Then
    mbCancel = False
    Me.Hide
  Else
    lResponse = MsgBox(sMessage, vbRetryCancel, "Invalid Information")
    If lResponse = vbCancel Then
      btnCancel_Click
    End If
  End If
End Sub

Public Property Get Cancel() As Boolean
  Cancel = mbCancel
End Property

Public Property Get DataOrientation() As XlRowCol
  Select Case True
    Case Me.optByColumn.Value
      DataOrientation = xlColumns
    Case Me.optByRow.Value
      DataOrientation = xlRows
  End Select
End Property

Public Property Get HeaderRows() As Long
  HeaderRows = Val(Me.txtHeaderRows.Text)
End Property

Public Property Get HeaderColumns() As Long
  HeaderColumns = Val(Me.txtHeaderColumns.Text)
End Property

Public Property Get ChartType() As XlChartType
  Select Case True
    Case Me.optChartTypeXY.Value
      ChartType = xlXYScatterLines
    Case Me.optChartTypeLine.Value
      ChartType = xlLineMarkers
    Case Me.optChartTypeBar.Value
      ChartType = xlBarClustered
    Case Me.optChartTypeColumn.Value
      ChartType = xlColumnClustered
  End Select
End Property

Public Property Get ChartDataRange() As Range
  Set ChartDataRange = Range(Me.refChartData.Text)
End Property

Public Property Get ChartPosition() As Range
  On Error Resume Next
  Set ChartPosition = Range(Me.refChartPosition.Text)
  On Error GoTo 0
End Property

Private Function Validated(sMsg As String) As Boolean

  ' Minimalist input validation

  Dim rTest As Range
  Dim iTest As Long

  Validated = True

  On Error Resume Next
  Set rTest = Range(Me.refChartData.Text)
  On Error GoTo 0
  If rTest Is Nothing Then
    Validated = False
    sMsg = "Invalid data range selected."
    GoTo ExitFunction
  End If

  iTest = Me.HeaderRows
  If iTest >= rTest.Rows.Count Then
    Validated = False
    sMsg = "Too many header rows specified."
    GoTo ExitFunction
  End If
  iTest = Me.HeaderColumns
  If iTest >= rTest.Columns.Count Then
    Validated = False
    If Len(sMsg) > 0 Then sMsg = sMsg & vbNewLine
    sMsg = sMsg & "Too many header columns specified."
    GoTo ExitFunction
  End If

ExitFunction:

End Function

Private Sub UserForm_Initialize()

  ' Define current range for RefEdit, if applicable

  Dim sAddress As String
  If TypeName(Selection) = "Range" Then
    If Selection.Cells.Count = 1 Then
      sAddress = Selection.CurrentRegion.Address(External:=True)
    Else
      sAddress = Selection.Address(External:=True)
    End If
    sAddress = Mid$(sAddress, InStr(sAddress, "]") + 1)
    If InStr(sAddress, "'") > 0 Then
      sAddress = "'" & sAddress
    End If
    Me.refChartData.Text = sAddress
  End If
End Sub

Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
  If CloseMode = vbFormControlMenu Then
    Cancel = True
    btnCancel_Click
  End If
End Sub

In the next article of the series, Build an Excel Add-In 5 – Tie the Code Together, we will develop code to call this dialog, extract the user selections, and produce a chart using these settings.

Contents: How to Build an Excel Add-In

Related Posts:

Bookmark and share this entry:
  • Twitter
  • Digg
  • Facebook
  • LinkedIn
  • del.icio.us
  • Technorati
  • StumbleUpon
  • Google Bookmarks
  • Reddit
  • MySpace
  • Slashdot
  • Yahoo! Buzz
  • Tumblr

Learn how to create Excel dashboards.

Comments


Comment from Mathias
Time: Wednesday, January 13, 2010, 2:15 pm

Hi Jon,

First, I think it’s great that you are going through with this tutorial from A to Z! I might give a shot at doing the same for VSTO.

Then, just one small addition: when adding controls to a user from, it’s a good idea to check the TabOrder property, which determines in what order each control gets the focus when the user presses Tab. I don’t use Tab much, and used not to pay attention to it, until some users of my stuff complained about that!

Mathias


Comment from Jon Peltier
Time: Wednesday, January 13, 2010, 2:35 pm

Mathias -

Right, tab order is important. So are accelerator keys. Perhaps a followup article could cover these aspects of good user interface design.

And by the way, I would like to see your VSTO article.


Comment from Jan Karel Pieterse
Time: Sunday, January 17, 2010, 11:00 am

One that is not very discoverable: You can drag (sets of) controls back onto the control toobox to store them for later re-use. NOte that you can right-click the toobox to add pages to it to store your own controls.


Comment from Jon Peltier
Time: Sunday, January 17, 2010, 11:20 am

Thanks, Jan Karel. In a while I will have another post or two about designing dialogs, more general than this post. I’ll include tricks like your Toolbox enhancements, and also suggestions for good UI design.


Comment from Kurt
Time: Friday, January 29, 2010, 7:34 pm

Hello Jon!

Thanks for this excellent series of articles.
Hope #6 will be published soon.

Write a comment

I welcome comments from my readers. If you have an opinion on this post, if you have a question or if there is anything to add, I want to hear from you. Whether you agree or disagree, please join the discussion.

If you want to include an image in your comment, post it on your own site or on one of the many free image sharing sites, and include a link in your comment. I'll download your image and insert the necessary html to display the image inline.

Read the PTS Blog Comment Policy.





Subscribe without commenting

Peltier Tech Waterfall Chart Utility Peltier Tech Cluster-Stack Chart Utility Peltier Tech Box and Whisker Chart Utility Peltier Tech Marimekko Chart Utility Peltier Tech Dot Plot Utility Peltier Tech Cascade Chart Utility

Create Excel dashboards quickly with Plug-N-Play reports.