Home
About me



 VBA Programming
Download my Add-In tool (run on 32-bit MS Office Excel)l
VBA Basic for beginners
Excel Main Objects
More with Rows, Columns, Cells, Range ...
Working around your Worksheet ...
Statements
Functions
Conditional Statements and Loops Structure
Errors Handling
UserForms
Pivot Tables
Charting
AutoFilter, Advanced Filter
File I/O VBA Examples
ADO and DAO, integrating Excel and Access
Other VBA fun staff

UserForm

These are Excel dialog boxes that allow you to display and allow you to get input from user, and to perform further task base on that information. First, you have to design the user form to have the correct functionality. Then you have to write the event code that are connected behind each of the UserForm’s controls in the VBE, that will respond appropriately to whatever the user selects on the user form. For example, when the user clicks on the Cancel button, the dialog box should disappear and unload userform. If the user clicks on the OK button, the user’s input should be captured to store in variables or in some other ways, and dialog box should also disappear.

MsgBox and InputBox functions


These two dialog boxes are the most common and simpler means of displaying information and getting user’s input. MsgBox function
displays information and waits for user to press a button before continuing, or it continues after an elapse of specified few seconds. MsgBox provides four buttons for you to configure from, including Yes, No, OK, and Cancel. You can configure the prompt, window title, and user Help files. The Syntax is:

MsgBox(prompt[, buttons] [, title] [, helpfile, context])

This example displays a message box with “Yes”,”No” and Cancel buttons for user to response, and using Select Case statement to execute action whenever each button is pressed.
Dim msg As String, response As String, btn As String, openfile As String
msg = " Want me to show you the directory of the text file?  ‘ define message
btn = vbYesNoCancel + vbExclamation + vbDefaultButton1   ‘ define buttons
response = MsgBox(msg, btn, "Action alert")
Select Case response
Case Is = vbYes        
' user chose Yes
    MsgBox "please select a text file", vbOKOnly
    openfile = Application.GetOpenFilename("Textfiles (*.txt),*.txt", , "")
    Workbooks.OpenText (openfile) 
' user chose Yes, it opens folder “My Documents” with all text files
Case Is = vbNo                     ‘ user chose No, it saves the current copy
    ActiveWorkbook.Save
Case Is = vbCancel      
' user chose Cancel, it stops the code from running
    Exit Sub
End Select


 

InputBox function requests some keystrokes input from user before the program can continue. You can configure the prompt, window title, a default value, window position and user Help files. InputBox provides only two buttons: OK and Cancel. The function returns a string value.

expression.InputBox(Prompt, Title, Default, Left, Top, HelpFile, HelpContextId, Type)

expression Required. An expression that returns an Application object.
Prompt Required String. The message to be displayed in the dialog box. This can be a string, a number, a date, or a Boolean value.
Title   Optional Variant. The title for the input box.
Default   Optional Variant. Specifies a value that will appear in the text box when the dialog box is initially displayed.
If it is omitted, the text box is left empty.
Left   Optional Variant. Specifies an x position for the dialog box in relation to the upper-left corner of the screen, in points.
Top   Optional Variant. Specifies a y position for the dialog box in relation to the upper-left corner of the screen, in points.
HelpFile   Optional Variant. The name of the Help file for this input box.
HelpContextId   Optional Variant. The context ID number of the Help topic in HelpFile.
Type   Optional Variant. Specifies the return data type. If this argument is omitted, the dialog box returns tex
t. If this argument is omitted, the dialog box returns text.

Type can be one or a sum of the following values. For example, for an input box that can accept both text and numbers, set Type to 1 + 2.

Value  Meaning
0 A formula
1 A number
2 Text (a string)
4 A logical value (True or False)
8 A cell reference, as a Range object
16 An error value, such as #N/A
64 An array of values


This prompts the user for a number.
Dim iNum As Byte
i
Num = Application.InputBox("Enter a number from 0 to 9")

This prompts the user to select a cell on the worksheet named "mySheet". You use it to obtain the column's letter of the selected cell.
Dim mycell As Range, C As String
  Sheets("mySheet").Activate
  Set mycell = Application.InputBox(prompt:="Select a cell:", Type:=8)
  C = myCell.EntireColumn.Address(False, False)
  C = Left(iC, InStr(1, iC, ":") - 1)
  MsgBox ("the Column's letter is: " & iC)


This prompts the user to select a range of cells instead of a single cell.
Dim Selectedarea As Range
  On Error Resume Next
TryAgain:
  Set Selectedarea = Application.InputBox(prompt:="Select the range of cells...", _
  Title:="SELECT RANGE AREA", Default:=Selection.Address, Type:=8)
     If Selectedarea Is Nothing Then
        MsgBox "You press Cancel, this procedure will now terminate."
        Exit Sub
     End If

     If Selectedarea.Cells.Count = 1 Then
        If MsgBox("Note:" & vbNewLine & _
           "You had selected only one cell. Please try again.", vbOKCancel) = vbOK Then
              GoTo TryAgain
        Else: Exit Sub
        End If
     Else: MsgBox "you selected range: " & Selectedarea.Address
     End If


The example below displays two input boxes asking input for a string value and the Row number you want to search from, then bold the cell that is found with the selected string value.
Dim rw As Long, str As String, addr1
str = InputBox("Enter the string to find")
rw = InputBox("Enter row letter to search")
Rows(rw & ":" & rw).EntireRow.Select
On Error GoTo handler:
Selection.Find(What:=str, After:=ActiveCell, LookIn:=xlFormulas, MatchCase:=False).Activate
addr1 = ActiveCell.Address
Range(addr).Font.Bold = True
handler:
If Err.Description <> "" Then
MsgBox "no match is found"

End If

 

The buttons argument settings are as in the table below. When adding numbers to create a final value for the buttons argument, use only one number from each group. The constants return values. 

Constant

Value

Description

vbOKOnly

0

Display OK button only

vbOKCancel

1

Display OK and Cancel buttons.

vbAbortRetryIgnore

2

Display Abort, Retry, and Ignore buttons.

vbYesNoCancel

3

Display Yes, No, and Cancel buttons.

vbYesNo

4

Display Yes and No buttons.

vbRetryCancel

5

Display Retry and Cancel buttons.

vbCritical

16

Display Critical Message icon. 

vbQuestion

32

Display Warning Query icon.

vbExclamation

48

Display Warning Message icon.

vbInformation

64

Display Information Message icon.

vbDefaultButton1

0

First button is default.

vbDefaultButton2

256

Second button is default.

vbDefaultButton3

 

Third button is default.

vbDefaultButton4

768

Fourth button is default.

vbApplicationModal

0

Application modal; the user must respond to the message box before continuing work in the current application.

vbSystemModal 

4096

System modal; all applications are suspended until the user responds to the message box.

 Note   These constants are specified by Visual Basic for Applications. As a result, the names can be used anywhere in your code in place of the actual values.

Constant

Value

Description

vbOK

1

OK

vbCancel

2

Cancel

vbAbort

3

Abort

vbRetry

4

Retry

vbIgnore

5

Ignore

vbYes

6

Yes

vbNo

7

No

 

Create a UserForm

UserForm combines the functionality of InputBox and MsgBox to allow a more efficient way of interacting with user. To insert a new UserForm, choose Insert | UserForm from the VBE menu bar. A blank UserForm and the ToolBox should appears.


Add Textbox, Combo Box and Label to the UserForm

The objects on a UserForm, such as buttons, and textboxes, are called Controls. To allow users to enter data, you can add textbox controls to the form, with label controls to describe them. To add controls to the form, click on the desired control in the toolbox, drag and draw it on the form. Controls can be resized and moved just as the userform itself.

Now click on the first label you created, then double-click on the Caption property in the Properties window and type: Part Number. Click on the TextBox to the right, then in the Properties window, double-click on Name property and type: txt_PartNumber. Now you have to repeat the above step for the remaining textboxes, combo box and labels. You would add: 

     a textbox named txt_CurrentTSL, with a label Current TSL Qty
     a textbox named txt_NewTSL, with a label New TSL Qty
     a combo box named cbo_Reason, with a label Reason for change
     a textbox named txt_Date, with a label Date of change

If the text boxes are not aligned, you can align them by dragging on the handle.

 

 

ListBox and ComboBox Controls
 
ListBox displays a list of values from which you select one or more. If the ListBox is bound to a data source, then the ListBox stores the selected value in that data source. The ListBox can either appear as a list or as a group of OptionButton controls or CheckBox controls.

ComboBox Control combines the features of a ListBox and a TextBox, and allows the user to enter a new value, or the user can select an existing value as with a ListBox.

The default name for the UserForms you created is called UserForm1, UserForm2, etc. It is a good practice to give the userform and its controls descriptive names because if you have multiple userforms, the default names can become a bit of pain in telling the difference. To rename UserForm1, in the Properties window, double-click on Name property -UserForm1at the top right of the window, and type: frm_TSLrecord. The userform name change in the Project Explorer, but the form still shows UserForm1 in its title bar. To change it from title bar, in the Properties window, double-click on the Caption property - UserForm1, and type: TSL Change Record. The title bar will now display the new caption.

 

Adding Frame, OptionButton and CheckBox to the UserForm

Using the Frame tool, you can draw a Frame. Then you draw the Option buttons to contain inside the frame. The frame is used to group the option buttons together that separates them from the text box controls on the userform. OptionButton Control show you whether a single item in a group is selected. If an OptionButton is bound to a data source, the OptionButton can show the value of that data source as either Yes/No, True/False, or On/Off. Depending on the value of the TripleState property, an OptionButton or a CheckBox can also have a null value. You can also use an OptionButton inside a group box to select one or more of a group of related items.

It is worth to take note of the TripleState Property and functionality. TripleState determines whether a user can specify, from the user interface, the Null state for a CheckBox or ToggleButton. Although the TripleState property exists on the OptionButton, the property is disabled. When the TripleState property is True, a user can choose from the values of Null, True, and False. The null value is displayed as a shaded button. When TripleState is False, the user can choose either True or False. A control set to Null does not initiate the Click event.

Next using the CheckBox tool, you draw a check box on the form. You would use a CheckBox to give the user a choice between two values such as Yes/No, True/False, or On/Off. A disabled CheckBox is dimmed and does not allow changes to the value as you see in the diagram below that the Enabled property is set to False.

To allow users to perform an action, you have to add command buttons to the user form. In the Toolbox, click on the  CommandButton button to draw on the userform. Select the CommandButton, double-click on the Name property in the Properties window and type: cmdAdd. Double-click on the Caption property and type: Add this part. Repeat the above steps to add another two command buttons named cmdCancel with a label Cancel, and cmdClearForm with a label Clear Form.

     a frame named FramLevel, with a label “Request From”
     an option button named opt_Customer, with a label “Customer”
     a textbox named opt_Field, with a label “Field Engineer”
     a textbox named opt_Division, with a label “Product Division”
     a checkbox named chk_Immediate, with a label “Immediate effect”
     a textbox named chk_NonCritical, with a label “Non-critical”
     a textbox named cmdAdd, with a label “Add this part”
     a textbox named cmdClearForm, with a label “Clear Form”

     a textbox named cmdCancel, with a label “Cancel”

 

Writing Event code for the UserForm

Events occur when the user does something such as – click on a button, enter text in textbox, click an option button, right-click on a cell, etc. Each of these events has a built-in event handler, where the subs are always available so that you can write appropriate code to it. Of course, there are other event handlers you want to ignore such as where the mouse is dragged over a command button.

Of all the VBA code I have shown you thus far are codes that you placed in standard modules. Event code is different which you have to place in the userform’s code window. To get to it, select View | Code from the VBE menu, or right-click on the UserForm and select View Code. Another way to get from the design window to the userform’s code window is to double-click on a control. This not only open the code window, but it also insert a private sub for the event code. The footer, header, and default action for the form’s control is automatically inserted for you. For example, when you double-click the Cancel button in design view, the following sub is inserted in the code window.
Private Sub cmdCancel_Click() 

End Sub

 

 

If you select other control from the Object drop-down view on the left, you would be able to see a list of other events that are available in the drop-down Properties. For example, if you select UserForm from the Object drop-down list, you would be able to see the event QueryClose at the drop-down list on the right, which I will explain to you in the next example.

If you click on the event item QueryClose, you will get the following private sub automatically inserted for you. You can not change the format of the sub and it must be named as shown below (control name, followed by an underscore, and the event type), and it must contain any arguments that are given.
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer) 

End Sub


If you like to prevent users from closing the form by clicking the X button on the top-right of the form, you would use the following example of event QueryClose of the UserForm Object. You place the following code in the userform’s code window.
Private Sub UserForm_QueryClose(Cancel As Integer, CloseMode As Integer)
  If CloseMode = vbFormControlMenu Then
     Cancel = True
     MsgBox "Please use the button to close"
  End If
End Sub


Show, Load, Hide and Unload the UserForm

A userform can be called from any module. Below is the Initialize event procedure for the userform frm_TSLrecord, sitting in the module. The Load method allows the userform to be loaded, but remains hidden. The Show method pops up the form you have just created.

Sub OpenTSLrecord_Form()
   Load frm_TSLrecord
   frm_TSLrecord.Show
End Sub


The Unload method unloads the form from memory and removes it from user’s view. The form is now no longer accessible by user. Select the cmdClose button, right-click and on the short-cut menu, choose View | Code, and type in this code:
Private Sub cmdCancel_Click()
   Unload frm_TSLrecord
End Sub


You can also use ‘Me’ which refers to the current object, and in this case, the active form
Private Sub cmdCancel_Click()
   Unload Me
End Sub


This is the Click event for frm_TSLrecord. Use the Hide method to hide the userform if you want. The form is still active but will be hidden from view.
Private Sub cmdHide_Click()
   frm_TSLrecord.Hide
End Sub

 

Introducing basic form Controls

Below is an example of asking input from the user, using the same userform that I have created in the previous example. After the text boxes are filled, combo box, option and check buttons are selected, and the user clicks OK, the information will be appended to a sheet as shown in the diagram. There are five event handlers: UserForm_Initialize, cmdAdd_Click, cmdClearForm_Click, cmdCancel_Click and chk_Immediate_Change. These event procedures would be placed in the form you have named as frm_TSLrecord. You can DOWNLOAD this example here.

Option Explicit

Sub UserForm_Initialize()
txt_PartNumber.Value = ""
txt_CurrentTSL.Value = ""
txt_NewTSL.Value = ""
With cbo_Reason
   .AddItem "Excess & Obsolescence"
   .AddItem "NPI IPP recommends"
   .AddItem "Globally slow-mover"
   .AddItem "GPP DSM SIMPLE-Opt"
   .AddItem "GPP PWS SIMPLE-Opt"
   .AddItem "GPP MDP SIMPLE-Opt"
   .AddItem "METRON SIMPLE-Opt"
End With
   cbo_Reason.Value = ""
txt_Date.Value = ""
opt_Customer = True
opt_Field = False
opt_Division = False
chk_Immediate = False
chk_NonCritical = False
txt_PartNumber.SetFocus
End Sub


Private Sub cmdAdd_Click()
Dim lastrow As Long
lastrow = Worksheets("datasheet").Range("A65536").End(xlUp).Row
ActiveWorkbook.Sheets("datasheet").Activate
Cells(lastrow, 1).Select
Do
  If IsEmpty(ActiveCell) = False Then
     ActiveCell.Offset(1, 0).Select
  End If
Loop Until IsEmpty(ActiveCell) = True
With txt_PartNumber
  If .Value = "" Then
     MsgBox "you must enter the part number"
     .SetFocus
     Exit Sub
  End If
End With
With txt_CurrentTSL
  If .Value = "" Or Not IsNumeric(.Value) Then
     MsgBox "Current TSL must be numeric and must not be blank"
     .SetFocus
     Exit Sub
  End If
End With
With txt_NewTSL
  If .Value = "" Or Not IsNumeric(.Value) Then
     MsgBox "New TSL must be numeric and must not be blank"
     .SetFocus
     Exit Sub
  End If
End With
With cbo_Reason
  If .ListIndex = -1 Then  
‘ -1 means no item is selected. ListIndex = 0 means first item is selected
     MsgBox "you must chose a reason for change from the list box"
     .SetFocus
     Exit Sub
  End If
End With
With txt_Date
    If .Value = "" Or Not IsDate(.Value) Then
        MsgBox "Date Changed must not be blank and must be date format"
        Me.txt_Date.SetFocus
        Exit Sub
    End If
End With
  If opt_Customer = True Then
     ActiveCell.Offset(0, 5).Value = "Customer"
  ElseIf opt_Field = True Then
     ActiveCell.Offset(0, 5).Value = "Field Engineer"
  Else
     ActiveCell.Offset(0, 5).Value = "Product Division"
  End If
  If chk_Immediate = True Then
     ActiveCell.Offset(0, 6).Value = "Yes"
  Else
     ActiveCell.Offset(0, 6).Value = ""
  End If
  If chk_NonCritical = True Then
     ActiveCell.Offset(0, 7).Value = "Yes"
  Else
     If chk_NonCritical = False Then
        ActiveCell.Offset(0, 7).Value = ""
     Else
        ActiveCell.Offset(0, 7).Value = "No"
     End If
  End If
ActiveCell.Value = txt_PartNumber.Value
ActiveCell.Offset(0, 1).Value = txt_CurrentTSL.Value
ActiveCell.Offset(0, 2).Value = txt_NewTSL.Value
ActiveCell.Offset(0, 3).Value = cbo_Reason.Value
ActiveCell.Offset(0, 4).Value = txt_Date.Value
Unload Me  
' unload the form
End Sub


Private Sub cmdClearForm_Click()
    Call UserForm_Initialize
End Sub


Private Sub cmdCancel_Click()
    Unload Me  
' or frm_TSLrecord.Hide
    End
End Sub


Private Sub chk_Immediate_Change()
If chk_Immediate = True Then
   chk_NonCritical.Enabled = True
Else
   chk_NonCritical.Enabled = False
   chk_NonCritical = False
End If
End Sub

UserForm_Initialize event handler determines how the userform will look like when the user first opens it. The “Reason for change” combo box should be filled with a list of pre-defined reasons, and only the “Customer” Option button is checked. Value property is the default property for an option button and a check box, which is either True or False. You can simply leave out the word .Value from the line opt_Customer.Value = True. Similarly, to make a text box blank, you can write txt_PartNumber = " " 

When the user click the Clear Form button, it erases the content which is because the cmdClearForm_Click event code is calling UserForm_Initialize event handler. When the user click Cancel button, the form disappears, which is driven by Unload Me, and then it ends the program. 

cmdAdd_Click event code captures the user’s input. Usually, these user’s inputs are stored in public variables, declared in a standard module, so that later you can re-use them again in the main module. Of course, these variables are recognized by the event code. This code performs errors-checking whether the user: (1) leave the text box blank, (2) type in non-numeric string in a numeric-only textbox, (3) fail to select an item in a combo box, (4) enter a value that is not in date format, (5) not selecting a checkbox. In either case, the code will display an alert message. ListIndex property identifies the currently selected item in a ComboBox or ListBox. When the user selects a row in the combo box, the system sets the ListIndex value. It starts with 0, and -1 indicates that no item is selected. This explains the error check. Below diagram is the output in datasheet when the Add button is clicked.
 

 

Create a Button to open the UserForm

To make it easy for users to open the UserForm, you can add a button to a worksheet, you then assign the following macro you created in the module to this button.

Sub OpenTSLrecord_Form()
    frm_TSLrecord.Show
End Sub

How to add a button?
On the Drawing toolbar, click on the rounded rectangle tool.
In the centre of the worksheet, draw a rectangle, and format as you desired.
Select the rectangle and type: “Click here to ADD part information”.
Right-click on the rectangle border, and choose 'Assign Macro'.

Select the macro name UserForm_Initialize, click OK.

 

Working with ListBox

List boxes are a lot trickier than combo box. There are four methods that I know you can populate them. If the ListBox items are not contained in a worksheet range, you can use AddItem method to fill the ListBox as shown in example 1.

‘ write in your module
Private Sub Example1_ListBox1()
With frm_Customers.ListBox1
    .RowSource = ""  
‘ to avoid getting “permission denied” error if there is nonempty RowSource setting
    .AddItem "SSMC"
    .AddItem "UMC"
    .AddItem "TSMC"
    .AddItem "IMF"
    .AddItem "INTEL"
End With
frm_Customers.Show
End Sub


You can also use AddItem method to fill in ListBox items from a range or a named range as shown in example 2. You can hide Sheet2 in case the content may accidentally be deleted by user.
Private Sub Example2_ListBox1()
With frm_Customers.ListBox1
Dim r As Integer
For r = 1 To 5
  frm_Customers.ListBox1.AddItem Sheets("Sheet2").Cells(r, 1)
Next
End With
frm_Customers.Show
End Sub


If you have named a range in Sheet2.Range(“A1:A5”) as "MyCustomers", you can substitute with a dynamic range as shown below.
Private Sub Example3_ListBox1()
Dim cell As Range
With frm_Customers.ListBox1
For Each cell In Sheets("Sheet2").Range("MyCustomers")
  frm_Customers.ListBox1.AddItem cell.Value
Next
End With

In the Property Window, if the RowSource property of the form frm_Customers is set to the named range "MyCustomers" at design time, the use of For..Each Next loop can be omitted. This setting tells VBA to populate the ListBox with the items in “MyCustomers” range. The diagram below is what the ListBox should look like using any of the above 4 methods.

 

This CheckBox event code allows you to check and uncheck the option button you have selected in ListBox 1. In the whole exercise of this example , it checks on valid data entry on each textbox and listbox. The Add Items command button would add the user input into Sheet2 which is hidden. The diagram below is the userform I have created. You can DOWNLOAD the example here.
Private Sub CheckBox1_Click()
Dim i As Long
For i = 0 To ListBox1.ListCount - 1
    ListBox1.Selected(i) = CheckBox1
Next

End Sub

 

Single and Multi Selection ListBox

The procedure below take a single selected ListBox item and places it into a range in Sheet2

Sheet2.Range("A65536").End(xlUp)(2, 1) = ListBox1.Value

For such code to work the ListBox must have its MultiSelect Property set to 1 fmMultiSelectSingle. When you set the MultiSelect Property set to -1 fmMultiSelectMulti, you can allow user to make multiple selections. However, due to MultiSelect Property set to -1 fmMultiSelectMulti we can no longer use simple code like above to return the selected items to our cells. To do this with multiple selections we can use code like shown below;

Private Sub CommandButton2_Click()
Dim lItem As Long
    For lItem = 0 To ListBox1.ListCount - 1
        If ListBox1.Selected(lItem) = True Then
            Sheet2.Range("A65536").End(xlUp)(2, 1) = ListBox1.List(lItem)
            ListBox1.Selected(lItem) = False
        End If
    Next
End Sub

Below is an example of the listbox using MultiSelect Property set to -1 fmMultiSelectMulti. DOWNLOAD the example here.

 

 

This site was created in Feb.2007
by William Tan