Visual Basic Documentation Map1
Visual Basic Documentation Map1
• Public variables
• Public constants
• Class names (Name property of a class module, a user control, a property page, or a user document)
aspect of the product. The documentation provided with Visual Basic is listed below.
Programmer's Guide
A guide to creating applications with Visual Basic. Explains programming techniques, using frequent
An introduction to the ActiveX controls — formerly called OLE controls — included with the Visual Basic
Professional and Enterprise editions. Start here for general information, scenarios of real-life uses, and
A guide to creating ActiveX controls, ActiveX documents, and ActiveX code components (formerly OLE
servers). Includes introductory step-by-step chapters as well as in-depth design guides. Included in the
A guide to using the Visual Basic extensibility object model to tailor the development environment to your
unique needs. Use objects in the model to build add-ins that automate repetitive tasks, monitor the
2
development environment for certain events, or perform complex tasks. Included in the Component Tools
Guide.
A guide to enhancing functionality provided by Visual Basic by calling functions in dynamic-link libraries
(DLLs). Through DLLs, you can access the thousands of procedures that form the backbone of the
Microsoft Windows operating system, as well as routines written in other languages. Included in the
An introduction to creating applications that can run on the Internet or an intranet, presenting HTML
pages inside forms-based applications, and deploying these applications and other ActiveX components on
A guide to creating and manipulating databases using Microsoft ActiveX Data Objects (ADO) and other
Reference
Provides a complete reference for features available in all editions of Visual Basic. Includes sections on the
Samples
Provides an overview and complete reference for Data Access Objects, a programming model that allows
you to programmatically access and manipulate data in local or remote databases, and to manage
A guide to using Microsoft Repository, an extensible object modeling system that allows full programmatic
access via Automation objects. Microsoft Repository comes with the Repository Add-in, a Visual Basic add-
3
in module that automatically stores and maintains the structure of your Visual Basic projects in an object-
Other Documentation
You may find the following sets of documentation useful; these are located elsewhere in the MSDN library.
Internet Information Services are a platform for creating ASP pages and developing Web applications.
Contains information about a variety of technologies that Microsoft has developed to facilitate
Provides information about ActiveX Data Objects (ADO), OLE DB, and Open Database Connectivity
(ODBC).
Provides information about the Microsoft Repository, which produces a common place to persist
This toolkit covers Transact-SQL, programming ODBC for SQL, and much more.
Microsoft Transaction Server (MTS) is a component-based transaction processing system for developing,
deploying, and managing high-performance, scalable, and robust enterprise, Internet, and intranet server
applications.
A guide to using the Database Designer and Query Designer to create data-driven applications that rely on
Explains how to use the Help browser and find information in the Microsoft Developer Network Library.
A guide to using Visual SourceSafe, an easy-to-use tool for storing files, controlling access to files, and
A guide to distributed application development for business-critical data management. This book includes
information on designing solutions based on a flexible architecture, developing large-scale data access
Under Books in the table of contents, you can also find Advanced Microsoft Visual Basic 5, Hardcore Visual
Basic, Internet Programming with Visual Basic 5.0, and the Microsoft Jet Database Engine Programmer's
Guide.
Welcome to Microsoft Visual Basic, the fastest and easiest way to create applications for Microsoft
Windows. Whether you are an experienced professional or brand new to Windows programming, Visual
Basic provides you with a complete set of tools to simplify rapid application development.
So what is Visual Basic? The "Visual" part refers to the method used to create the graphical user interface
(GUI). Rather than writing numerous lines of code to describe the appearance and location of interface
elements, you simply add prebuilt objects into place on screen. If you've ever used a drawing program
such as Paint, you already have most of the skills necessary to create an effective user interface.
The "Basic" part refers to the BASIC (Beginners All-Purpose Symbolic Instruction Code) language, a
language used by more programmers than any other language in the history of computing. Visual Basic
has evolved from the original BASIC language and now contains several hundred statements, functions,
and keywords, many of which relate directly to the Windows GUI. Beginners can create useful applications
5
by learning just a few of the keywords, yet the power of the language allows professionals to accomplish
anything that can be accomplished using any other Windows programming language.
The Visual Basic programming language is not unique to Visual Basic. The Visual Basic programming
system, Applications Edition included in Microsoft Excel, Microsoft Access, and many other Windows
applications uses the same language. The Visual Basic Scripting Edition (VBScript) is a widely used
scripting language and a subset of the Visual Basic language. The investment you make in learning Visual
Whether your goal is to create a small utility for yourself or your work group, a large enterprise-wide
system, or even distributed applications spanning the globe via the Internet, Visual Basic has the tools you
need.
• Data access features allow you to create databases, front-end applications, and scalable server-side
components for most popular database formats, including Microsoft SQL Server and other enterprise-
level databases.
• ActiveX technologies allow you to use the functionality provided by other applications, such as
Microsoft Word word processor, Microsoft Excel spreadsheet, and other Windows applications. You can
even automate applications and objects created using the Professional or Enterprise editions of Visual
Basic.
• Internet capabilities make it easy to provide access to documents and applications across the Internet
• Your finished application is a true .exe file that uses a Visual Basic Virtual Machine that you can freely
distribute.
Visual Basic is available in three versions, each geared to meet a specific set of development
requirements.
• The Visual Basic Learning edition allows programmers to easily create powerful applications for
Microsoft Windows and Windows NT. It includes all intrinsic controls, plus grid, tab, and data-bound
controls. Documentation provided with this edition includes the Learn VB Now CD plus the Microsoft
• The Professional edition provides computer professionals with a full-featured set of tools for
developing solutions for others. It includes all the features of the Learning edition, plus additional
ActiveX controls, the Internet Information Server Application Designer, integrated Visual Database
Tools and Data Environment, Active Data Objects, and the Dynamic HTML Page Designer.
Documentation provided with the Professional edition includes the Visual Studio Professional Features
book plus Microsoft Developer Network CDs containing full online documentation.
• The Enterprise edition allows professionals to create robust distributed applications in a team setting.
It includes all the features of the Professional edition, plus Back Office tools such as SQL Server,
Microsoft Transaction Server, Internet Information Server, Visual SourceSafe, SNA Server, and more.
Printed documentation provided with the Enterprise edition includes the Visual Studio Enterprise
Features book plus Microsoft Developer Network CDs containing full online documentation.
In order to understand the application development process, it is helpful to understand some of the key
concepts upon which Visual Basic is built. Because Visual Basic is a Windows development language, some
familiarity with the Windows environment is necessary. If you are new to Windows programming, you
need to be aware of some fundamental differences between programming for Windows versus other
environments.
A complete discussion of the inner workings of Windows would require an entire book. A deep
understanding of all of the technical details isn't necessary. A simplified version of the workings of
Think of a window as simply a rectangular region with its own boundaries. You are probably already aware
of several different types of windows: an Explorer window in Windows, a document window within your
word processing program, or a dialog box that pops up to remind you of an appointment. While these are
the most common examples, there are actually many other types of windows. A command button is a
window. Icons, text boxes, option buttons and menu bars are all windows.
The Microsoft Windows operating system manages all of these many windows by assigning each one a
unique id number (window handle or hWnd). The system continually monitors each of these windows for
signs of activity or events. Events can occur through user actions such as a mouse click or a key press,
Each time an event occurs, it causes a message to be sent to the operating system. The system processes
the message and broadcasts it to the other windows. Each window can then take the appropriate action
based on its own instructions for dealing with that particular message (for example, repainting itself when
As you might imagine, dealing with all of the possible combinations of windows, events and messages
could be mind-boggling. Fortunately, Visual Basic insulates you from having to deal with all of the low-
level message handling. Many of the messages are handled automatically by Visual Basic; others are
exposed as Event procedures for your convenience. This allows you to quickly create powerful applications
In traditional or "procedural" applications, the application itself controls which portions of code execute
and in what sequence. Execution starts with the first line of code and follows a predefined path through
In an event-driven application, the code doesn't follow a predetermined path — it executes different code
sections in response to events. Events can be triggered by the user's actions, by messages from the
system or other applications, or even from the application itself. The sequence of these events determines
the sequence in which the code executes, thus the path through the application's code differs each time
Because you can't predict the sequence of events, your code must make certain assumptions about the
"state of the world" when it executes. When you make assumptions (for example, that an entry field must
contain a value before running a procedure to process that value), you should structure your application in
such a way as to make sure that the assumption will always be valid (for example, disabling the command
button that starts the procedure until the entry field contains a value).
Your code can also trigger events during execution. For example, programmatically changing the text in a
text box cause the text box's Change event to occur. This would cause the code (if any) contained in the
Change event to execute. If you assumed that this event would only be triggered by user interaction, you
might see unexpected results. It is for this reason that it is important to understand the event-driven
Interactive Development
8
The traditional application development process can be broken into three distinct steps: writing, compiling,
and testing code. Unlike traditional languages, Visual Basic uses an interactive approach to development,
With most languages, if you make a mistake in writing your code, the error is caught by the compiler
when you start to compile your application. You must then find and fix the error and begin the compile
cycle again, repeating the process for each error found. Visual Basic interprets your code as you enter it,
catching and highlighting most syntax or spelling errors on the fly. It's almost like having an expert
In addition to catching errors on the fly, Visual Basic also partially compiles the code as it is entered. When
you are ready to run and test your application, there is only a brief delay to finish compiling. If the
compiler finds an error, it is highlighted in your code. You can fix the error and continue compiling without
Because of the interactive nature of Visual Basic, you'll find yourself running your application frequently as
you develop it. This way you can test the effects of your code as you work rather than waiting to compile
later.
2. Set properties.
3. Write code.
To see how this is done, use the steps in the following procedures to create a simple application that
consists of a text box and a command button. When you click the command button, the message "Hello,
Forms are the foundation for creating the interface of an application. You can use forms to add windows
and dialog boxes to your application. You can also use them as containers for items that are not a visible
part of the application's interface. For example, you might have a form in your application that serves as a
The first step in building a Visual Basic application is to create the forms that will be the basis for your
application's interface. Then you draw the objects that make up the interface on the forms you create. For
this first application, you'll use two controls from the Toolbox.
Button Control
Text box
Command button
1. Click the tool for the control you choose to draw — in this case, the text box.
2. Move the pointer onto your form. The pointer becomes a cross hair, as shown in Figure 2.3.
3. Place the cross hair where you want the upper-left corner of the control.
10
4. Drag the cross hair until the control is the size you want. (Dragging means holding the left mouse
button down while you move an object with the mouse.)
Another simple way to add a control to a form is to double-click the button for that control in the Toolbox.
This creates a default-size control located in the center of the form; then you can move the control to
Notice that small rectangular boxes called sizing handles appear at the corners of the control; you'll use
these sizing handles in the next step as you resize the control. You can also use the mouse, keyboard, and
menu commands to move controls, lock and unlock control positions, and adjust their positions.
To resize a control
1. Select the control you intend to resize by clicking it with the mouse.
2. Position the mouse pointer on a sizing handle, and drag it until the control is the size you choose.
The corner handles resize controls horizontally and vertically, while the side handles resize in only one
direction.
–or–
Use SHIFT with the arrow keys to resize the selected control.
To move a control
• Use the mouse to drag the control to a new location on the form.
–or–
Use the Properties window to change the Top and Left properties.
When a control is selected, you can use CTRL with the arrow keys to move the control one grid unit at a
time. If the grid is turned off, the control moves one pixel at a time.
11
–or–
Click the Lock Controls Toggle button on the Form Editor toolbar.
This will lock all controls on the form in their current positions so that you don't inadvertently move them
once you have them in the desired location. This will lock controls only on the selected form; controls on
other forms are untouched. This is a toggle command, so you can also use it to unlock control positions.
• You can "nudge" the control that has the focus by holding CTRL down and pressing the appropriate
arrow key.
–or–
You can change the control's Top and Left properties in the Property window.
You now have the interface for the "Hello, world!" application, as shown in Figure 2.4.
Setting Properties
The next step is to set properties for the objects you've created. The Properties window (Figure 2.5)
provides an easy way to set properties for all objects on a form. To open the Properties window, choose
12
the Properties Window command from the View menu, click the Properties Window button on the toolbar,
• Object box — Displays the name of the object for which you can set properties. Click the arrow to the
right of the object box to display the list of objects for the current form.
• Sort tabs — Choose between an alphabetic listing of properties or a hierarchical view divided by
• Properties list — The left column displays all of the properties for the selected object. You can edit
1. From the View menu, choose Properties, or click the Properties button on the toolbar.
The Properties window displays the settings for the selected form or control.
Enumerated properties have a predefined list of settings. You can display the list by clicking the down
arrow at the right of the Settings box, or you can cycle through the list by double-clicking a list item.
13
For the "Hello, world!" example, you'll need to change three property settings. Use the default settings for
All forms in Visual Basic have a generic, default icon that appears when you minimize that form. However,
you will probably change this icon to one that illustrates the use of the form or your application. To assign
an icon to a form, set the Icon property for that form. You can use 32 x 32 pixel icons that were standard
in 16-bit versions of Microsoft Windows and are also used in Windows 95/98 and Windows NT, as well as
Writing Code
The Code Editor window is where you write Visual Basic code for your application. Code consists of
language statements, constants, and declarations. Using the Code Editor window, you can quickly view
• Double-click the form or control for which you choose to write code.
–or–
From the Project Explorer window, select the name of a form or module, and choose the View Code
button.
Figure 2.6 shows the Code Editor window that appears when you double-click the Command button
You can choose to display all procedures in the same Code window, or display a single procedure at a
time.
2. On the Editor tab in the Options dialog box, select the check box to the left of Default to Full
Module View. The check box to the left of Procedure Separator adds or removes a separator line
between procedures.
–or–
Click the Full Module View button in the lower left corner of the Code Editor window.
2. On the Editor tab in the Options dialog box, clear the check box to the left of Default to Full
Module View.
–or–
Click the Procedure View button in the lower left corner of the Code Editor window.
• Object list box — Displays the name of the selected object. Click the arrow to the right of the list box
• Procedure list box — Lists the procedures, or events, for an object. The box displays the name of the
selected procedure — in this case, Click. Choose the arrow to the right of the box to display all the
Code in a Visual Basic application is divided into smaller blocks called procedures. An event procedure,
such as those you'll create here, contains code that is executed when an event occurs (such as when a
user clicks a button). An event procedure for a control combines the control's actual name (specified in the
Name property), an underscore (_), and the event name. For example, if you want a command button
named Command1 to invoke an event procedure when it is clicked, use the procedure Command1_Click.
1. In the Object list box, select the name of an object in the active form. (The active form is the form
that currently has the focus.)
2. In the Procedure list box, select the name of an event for the selected object.
Here, the Click procedure is already selected, because it's the default procedure for a command
button. Note that a template for the event procedure is now displayed in the Code window.
3. Type the following code between the Sub and End Sub statements:
End Sub
You'll note here that the code is simply changing the Text property of the control named Text1 to read
"Hello, world!" The syntax for this example takes the form of object.property, where Text1 is the object
and Text is the property. You can use this syntax to change property settings for any form or control in
response to events that occur while your application is running.
16
For More Information For information on creating other types of procedures, see "Introduction to
To run the application, choose Start from the Run menu, or click the Start button on the toolbar, or press
F5. Click the command button you've created on the form, and you'll see "Hello, world!" displayed in the
text box.
Visual Basic provides you with a wealth of tools beyond the ones used in this first application, so you'll
soon use many other features to manage and customize your applications. Reviewing sample applications
can be an excellent way to learn more about Visual Basic. The following example illustrates how easy it
The Firstapp application demonstrates how a data control and a grid control can be used to display a table
of information from a database. Visual Basic makes it easy to access database information from within
your application. The data control provides the ability to navigate through the database
recordset, synchronizing the display of records in the grid control with the position in the recordset.
The application consists of a data control, a MSFlexGrid control, a list box control, and two command
buttons. The grid displays a table of information about products retrieved from the Northwind database.
As the user selects an item by using the navigation buttons on the data control, the name of the selected
product is displayed in the data control. The user can also add items to a "shopping list" in the list box
To add items to the list box, you use the AddItem method. (A method is a Visual Basic function that
acts on a particular object, in this case a ListBox object.) The syntax for specifying a method
(object.method) is similar to the syntax for setting a property (object.property). The AddItem method
allows you to dynamically add items to the list box while the application is running. Conversely, the Clear
For More Information To learn more about methods, see "Understanding Properties, Methods, and
Creating a Project
17
You begin creating this application by choosing New Project from the File menu, then selecting Standard
EXE in the New Project dialog box (when you first start Visual Basic, the New Project dialog box is
presented). Visual Basic creates a new project and displays a new form. To draw the interface, you use a
data control, a MSFlexGrid control, a list box control, and two command buttons. The MSFlexGrid control
1. Select Components from the context menu for the toolbox. (You can right-click within the toolbox
window to display the context menu.)
2. Find the MSFlexGrid (Microsoft Flex Grid 6.0) in the Controls list box and select the check box to its
left.
The icon for the MSFlexGrid control will appear in the toolbox.
Use the Toolbox to draw a data control, an MSFlexGrid control, a list box control, and two command
buttons on the form. If you don't remember how, check out "Creating the Interface" earlier in this chapter.
Setting Properties
In the Properties window, set properties for the objects according to the following table. Use the default
The DatabaseName property of the data control must include the actual path to the database. By default,
the Nwind.mdb database is installed in the same directory as Visual Basic. When you select the
DatabaseName property in the Properties window, you can click the button to the right of the property to
display a standard File Open dialog box to browse for the file. Once the DatabaseName property has been
set, the RecordSource property in the Properties window will contain a list of tables or recordsets for the
18
selected database. Setting the DataSource property of the MSFlexGrid control to Data1 automatically links
All the code for the application is contained in the Command1_Click, Command2_Click, Data1_Reposition,
and MSFlexGrid1_DblClick event procedures. Double-click the form or control to display the Code window,
Add this code to the Command1_Click event procedure to clear the list box when the user clicks the
button:
End Sub
In the above statement, you are invoking the Clear method of the list box, List1. The Clear method
Add this code to the Command2_Click event procedure to unload the form from memory and end the
application:
Unload Form1
End Sub
In the above procedure, the first statement invokes the Unload event for the form. If you needed to
perform a function at shutdown, such as saving a file, you could place that code in the form's Unload
event procedure. The second statement calls the End function, which ends the application.
Add this code to the Data1_Reposition event procedure to update the caption each time a record is
selected:
Data1.Caption = Data1.Recordset("ProductName")
End Sub
19
In the above statement, you are assigning the value on the right (the contents of the Title field in the
Recordset of the data control) to the property on the left (the Caption property of the data control object).
Add this code to the MSFlexGrid_DblClick event procedure to add an item to the list box when the user
List1.AddItem MSFlexGrid1.Text
End Sub
In the above statement, you are invoking the AddItem method of the list box (List1). The text to be added
to the list box is contained in the argument of the method, in this case, the value of the title field in the
recordset of the data control. Passing a value to an argument is similar to assigning a value to a property;
Saving a Project
You finish your work on the application by choosing Save Project from the File menu. Visual Basic will
prompt you separately to save the form and then the project. One possible name for the project is
"Northwind Shopping List." Windows 95, Windows 98, and Windows NT allow you
to use file names up to 255 characters in length, and file names can include
spaces. Older versions of Microsoft Windows limited you to file names of
eight characters, with a three-character extension.
You have just completed your first Visual Basic application: one that performs a simple but useful function.
You can use this application as a basis for adding similar functionality in your own applications,
substituting your own data instead of Nwind.mdb. Of course, to make this application truly useful, you
might want to add functionality to save or print the contents of the list box, to add additional information
such as price and availability, and even to gather credit card information and transmit an order across the
Internet. As you continue on through the rest of the Programmer's Guide, you will find examples of doing
The first step to creating an application with Visual Basic is to create the interface, the visual part of the
application with which the user will interact. Forms and controls are the basic building blocks used to
create the interface; they are the objects that you will work with to build your application.
Forms are objects that expose properties which define their appearance, methods which define
their behavior, and events which define their interaction with the user. By setting the
properties of the form and writing Visual Basic code to respond to its events, you customize the
Controls are objects that are contained within form objects. Each type of control has its own
set of properties, methods and events that make it suitable for a particular purpose. Some of
the controls you can use in your applications are best suited for entering or displaying text.
Other controls let you access other applications and process data as if the remote application
This chapter introduces the basic concepts of working with forms and controls and their associated
properties, methods, and events. Many of the standard controls are discussed, as well as form-specific
Topics
Understanding Properties, Methods and Events
Designing a Form
An introduction to the check box, option button, list box, combo box, and scroll bar controls.
Additional Controls
Understanding Focus
Menu Basics
Sample application
Controls.vbp
The code examples in this chapter are taken from the Controls.vbp sample application which is listed
Visual Basic forms and controls are objects which expose their own properties, methods and events.
Properties can be thought of as an object's attributes, methods as its actions, and events as its responses.
An everyday object like a child's helium balloon also has properties, methods and events. A balloon's
properties include visible attributes such as its height, diameter and color. Other properties describe its
state (inflated or not inflated), or attributes that aren't visible such as its age. By definition, all balloons
have these properties; the settings of these properties may differ from one balloon to another.
22
A balloon also has inherent methods or actions that it might perform. It has an inflate method (the action
of filling it with helium), a deflate method (expelling its contents) and a rise method (if you were to let go
Balloons also have predefined responses to certain external events. For instance, a balloon would respond
to the event of being punctured by deflating itself, or to the event of being released by rising into the air.
Figure 3.1 Objects have properties, respond to events, and perform methods
If you were able to program a balloon, the Visual Basic code might look like the following. To set the
balloon's properties:
Balloon.Color = Red
Balloon.Diameter = 10
Balloon.Inflated = True
Note the syntax of the code — the object (Balloon) followed by the property (.Color) followed by the
assignment of the value (Red). You could change the color of the balloon from code by repeating this
statement and substituting a different value. Properties can also be set in the Properties window while you
Balloon.Inflate
Balloon.Deflate
Balloon.Rise 5
23
The syntax is similar to the property — the object (a noun) followed by the method (a verb). In the third
example, there is an additional item, called an argument, which denotes the distance to rise. Some
methods will have one or more arguments to further describe the action to be performed.
Sub Balloon_Puncture()
Balloon.Deflate
Balloon.MakeNoise "Bang"
Balloon.Inflated = False
Balloon.Diameter = 1
End Sub
In this case, the code describes the balloon's behavior when a puncture event occurs: invoke the Deflate
method, then invoke the MakeNoise method with an argument of "Bang" (the type of noise to make).
Since the balloon is no longer inflated, the Inflated property is set to False and the Diameter property is
While you can't actually program a balloon, you can program a Visual Basic form or control. As the
programmer, you are in control. You decide which properties should be changed, methods invoked or
Designing a Form
See Also
Form objects are the basic building blocks of a Visual Basic application, the actual windows with which a
user interacts when they run the application. Forms have their own properties, events, and methods with
Figure 3.2 Forms and controls have their own properties, events, and methods
24
The first step in designing a form is to set its properties. You can set a form's properties at design time in
Note You work with forms and controls, set their properties, and write code for their events at design
time, which is any time you're building an application in the Visual Basic environment. Run time is any
time you are actually running the application and interacting with the application as the user would.
Many of a form's properties affect its physical appearance. The Caption property determines the text that
is shown in the form's title bar; the Icon property sets the icon that is displayed when a form is minimized.
The MaxButton and MinButton properties determine whether the form can be maximized or minimized. By
changing the BorderStyle property, you can control the resizing behavior of the form.
Height and Width properties determine the initial size of a form; Left and Top properties determine the
form's location in relation to the upper left-hand corner of the screen. The WindowState property can be
The Name property sets the name by which you will refer to the form in code. By default, when a form is
first added to a project, its name is set to Form1, Form2, and so forth. It's a good idea to set the Name
property to something more meaningful, such as "frmEntry" for an order entry form.
The best way to familiarize yourself with the many form properties is to experiment. Change some of the
properties of a form in the Properties window (Figure 3.3), then run the application to see their effect. You
can learn more about each property by selecting it and pressing F1 to view the context-sensitive Help.
The Resize event of a form is triggered whenever a form is resized, either by user interaction or through
code. This allows you to perform actions such as moving or resizing controls on a form when its
The Activate event occurs whenever a form becomes the active form; the Deactivate event occurs when
another form or application becomes active. These events are convenient for initializing or finalizing the
form's behavior. For example, in the Activate event you might write code to highlight the text in a
particular text box; in the Deactivate event you might save changes to a file or database.
Form2.Show
Invoking the Show method has the same effect as setting a form's Visible property to True.
Many of a form's methods involve text or graphics. The Print, Line, Circle, and Refresh methods are useful
for printing or drawing directly onto a form's surface. These methods and more are discussed in "Working
For More Information For additional information on forms, see "More About Forms" in "Creating a User
Interface."
The easiest way to allow the user to interact with an application is to provide a button to click. You can use
the command button control provided by Visual Basic, or you can create your own "button" using an
Most Visual Basic applications have command buttons that allow the user to simply click them to perform
actions. When the user chooses the button, it not only carries out the appropriate action, it also looks as if
it's being pushed in and released. Whenever the user clicks a button, the Click event procedure is invoked.
You place code in the Click event procedure to perform any action you choose.
• Move the focus to the button by pressing the TAB key, and then choose the button by pressing the
• Press an access key (ALT+ the underlined letter) for a command button.
• cmdClose.Value = True
• cmdClose_Click
• If the command button is the default command button for the form, pressing ENTER chooses the
button, even if you change the focus to a different control other than a command button. At design
time, you specify a default command button by setting that button's Default property to True.
• If the command button is the default Cancel button for the form, then pressing ESC chooses the
button, even if you change the focus to another control. At design time, you specify a default Cancel
All these actions cause Visual Basic to invoke the Click event procedure.
You use the Caption property to display text on the button to tell the user what the button does. In Figure
3.4, the Test Buttons example from the Controls sample application contains a command button with its
27
Caption property set to "Change Signal." (For a working version of this example, see Button.frm in the
Notice that 'S' is the access key for this button, denoted by an underline. Inserting an ampersand (&) in
the text of the Caption property makes the character following it the access key for that button (for
When a user clicks the command button, the code in the command button's Click event procedure is
executed. In the example, a different traffic light icon is displayed each time the button is clicked.
For More Information For information on additional properties of the command button, see "Using
Label and text box controls are used to display or enter text. Use labels when you want your application to
display text on a form, and text boxes when you want to allow the user to enter text. Labels contain text
that can only be read, while text boxes contain text that can be edited.
Text that can be edited by the user, for example an Text box
order entry field or a password box
• Using Labels to Display Text The basics of using the label control.
A label control displays text that the user cannot directly change. You can use labels to identify controls,
such as text boxes and scroll bars, that do not have their own Caption property. The actual text displayed
in a label is controlled by the Caption property, which can be set at design time in the Properties window
By default, the caption is the only visible part of the label control. However, if you set the BorderStyle
property to 1 (which you can do at design time), the label appears with a border — giving it a look similar
to a text box. You can also change the appearance of the label by setting the BackColor, BackStyle,
Single-line label captions can be specified at design time in the Properties window. But what if you want to
enter a longer caption, or a caption that will change at run time? Labels have two properties that help you
size the controls to fit larger or smaller captions: AutoSize and WordWrap.
The AutoSize property determines if a control should be automatically resized to fit its contents. If set to
True, the label grows horizontally to fit its contents, as shown in Figure 3.5.
The WordWrap property causes the label to grow vertically to fit its contents, while retaining the same
width, as shown in Figure 3.6. For a working version of this example, see Wordwrap.frm in the
Note If you run the AutoSize example from Controls.vbp, you'll notice that for the WordWrap example to
actually work, both check boxes must be selected. This is because, for the label's WordWrap property to
30
take effect, AutoSize must be set to True. The width of the label is increased only if the width of a single
For More Information For additional information on the label control's properties, see "Using Visual
Text boxes are versatile controls that can be used to get input from the user or to display text. Text boxes
should not be used to display text that you don't want the user to change, unless you've set the Locked
property to True.
The actual text displayed in a text box is controlled by the Text property. It can be set in three different
ways: at design time in the Property window, at run time by setting it in code, or by input from the user at
run time. The current contents of a text box can be retrieved at run time by reading the Text property.
By default, a text box displays a single line of text and does not display scroll bars. If the text is longer
than the available space, only part of the text will be visible. The look and behavior of a text box can be
changed by setting two properties, MultiLine and ScrollBars, which are available only at design time.
Note The ScrollBars property should not be confused with scroll bar controls, which are not attached to
Setting MultiLine to True enables a text box to accept or display multiple lines of text at run time. A
multiple-line text box automatically manages word wrap as long as there is no horizontal scroll bar. The
ScrollBars property is set to 0-None by default. Automatic word wrap saves the user the trouble of
inserting line breaks at the end of lines. When a line of text is longer than what can be displayed on a line,
Line breaks cannot be entered in the Properties window at design time. Within a procedure, you create a
line break by inserting a carriage return followed by a linefeed (ANSI characters 13 and 10). You can also
use the constant vbCrLf to insert a carriage return/linefeed combination. For example, the following event
procedure puts two lines of text into a multiple-line text box (Text1) when the form is loaded:
Sub Form_Load ()
End Sub
You can control the insertion point and selection behavior in a text box with the SelStart, SelLength and
When a text box first receives the focus, the default insertion point or cursor position within the text box is
to the left of any existing text. It can be moved by the user from the keyboard or with the mouse. If the
text box loses and then regains the focus, the insertion point will be wherever the user last placed it.
In some cases, this behavior can be disconcerting to the user. In a word processing application, the user
might expect new characters to appear after any existing text. In a data entry application, the user might
expect their typing to replace any existing entry. The SelStart and SelLength properties allow you to
The SelStart property is a number that indicates the insertion point within the string of text, with 0 being
the left-most position. If the SelStart property is set to a value equal to or greater than the number of
characters in the text box, the insertion point will be placed after the last character, as shown in Figure
3.7. For a working version of this example, see Text.frm in the Controls.vbp sample application.
The SelLength property is a numeric value that sets the width of the insertion point. Setting the SelLength
to a number greater than 0 causes that number of characters to be selected and highlighted, starting from
the current insertion point. Figure 3.8 shows the selection behavior.
If the user starts typing while a block of text is selected, the selected text will be replaced. In some cases,
you might want to replace a text selection with new text by using a paste command. The SelText property
is a string of text that you can assign at run time to replace the current selection. If no text is selected,
For More Information For additional information on the text box control's properties, see "Using Visual
The easiest way to allow the user to interact with an application is to provide a button to click. You can use
the command button control provided by Visual Basic, or you can create your own "button" using an
Most Visual Basic applications have command buttons that allow the user to simply click them to perform
actions. When the user chooses the button, it not only carries out the appropriate action, it also looks as if
it's being pushed in and released. Whenever the user clicks a button, the Click event procedure is invoked.
You place code in the Click event procedure to perform any action you choose.
• Move the focus to the button by pressing the TAB key, and then choose the button by pressing the
• Press an access key (ALT+ the underlined letter) for a command button.
• cmdClose.Value = True
• cmdClose_Click
• If the command button is the default command button for the form, pressing ENTER chooses the
button, even if you change the focus to a different control other than a command button. At design
time, you specify a default command button by setting that button's Default property to True.
• If the command button is the default Cancel button for the form, then pressing ESC chooses the
button, even if you change the focus to another control. At design time, you specify a default Cancel
All these actions cause Visual Basic to invoke the Click event procedure.
You use the Caption property to display text on the button to tell the user what the button does. In Figure
3.4, the Test Buttons example from the Controls sample application contains a command button with its
Caption property set to "Change Signal." (For a working version of this example, see Button.frm in the
Notice that 'S' is the access key for this button, denoted by an underline. Inserting an ampersand (&) in
the text of the Caption property makes the character following it the access key for that button (for
When a user clicks the command button, the code in the command button's Click event procedure is
executed. In the example, a different traffic light icon is displayed each time the button is clicked.
For More Information For information on additional properties of the command button, see "Using
Most applications need to present choices to their users, ranging from a simple yes/no option to selecting
from a list containing hundreds of possibilities. Visual Basic includes several standard controls that are
useful for presenting choices. The following table summarizes these controls and their appropriate uses.
A small set of choices from which a user can choose one Check boxes
or more options.
A small set of options from which a user can choose Option buttons (use frames if additional groups
just one. are needed)
A scrollable list of choices from which the user can List box
choose.
A scrollable list of choices along with a text edit field. Combo box
The user can either choose from the list or type a
choice in the edit field.
35
Check boxes, option buttons, list boxes, and combo boxes are discussed in the following sections:
• Selecting Individual Options with Check Boxes The basics of using the check box control.
• Grouping Options with Option Buttons The basics of using the option button control.
• Using List Boxes and Combo Boxes An introduction to the list box and combo box controls.
• Using Scroll Bars as Input Devices A brief introduction to the scroll bar control.
A check box indicates whether a particular condition is on or off. You use check boxes in an application to
give users true/false or yes/no options. Because check boxes work independently of each other, a user can
select any number of check boxes at the same time. For example in Figure 3.9, Bold and Italic can both be
checked.
The Check Box example uses a check box to determine whether the text is displayed in regular or italic
font. For a working version of this example, see Check.frm in the Controls.vbp sample application.
The application has a text box, a label, a command button, and two check boxes, as shown in Figure 3.10.
The following table lists the property settings for the objects in the application.
When you check Bold or Italic, the check box's Value property is set to 1; when unchecked, its Value
property is set to 0. The default Value is 0, so unless you change Value, the check box will be unchecked
when it is first displayed. You can use the constants vbChecked and vbUnchecked to represent the values
1 and 0.
The Click event for the check box occurs as soon as you click the box. This event procedure tests to see
whether the check box has been selected (that is, if its Value = vbChecked). If so, the text is converted to
bold or italic by setting the Bold or Italic properties of the Font object returned by the Font property of the
text box.
txtDisplay.Font.Bold = True
37
txtDisplay.Font.Bold = False
End If
End Sub
txtDisplay.Font.Italic = True
txtDisplay.Font.Italic = False
End If
End Sub
Option buttons present a set of two or more choices to the user. Unlike check boxes, however, option
buttons should always work as part of a group; selecting one option button immediately clears all the
other buttons in the group. Defining an option button group tells the user, "Here is a set of choices from
For example, in the option button group shown in Figure 3.11, the user can select one of three option
buttons.
All of the option buttons placed directly on a form (that is, not in a frame or picture box) constitute one
group. If you want to create additional option button groups, you must place some of them inside frames
or picture boxes.
All the option buttons inside any given frame constitute a separate group, as do all the option buttons
inside a picture box. When you create a separate group this way, always draw the frame or picture box
first, and then draw the option buttons on top of it. Figure 3.12 shows a form with two option button
groups.
A user can select only one option button in the group when you draw option buttons in a frame.
1. Select the frame control from the toolbox and draw the frame on the form.
2. Select the option button control from the toolbox and draw the control within the frame.
3. Repeat step 2 for each additional option button you wish to add to the frame.
Drawing the frame first and then drawing each control on the frame allows you to move the frame and
controls together. If you try to move existing controls onto a frame, the controls will not move with the
frame.
39
Note If you have existing controls that you want to group in a frame, you can select all the controls and
While controls are independent objects, a certain parent and child relationship exists between forms and
controls. Figure 3.12 demonstrates how option buttons can be contained within a form or within a frame
control.
To understand the concept of containers, you need to understand that all controls are children of the form
on which they are drawn. In fact, most controls support the read-only Parent property, which returns the
form on which a control is located. Being a child affects the placement of a control on the parent form. The
Left and Top properties of a control are relative to the parent form, and controls cannot be moved outside
the boundaries of the parent. Moving a container moves the controls as well, and the control's position
relative to the container's Left and Top properties does not change because the control moves with the
container.
• Tabbing to the option button group and then using the arrow keys to select an option button within
the group.
• optChoice.Value = True
To make a button the default in an option button group, set its Value property to True at design time. It
remains selected until a user selects a different option button or code changes it.
To disable an option button, set its Enabled property to False. When the program is run it will appear
The form shown in Figure 3.13 uses option buttons to determine the processor type and operating system
for a fictional computer. When the user selects a option button in either group, the caption of the label is
40
changed to reflect the current choices. For a working version of this example, see Options.frm in the
The following table lists the property settings for the objects in the application.
Value True
Value True
• The Click events for the first three option buttons assign a corresponding description to a form-level
• The Click events for the last two option buttons assign a corresponding description to a second form-
The key to this approach is the use of these two form-level variables, strComputer and strSystem.
These variables contain different string values, depending on which option buttons were last selected.
Each time a new option button is selected, the code in its Click event updates the appropriate variable:
strComputer = "Pentium"
Call DisplayCaption
End Sub
It then calls a sub procedure, called DisplayCaption, that concatenates the two variables and updates the
Sub DisplayCaption()
End Sub
A sub procedure is used because the procedure of updating the Caption property is essentially the same
for all five option buttons, only the value of the variables change from one instance to the next. This saves
you from having to repeat the same code in each of the Click events.
For More Information Variables and sub procedures are discussed in detail in "Programming
Fundamentals."
42
http://msdn.microsoft.com/library/default.asp?url=/library/en-
us/vbcon98/html/vbcongroupingoptions.asp
Using List Boxes and Combo Boxes
See Also
List boxes and combo boxes present a list of choices to the user. By default, the choices are displayed
vertically in a single column, although you can set up multiple columns as well. If the number of items
exceeds what can be displayed in the combo box or list box, scroll bars automatically appear on the
control. The user can then scroll up and down or left to right through the list. Figure 3.14 shows a single-
A combo box control combines the features of a text box and a list box. This control allows the user to
select either by typing text into the combo box or by selecting an item from its list. Figure 3.15 shows a
combo box.
In contrast to some other controls that contain a single value; for example the label's Caption property or
the text box's Text property, list boxes and combo boxes contain multiple values or a collection of values.
They have built-in methods for adding, removing and retrieving values from their collections at run time.
To add several items to a list box named List1, the code would look like this:
List1.AddItem "Paris"
List boxes and combo boxes are an effective way to present a large number of choices to the user in a
For More Information For additional information on the list box and combo box controls, see "Using
Although scroll bars are often tied to text boxes or windows, you'll sometimes see them used as input
devices. Because these controls can indicate the current position on a scale, scroll bar controls can be
used individually to control program input — for example, to control the sound volume or to adjust the
colors in a picture. The HScrollBar (horizontal) and VScrollBar (vertical) controls operate independently
from other controls and have their own set of events, properties, and methods. Scroll bar controls are not
the same as the built-in scroll bars that are attached to text boxes, list boxes, combo boxes, or MDI forms
(text boxes and MDI forms have a ScrollBars property to add or remove scroll bars that are attached to
the control).
Windows interface guidelines now suggest using slider controls as input devices instead of scroll bars.
Examples of slider controls can be seen in the Windows 95/98 control panel. A slider control of this type is
For More Information For additional information on scroll bar controls, see "Using Visual Basic's
Standard Controls."
Because Windows is a graphical user interface, it's important to have a way to display graphical images in
your application's interface. Visual Basic includes four controls that make it easy to work with graphics:
the picture box control, the image control, the shape control, and the line control.
The image, shape and line controls are sometimes referred to as "lightweight" graphical controls. They
require less system resources and consequently display somewhat faster than the picture box control;
they contain a subset of the properties, methods and events available in the picture box. Each is best
Picture boxes, image controls, shape controls, and line controls are discussed in the following sections:
• Working with the Picture Box Control The basics of using the picture box control.
• Lightweight Graphical Controls The basics of using the image, shape, and line controls.
The primary use for the picture box control is to display a picture to the user. The actual picture that is
displayed is determined by the Picture property. The Picture property contains the file name (and optional
Note Form objects also have a Picture property that can be set to display a picture directly on the form's
background.
To display or replace a picture at run time, you can use the LoadPicture function to set the Picture
property. You supply the name (and optional path) for the picture and the LoadPicture function handles
picMain.Picture = LoadPicture("VANGOGH.gif")
The picture box control has an AutoSize property that, when set to True, causes the picture box to resize
automatically to match the dimensions of its contents. Take extra care in designing your form if you plan
on using a picture box with the AutoSize enabled. The picture will resize without regard to other controls
on the form, possibly causing unexpected results, such as covering up other controls. It's a good idea to
The picture box control can also be used as a container for other controls. Like the frame control, you can
draw other controls on top of the picture box. The contained controls move with the picture box and their
Top and Left properties will be relative to the picture box rather than the form.
A common use for the picture box container is as a toolbar or status bar. You can place image controls on
it to act as buttons, or add labels to display status messages. By setting the Align property to Top,
Bottom, Left, or Right, the picture box will "stick" to the edge of the form. Figure 3.16 shows a picture box
with its Align property set to Bottom. It contains two label controls which could be used to display status
messages.
The picture box control has several methods that make it useful for other purposes. Think of the picture
box as a blank canvas upon which you can paint, draw or print. A single control can be used to display
The Print method allows you to output text to the picture box control just as you would to a printer.
Several font properties are available to control the characteristics of text output by the Print method; the
Circle, Line, Point and Pset methods may be used to draw graphics on the picture box. Properties such as
DrawWidth, FillColor, and FillStyle allow you to customize the appearance of the graphics.
Animation can be created using the PaintPicture method by moving images within the picture control and
For More Information For additional information on the picture box control, see "Using Visual Basic's
Standard Controls."
46
The image, shape and line controls are considered to be lightweight controls; that is, they support only a
subset of the properties, methods, and events found in the picture box. Because of this, they typically
require less system resources and load faster than the picture box control.
The image control is similar to the picture box control but is used only for displaying pictures. It doesn't
have the ability to act as a container for other controls, and it doesn't support the advanced methods of
Pictures are loaded into the image control just as they are in the picture box: at design time, set the
Picture property to a file name and path; at run time, use the LoadPicture function.
The sizing behavior of the image control differs from that of the picture box. It has a Stretch property
while the picture box has an AutoSize property. Setting the AutoSize property to True causes a picture box
to resize to the dimensions of the picture; setting it to False causes the picture to be cropped (only a
portion of the picture is visible). When set to False (the default), the Stretch property of the image control
causes it to resize to the dimensions of the picture. Setting the Stretch property to True causes the picture
to resize to the size of the image control, which may cause the picture to appear distorted.
For More Information For additional information on the image control, see "Using Visual Basic's
Standard Controls."
An image control also recognizes the Click event, so you can use this control anywhere you'd use a
command button. This is a convenient way to create a button with a picture instead of a caption. Grouping
several image controls together horizontally across the top of the screen — usually within a picture box —
For instance, the Test Buttons example shows an image control that users can choose like they choose a
command button. When the form is first displayed, the control displays one of three traffic icons from the
Icon Library included with Visual Basic. Each time the image control is clicked, a different icon is displayed.
(For a working version of this example, see Button.frm in the Controls.vbp sample application.)
47
If you inspect the form at design time, you will see that it actually contains all three icons "stacked" on top
of each other. By changing the Visible property of the top image control to False, you allow the next image
Figure 3.17 shows the image control with one of the traffic icons (Trffc10a.ico).
To create a border around the image control, set the BorderStyle property to 1-Fixed Single.
Note Unlike command buttons, image controls do not appear pushed in when clicked. This means that
unless you change the bitmap in the MouseDown event, there is no visual cue to the user that the
For More Information For information on displaying a graphic image in an image control, see "Using
Shape and line controls are useful for drawing graphical elements on the surface of a form. These controls
don't support any events; they are strictly for decorative purposes.
Several properties are provided to control the appearance of the shape control. By setting the Shape
property, it can be displayed as a rectangle, square, oval, circle, rounded rectangle, or rounded square.
The BorderColor and FillColor properties can be set to change the color; the BorderStyle, BorderWidth,
The line control is similar to the shape control but can only be used to draw straight lines.
For More Information For additional information on the shape and line controls, see "Using Visual
The form shown in Figure 3.18 uses four image controls, a shape control, a picture box, and a command
button. When the user selects a playing card symbol, the shape control highlights the symbol and a
48
description is displayed in the picture box. For a working version of this example, see Images.frm in the
The following table lists the property settings for the objects in the application.
Height 735
Width 495
• The Click event in each of the image controls sets the Left property of the shape control equal to its
• The Cls method of the picture box is invoked, clearing the current caption from the status bar.
• The Print method of the picture box is invoked, printing the new caption on the status bar.
The code in the image control Click event looks like this:
shpCard.Left = imgClub.Left
picStatus.Cls
shpCard.Visible = True
End Sub
Note that the first line in the Click event code assigns a value (the Left property of the image control) to
the Left property of the shape control using the = operator. The next two lines invoke methods, so no
operator is needed. In the third line, the value ("Selected: Club") is an argument to the Print method.
There is one more line of code in the application that is of interest; it is in the Form Load event.
shpCard.Visible = False
By setting the Visible property of the shape control to False, the shape control is hidden until the first
image is clicked. The Visible property is set to True as the last step in the image control Click event.
For More Information For additional information on properties, methods, and events see
"Programming Fundamentals."
Additional Controls
See Also
50
Several other standard controls are included in the Visual Basic toolbox. Some controls are useful for
working with large amounts of data contained in an external database. Other controls can be used to
access the Windows file system. Still other controls defy categorization, but are useful nonetheless.
You can also use ActiveX controls, previously called custom or OLE controls, in a Visual Basic application in
the same way that you use the standard controls. The Professional and Enterprise editions of Visual Basic
include several ActiveX controls as well as the capability to build your own controls. Additional ActiveX
controls for just about any purpose imaginable are available for purchase from numerous vendors.
For More Information For additional information on using ActiveX controls, see "Managing Projects."
In today's business, most information is stored in one or more central databases. Visual Basic includes
several data access controls for accessing most popular databases, including Microsoft Access and SQL
Server.
• The ADO Data control is used to connect to a database. Think of it as a pipeline between the database
and the other controls on your form. Its properties, methods, and events allow you to navigate and
• The DataList control is similar to the list box control. When used in conjunction with an ADO Data
control, it can be automatically filled with a list of data from a field in an external database.
• The DataCombo control is like a combination of the DataList control and a text box. The selected text
in the text box portion can be edited, with the changes appearing in the underlying database.
• The DataGrid control displays data in a grid or table. When used in conjunction with an ADO Data
control, it presents fully editable data from multiple fields in an external database.
• The Microsoft Hierarchical FlexGrid control is a unique control for presenting multiple views of data.
Think of it as a combination of a grid and a tree or outline control. At run time, the user can
For More Information For additional information on data access controls, see "Using Visual Basic's
Standard Controls." For more information on working with external data, see the Visual Basic Data Access
Guide.
Visual Basic includes three controls for adding file handling capabilities to your application. These controls
are normally used together to provide a view of drives, directories and files; they have special properties
• The DriveListBox control looks like a combo box. It provides a drop-down list of drives from which the
• The DirListBox is similar to a list box control, but with the built-in capability of displaying a list of
• The FileListBox control also looks like a list box with a list of file names in a selected directory.
Note These controls are provided primarily for backward compatibility with applications created in earlier
versions of Visual Basic. The common dialog control provides an easier method of working with file access.
For more information on common dialog control, see "Miscellaneous Controls" later in this chapter.
Miscellaneous Controls
Several other standard controls are included in Visual Basic. Each serves a unique purpose.
• The timer control can be used to create an event in your application at a recurring interval. This is
useful for executing code without the need for user interaction.
• The OLE container control is an easy way to add capabilities like linking and embedding to your
application. Through the OLE container control, you can provide access to the functionality of any
• The common dialog control adds built-in dialog boxes to your application for the selection of files,
For More Information For additional information on any of the standard controls, see "Using Visual
Understanding Focus
See Also
Focus is the ability to receive user input through the mouse or keyboard. When an object has the focus, it
can receive input from a user. In the Microsoft Windows interface, several applications can be running at
any time, but only the application with the focus will have an active title bar and can receive user input.
52
On a Visual Basic form with several text boxes, only the text box with the focus will display text entered
The GotFocus and LostFocus events occur when an object receives or loses focus. Forms and most controls
Event Description
LostFocus Occurs when an object loses focus. A LostFocus event procedure is primarily
used for verification and validation updates, or for reversing or changing
conditions you set up in the object's GotFocus procedure.
You can see when some objects have the focus. For example, when command buttons have the focus,
they appear with a highlighted border around the caption (see Figure 3.19).
An object can receive focus only if its Enabled and Visible properties are set to True. The Enabled property
allows the object to respond to user-generated events such as keyboard and mouse events. The Visible
Note A form can receive focus only if it doesn't contain any controls that can receive the focus.
Controls also have a Validate event, which occurs before a control loses focus. However, this event occurs
only when the CausesValidation property of the control that is about to receive the focus is set to True. In
53
many cases, because the Validate event occurs before the focus is lost, it is more appropriate than the
LostFocus event for data validation. For more information, see "Validating Control Data By Restricting
Some controls, such as the lightweight controls, cannot receive focus. Lightweight controls include the
following:
• Frame control
• Image control
• Label control
• Line control
• Shape control
Additionally, controls that are invisible at run time, such as the Timer control, cannot receive focus.
The tab order is the order in which a user moves from one control to another by pressing the TAB key.
Each form has its own tab order. Usually, the tab order is the same as the order in which you created the
controls.
For example, assume you create two text boxes, Text1 and Text2, and then a command button,
Command1. When the application starts, Text1 has the focus. Pressing TAB moves the focus between
To change the tab order for a control, set the TabIndex property. The TabIndex property of a control
determines where it is positioned in the tab order. By default, the first control drawn has a TabIndex value
of 0, the second has a TabIndex of 1, and so on. When you change a control's tab order position, Visual
Basic automatically renumbers the tab order positions of the other controls to reflect insertions and
deletions. For example, if you make Command1 first in the tab order, the TabIndex values for the other
Text1 0 1
Text2 1 2
Command1 2 0
The highest TabIndex setting is always one less than the number of controls in the tab order (because
numbering starts at 0). Even if you set the TabIndex property to a number higher than the number of
controls, Visual Basic converts the value back to the number of controls minus 1.
Note Controls that cannot get the focus, as well as disabled and invisible controls, don't have a TabIndex
property and are not included in the tab order. As a user presses the TAB key, these controls are skipped.
Usually, pressing TAB at run time selects each control in the tab order. You can remove a control from the
A control whose TabStop property has been set to False still maintains its position in the actual tab order,
even though the control is skipped when you cycle through the controls with the TAB key.
Note An option button group has a single tab stop. The selected button (that is, the button with its Value
set to True) has its TabStop property automatically set to True, while the other buttons have their TabStop
Menu Basics
See Also
If you want your application to provide a set of commands to users, menus offer a convenient and
consistent way to group commands and an easy way for users to access them.
55
The menu bar appears immediately below the title bar on the form and contains one or more menu titles.
When you click a menu title (such as File), a menu containing a list of menu items drops down. Menu
items can include commands (such as New and Exit), separator bars, and submenu titles. Each menu item
the user sees corresponds to a menu control you define in the Menu Editor (described later in this
chapter).
To make your application easier to use, you should group menu items according to their function. In
Figure 3.21, for example, the file-related commands New, Open, and Save As are all found on the File
menu.
Some menu items perform an action directly; for example, the Exit menu item on the File menu closes the
application. Other menu items display a dialog box — a window that requires the user to supply
information needed by the application to perform the action. These menu items should be followed by an
ellipsis (). For example, when you choose Save As from the File menu, the Save File As dialog box
appears.
A menu control is an object; like other objects it has properties that can be used to define its appearance
and behavior. You can set the Caption property, the Enabled and Visible properties, the Checked property,
56
and others at design time or at run time. Menu controls contain only one event, the Click event, which is
invoked when the menu control is selected with the mouse or using the keyboard.
For More Information For additional information on menu controls, see "Creating Menus with the Menu
Pop-up Menus
A pop-up menu is a floating menu that is displayed over a form, independent of the menu bar, as shown in
Figure 3.22. The items displayed on the pop-up menu depend on the location of the pointer when the right
mouse button is pressed; therefore, pop-up menus are also called context menus. (In Windows 95 or
later, you activate context menus by clicking the right mouse button.) You should use pop-up menus to
provide an efficient method for accessing common, contextual commands. For example, if you click a text
box with the right mouse button, a contextual menu would appear, as shown in Figure 3.22.
Any menu that has at least one menu item can be displayed at run time as a pop-up menu. To display a
For More Information For additional information on creating pop-up menus, see "Creating Menus" in
With the Menu Editor, you can add new commands to existing menus, replace existing menu commands
with your own commands, create new menus and menu bars, and change and delete existing menus and
57
menu bars. The main advantage of the Menu Editor is its ease of use. You can customize menus in a
While most menu control properties can be set using the Menu Editor; all menu properties are also
available in the Properties window. You would normally create a menu in the Menu Editor; however, to
quickly change a single property, you could use the Properties window.
For More Information For additional information on creating menus and using the Menu Editor, see
In Windows-based applications, dialog boxes are used to prompt the user for data needed by the
application to continue or to display information to the user. Dialog boxes are a specialized type of form
• Predefined dialog boxes can be created from code using the MsgBox or InputBox functions.
• Customized dialog boxes can be created using a standard form or by customizing an existing dialog
box.
• Standard dialog boxes, such as Print and File Open, can be created using the common dialog control.
Figure 3.24 shows an example of a predefined dialog box created using the MsgBox function.
This dialog is displayed when you invoke the MsgBox function in code. The code for displaying the dialog
MsgBox "Error encountered while trying to open file," & vbCrLf & "please retry.",
vbExclamation, "Text Editor"
You supply three pieces of information, or arguments, to the MsgBox function: the message text, a
constant (numeric value) to determine the style of the dialog box, and a title. Styles are available with
various combinations of buttons and icons to make creating dialog boxes easy.
Because most dialog boxes require user interaction, they are usually displayed as modal dialog boxes. A
modal dialog box must be closed (hidden or unloaded) before you can continue working with the rest of
the application. For example, a dialog box is modal if it requires you to click OK or Cancel before you can
Modeless dialog boxes let you shift the focus between the dialog box and another form without having to
close the dialog box. You can continue to work elsewhere in the current application while the dialog box is
displayed. Modeless dialog boxes are rare; you will usually display a dialog because a response is needed
59
before the application can continue. From the Edit menu, the Find dialog box in Visual Basic is an example
of a modeless dialog box. Use modeless dialog boxes to display frequently used commands or information.
For More Information For additional information on creating dialog boxes, see "Creating a User
Interface."
Managing Projects
See Also
To create an application with Visual Basic, you work with projects. A project is the collection of files you
use to build an application. This chapter describes how to build and manage projects.
When you create an application, you will usually create new forms; you might also reuse or modify forms
that were created for previous projects. The same is true for other modules or files that you might include
in your project. ActiveX controls and objects from other applications can also be shared between projects.
After all of the components in a project have been assembled and the code written, you compile your
Topics
Working with Projects
A discussion of some of the options that can be set on a project by project basis.
A discussion of additional tools for working with projects and extending Visual Basic.
As you develop an application, you work with a project to manage all the different files that make up the
• One project file that keeps track of all the components (.vbp).
• One binary data file for each form containing data for properties of controls on the form (.frx). These
files are not editable and are automatically generated for any .frm file that contains binary properties,
The project file is simply a list of all the files and objects associated with the project, as well as
information on the environment options you set. This information is updated every time you save the
project. All of the files and objects can be shared by other projects as well.
When you have completed all the files for a project, you can convert the project into an executable file
(.exe): From the File menu, choose the Make project.exe command.
61
Note With the Professional and Enterprise editions of Visual Basic, you can also create other types of
executable files such as .ocx and .dll files. References in this chapter assume a standard .exe project; for
additional information related to other project types see the Component Tools Guide.
For More Information For more details about creating executables, see "Making and Running an
Executable File," later in this chapter. For information about binary data files and project files, see "Visual
As you create, add, or remove editable files from a project, Visual Basic reflects your changes in the
Project Explorer window, which contains a current list of the files in the project. The Project Explorer
window in Figure 4.1 shows some of the types of files you can include in a Visual Basic project.
Each time you save a project, Visual Basic updates the project file (.vbp). A project file contains the same
list of files that appears in the Project Explorer window, as well as references to the ActiveX controls and
You can open an existing project file by double-clicking its icon, by choosing the Open Project command
from the File menu, or by dragging the file and dropping it on the Project Explorer window.
For More Information The specific format of information stored in the .vbp file is described in "Visual
The following sections describe the different types of files and objects that you can include in a project.
Form Modules
Form modules (.frm file name extension) can contain textual descriptions of the form and its controls,
including their property settings. They can also contain form-level declarations of constants, variables, and
For More Information For more about creating forms, see "Developing an Application in Visual Basic"
and "Creating a User Interface." For information about the format and content of form files, see "Visual
Class Modules
Class modules (.cls file name extension) are similar to form modules, except that they have no visible user
interface. You can use class modules to create your own objects, including code for methods and
properties.
For More Information For information about writing code in class modules, see "Creating Your Own
Standard Modules
Standard modules (.bas file name extension) can contain public or module-level declarations of types,
For More Information For information about using modules, see "Programming Fundamentals" and
Resource Files
Resource files (.res file name extension) contain bitmaps, text strings, and other data that you can change
without having to re-edit your code. For example, if you plan to localize your application in a foreign
language, you can keep all of the user-interface text strings and bitmaps in a resource file, which you can
then localize instead of the entire application. A project can contain no more than one resource file.
For More Information For more information on using resource files, see "Using a Resource File" later in
ActiveX Documents
63
ActiveX documents (.dob) are similar to forms, but are displayable in an Internet browser such as Internet
Explorer. The Professional and Enterprise editions of Visual Basic are capable of creating ActiveX
documents.
For More Information For more information on ActiveX documents, see "Creating ActiveX
User Control (.ctl) and Property Page (.pag) modules are also similar to forms, but are used to create
ActiveX controls and their associated property pages for displaying design-time properties. The
Professional and Enterprise editions of Visual Basic are capable of creating ActiveX controls.
For More Information For more information on ActiveX control creation, see "Creating an ActiveX
Components
In addition to files and modules, several other types of components can be added to the project.
ActiveX Controls
ActiveX controls (.ocx file name extension) are optional controls which can be added to the toolbox and
used on forms. When you install Visual Basic, the files containing the controls included with Visual Basic
are copied to a common directory (the \Windows\System subdirectory under Windows 95 or later).
Additional ActiveX controls are available from a wide variety of sources. You can also create your own
For More Information For more information on using the included ActiveX controls, see "Using the
Insertable Objects
Insertable objects, such as a Microsoft Excel Worksheet object, are components you can use as building
blocks to build integrated solutions. An integrated solution can contain data in different formats, such as
spreadsheets, bitmaps, and text, which were all created by different applications.
For More Information For more information on using other applications' objects, see "Programming
with Components."
References
64
You can also add references to external ActiveX components that may be used by your application. You
assign references by using the References dialog, accessed from the References menu item on the Project
menu.
For More Information For more information on references, see "Using Other Applications' Objects"
ActiveX Designers
ActiveX designers are tools for designing classes from which objects can be created. The design interface
for forms is the default designer. Additional designers may be available from other sources.
For More Information For more information about ActiveX designers, see "ActiveX Designers" in
Standard Controls
Standard controls are supplied by Visual Basic. Standard controls, such as the command button or frame
control, are always included in the toolbox, unlike ActiveX controls and insertable objects, which can be
For More Information For more information on standard controls, see "Forms, Controls, and Menus"
Four commands on the File menu allow you to create, open, and save projects.
New Project Closes the current project, prompting you to save any files that have
changed. You can select a type of project from the New Project dialog. Visual
Basic then creates a new project with a single new file.
Open Project Closes the current project, prompting you to save any changes. Visual Basic
then opens an existing project, including the forms, modules, and ActiveX
controls listed in its project (.vbp) file.
Save Project Updates the project file of the current project and all of its form, standard,
and class modules.
Save Project As Updates the project file of the current project, saving the project file under a
file name that you specify. Visual Basic also prompts you to save any forms
or modules that have changed.
65
It is also possible to share files between projects. A single file, such as a form, can be part of more than
one project. Note that changes made to a form or module in one project will be propagated amongst all
For More Information For more information about sharing files, see "Adding, Removing, and Saving
In the Professional and Enterprise editions of Visual Basic, it is possible to have more than one project
open at a time. This is useful for building and testing solutions involving user-created controls or other
components. When more than one project is loaded, the caption of the Project Explorer window will
change to Project Group and the components of all open projects will be displayed.
For More Information To learn more about working with multiple projects, see "Creating ActiveX
Working with files within a project is similar to working with the projects themselves.
When you add a file to a project, you are simply including a reference to the existing file in the project;
you are not adding a copy of the file. Therefore, if you make changes to a file and save it, your changes
will affect any project that includes the file. To change a file without affecting other projects, select the file
in the Project Explorer, choose Save filename As from the File menu, and then save the file under a new
file name.
Note You can drag and drop files from the Windows Explorer, File Manager, or Network Neighborhood
into the Project window to add them to a project. You can also drag and drop .ocx files onto the toolbox to
3. The file will be removed from the project but not from the disk.
If you remove a file from a project, Visual Basic updates this information in the project file when you save
it. If you delete a file outside of Visual Basic, however, Visual Basic cannot update the project file;
67
therefore, when you open the project, Visual Basic displays an error message warning you that a file is
missing.
Merging Text
You can also insert existing text from other files into one of your code modules. This is useful for adding a
list of constants or for adding snippets of code that you might have saved in text files.
1. From the Project window, select the form or module into which you want to insert code.
2. Choose the View Code button, and move the cursor to the point in the Code Editor where you want
to insert code.
4. Select the name of the text file you want to insert, and choose Open.
Note If you edit Visual Basic source files using a text or code editor other than Visual Basic, be careful
not to change settings of the attribute VB_PredeclaredId. In particular, changing this attribute may cause
In general, you should not edit attributes manually, as doing so may put the module into an internally
inconsistent state.
The set of controls available in the toolbox can be customized for each project. Any given control must be
in the toolbox before you can add it to a form in the project. The basic set of standard controls that always
You can add ActiveX controls and insertable objects to your project by adding them to the toolbox.
The Components dialog box is displayed, as shown in Figure 4.3. The items listed in this dialog box
include all registered ActiveX controls, insertable objects, and ActiveX designers.
2. To add a control (.ocx file name extension) or an insertable object to the toolbox, select the check
box to the left of the control name.
To view controls with .ocx file name extensions, select the Controls tab. To view insertable objects,
3. Choose OK to close the Components dialog box. All of the ActiveX controls that you selected will
now appear in the toolbox.
To add ActiveX controls to the Components dialog box, choose the Browse button, and search other
directories for files with a .ocx file name extension. When you add an ActiveX control to the list of
Note Each ActiveX control is accompanied by a file with an .oca extension. This file stores cached type
library information and other data specific to the control. The .oca files are typically stored in the same
directory as the ActiveX controls and are recreated as needed (file sizes and dates may change).
2. Clear the check box next to each control you want to remove.
Note You cannot remove any control from the toolbox if an instance of that control is used on any form
in the project.
You can also use objects from other applications, such as those included in the Microsoft Excel object
library, either as controls in the toolbox or as programmable objects in your code. To add objects to the
To make another application's objects available in your code, but not as controls, set a reference to that
2. Select the check box next to each reference you want to add to your project.
To add references to applications not listed in the References dialog box, choose the Browse
If you are not using any objects in a referenced library, you should clear the check box for that reference
to minimize the number of object references Visual Basic must resolve, thus reducing the time it takes
Once you have set references to the object libraries you want, you can find a specific object and its
methods and properties in the Object Browser by choosing Object Browser from the View menu. You can
For More Information " For information on the Object Browser, see "Finding Out About Objects" in
A resource file allows you to collect all of the version-specific text and bitmaps for an application in one
place. This can include constant declarations, icons, screen text, and other material that may change
A single project can have only one resource file; if you add a second file with a .res extension, an error
occurs.
For More Information For more information on the contents of a resource file, see "International
Issues."
You can make an executable file (.exe) from Visual Basic using the following procedure.
1. From the File menu, choose Make projectname .exe where projectname is the application name for
the project.
2. Type a file name, or browse through the directories and select an existing file name to overwrite an
existing executable with a newer version.
3. By clicking the Options button, you can also specify a number of version-specific details about the
executable file in the Project Properties dialog box.
4. If you want to modify the version number of the project, set the appropriate Major, Minor, and
Revision numbers. Selecting Auto Increment will automatically step the Revision number each
time you run the Make projectname .exe command for this project.
5. To specify a new name for the application, under Application, type a new name in the Title box. If
you want to specify a new icon, choose one from the list.
6. You can also enter version-specific commentary on a variety of issues under the Version
Information box (comments, company name, trademark and copyright information, and so on) by
selecting a topic from the list box and entering information in the text box.
7. Choose OK to close the Project Properties dialog box, and then choose OK in the Make appname
.exe dialog box to compile and link the executable file.
You can run the executable file like any other Windows-based application: double-click the icon for the
executable file.
Note Building an executable file from the command line in a DOS session can be useful when you want
For projectname, type the name of the project file. Use the variable exename to rename the resulting
executable file.
Conditional Compilation
Conditional compilation lets you selectively compile certain parts of the program. You can include specific
features of your program in different versions, such as changing the date and currency display filters for
For More Information To learn more about conditional compilation, see "Using Conditional Compilation"
Visual Basic allows you to customize each project by setting a number of properties. Use the Project
Properties dialog box, accessible through the Project Properties command on the Project menu. Property
The following table describes some of the options you can set.
Option Description
Startup Object The first form that Visual Basic displays at run time, or Sub Main ( ).
Project Name Identifies the project in code. It can't contain periods (.), spaces, or
start with a nonalphabetic character. For a public class name, the
project name and class name cannot exceed a total of 37 characters.
Help File The name of the Help file associated with the project.
Project Help Context ID The context ID for the specific Help topic to be called when the user
selects the "?" button while the application's object library is selected
in the Object Browser.
Project Description A user-friendly name for the project. Displayed in the References and
Object Browser dialog boxes.
Many other options are also available, including those for compiling, components, and multithreading.
When you're ready to access some of the more advanced options, you can find more information by
searching Help.
For More Information To learn about setting environment options that affect all projects, see
See Also
Visual Basic allows you to select and manage add-ins, which are extensions to Visual Basic. These
extensions add capabilities to the Visual Basic development environment, for example, special source code
control capabilities.
Microsoft and other developers have created add-ins you can use in your applications. Wizards are a type
of add-in that can simplify certain tasks, such as creating a form. Several wizards are included in Visual
Basic.
To have an add-in appear on the Add-In Manager dialog box, the developer of the add-in must ensure that
it is installed properly.
You can add or remove an add-in to your project by using the Add-In Manager, which is accessible from
the Add-Ins menu. The Add-In Manager dialog box lists the available add-ins.
To install an add-in
2. Highlight an add-in from the list and click the desired behaviors in Load Behavior. To unload an add-in
or prevent it from loading, clear all Load Behavior boxes.
Depending upon your Load Behavior selections, Visual Basic connects the selected add-ins and
Note Selecting an add-in may add menu items to the Visual Basic Add-Ins menu.
Using Wizards
Wizards make working with Visual Basic even easier by providing task-specific assistance. For example,
the Application Wizard included in Visual Basic helps you to create the framework for an application by
presenting a series of questions or choices. It generates the forms and the code behind the forms based
on your choices; all you need to do is add code for your own specific functionality.
74
The Professional and Enterprise editions of Visual Basic include other wizards, including a Data Form
Wizard for creating forms to be used with databases, and an ActiveX Document Wizard for converting
Wizards are installed or removed using the Add-in Manager. Once installed, they will appear as selections
on the Add-Ins menu. Some of the wizards also appear as icons in the related dialog boxes; for example,
the Application Wizard can also be accessed using its icon in the New Project dialog box.
–or–
Programming Fundamentals
See Also
This chapter introduces the essential components of the Visual Basic language. After creating the interface
for your application using forms and controls, you will need to write the code that defines the application's
behavior. As with any modern programming language, Visual Basic supports a number of common
Visual Basic is an object-based programming language. The mere mention of objects may cause undue
anxiety in many programmers. Don't worry: whether you realize it or not, you've been dealing with
objects most of your life. Once you understand a few basic concepts, objects actually help to make
If you've programmed in other languages, much of the material covered in this chapter will seem familiar.
While most of the constructs are similar to other languages, the event-driven nature of Visual Basic
introduces some subtle differences. Try and approach this material with an open mind; once you
If you're new to programming, the material in this chapter will serve as an introduction to the basic
building blocks for writing code. Once you understand the basics, you will be able to create powerful
Topics
The Structure of a Visual Basic Application
An introduction to the various components or modules that make up a Visual Basic application.
An introduction to the features of the Code Editor, plus the rules and regulations for writing code.
Introduction to Procedures
Sample application
Vcr.vbp
Many of the code samples in this chapter are taken from the Vcr.vbp sample application which is
An application is really nothing more than a set of instructions directing the computer to perform a task or
tasks. The structure of an application is the way in which the instructions are organized; that is, where the
instructions are stored and the order in which instructions are executed.
76
Simple applications such as the classic "hello world" example have a simple structure; organization isn't
very important with a single line of code. As applications become more complex, the need for organization
or structure becomes obvious. Imagine the chaos that would result if your application's code was allowed
to execute in random order. In addition to controlling the execution of an application, the structure is
important to the programmer: how easily can you find specific instructions within your application?
Because a Visual Basic application is based on objects, the structure of its code closely models its physical
representation on screen. By definition, objects contain data and code. The form that you see on screen is
a representation of the properties that define its appearance and intrinsic behavior. For each form in an
application, there is a related form module (with file name extension .frm) that contains its code.
Each form module contains event procedures — sections of code where you place the instructions that will
execute in response to specific events. Forms can contain controls. For each control on a form, there is a
corresponding set of event procedures in the form module. In addition to event procedures, form modules
can contain general procedures that are executed in response to a call from any event procedure.
77
Code that isn't related to a specific form or control can be placed in a different type of module, a standard
module (.BAS). A procedure that might be used in response to events in several different objects should
be placed in a standard module, rather than duplicating the code in the event procedures for each object.
A class module (.CLS) is used to create objects that can be called from procedures within your application.
Whereas a standard module contains only code, a class module contains both code and data — you can
While "Managing Projects" describes which components you can add to an application, this chapter
explains how to write code in the various components that make up an application. By default, your
project contains a single form module. You can add additional form, class, and standard modules, as
An event is an action recognized by a form or control. Event-driven applications execute Basic code in
response to an event. Each form and control in Visual Basic has a predefined set of events. If one of these
events occurs and there is code in the associated event procedure, Visual Basic invokes that code.
Although objects in Visual Basic automatically recognize a predefined set of events, it is up to you to
decide if and how they will respond to a particular event. A section of code — an event procedure —
corresponds to each event. When you want a control to respond to an event, you write code in the event
The types of events recognized by an object vary, but many types are common to most controls. For
example, most objects recognize a Click event — if a user clicks a form, code in the form's Click event
procedure is executed; if a user clicks a command button, code in the button's Click event procedure is
executed. The actual code in each case will most likely be quite different.
2. The form (or a control on the form) receives an event. The event might be caused by the user (for
example, a keystroke), by the system (for example, a timer event), or indirectly by your code (for
example, a Load event when your code loads a form).
Note Many events occur in conjunction with other events. For example, when the DblClick event occurs,
Perhaps the most important (and often overlooked) part of creating an application in Visual Basic is the
design phase. While it's obvious that you need to design a user interface for your application, it may not
be as obvious that you need to design the structure of the code. The way you structure your application
can make a difference in its performance as well as in the maintainability and usability of your code.
The code in a Visual Basic application is organized in a hierarchical fashion. A typical application consists of
one or more modules: a form module for each form in the application, optional standard modules for
shared code, and optional class modules. Each module contains one or more procedures that contain the
Determining which procedures belong in which module depends somewhat on the type of application that
you are creating. Because Visual Basic is based on objects, it helps to think of your application in terms of
the objects that it represents. The design of the sample application for this chapter, Vcr.vbp, is based on
the objects that comprise a video cassette recorder and a television. The VCR application consists of two
form modules, a standard module, and two class modules. You can use the Object Browser to examine the
Figure 5.2 The structure of the VCR project is shown in the Object Browser
79
The main form for the VCR application (frmVCR) is a visual representation of a combination VCR and
television screen (Figure 5.3). It is composed of several objects that model those found in the real world
version. A group of Command buttons (cmdPlay, cmdRecord, and so on) mimic the buttons used to
operate a VCR. The software VCR also contains a clock (lblTime), a channel indicator (lblChannel), function
indicators (shpPlay, shpRecord, and so on), and a "picture tube" (picTV). The event procedures for all of
In many cases there are repetitive procedures that are shared by more than one object. For example,
when the Play, Rewind, or Record buttons are "pushed," the Pause and Stop buttons need to be enabled.
Rather than repeat this code in each button's Click event procedure, it's better to create a shared Sub
procedure that can be called by any button. If these procedures need to be modified in the future, all of
the modifications can be done in one place. This and other shared procedures are contained in the
Some parts of a VCR aren't visible, such as the tape transport mechanism or the logic for recording a
television program. Likewise, some of the functions of the software VCR have no visual representation.
These are implemented as two class modules: Recorder.cls and Tape.cls. Code to initiate the "recording"
process is contained in the clsRecorder module; code to control the direction and speed of the "tape" is
contained in the clsTape module. The classes defined in these modules have no direct references to any of
the objects in the forms. Because they are independent code modules, they could easily be reused to build
In addition to designing the structure of your code, it's important to establish naming conventions. By
default, Visual Basic names the first form in a project Form1, the second Form2, and so on. If you have
several forms in an application, it's a good idea to give them meaningful names to avoid confusion when
writing or editing your code. Some suggested naming conventions are presented in "Visual Basic Coding
Conventions."
As you learn more about objects and writing code, you can refer to the VCR sample application for
Before you begin, it's important to understand the mechanics of writing code in Visual Basic. Like any
programming language, Visual Basic has its own rules for organizing, editing, and formatting code.
The following topics introduce code modules and procedures, discuss the basics of using the Code Editor,
• Code Modules An introduction to the different types of code modules and the procedures that they
contain.
• Using the Code Editor An introduction to working with code using the Code Editor.
Code Modules
See Also
Code in Visual Basic is stored in modules. There are three kinds of modules: form, standard, and class.
Simple applications can consist of just a single form, and all of the code in the application resides in that
form module. As your applications get larger and more sophisticated, you add additional forms. Eventually
you might find that there is common code you want to execute in several forms. You don't want to
duplicate the code in both forms, so you create a separate module containing a procedure that
implements the common code. This separate module should be a standard module. Over time, you can
• Declarations. You can place constant, type, variable, and dynamic-link library (DLL) procedure
• Procedures. A Sub, Function, or Property procedure contains pieces of code that can be executed as a
unit. These are discussed in the section "Procedures" later in this chapter.
Form Modules
Form modules (.FRM file name extension) are the foundation of most Visual Basic applications. They can
contain procedures that handle events, general procedures, and form-level declarations of variables,
constants, types, and external procedures. If you were to look at a form module in a text editor, you
would also see descriptions of the form and its controls, including their property settings. The code that
you write in a form module is specific to the particular application to which the form belongs; it might also
Standard Modules
Standard modules (.BAS file name extension) are containers for procedures and declarations commonly
accessed by other modules within the application. They can contain global (available to the whole
application) or module-level declarations of variables, constants, types, external procedures, and global
procedures. The code that you write in a standard module isn't necessarily tied to a particular application;
if you're careful not to reference forms or controls by name, a standard module can be reused in many
different applications.
Class Modules
Class modules (.CLS file name extension) are the foundation of object-oriented programming in Visual
Basic. You can write code in class modules to create new objects. These new objects can include your own
customized properties and methods. Actually, forms are just class modules that can have controls placed
For More Information For information about writing code in class modules, see "Programming with
Objects."
Note The Professional and Enterprise editions of Visual Basic also include ActiveX Documents, ActiveX
Designers, and User Controls. These introduce new types of modules with different file name extensions.
From the standpoint of writing code, these modules should be considered the same as form modules.
The Visual Basic Code Editor is a window where you write most of your code. It is like a highly specialized
word processor with a number of features that make writing Visual Basic code a lot easier. The Code Editor
Because you work with Visual Basic code in modules, a separate Code Editor window is opened for each
module you select from the Project Explorer. Code within each module is subdivided into separate sections
for each object contained in the module. Switching between sections is accomplished using the Object
Listbox. In a form module, the list includes a general section, a section for the form itself, and a section
for each control contained on the form. For a class module, the list includes a general section and a class
Each section of code can contain several different procedures, accessed using the Procedure Listbox. The
procedure list for a form module contains a separate section for each event procedure for the form or
84
control. For example, the procedure list for a Label control includes sections for the Change, Click, and
DblClick events, among others. Class modules list only the event procedures for the class itself — Initialize
and Terminate. Standard modules don't list any event procedures, because a standard module doesn't
support events.
The procedure list for a general section of a module contains a single selection — the Declarations section,
where you place module-level variable, constant, and DLL declarations. As you add Sub or Function
procedures to a module, those procedures are added in the Procedure Listbox below the Declarations
section.
Two different views of your code are available in the Code Editor window. You can choose to view a single
procedure at a time, or to view all of the procedures in the module with each procedure separated from
the next by a line (as shown in Figure 5.4). To switch between the two views, use the View Selection
Visual Basic makes writing code much easier with features that can automatically fill in statements,
properties, and arguments for you. As you enter code, the editor displays lists of appropriate choices,
statement or function prototypes, or values. Options for enabling or disabling these and other code
settings are available on the Editor tab of the Options dialog, accessed through the Options command on
When you enter the name of a control in your code, the Auto List Members feature presents a drop-down
list of properties available for that control (Figure 5.5). Type in the first few letters of the property name
and the name will be selected from the list; the TAB key will complete the typing for you. This option is
also helpful when you aren't sure which properties are available for a given control. Even if you choose to
disable the Auto List Members feature, you can still access it with the CTRL+J key combination.
The Auto Quick Info feature displays the syntax for statements and functions (Figure 5.6). When you enter
the name of a valid Visual Basic statement or function the syntax is shown immediately below the current
line, with the first argument in bold. After you enter the first argument value, the second argument
appears in bold. Auto Quick Info can also be accessed with the CTRL+I key combination.
Bookmarks
Bookmarks can be used to mark lines of code in the Code Editor so that you can easily return to them
later. Commands to toggle bookmarks on or off as well as to navigate existing bookmarks are available
from the Edit, Bookmarks menu item, or from the Edit toolbar
86
For More Information For more information on key combinations to access these and other functions
Code Basics
See Also
This section presents information on code writing mechanics, including breaking and combining lines of
code, adding comments to your code, using numbers in code, and following naming conventions in Visual
Basic.
You can break a long statement into multiple lines in the Code window using the line-continuation
character (a space followed by an underscore). Using this character can make your code easier to read,
both online and when printed. The following code is broken into three lines with line-continuation
characters ( _):
Data1.RecordSource = _
You can't follow a line-continuation character with a comment on the same line. There are also some
There is usually one Visual Basic statement to a line, and there is no statement terminator. However, you
can place two or more statements on a line if you use a colon (:) to separate them:
Red
In order to make your code more readable, however, it's better to place each statement on a separate
line.
For More Information For more information, see "Visual Basic Specifications, Limitations, and File
Formats."
As you read through the examples in this guide, you'll often come across the comment symbol ('). This
symbol tells Visual Basic to ignore the words that follow it. Such words are remarks placed in the code for
the benefit of the developer, and other programmers who might examine the code later. For example:
' screen.
' box.
Comments can follow a statement on the same line or can occupy an entire line. Both are illustrated in the
preceding code. Remember that comments can't follow a line-continuation character on the same line.
Note You can add or remove comment symbols for a block of code by selecting two or more lines of
code and choosing the Comment Block or Uncomment Block buttons on the Edit toolbar.
Most numbers in this documentation are decimal (base 10). But occasionally it's convenient to use
hexadecimal numbers (base 16) or octal numbers (base 8). Visual Basic represents numbers in
hexadecimal with the prefix &H and in octal with &O. The following table shows the same numbers in
9 &O11 &H9
15 &O17 &HF
16 &O20 &H10
20 &O24 &H14
You generally don't have to learn the hexadecimal or octal number system yourself because the computer
can work with numbers entered in any system. However, some number systems lend themselves to
certain tasks, such as using hexadecimals to set the screen and control colors.
While you are writing Visual Basic code, you declare and name many elements (Sub and Function
procedures, variables, constants, and so on). The names of the procedures, variables, and constants that
you declare in your Visual Basic code must follow these guidelines:
88
• They can't contain embedded periods or type-declaration characters (special characters that specify a
data type.
• They can be no longer than 255 characters. The names of controls, forms, classes, and modules must
A restricted keyword is a word that Visual Basic uses as part of its language. This includes predefined
statements (such as If and Loop), functions (such as Len and Abs), and operators (such as Or and Mod).
For More Information For a complete list of keywords, see the Language Reference.
Your forms and controls can have the same name as a restricted keyword. For example, you can have a
control named Loop. In your code you cannot refer to that control in the usual way, however, because
Visual Basic assumes you mean the Loop keyword. For example, this code causes an error:
To refer to a form or control that has the same name as a restricted keyword, you must either qualify it or
surround it with square brackets: [ ]. For example, this code does not cause an error:
' name.
' work.
You can use square brackets in this way when referring to forms and controls, but not when declaring a
variable or defining a procedure with the same name as a restricted keyword. Square brackets can also be
used to force Visual Basic to accept names provided by other type libraries that conflict with restricted
keywords.
Note Because typing square brackets can get tedious, you might want to refrain from using restricted
keywords as the name of forms and controls. However, you can use this technique if a future version of
Visual Basic defines a new keyword that conflicts with an existing form or control name when you update
You often need to store values temporarily when performing calculations with Visual Basic. For example,
you might want to calculate several values, compare them, and perform different operations on them,
depending on the result of the comparison. You need to retain the values if you want to compare them,
Visual Basic, like most programming languages, uses variables for storing values. Variables have a name
(the word you use to refer to the value the variable contains) and a data type (which determines the kind
of data the variable can store). Arrays can be used to store indexed collections of related variables.
Constants also store values, but as the name implies, those values remain constant throughout the
execution of an application. Using constants can make your code more readable by providing meaningful
names instead of numbers. There are a number of built-in constants in Visual Basic, but you can also
Data types control the internal storage of data in Visual Basic. By default, Visual Basic uses the Variant
data type. There are a number of other available data types that allow you to optimize your code for
speed and size when you don't need the flexibility that Variant provides.
• Variables An introduction to variables: what they are and how to use them.
• Advanced Variant Topics Detailed information about the Variant data type.
• Dynamic Arrays A discussion of using dynamic arrays to work with groups of values.
Variables
See Also
90
In Visual Basic, you use variables to temporarily store values during the execution of an application.
Variables have a name (the word you use to refer to the value the variable contains) and a data type
You can think of a variable as a placeholder in memory for an unknown value. For example, imagine you
are creating a program for a fruit stand to track the sales of apples. You don't know the price of an apple
or the quantity sold until the sale actually occurs. You can use two variables to hold the unknown values —
let's name them ApplePrice and ApplesSold. Each time the program is run, the user supplies the values for
the two variables. To calculate the total sales and display it in a Textbox named txtSales, your code would
The expression returns a different total each time, depending on what values the user provides. The
variables allow you to make a calculation without having to know in advance what the actual inputs are.
In this example, the data type of ApplePrice is Currency; the data type of ApplesSold is an integer.
Variables can represent many other values as well: text values, dates, various numeric types, even
objects.
You use assignment statements to perform calculations and assign the result to a variable:
' variable.
' incremented.
Note that the equal sign in this example is an assignment operator, not an equality operator; the value
Declaring Variables
To declare a variable is to tell the program about it in advance. You declare a variable with the Dim
Variables declared with the Dim statement within a procedure exist only as long as the procedure is
executing. When the procedure finishes, the value of the variable disappears. In addition, the value of a
91
variable in a procedure is local to that procedure — that is, you can't access a variable in one procedure
from another procedure. These characteristics allow you to use the same variable names in different
A variable name:
• Must be unique within the same scope, which is the range from which the variable can be referenced
The optional As type clause in the Dim statement allows you to define the data type or object type of the
variable you are declaring. Data types define the type of information the variable stores. Some examples
of data types include String, Integer, and Currency. Variables can also contain objects from Visual Basic or
other applications. Examples of Visual Basic object types, or classes, include Object, Form1, and TextBox.
For More Information For more information on objects, see "Programming with Objects" and
"Programming with Components." Data types are discussed in detail in the section, "Data Types," later in
this chapter.
• Declaring a variable in the Declarations section of a form, standard, or class module, rather than
within a procedure, makes the variable available to all the procedures in the module.
• Declaring a variable using the Public keyword makes it available throughout your application.
• Declaring a local variable using the Static keyword preserves its value even when a procedure ends.
Implicit Declaration
You don't have to declare a variable before using it. For example, you could write a function where you
Function SafeSqr(num)
TempVal = Abs(num)
92
SafeSqr = Sqr(TempVal)
End Function
Visual Basic automatically creates a variable with that name, which you can use as if you had explicitly
declared it. While this is convenient, it can lead to subtle errors in your code if you misspell a variable
name. For example, suppose that this was the function you wrote:
Function SafeSqr(num)
TempVal = Abs(num)
SafeSqr = Sqr(TemVal)
End Function
At first glance, this looks the same. But because the TempVal variable was misspelled on the next-to-last
line, this function will always return zero. When Visual Basic encounters a new name, it can't determine
whether you actually meant to implicitly declare a new variable or you just misspelled an existing variable
Explicit Declaration
To avoid the problem of misnaming variables, you can stipulate that Visual Basic always warn you
• Place this statement in the Declarations section of a class, form, or standard module:
Option Explicit
–or–
From the Tools menu, choose Options, click the Editor tab and check the Require Variable
Declaration option. This automatically inserts the Option Explicit statement in any new modules, but
not in modules already created; therefore, you must manually add Option Explicit to any existing
Had this statement been in effect for the form or standard module containing the SafeSqr function, Visual
Basic would have recognized TempVal and TemVal as undeclared variables and generated errors for
both of them. You could then explicitly declare TempVal:
Function SafeSqr(num)
93
Dim TempVal
TempVal = Abs(num)
SafeSqr = Sqr(TemVal)
End Function
Now you'd understand the problem immediately because Visual Basic would display an error message for
the incorrectly spelled TemVal. Because the Option Explicit statement helps you catch these kinds of
errors, it's a good idea to use it with all your code.
Note The Option Explicit statement operates on a per-module basis; it must be placed in the
Declarations section of every form, standard, and class module for which you want Visual Basic to enforce
explicit variable declarations. If you select Require Variable Declaration, Visual Basic inserts Option Explicit
in all subsequent form, standard, and class modules, but does not add it to existing code. You must
The scope of a variable defines which parts of your code are aware of its existence. When you declare a
variable within a procedure, only code within that procedure can access or change the value of that
variable; it has a scope that is local to that procedure. Sometimes, however, you need to use a variable
with a broader scope, such as one whose value is available to all the procedures within the same module,
or even to all the procedures in your entire application. Visual Basic allows you to specify the scope of a
Scoping Variables
variable.
Procedure-level Variables are private to the procedure in Not applicable. You cannot declare
which they appear. public variables within a procedure.
Module-level Variables are private to the module in Variables are available to all modules.
which they appear.
Procedure-level variables are recognized only in the procedure in which they're declared. These are also
known as local variables. You declare them with the Dim or Static keywords. For example:
–or–
Values in local variables declared with Static exist the entire time your application is running while
variables declared with Dim exist only as long as the procedure is executing.
Local variables are a good choice for any kind of temporary calculation. For example, you can create a
dozen different procedures containing a variable called intTemp. As long as each intTemp is declared
as a local variable, each procedure recognizes only its own version of intTemp. Any one procedure can
alter the value in its local intTemp without affecting intTemp variables in other procedures.
By default, a module-level variable is available to all the procedures in that module, but not to code in
other modules. You create module-level variables by declaring them with the Private keyword in the
At the module level, there is no difference between Private and Dim, but Private is preferred because it
readily contrasts with Public and makes your code easier to understand.
To make a module-level variable available to other modules, use the Public keyword to declare the
variable. The values in public variables are available to all procedures in your application. Like all module-
level variables, public variables are declared in the Declarations section at the top of the module. For
example:
Note You can't declare public variables within a procedure, only within the Declarations section of a
module.
For More Information For additional information about variables, see "Advanced Variable Topics."
See Also
If public variables in different modules share the same name, it's possible to differentiate between them in
code by referring to both the module and variable names. For example, if there is a public Integer variable
intX declared in both Form1 and in Module1, you can refer to them as Module1.intX and Form1.intX
to get the correct values.
To see how this works, insert two standard modules in a new project and draw three command buttons on
a form.
One variable, intX, is declared in the first standard module, Module1. The Test procedure sets its value:
Sub Test()
intX = 1
End Sub
The second variable, which has the same name, intX, is declared in the second standard module,
Module2. Again, a procedure named Test sets its value:
Sub Test()
intX = 2
End Sub
The third intX variable is declared in the form module. And again, a procedure named Test sets its value.
' variable.
Sub Test()
' Set the value for the intX variable in the form.
intX = 3
96
End Sub
Each of the three command buttons' Click event procedures calls the appropriate Test procedure and uses
End Sub
End Sub
End Sub
Run the application and click each of the three command buttons. You'll see the separate references to the
three public variables. Notice in the third command button's Click event procedure, you don't need to
specify Form1.Test when calling the form's Test procedure, or Form1.intX when calling the value of
the form's Integer variable. If there are multiple procedures and variables with the same name, Visual
Basic takes the value of the more local variable, which in this case, is the Form1 variable.
You can also have a variable with the same name at a different scope. For example, you could have a
public variable named Temp and then, within a procedure, declare a local variable named Temp.
References to the name Temp within the procedure would access the local variable; references to Temp
outside the procedure would access the public variable. The module-level variable can be accessed from
within the procedure by qualifying the variable with the module name.
Sub Test()
End Sub
End Sub
Test
End Sub
In general, when variables have the same name but different scope, the more local variable always
shadows (that is, it is accessed in preference to) less local variables. So if you also had a procedure-level
variable named Temp, it would shadow the public variable Temp within that module.
Due to the effect of shadowing, form properties, controls, constants, and procedures are treated as
module-level variables in the form module. It is not legal to have a form property or control with the same
name as a module-level variable, constant, user-defined type, or procedure because both are in the same
scope.
Within the form module, local variables with the same names as controls on the form shadow the controls.
You must qualify the control with a reference to the form or the Me keyword to set or get its value or any
' Text1.
' control.
' control.
End Sub
The names of your private module-level and public module-level variables can also conflict with the names
of your procedures. A variable in the module cannot have the same name as any procedures or types
defined in the module. It can, however, have the same name as public procedures, types, or variables
defined in other modules. In this case, when the variable is accessed from another module, it must be
While the shadowing rules described above are not complex, shadowing can be confusing and lead to
subtle bugs in your code; it is good programming practice to keep the names of your variables distinct
from each other. In form modules, try to use variables names that are different from names of controls on
those forms.
Static Variables
See Also
In addition to scope, variables have a lifetime, the period of time during which they retain their value. The
values in module-level and public variables are preserved for the lifetime of your application. However,
local variables declared with Dim exist only while the procedure in which they are declared is executing.
Usually, when a procedure is finished executing, the values of its local variables are not preserved and the
memory used by the local variables is reclaimed. The next time the procedure is executed, all its local
However, you can preserve the value of a local variable by making the variable static. Use the Static
keyword to declare one or more variables inside a procedure, exactly as you would with the Dim
statement:
Static Depth
99
For example, the following function calculates a running total by adding a new value to the total of
Function RunningTotal(num)
Static ApplesSold
RunningTotal = ApplesSold
End Function
If ApplesSold was declared with Dim instead of Static, the previous accumulated values would not be
preserved across calls to the function, and the function would simply return the same value with which it
was called.
You can produce the same result by declaring ApplesSold in the Declarations section of the module,
making it a module-level variable. Once you change the scope of a variable this way, however, the
procedure no longer has exclusive access to it. Because other procedures can access and change the value
of the variable, the running totals might be unreliable and the code would be more difficult to maintain.
To make all local variables in a procedure static, place the Static keyword at the beginning of a procedure
This makes all the local variables in the procedure static regardless of whether they are declared with
Static, Dim, Private, or declared implicitly. You can place Static in front of any Sub or Function procedure
Constants
See Also
Often you'll find that your code contains constant values that reappear over and over. Or you may find
that the code depends on certain numbers that are difficult to remember — numbers that, in and of
In these cases, you can greatly improve the readability of your code — and make it easier to maintain —
by using constants. A constant is a meaningful name that takes the place of a number or string that does
100
not change. Although a constant somewhat resembles a variable, you can't modify a constant or assign a
new value to it as you can to a variable. There are two sources for constants:
• Intrinsic or system-defined constants are provided by applications and controls. Visual Basic
constants are listed in the Visual Basic (VB) and Visual Basic for applications (VBA) object libraries in
the Object Browser. Other applications that provide object libraries, such as Microsoft Excel and
Microsoft Project, also provide a list of constants you can use with their objects, methods, and
properties. Constants are also defined in the object library for each ActiveX control. For details on
• Symbolic or user-defined constants are declared using the Const statement. User-defined constants
In Visual Basic, constant names are in a mixed-case format, with a prefix indicating the object library that
defines the constant. Constants from the Visual Basic and Visual Basic for applications object libraries are
The prefixes are intended to prevent accidental collisions in cases where constants have identical names
and represent different values. Even with prefixes, it's still possible that two object libraries may contain
identical constants representing different values. Which constant is referenced in this case depends on
which object library has the higher priority. For information on changing the priority of object libraries, see
To be absolutely sure you avoid constant name collisions, you can qualify references to constants with the
following syntax:
[libname.][modulename.]constname
Libname is usually the class name of the control or library. Modulename is the name of the module that
defines the constant. Constname is the name of the constant. Each of these elements is defined in the
The argument constantname is a valid symbolic name (the rules are the same as those for creating
variable names), and expression is composed of numeric or string constants and operators; however, you
You can place more than one constant declaration on a single line if you separate them with commas:
conWorldPop = 6E+09
The expression on the right side of the equal sign ( = ) is often a number or literal string, but it can also
be an expression that results in a number or string (although that expression can't contain calls to
functions). You can even define constants in terms of previously defined constants:
Once you define constants, you can place them in your code to make it more readable. For example:
A Const statement has scope like a variable declaration, and the same rules apply:
• To create a constant that exists only within a procedure, declare it within that procedure.
• To create a constant available to all procedures within a module, but not to any code outside that
• To create a constant available throughout the application, declare the constant in the Declarations
section of a standard module, and place the Public keyword before Const. Public constants cannot be
For More Information For more information regarding scope, see "Understanding the Scope of
Because constants can be defined in terms of other constants, you must be careful not to set up a cycle,
or circular reference between two or more constants. A cycle occurs when you have two or more public
For example:
' In Module 1:
' application.
' In Module 2:
' application.
If a cycle occurs, Visual Basic generates an error when you attempt to run your application. You cannot
run your code until you resolve the circular reference. To avoid creating a cycle, restrict all your public
Data Types
See Also
Variables are placeholders used to store values; they have names and data types. The data type of a
variable determines how the bits representing those values are stored in the computer's memory. When
you declare a variable, you can also supply a data type for it. All variables have a data type that
By default, if you don't supply a data type, the variable is given the Variant data type. The Variant data
type is like a chameleon — it can represent many different data types in different situations. You don't
have to convert between these types of data when assigning them to a Variant variable: Visual Basic
If you know that a variable will always store data of a particular type, however, Visual Basic can handle
that data more efficiently if you declare a variable of that type. For example, a variable to store a person's
name is best represented as a string data type, because a name is always composed of characters.
Data types apply to other things besides variables. When you assign a value to a property, that value has
a data type; arguments to functions also have data types. In fact, just about anything in Visual Basic that
For More Information For more information, see the section, "Arrays," later in this chapter. Selecting
data types to improve your application's performance is discussed in "Designing for Performance and
Compatibility."
Before using a non-Variant variable, you must use the Private, Public, Dim or Static statement to declare it
As type. For example, the following statements declare an Integer, Double, String, and Currency type,
respectively:
Private I As Integer
Note If you do not supply a data type, the variable is given the default type. In the preceding example,
the variables Test and Amount are of the Variant data type. This may surprise you if your experience
with other programming languages leads you to expect all variables in the same declaration statement to
Visual Basic supplies several numeric data types — Integer, Long (long integer), Single (single-precision
floating point), Double (double-precision floating point), and Currency. Using a numeric data type
If you know that a variable will always store whole numbers (such as 12) rather than numbers with a
fractional amount (such as 3.57), declare it as an Integer or Long type. Operations are faster with
integers, and these types consume less memory than other data types. They are especially useful as the
For More Information To read more about control structures, see "Introduction to Control Structures"
If the variable contains a fraction, declare it as a Single, Double, or Currency variable. The Currency data
type supports up to four digits to the right of the decimal separator and fifteen digits to the left; it is an
accurate fixed-point data type suitable for monetary calculations. Floating-point (Single and Double)
numbers have much larger ranges than Currency, but can be subject to small rounding errors.
Note Floating-point values can be expressed as mmmEeee or mmmDeee, in which mmm is the mantissa
and eee is the exponent (a power of 10). The highest positive value of a Single data type is
3.402823E+38, or 3.4 times 10 to the 38th power; the highest positive value of a Double data type is
1.79769313486232D+308, or about 1.8 times 10 to the 308th power. Using D to separate the mantissa
and exponent in a numeric literal causes the value to be treated as a Double data type. Likewise, using E
If the variable contains binary data, declare it as an array of the Byte data type. (Arrays are discussed in
"Arrays" later in this chapter). Using Byte variables to store binary data preserves it during format
conversions. When String variables are converted between ANSI and Unicode formats, any binary data in
the variable is corrupted. Visual Basic may automatically convert between ANSI and Unicode when:
• Writing to files
• Calling DLLs
All operators that work on integers work with the Byte data type except unary minus. Since Byte is an
unsigned type with the range 0-255, it cannot represent a negative number. So for unary minus, Visual
All numeric variables can be assigned to each other and to variables of the Variant type. Visual Basic
rounds off rather than truncates the fractional part of a floating-point number before assigning it to an
integer.
For More Information For details on Unicode and ANSI conversions, see "International Issues."
If you have a variable that will always contain a string and never a numeric value, you can declare it to be
of type String:
Private S As String
You can then assign strings to this variable and manipulate it using string functions:
S = "Database"
S = Left(S, 4)
By default, a string variable or argument is a variable-length string; the string grows or shrinks as you
assign new data to it. You can also declare strings that have a fixed length. You specify a fixed-length
String * size
For example, to declare a string that is always 50 characters long, use code like this:
If you assign a string of fewer than 50 characters, EmpName is padded with enough trailing spaces to
total 50 characters. If you assign a string that is too long for the fixed-length string, Visual Basic simply
Because fixed-length strings are padded with trailing spaces, you may find the Trim and RTrim functions,
Fixed-length strings in standard modules can be declared as Public or Private. In forms and class modules,
For More Information See "Ltrim, RTrim Function and Trim Functions" in the Language Reference.
You can assign a string to a numeric variable if the string represents a numeric value. It's also possible to
assign a numeric value to a string variable. For example, place a command button, text box, and list box
on a form. Enter the following code in the command button's Click event. Run the application, and click
strY = "100.23"
' variable.
End Sub
Visual Basic will automatically coerce the variables to the appropriate data type. You should use caution
when exchanging strings and numbers; passing a non-numeric value in the string will cause a run-time
error to occur.
If you have a variable that will contain simple true/false, yes/no, or on/off information, you can declare it
to be of type Boolean. The default value of Boolean is False. In the following example, blnRunning is a
Boolean variable which stores a simple yes/no setting.
If Recorder.Direction = 1 Then
blnRunning = True
End if
Date and time values can be contained both in the specific Date data type and in Variant variables. The
For More Information See the section, "Date/Time Values Stored in Variants," in "Advanced Variant
Topics."
When other numeric data types are converted to Date, values to the left of the decimal represent date
information, while values to the right of the decimal represent time. Midnight is 0, and midday is 0.5.
Object variables are stored as 32-bit (4-byte) addresses that refer to objects within an application or
within some other application. A variable declared as Object is one that can subsequently be assigned
(using the Set statement) to refer to any actual object recognized by the application.
When declaring object variables, try to use specific classes (such as TextBox instead of Control or, in
the preceding case, Database instead of Object) rather than the generic Object. Visual Basic can
resolve references to the properties and methods of objects with specific types before you run an
application. This allows the application to perform faster at run time. Specific classes are listed in the
Object Browser.
When working with other applications' objects, instead of using a Variant or the generic Object, declare
objects as they are listed in the Classes list in the Object Browser. This ensures that Visual Basic
recognizes the specific type of object you're referencing, allowing the reference to be resolved at run time.
For More Information For more information on creating and assigning objects and object variables, see
Visual Basic provides several conversion functions you can use to convert values into a specific data type.
To convert a value to Currency, for example, you use the CCur function:
Conversion
function
Converts an expression to
Cbool Boolean
Cbyte Byte
Ccur Currency
Cdate Date
CDbl Double
Cint Integer
CLng Long
CSng Single
CStr String
Cvar Variant
CVErr Error
Note Values passed to a conversion function must be valid for the destination data type or an error
occurs. For example, if you attempt to convert a Long to an Integer, the Long must be within the valid
For More Information See the Language Reference for a specific conversion function.
A Variant variable is capable of storing all system-defined types of data. You don't have to convert
between these types of data if you assign them to a Variant variable; Visual Basic automatically performs
While you can perform operations on Variant variables without much concern for the kind of data they
• If you perform arithmetic operations or functions on a Variant, the Variant must contain something
that is a number. For details, see the section, "Numeric Values Stored in Variants," in "Advanced
Variant Topics."
• If you are concatenating strings, use the & operator instead of the + operator. For details, see the
In addition to being able to act like the other standard data types, Variants can also contain three special
Sometimes you need to know if a value has ever been assigned to a created variable. A Variant variable
has the Empty value before it is assigned a value. The Empty value is a special value different from 0, a
zero-length string (""), or the Null value. You can test for the Empty value with the IsEmpty function:
If IsEmpty(Z) Then Z = 0
When a Variant contains the Empty value, you can use it in expressions; it is treated as either 0 or a zero-
The Empty value disappears as soon as any value (including 0, a zero-length string, or Null) is assigned to
a Variant variable. You can set a Variant variable back to Empty by assigning the keyword Empty to the
Variant.
The Variant data type can contain another special value: Null. Null is commonly used in database
applications to indicate unknown or missing data. Because of the way it is used in databases, Null has
• Expressions involving Null always result in Null. Thus, Null is said to "propagate" through expressions;
if any part of the expression evaluates to Null, the entire expression evaluates to Null.
110
• Passing Null, a Variant containing Null, or an expression that evaluates to Null as an argument to
• Null values propagate through intrinsic functions that return Variant data types.
Z = Null
You can use the IsNull function to test if a Variant variable contains Null:
Z = Null
Else
Z=0
End If
If you assign Null to a variable of any type other than Variant, a trappable error occurs. Assigning Null to a
Variant variable doesn't cause an error, and Null will propagate through expressions involving Variant
variables (though Null does not propagate through certain functions). You can return Null from any
Variables are not set to Null unless you explicitly assign Null to them, so if you don't use Null in your
application, you don't have to write code that tests for and handles it.
For More Information For information on how to use Null in expressions, see "Null" in the Language
Reference.
In a Variant, Error is a special value used to indicate that an error condition has occurred in a procedure.
However, unlike for other kinds of errors, normal application-level error handling does not occur. This
allows you, or the application itself, to take some alternative based on the error value. Error values are
created by converting real numbers to error values using the CVErr function.
For More Information For information on how to use the Error value in expressions, see "CVErr
Function" in the Language Reference. For information on error handling, see "Debugging Your Code and
Handling Errors." For additional information about the Variant data type, see "Advanced Variant Topics."
See Also
Variant variables maintain an internal representation of the values that they store. This representation
determines how Visual Basic treats these values when performing comparisons and other operations.
When you assign a value to a Variant variable, Visual Basic uses the most compact representation that
accurately records the value. Later operations may cause Visual Basic to change the representation it is
using for a particular variable. (A Variant variable is not a variable with no type; rather, it is a variable that
can freely change its type.) These internal representations correspond to the explicit data types discussed
Note A variant always takes up 16 bytes, no matter what you store in it. Objects, strings, and arrays are
not physically stored in the Variant; in these cases, four bytes of the Variant are used to hold either an
object reference, or a pointer to the string or array. The actual data are stored elsewhere.
Most of the time, you don't have to be concerned with what internal representation Visual Basic is using
for a particular variable; Visual Basic handles conversions automatically. If you want to know what value
Visual Basic is using, however, you can use the VarType function.
For example, if you store values with decimal fractions in a Variant variable, Visual Basic always uses the
Double internal representation. If you know that your application does not need the high accuracy (and
slower speed) that a Double value supplies, you can speed your calculations by converting the values to
With an array variable, the value of VarType is the sum of the array and data type return values. For
MsgBox VarType(dblSample)
End Sub
Future versions of Visual Basic may add additional Variant representations, so any code you write that
makes decisions based on the return value of the VarType function should gracefully handle return values
For More Information For information about the VarType function, see "VarType Function" in the
Language Reference. To read more about arrays, see "Arrays" later in this chapter. For details on
When you store whole numbers in Variant variables, Visual Basic uses the most compact representation
possible. For example, if you store a small number without a decimal fraction, the Variant uses an Integer
representation for the value. If you then assign a larger number, Visual Basic will use a Long value or, if it
Sometimes you want to use a specific representation for a number. For example, you might want a Variant
variable to store a numeric value as Currency to avoid round-off errors in later calculations. Visual Basic
provides several conversion functions that you can use to convert values into a specific type (see
"Converting Data Types" earlier in this chapter). To convert a value to Currency, for example, you use the
CCur function:
An error occurs if you attempt to perform a mathematical operation or function on a Variant that does not
contain a number or something that can be interpreted as a number. For example, you cannot perform
any arithmetic operations on the value U2 even though it contains a numeric character, because the entire
value is not a valid number. Likewise, you cannot perform any calculations on the value 1040EZ; however,
you can perform calculations on the values +10 or -1.7E6 because they are valid numbers. For this
reason, you often want to determine if a Variant variable contains a value that can be used as a number.
Do
When Visual Basic converts a representation that is not numeric (such as a string containing a number) to
a numeric value, it uses the Regional settings (specified in the Windows Control Panel) to interpret the
Thus, if the country setting in the Windows Control Panel is set to United States, Canada, or Australia,
IsNumeric("$100")
IsNumeric("1,560.50")
IsNumeric("DM100")
IsNumeric("1.560,50")
However, the reverse would be the case — the first two would return false and the second two true — if
the country setting in the Windows Control Panel was set to Germany.
If you assign a Variant containing a number to a string variable or property, Visual Basic converts the
representation of the number to a string automatically. If you want to explicitly convert a number to a
string, use the CStr function. You can also use the Format function to convert a number to a string that
includes formatting such as currency, thousands separator, and decimal separator symbols. The Format
function automatically uses the appropriate symbols according to the Regional Settings Properties dialog
For More Information See "Format Function" and topics about the conversion functions in the
Language Reference. For information on writing code for applications that will be distributed in foreign
Generally, storing and using strings in Variant variables poses few problems. As mentioned earlier,
however, sometimes the result of the + operator can be ambiguous when used with two Variant values. If
both of the Variants contain numbers, the + operator performs addition. If both of the Variants contain
strings, then the + operator performs string concatenation. But if one of the values is represented as a
number and the other is represented as a string, the situation becomes more complicated. Visual Basic
first attempts to convert the string into a number. If the conversion is successful, the + operator adds the
To make sure that concatenation occurs, regardless of the representation of the value in the variables, use
Sub Form_Click ()
Dim X, Y
X = "6"
Y = "7"
114
Print X + Y, X & Y
X=6
Print X + Y, X & Y
End Sub
67 67
13 67
Note Visual Basic stores strings internally as Unicode. For more information on Unicode, see
"International Issues."
Variant variables can also contain date/time values. Several functions return date/time values. For
daysleft = Int(DateSerial(Year(rightnow) _
+ 1, 1, 1) - rightnow)
hoursleft = 24 - Hour(rightnow)
minutesleft = 60 - Minute(rightnow)
End Sub
You can also perform math on date/time values. Adding or subtracting integers adds or subtracts days;
adding or subtracting fractions adds or subtracts time. Therefore, adding 20 adds 20 days, while
The range for dates stored in Variant variables is January 1, 0100, to December 31, 9999. Calculations on
dates don't take into account the calendar revisions prior to the switch to the Gregorian calendar, however,
so calculations producing date values earlier than the year in which the Gregorian calendar was adopted
(1752 in Britain and its colonies at that time; earlier or later in other countries) will be incorrect.
You can use date/time literals in your code by enclosing them with the number sign (#), in the same way
you enclose string literals with double quotation marks (""). For example, you can compare a Variant
Similarly, you can compare a date/time value with a complete date/time literal:
If you do not include a time in a date/time literal, Visual Basic sets the time part of the value to midnight
(the start of the day). If you do not include a date in a date/time literal, Visual Basic sets the date part of
Visual Basic accepts a wide variety of date and time formats in literals. These are all valid date/time
values:
SomeDate = #Apr-2-93#
For More Information For information on handling dates in international formats, see "International
Issues."
In the same way that you can use the IsNumeric function to determine if a Variant variable contains a
value that can be considered a valid numeric value, you can use the IsDate function to determine if a
Variant contains a value that can be considered a valid date/time value. You can then use the CDate
For example, the following code tests the Text property of a text box with IsDate. If the property contains
text that can be considered a valid date, Visual Basic converts the text into a date and computes the days
If IsDate(Text1.Text) Then
SomeDate = CDate(Text1.Text)
daysleft = DateSerial(Year(SomeDate) + _
1, 1, 1) - SomeDate
Else
End If
For More Information For information about the various date/time functions, see "Date Function" in
Objects can be stored in Variant variables. This can be useful when you need to gracefully handle a variety
of data types, including objects. For example, all the elements in an array must have the same data type.
Setting the data type of an array to Variant allows you to store objects alongside other data types in an
array.
Arrays
See Also
If you have programmed in other languages, you're probably familiar with the concept of arrays. Arrays
allow you to refer to a series of variables by the same name and to use a number (an index) to tell them
apart. This helps you create smaller and simpler code in many situations, because you can set up loops
that deal efficiently with any number of cases by using the index number. Arrays have both upper and
lower bounds, and the elements of the array are contiguous within those bounds. Because Visual Basic
allocates space for each index number, avoid declaring an array larger than necessary.
Note The arrays discussed in this section are arrays of variables, declared in code. They are different
from the control arrays you specify by setting the Index property of controls at design time. Arrays of
variables are always contiguous; unlike control arrays, you cannot load and unload elements from the
All the elements in an array have the same data type. Of course, when the data type is Variant, the
individual elements may contain different kinds of data (objects, strings, numbers, and so on). You can
117
declare an array of any of the fundamental data types, including user-defined types (described in the
section, "Creating Your Own Data Types," in "More About Programming") and object variables (described
In Visual Basic there are two types of arrays: a fixed-size array which always remains the same size, and
a dynamic array whose size can change at run-time. Dynamic arrays are discussed in more detail in the
There are three ways to declare a fixed-size array, depending on the scope you want the array to have:
• To create a public array, use the Public statement in the Declarations section of a module to declare
the array.
• To create a module-level array, use the Private statement in the Declarations section of a module to
• To create a local array, use the Private statement in a procedure to declare the array.
When declaring an array, follow the array name by the upper bound in parentheses. The upper bound
cannot exceed the range of a Long data type (-2,147,483,648 to 2,147,483,647). For example, these
The first declaration creates an array with 15 elements, with index numbers running from 0 to 14. The
second creates an array with 21 elements, with index numbers running from 0 to 20. The default lower
bound is 0.
To specify a lower bound, provide it explicitly (as a Long data type) using the To keyword:
In the preceding declarations, the index numbers of Counters range from 1 to 15, and the index
numbers of Sums range from 100 to 120.
It's possible to create a Variant array, and populate it with other arrays of different data types. The
following code creates two arrays, one containing integers and the other strings. It then declares a third
Variant array and populates it with the integer and string arrays.
For intX = 0 To 4
countersA(intX) = 5
Next intX
For intX = 0 To 4
countersB(intX) = "hello"
Next intX
' array.
arrX(2) = countersB()
' array.
MsgBox arrX(2)(3)
End Sub
Multidimensional Arrays
Sometimes you need to keep track of related information in an array. For example, to keep track of each
pixel on your computer screen, you need to refer to its X and Y coordinates. This can be done using a
With Visual Basic, you can declare arrays of multiple dimensions. For example, the following statement
You can extend this to more than two dimensions. For example:
This declaration creates an array that has three dimensions with sizes 4 by 10 by 15. The total number of
Note When you start adding dimensions to an array, the total storage needed by the array increases
dramatically, so use multidimensional arrays with care. Be especially careful with Variant arrays, because
You can efficiently process a multidimensional array by using nested For loops. For example, these
statements initialize every element in MatrixA to a value based on its location in the array:
For I = 1 To 10
For J = 1 To 10
120
MatrixA(I, J) = I * 10 + J
Next J
Next I
For More Information For information about loops, see "Loop Structures" later in this chapter.
Dynamic Arrays
See Also
Sometimes you may not know exactly how large to make an array. You may want to have the capability of
A dynamic array can be resized at any time. Dynamic arrays are among the most flexible and convenient
features in Visual Basic, and they help you to manage memory efficiently. For example, you can use a
large array for a short time and then free up memory to the system when you're no longer using the
array.
The alternative is to declare an array with the largest possible size and then ignore array elements you
don't need. However, this approach, if overused, might cause the operating environment to run low on
memory.
1. Declare the array with a Public statement (if you want the array to be public) or Dim statement at the
module level (if you want the array to be module level), or a Static or Dim statement in a procedure
(if you want the array to be local). You declare the array as dynamic by giving it an empty dimension
list.
2. Dim DynArray()
4. ReDim DynArray(X + 1)
The ReDim statement can appear only in a procedure. Unlike the Dim and Static statements, ReDim is an
executable statement — it makes the application carry out an action at run time.
The ReDim statement supports the same syntax used for fixed arrays. Each ReDim can change the
number of elements, as well as the lower and upper bounds, for each dimension. However, the number of
For example, the dynamic array Matrix1 is created by first declaring it at the module level:
Sub CalcValuesNow ()
End Sub
The ReDim statement shown here allocates a matrix of 20 by 30 integers (at a total size of 600 elements).
ReDim Matrix1(X, Y)
Note You can assign strings to resizable arrays of bytes. An array of bytes can also be assigned to a
variable-length string. Be aware that the number of bytes in a string varies among platforms. On Unicode
platforms the same string contains twice as many bytes as it does on a non-Unicode platform.
Each time you execute the ReDim statement, all the values currently stored in the array are lost. Visual
Basic resets the values to the Empty value (for Variant arrays), to zero (for numeric arrays), to a zero-
This is useful when you want to prepare the array for new data, or when you want to shrink the size of the
array to take up minimal memory. Sometimes you may want to change the size of the array without losing
the data in the array. You can do this by using ReDim with the Preserve keyword. For example, you can
enlarge an array by one element without losing the values of the existing elements using the UBound
Only the upper bound of the last dimension in a multidimensional array can be changed when you use the
Preserve keyword; if you change any of the other dimensions, or the lower bound of the last dimension, a
run-time error occurs. Thus, you can use code like this:
122
For More Information For information about dynamic arrays, see "ReDim Statement" in the Language
Reference. To learn more about object arrays, see "Programming with Objects."
Introduction to Procedures
See Also
You can simplify programming tasks by breaking programs into smaller logical components. These
components — called procedures — can then become building blocks that let you enhance and extend
Visual Basic.
Procedures are useful for condensing repeated or shared tasks, such as frequently used calculations, text
• Procedures allow you to break your programs into discrete logical units, each of which you can debug
• Procedures used in one program can act as building blocks for other programs, usually with little or
no modification.
• Property procedures can return and assign values, and set references to objects.
For More Information Property procedures are discussed in "Programming with Objects."
To learn more about Sub and Function procedures, see the following topics:
Sub Procedures
See Also
A Sub procedure is a block of code that is executed in response to an event. By breaking the code in a
module into Sub procedures, it becomes much easier to find or modify the code in your application.
End Sub
Each time the procedure is called, the statements between Sub and End Sub are executed. Sub
procedures can be placed in standard modules, class modules, and form modules. Sub procedures are by
default Public in all modules, which means they can be called from anywhere in the application.
The arguments for a procedure are like a variable declaration, declaring values that are passed in from the
calling procedure.
In Visual Basic, it's useful to distinguish between two types of Sub procedures, general procedures and
event procedures.
General Procedures
A general procedure tells the application how to perform a specific task. Once a general procedure is
defined, it must be specifically invoked by the application. By contrast, an event procedure remains idle
until called upon to respond to events caused by the user or triggered by the system.
Why create general procedures? One reason is that several different event procedures might need the
same actions performed. A good programming strategy is to put common statements in a separate
procedure (a general procedure) and have your event procedures call it. This eliminates the need to
duplicate code and also makes the application easier to maintain. For example, the VCR sample
application uses a general procedure called by the click events for several different scroll buttons. Figure
124
5.7 illustrates the use of a general procedure. Code in the Click events calls the ButtonManager Sub
procedure, which runs its own code, and then returns control to the Click event procedure.
Event Procedures
When an object in Visual Basic recognizes that an event has occurred, it automatically invokes the event
procedure using the name corresponding to the event. Because the name establishes an association
between the object and the code, event procedures are said to be attached to forms and controls.
• An event procedure for a control combines the control's actual name (specified in the Name
property), an underscore (_), and the event name. For instance, if you want a command button
named cmdPlay to invoke an event procedure when it is clicked, use the procedure cmdPlay_Click.
• An event procedure for a form combines the word "Form," an underscore, and the event name. If you
want a form to invoke an event procedure when it is clicked, use the procedure Form_Click. (Like
controls, forms do have unique names, but they are not used in the names of event procedures.) If
you are using the MDI form, the event procedure combines the word "MDIForm," an underscore, and
Although you can write event procedures from scratch, it's easier to use the code procedures provided by
Visual Basic, which automatically include the correct procedure names. You can select a template in the
125
Code Editor window by selecting an object from the Object box and then selecting a procedure from the
Procedure box.
It's also a good idea to set the Name property of your controls before you start writing event procedures
for them. If you change the name of a control after attaching a procedure to it, you must also change the
name of the procedure to match the new name of the control. Otherwise, Visual Basic won't be able to
match the control to the procedure. When a procedure name does not match a control name, it becomes a
general procedure.
For More Information Visual Basic recognizes a variety of events for each kind of form and control. For
Function Procedures
See Also
Visual Basic includes built-in, or intrinsic functions, like Sqr, Cos or Chr. In addition, you can use the
End Function
Like a Sub procedure, a Function procedure is a separate procedure that can take arguments, perform a
series of statements, and change the value of its arguments. Unlike a Sub procedure, a Function
procedure can return a value to the calling procedure. There are three differences between Sub and
Function procedures:
• Generally, you call a function by including the function procedure name and arguments on the right
• Function procedures have data types, just as variables do. This determines the type of the return
value. (In the absence of an As clause, the type is the default Variant type.)
• You return a value by assigning it to the procedurename itself. When the Function procedure returns a
For example, you could write a function that calculates the third side, or hypotenuse, of a right triangle,
As String
Hypotenuse = Sqr(A ^ 2 + B ^ 2)
End Function
You call a Function procedure the same way you call any of the built-in functions in Visual Basic:
Label1.Caption = Hypotenuse(CInt(Text1.Text), _
CInt(Text2.Text))
For More Information For additional details about the Function procedure, see "Function Statement" in
the Language Reference. The techniques for calling all types of procedures are discussed in the section,
• Type a procedure heading in the Code window and press ENTER. The procedure heading can be as
simple as Sub or Function followed by a name. For example, you can enter either of the following:
• Sub UpdateForm ()
• Function GetCoord ()
Visual Basic responds by completing the template for the new procedure.
• To view an existing general procedure, select "(General)" from the Object box in the Code window,
–or–
To view an event procedure, select the appropriate object from the Object box in the Code window,
3. Select the module from the Classes list, and the procedure from the Members of list.
Calling Procedures
The techniques for calling procedures vary, depending on the type of procedure, where it's located, and
how it's used in your application. The following sections describe how to call Sub and Function procedures.
A Sub procedure differs from a Function procedure in that a Sub procedure cannot be called by using its
name within an expression. A call to a Sub is a stand-alone statement. Also, a Sub does not return a value
in its name as does a function. However, like a Function, a Sub can modify the values of any variables
passed to it.
Note that when you use the Call syntax, arguments must be enclosed in parentheses. If you omit the Call
keyword, you must also omit the parentheses around the arguments.
Usually, you call a function procedure you've written yourself the same way you call an intrinsic Visual
Basic function like Abs; that is, by using its name in an expression:
Print 10 * ToDec
X = ToDec
X = AnotherFunction(10 * ToDec)
It's also possible to call a function just like you would call a Sub procedure. The following statements both
Call Year(Now)
Year Now
When you call a function this way, Visual Basic throws away the return value.
Public procedures in other modules can be called from anywhere in the project. You might need to specify
the module that contains the procedure you're calling. The techniques for doing this vary, depending on
Procedures in Forms
All calls from outside the form module must point to the form module containing the procedure. If a
procedure named SomeSub is in a form module called Form1, then you can call the procedure in Form1 by
Call Form1.SomeSub(arguments)
Like calling a procedure in a form, calling a procedure in a class module requires that the call to the
procedure be qualified with a variable that points to an instance of the class. For example, DemoClass is
DemoClass.SomeSub
However, unlike a form, the class name cannot be used as the qualifier when referencing an instance of
the class. The instance of the class must be first be declared as an object variable (in this case,
For More Information You can find details on object variables and class modules in "Programming with
Objects."
129
If a procedure name is unique, you don't need to include the module name in the call. A call from inside or
outside the module will refer to that unique procedure. A procedure is unique if it appears only in one
place.
If two or more modules contain a procedure with the same name, you may need to qualify it with the
module name. A call to a common procedure from the same module runs the procedure in that module.
For example, with a procedure named CommonName in Module1 and Module2, a call to CommonName
from Module2 will run the CommonName procedure in Module2, not the CommonName procedure in
Module1.
A call to a common procedure name from another module must specify the intended module. For example,
if you want to call the CommonName procedure in Module2 from Module1, use:
Module2.CommonName(arguments)
Usually the code in a procedure needs some information about the state of the program to do its job. This
information consists of variables passed to the procedure when it is called. When a variable is passed to a
The arguments for procedures you write have the Variant data type by default. However, you can declare
other data types for arguments. For example, the following function accepts a string and an integer:
As Integer) As String
WhatsForLunch = "Fish"
Else
WhatsForLunch = "Chicken"
End If
End Function
For More Information Details on Visual Basic data types are presented earlier in this chapter. You can
Only a copy of a variable is passed when an argument is passed by value. If the procedure changes the
value, the change affects only the copy and not the variable itself. Use the ByVal keyword to indicate an
For example:
End Sub
Passing arguments by reference gives the procedure access to the actual variable contents in its memory
address location. As a result, the variable's value can be permanently changed by the procedure to which
If you specify a data type for an argument passed by reference, you must pass a value of that type for the
argument. You can work around this by passing an expression, rather than a data type, for an argument.
Visual Basic evaluates an expression and passes it as the required type if it can.
The simplest way to turn a variable into an expression is to enclose it in parentheses. For example, to pass
a variable declared as an integer to a procedure expecting a string as an argument, you would do the
following:
Sub CallingProcedure()
intX = 12 * 3
Foo(intX)
End Sub
131
End Sub
You can specify arguments to a procedure as optional by placing the Optional keyword in the argument
list. If you specify an optional argument, all subsequent arguments in the argument list must also be
optional and declared with the Optional keyword. The two pieces of sample code below assume there is a
As String)
List1.AddItem x
List1.AddItem y
End Sub
strName = "yourname"
End Sub
List1.AddItem x
List1.AddItem y
End If
End Sub
' provided.
Call ListText(strName)
End Sub
In the case where an optional argument is not provided, the argument is actually assigned as a variant
with the value of Empty. The example above shows how to test for missing optional arguments using the
IsMissing function.
It's also possible to specify a default value for an optional argument. The following example returns a
default value if the optional argument isn't passed to the function procedure:
Integer = 12345)
List1.AddItem x
List1.AddItem y
End Sub
' provided.
' "12345".
End Sub
Generally, the number of arguments in the procedure call must be the same as in the procedure
specification. Using the ParamArray keyword allows you to specify that a procedure will accept an arbitrary
Dim x As Integer
Dim y As Integer
y=y+x
Next x
intSum = y
End Sub
Sum 1, 3, 5, 7, 8
List1.AddItem intSum
End Sub
For many built-in functions, statements, and methods, Visual Basic provides the option of using named
arguments as a shortcut for typing argument values. With named arguments, you can provide any or all of
the arguments, in any order, by assigning a value to the named argument. You do this by typing the
argument name plus a colon followed by an equal sign and the value ( MyArgument:= "SomeValue") and
placing that assignment in any sequence delimited by commas. Notice that the arguments in the following
List1.AddItem strName
List2.AddItem strAddress
End Sub
End Sub
This is especially useful if your procedures have several optional arguments that you do not always need
to specify.
To determine which functions, statements, and methods support named arguments, use the AutoQuickInfo
feature in the Code window, check the Object Browser, or see the Language Reference. Consider the
• Named arguments are not supported by methods on objects in the Visual Basic (VB) object library.
They are supported by all language keywords in the Visual Basic for applications (VBA) object library.
• In syntax, named arguments are shown as bold and italic. All other arguments are shown in italic
only.
Important You cannot use named arguments to avoid entering required arguments. You can omit only
the optional arguments. For Visual Basic (VB) and Visual Basic for applications (VBA) object libraries, the
For More Information See "ByVal," "ByRef," "Optional," and "ParamArray" in the Language Reference.
Control structures allow you to control the flow of your program's execution. If left unchecked by control-
flow statements, a program's logic will flow through statements from left to right, and top to bottom.
While some very simple programs can be written with only this unidirectional flow, and while some flow
can be controlled by using operators to regulate precedence of operations, most of the power and utility of
any programming language comes from its ability to change statement order with structures and loops.
135
To learn more about specific control structures, see the following topics:
• Working with Control Structures The basics of working with control structures in your code.
Decision Structures
See Also
Visual Basic procedures can test conditions and then, depending on the results of that test, perform
different operations. The decision structures that Visual Basic supports include:
• If...Then
• If...Then...Else
• Select Case
If...Then
Use an If...Then structure to execute one or more statements conditionally. You can use either a single-
If condition Then
statements
End If
The condition is usually a comparison, but it can be any expression that evaluates to a numeric value.
Visual Basic interprets this value as True or False; a zero numeric value is False, and any nonzero numeric
value is considered True. If condition is True, Visual Basic executes all the statements following the Then
keyword. You can use either single-line or multiple-line syntax to execute just one statement conditionally
anyDate = Now
End If
Notice that the single-line form of If...Then does not use an End If statement. If you want to execute more
than one line of code when condition is True, you must use the multiple-line block If...Then...End If
syntax.
anyDate = Now
End If
If...Then...Else
Use an If...Then...Else block to define several blocks of statements, one of which will execute:
If condition1 Then
[statementblock-1]
[ElseIf condition2 Then
[statementblock-2]] ...
[Else
[statementblock-n]]
End If
Visual Basic first tests condition1. If it's False, Visual Basic proceeds to test condition2, and so on, until it
finds a True condition. When it finds a True condition, Visual Basic executes the corresponding statement
block and then executes the code following the End If. As an option, you can include an Else statement
block, which Visual Basic executes if none of the conditions are True.
If...ThenElseIf is really just a special case of If...Then...Else. Notice that you can have any number of
ElseIf clauses, or none at all. You can include an Else clause regardless of whether you have ElseIf clauses.
For example, your application could perform different actions depending on which control in a menu
ClearActiveControl
CopyActiveControl
ClearActiveControl
PasteActiveControl
End If
End Sub
Notice that you can always add more ElseIf parts to your If...Then structure. However, this syntax can get
tedious to write when each ElseIf compares the same expression to a different value. For this situation,
Select Case
Visual Basic provides the Select Case structure as an alternative to If...Then...Else for selectively executing
one block of statements from among multiple blocks of statements. A Select Case statement provides
capability similar to the If...Then...Else statement, but it makes code more readable when there are
several choices.
A Select Case structure works with a single test expression that is evaluated once, at the top of the
structure. Visual Basic then compares the result of this expression with the values for each Case in the
structure. If there is a match, it executes the block of statements associated with that Case:
[Case Else
[statementblock-n]]
End Select
Each expressionlist is a list of one or more values. If there is more than one value in a single list, the
values are separated by commas. Each statementblock contains zero or more statements. If more than
one Case matches the test expression, only the statement block associated with the first matching Case
will execute. Visual Basic executes statements in the Case Else clause (which is optional) if none of the
For example, suppose you added another command to the Edit menu in the If...Then...Else example. You
could add another ElseIf clause, or you could write the function with Select Case:
ClearActiveControl
CopyActiveControl
ClearActiveControl
PasteActiveControl
Case Else
End Select
End Sub
Notice that the Select Case structure evaluates an expression once at the top of the structure. In contrast,
the If...Then...Else structure can evaluate a different expression for each ElseIf statement. You can replace
139
an If...Then...Else structure with a Select Case structure only if the If statement and each ElseIf statement
Loop Structures
See Also
Loop structures allow you to execute one or more lines of code repetitively. The loop structures that Visual
• Do...Loop
• For...Next
• For Each...Next
Do...Loop
Use a Do loop to execute a block of statements an indefinite number of times. There are several variations
of the Do...Loop statement, but each evaluates a numeric condition to determine whether to continue
execution. As with If...Then, the condition must be a value or expression that evaluates to False (zero) or
to True (nonzero).
In the following Do...Loop, the statements execute as long as the condition is True:
Do While condition
statements
Loop
When Visual Basic executes this Do loop, it first tests condition. If condition is False (zero), it skips past all
the statements. If it's True (nonzero), Visual Basic executes the statements and then goes back to the Do
Consequently, the loop can execute any number of times, as long as condition is nonzero or True. The
statements never execute if condition is initially False. For example, this procedure counts the occurrences
of a target string within another string by looping as long as the target string is found:
position = 1
140
+1
count = count + 1
Loop
CountStrings = count
End Function
If the target string doesn't occur in the other string, then InStr returns 0, and the loop doesn't execute.
Another variation of the Do...Loop statement executes the statements first and then tests condition after
Do
statements
Two other variations are analogous to the previous two, except that they loop as long as condition is False
Do Until condition Do
statements statements
Loop Loop Until condition
For...Next
Do loops work well when you don't know how many times you need to execute the statements in the loop.
When you know you must execute the statements a specific number of times, however, a ForNext loop is a
better choice. Unlike a Do loop, a For loop uses a variable called a counter that increases or decreases in
Next [counter]
141
The arguments counter, start, end, and increment are all numeric.
Note The increment argument can be either positive or negative. If increment is positive, start must be
less than or equal to end or the statements in the loop will not execute. If increment is negative, start
must be greater than or equal to end for the body of the loop to execute. If Step isn't set, then increment
defaults to 1.
2. Tests to see if counter is greater than end. If so, Visual Basic exits the loop.
(If increment is negative, Visual Basic tests to see if counter is less than end.)
This code prints the names of all the available Screen fonts:
Dim I As Integer
For i = 0 To Screen.FontCount
Print Screen.Fonts(i)
Next
End Sub
In the VCR sample application, the HighlightButton procedure uses a For...Next loop to step through the
controls collection of the VCR form and show the appropriate Shape control:
Dim i As Integer
For i = 0 To frmVCR.Controls.Count - 1
frmVCR.Controls(i).Visible = True
Else
frmVCR.Controls(i).Visible = False
End If
End If
Next
End Sub
For Each...Next
A For Each...Next loop is similar to a For...Next loop, but it repeats a group of statements for each element
in a collection of objects or in an array instead of repeating the statements a specified number of times.
This is especially helpful if you don't know how many elements are in a collection.
Next element
For example, the following Sub procedure opens Biblio.mdb and adds the name of each table to a list box.
Sub ListTableDefs()
True, False)
List1.AddItem MyTableDef.Name
Next MyTableDef
End Sub
• For collections, element can only be a Variant variable, a generic Object variable, or an object listed in
• You cannot use For Each...Next with an array of user-defined types because a Variant cannot contain
a user-defined type.
You can place control structures inside other control structures (such as an If...Then block within a
For...Next loop). A control structure placed inside another control structure is said to be nested.
Control structures in Visual Basic can be nested to as many levels as you want. It's common practice to
make nested decision structures and loop structures more readable by indenting the body of the decision
structure or loop.
For example, this procedure prints all the font names that are common to both the Printer and Screen:
Print SFont
End If
Next PFont
Next SFont
End Sub
Notice that the first Next closes the inner For loop and the last For closes the outer For loop. Likewise, in
nested If statements, the End If statements automatically apply to the nearest prior If statement. Nested
144
Do...Loop structures work in a similar fashion, with the innermost Loop statement matching the innermost
Do statement.
The Exit statement allows you to exit directly from a For loop, Do loop, Sub procedure, or Function
procedure. The syntax for the Exit statement is simple: Exit For can appear as many times as needed
inside a For loop, and Exit Do can appear as many times as needed inside a Do loop:
Loop
The Exit Do statement works with all versions of the Do loop syntax.
Exit For and Exit Do are useful because sometimes it's appropriate to quit a loop immediately, without
performing any further iterations or statements within the loop. For example, in the previous example that
printed the fonts common to both the Screen and Printer, the code continues to compare Printer fonts
against a given Screen font even when a match has already been found with an earlier Printer font. A
more efficient version of the function would exit the loop as soon as a match is found:
Print Sfont
End If
Next PFont
Next SFont
End Sub
As this example illustrates, an Exit statement almost always appears inside an If statement or Select Case
When you use an Exit statement to break out of a loop, the value of the counter variable differs,
• When you complete a loop, the counter variable contains the value of the upper bound plus the step.
• When you exit a loop prematurely, the counter variable retains its value subject to the usual rules on
scope.
• When you iterate off the end of a collection, the counter variable contains Nothing if it's an Object
You can also exit a procedure from within a control structure. The syntax of Exit Sub and Exit Function is
similar to that of Exit For and Exit Do in the previous section, "Exiting a Control Structure." Exit Sub can
appear as many times as needed, anywhere within the body of a Sub procedure. Exit Function can appear
Exit Sub and Exit Function are useful when the procedure has done everything it needs to do and can
return immediately. For example, if you want to change the previous example so it prints only the first
common Printer and Screen font it finds, you would use Exit Sub:
Print Sfont
End If
Next PFont
Next SFont
End Sub
When you create an application in Visual Basic, you work with objects. You can use objects provided by
Visual Basic — such as controls, forms, and data access objects. You can also control other applications'
objects from within your Visual Basic application. You can even create your own objects, and define
• What Can You Do with Objects? A discussion of some ways that objects can be used in an
application.
• The Basics of Working with Objects An introduction to the properties and methods exposed by
objects.
• How are Objects Related to Each Other? A discussion of object hierarchies, collections, and
containers.
• Creating Objects A discussion of how objects can be created and used at run time.
What is an Object?
See Also
An object is a combination of code and data that can be treated as a unit. An object can be a piece of an
application, like a control or a form. An entire application can also be an object. The following table
describes examples of the types of objects you can use in Visual Basic.
Example Description
Command button Controls on a form, such as command buttons and frames, are objects.
Database Databases are objects, and contain other objects, like fields and indexes.
147
Each object in Visual Basic is defined by a class. To understand the relationship between an object and its
class, think of cookie cutters and cookies. The cookie cutter is the class. It defines the characteristics of
each cookie — for instance, size and shape. The class is used to create objects. The objects are the
cookies.
Two examples of the relationship between classes and objects in Visual Basic may make this clearer.
• The controls on the Toolbox in Visual Basic represent classes. The object known as a control doesn't
exist until you draw it on a form. When you create a control, you're creating a copy or instance of the
control class. That instance of the class is the object you refer to in your application.
• The form you work with at design time is a class. At run time, Visual Basic creates an instance of the
form's class.
The Properties window displays the class and Name property of objects in your Visual Basic application, as
Figure 5.8 Object and class names shown in the Properties window
148
All objects are created as identical copies of their class. Once they exist as individual objects, their
properties can be changed. For example, if you draw three command buttons on a form, each command
button object is an instance of the CommandButton class. Each object shares a common set of
characteristics and capabilities (properties, methods, and events), defined by the class. However, each has
its own name, can be separately enabled and disabled, can be placed in a different location on the form,
and so on.
For simplicity, most of the material outside of this chapter won't make many references to an object's
class. Just remember that the term "list box control," for example, means "an instance of the ListBox
class."
An object provides code you don't have to write. For example, you could create your own File Open and
File Save dialog boxes, but you don't have to. Instead, you can use the common dialog control (an object)
provided by Visual Basic. You could write your own scheduling and resource management code, but you
don't have to. Instead, you can use the Calendar, Resources, and Task objects provided by Microsoft
Project.
Visual Basic provides the tools to allow you to combine objects from different sources. You can now build
custom solutions combining the most powerful features of Visual Basic and applications that support
Automation (formerly known as OLE Automation). Automation is a feature of the Component Object Model
(COM), an industry standard used by applications to expose objects to development tools and other
applications.
You can build applications by tying together intrinsic Visual Basic controls, and you can also use objects
provided by other applications. Consider placing these objects on a Visual Basic form:
You could use these objects to create a checkbook application like the one shown in Figure 5.9. This saves
you time because you don't have to write the code to reproduce the functionality provided by the Microsoft
Visual Basic objects support properties, methods, and events. In Visual Basic, an object's data (settings or
attributes) are called properties, while the various procedures that can operate on the object are called its
methods. An event is an action recognized by an object, such as clicking a mouse or pressing a key, and
You can change an object's characteristics by changing its properties. Consider a radio: One property of a
radio is its volume. In Visual Basic, you might say that a radio has a "Volume" property that you can
adjust by changing its value. Assume you can set the volume of the radio from 0 to 10. If you could
150
control a radio with Visual Basic, you might write code in a procedure that changes the value of the
Radio.Volume = 5
In addition to properties, objects have methods. Methods are a part of objects just as properties are.
Generally, methods are actions you want to perform, while properties are the attributes you set or
retrieve. For example, you dial a telephone to make a call. You might say that telephones have a "Dial"
method, and you could use this syntax to dial the seven-digit number 5551111:
Phone.Dial 5551111
Objects also have events. Events are triggered when some aspect of the object is changed. For example, a
radio might have a "VolumeChange" event. A telephone might have a "Ring" event.
Individual properties vary as to when you can set or get their values. Some properties can be set at
design time. You can use the Properties window to set the value of these properties without writing any
code at all. Some properties are not available at design time; therefore, you must write code to set those
Properties that you can set and get at run time are called read-write properties. Properties you can only
You set the value of a property when you want to change the appearance or behavior of an object. For
example, you change the Text property of a text box control to change the contents of the text box.
object.property = expression
' box.
You get the value of a property when you want to find the state of an object before your code performs
additional actions (such as assigning the value to another object). For example, you can return the Text
property of a text box control to determine the contents of the text box before running code that might
In most cases, to get the value of a property, you use the following syntax:
variable = object.property
You can also get a property value as part of a more complex expression, without assigning the property to
a variable. In the following code example, the Top property of the new member of a control array is
' [statements]
' [statements]
End Sub
Tip If you're going to use the value of a property more than once, your code will run faster if you store
Methods can affect the values of properties. For example, in the radio analogy, the SetVolume method
changes the Volume property. Similarly, in Visual Basic, list boxes have a List property, which can be
When you use a method in code, how you write the statement depends on how many arguments the
method requires, and whether the method returns a value. When a method doesn't take arguments, you
object.method
Some methods, such as the Refresh method, don't have arguments and don't return values.
152
If the method takes more than one argument, you separate the arguments with a comma. For example,
the Circle method uses arguments specifying the location, radius, and color of a circle on a form:
If you keep the return value of a method, you must enclose the arguments in parentheses. For example,
If there is no return value, the arguments appear without parentheses. For example, the AddItem method
For More Information See the Language Reference for the syntax and arguments for all methods
When you put two command buttons on a form, they are separate objects with distinct Name property
settings (Command1 and Command2), but they share the same class — CommandButton.
They also share the characteristic that they're on the same form. You've seen earlier in this chapter that a
control on a form is also contained by the form. This puts controls in a hierarchy. To reference a control
you may have to reference the form first, in the same way you may have to dial a country code or area
The two command buttons also share the characteristic that they're controls. All controls have common
characteristics that make them different from forms and other objects in the Visual Basic environment.
The following sections explain how Visual Basic uses collections to group objects that are related.
Object Hierarchies
An object hierarchy provides the organization that determines how objects are related to each other, and
how you can access them. In most cases, you don't need to concern yourself with the Visual Basic object
hierarchy. However:
153
• When manipulating another application's objects, you should be familiar with that application's object
hierarchy. For information on navigating object hierarchies, see "Programming with Components."
• When working with data access objects, you should be familiar with the Data Access Object hierarchy.
There are some common cases in Visual Basic where one object contains others. These are described in
Collection objects have their own properties and methods. The objects in a collection object are referred to
as members of the collection. Each member of the collection is numbered sequentially beginning at 0; this
is the member's index number. For example, the Controls collection contains all the controls on a given
form, as shown in Figure 5.10. You can use collections to simplify code if you need to perform the same
For example, the following code scrolls through the Controls collection and lists each member's name in a
list box.
List1.AddItem MyControl.Name
Next MyControl
There are two general techniques you can use to address a member of a collection object:
• Specify the name of the member. The following expressions are equivalent:
• Controls("List1")
• Controls!List1
• Controls(3)
Once you're able to address all the members collectively, and single members individually, you can apply
' Set the Top property of the list box control to 200.
Controls!List1.Top = 200
–or–
MyControl.Top = 200
Next MyControl
Some objects in Visual Basic contain other objects. For example, a form usually contains one or more
controls. The advantage of having objects as containers for other objects is that you can refer to the
container in your code to make it clear which object you want to use. For example, Figure 5.11 illustrates
two different forms you could have in an application — one for entering accounts payable transactions,
Figure 5.11 Two different forms can contain controls that have the same name
155
Both forms can have a list box named lstAcctNo. You can specify exactly which one you want to use by
frmReceivable.lstAcctNo.AddItem 1201
–or–
frmPayable.lstAcctNo.AddItem 1201
There are some common cases in Visual Basic where one object contains other objects. The following table
Collection Description
For More Information "For information about object containment, see "Using Collections" in "More
About Programming." For information on the Printers collection, see "Working with Text and Graphics." For
details on the forms and controls collections, see the Language Reference.
You can use the Container property to change an object's container within a form. The following controls
• Frame control
156
This example demonstrates moving a command button around from container to container on a form.
Open a new project, and draw a frame control, picture box control and a command button on the form.
The following code in the form's click event increments a counter variable, and uses a Select Case loop to
Case 0
Command1.Top= 0
Command1.Left= 0
Case 1
Command1.Top= 0
Command1.Left= 0
Case 2
Command1.Top= 0
Command1.Left= 0
End Select
intX = intX + 1
End Sub
157
In addition to using and creating objects within Visual Basic, you can communicate with other applications
and manipulate their objects from within your application. The ability to share data between applications is
one of the key features of the Microsoft Windows operating system. With Visual Basic, you have great
For More Information For details on using and communicating with other applications' objects, see
Creating Objects
See Also
The easiest way to create an object is to double-click a control in the Toolbox. However, to realize the full
benefit of all the objects available in Visual Basic and from other applications, you can use Visual Basic's
• You can create your own objects "from scratch" with class modules.
• You can create your own collections with the Collection object.
For More Information Other chapters show you how to access objects. The CreateObject and
In addition to storing values, a variable can refer to an object. You assign an object to a variable for the
• Variable names are often shorter and easier to remember than the values they contain (or, in this
• Variables can be changed to refer to other objects while your code is running.
• Referring to a variable that contains an object is more efficient than repeatedly referring to the object
itself.
158
Using an object variable is similar to using a conventional variable, but with one additional step —
You declare an object variable in the same way you declare other variables, with Dim, ReDim, Static,
Private, or Public. The only differences are the optional New keyword and the class argument; both of
For example, you can declare an object variable that refers to a form in the application called frmMain:
You can also declare an object variable that can refer to any form in the application:
Similarly, you can declare an object variable that can refer to any text box in your application:
You can also declare an object variable that can refer to a control of any type:
Notice that you can declare a form variable that refers to a specific form in the application, but you cannot
declare a control variable that refers to a particular control. You can declare a control variable that can
refer to a specific type of control (such as TextBox or ListBox), but not to one particular control of that
type (such as txtEntry or List1). However, you can assign a particular control to a variable of that type.
For example, for a form with a list box called lstSample, you could write:
159
Use the Set statement whenever you want an object variable to refer to an object.
Sometimes you may use object variables, and particularly control variables, simply to shorten the code
you have to type. For example, you might write code like this:
frmAccountDisplay!txtAccountBalance.BackColor = 0
frmAccountDisplay!txtAccountBalance.ForeColor = 255
End If
You can shorten this code significantly if you use a control variable:
Bal.BackColor = 0
Bal.ForeColor = 255
End If
Specific object variables must refer to one specific type of object or class. A specific form variable can
refer to only one form in the application (though it can refer to one of many instances of that form).
Similarly, a specific control variable can refer to only one particular type of control in your application,
such as TextBox or ListBox. To see an example, open a new project and place a text box on a form. Add
anyText.Text = "Hello"
End Sub
Run the application, and click the form. The Text property of the text box will be changed to "Hello."
Generic object variables can refer to one of many specific types of objects. A generic form variable, for
example, can refer to any form in an application; a generic control variable can refer to any control on any
form in an application. To see an example, open a new project and place several frame, label, and
command button controls on a form, in any order. Add the following code to the form:
anyControl.Caption = "Hello"
End Sub
Run the application, and click the form. The caption of the control you placed third in sequence on the
Generic Object
Type Object referenced
Form Any form in the application (including MDI children and the MDI form).
MDIForm The MDI form in the application (if your application has one).
Generic object variables are useful when you don't know the specific type of object a variable will refer to
at run time. For example, if you want to write code that can operate on any form in the application, you
Note Because there can be only one MDI form in the application, there is no need to use the generic
MDIForm type. Instead, you can use the specific MDIForm type (MDIForm1, or whatever you specified
for the Name property of the MDI form) whenever you need to declare a form variable that refers to the
MDI form. In fact, because Visual Basic can resolve references to properties and methods of specific form
types before you run your application, you should always use the specific MDIForm type.
161
The generic MDIForm type is provided only for completeness; should a future version of Visual Basic allow
Forms as Objects
Forms are most often used to make up the interface of an application, but they're also objects that can be
called by other modules in your application. Forms are closely related to class modules. The major
difference between the two is that forms can be visible objects, whereas class modules have no visible
interface.
You can add custom methods and properties to forms and access them from other modules in your
application. To create a new method for a form, add a procedure declared using Public.
. ' <statements>
End Sub
You can call the LateJobsCount procedure from another module using this statement:
Form1.LateJobsCount
Creating a new property for a form can be as simple as declaring a public variable in the form module:
You can set and return the value of IDNumber on Form1 from another module using these two
statements:
Form1.IDNumber = 3
Text1.Text = Form1.IDNumber
You can also use Property procedures to add custom properties to a form.
For More Information Details on Property procedures are provided in "Programming with Objects."
162
Note You can call a variable, a custom method, or set a custom property on a form without loading the
form. This allows you to run code on a form without loading it into memory. Also, referencing a control
without referencing one of its properties or methods does not load the form.
Use the New keyword to create a new object as defined by its class. New can be used to create instances
Each form you create at design time is a class. The New keyword can be used to create new instances of
that class. To see how this works, draw a command button and several other controls on a form. Set the
form's Name property to Sample in the Properties window. Add the following code to your command
x.Show
Run the application, and click the command button several times. Move the front-most form aside.
Because a form is a class with a visible interface, you can see the additional copies. Each form has the
Note To make a form variable and an instance of the loaded form persist, use a Static or Public variable
You can also use New with the Set statement. Try the following code in a command button's Click event
procedure:
Dim f As Form1
f.Caption = "hello"
f.Show
Using New with the Set statement is faster and is the recommended method.
The New keyword can be used to create collections and objects from the classes you define in class
This example demonstrates how the New keyword creates instances of a class. Open a new project, and
draw a command button on Form1. From the Project menu, choose Add Class Module to add a class
module to the project. Set the class module's Name property to ShowMe.
The following code in the Form1 module creates a new instance of the class ShowMe, and calls the
clsNew.ShowFrm
End Sub
The ShowFrm procedure in the class module creates a new instance of the class Form1, shows the form,
Sub ShowFrm()
frmNew.Show
frmNew.WindowState = 1
End Sub
To use the example, run the application, and click the command button several times. You'll see a
minimized form icon appear on your desktop as each new instance of the ShowMe class is created.
For More Information For information on using New to create objects, see "Programming with
Components."
The following table describes what you cannot do with the New keyword.
Each object uses memory and system resources. It is good programming practice to release these
• Use Nothing to release resources used by an object variable. Assign Nothing to an object variable
For More Information See "Unload Event" and "Nothing" in the Language Reference.
You can pass objects to procedures in Visual Basic. In the following code example, it's assumed that there
' Calls the Demo sub, and passes the form to it.
Demo Form1
End Sub
End Sub
It's also possible to pass an object to an argument by reference and then, inside the procedure, set the
argument to a new object. To see how this works, open a project, and insert a second form. Place a
picture box control on each form. The following table shows the property settings that need changes:
The Form1_Click event procedure calls the GetPicture procedure in Form2, and passes the empty picture
box to it.
Form2.GetPicture Picture1
End Sub
The GetPicture procedure in Form2 assigns the Picture property of the picture box on Form2 to the empty
' variable.
Set objX = x
objX.Picture = picture2.Picture
End Sub
To use the example, run the application, and click Form1. You'll see the icon from Form2 appear in the
For More Information The previous topics are intended to serve as an introduction to objects. To learn
challenges. So, what can you do with Visual Basic? It might be more appropriate to ask what cant be
done. The answer is: not much! From designing innovative user interfaces to taking advantage of other
applications objects, from manipulating text and graphics to working with databases, Visual Basic provides
the tools that youll need to get the job done right.
166
Part 1 of the Programmer's Guide provided the foundation; Part 2 provides the bricks and mortar to build
upon that foundation to create increasingly complex applications with Visual Basic.
Chapters
Creating a User Interface
Covers Visual Basic's intrinsic controls and how you can use them.
A discussion of more programming concepts, techniques, and additional tools available in Visual
Basic.
In-depth coverage of objects, including creating classes and using ActiveX Designers.
Explains how to use Visual Basics text and graphics methods for display and printing.
Explains what to do when something doesnt works as planned, either at design time or run time.
International Issues
Explains how to use the Package and Deployment Wizard to create installation programs.
The user interface is perhaps the most important part of an application; it's certainly the most visible. To
users, the interface is the application; they probably aren't aware of the code that is executing behind the
scenes. No matter how much time and effort you put into writing and optimizing your code, the usability
When you design an application, a number of decisions need to be made regarding the interface. Should
you use the single-document or multiple-document style? How many different forms will you need? What
commands will your menus include, and will you use toolbars to duplicate menu functions? What about
dialog boxes to interact with the user? How much assistance do you need to provide?
Before you begin designing the user interface, you need to think about the purpose of the application. The
design for a primary application that will be in constant use should be different from one that is only used
occasionally for short periods of time. An application with the primary purpose of displaying information
The intended audience should also influence your design. An application aimed at a beginning user
demands simplicity in its design, while one for experienced users may be more complex. Other
applications used by your target audience may influence their expectations for an application's behavior. If
you plan on distributing internationally, language and culture must be considered part of your design.
Designing a user interface is best approached as an iterative process — you will rarely come up with a
perfect design on the first pass. This chapter introduces you to the process of designing an interface in
Visual Basic, providing an introduction to the tools you need to create a great application for your users.
Topics
Interface Styles
Toolbars
Dialog Boxes
Sample applications
Mdinote.vpb, Sdinote.vbp
Many of the code samples in this chapter are taken from the Mdinote.vbp and Sdinote.vbp sample
Interface Styles
See Also
If you've been using Windows-based applications for a while, you've probably noticed that not all user
interfaces look or behave the same. There are two main styles of user interface: the single-document
interface (SDI) and the multiple-document interface (MDI). An example of the SDI interface is the
WordPad application included with Microsoft Windows (Figure 6.1). In WordPad, only a single document
may be open; you must close one document in order to open another.
169
Applications such as Microsoft Excel and Microsoft Word for Windows are MDI interfaces; they allow you to
display multiple documents at the same time, with each document displayed in its own window (Figure
6.2). You can recognize a MDI application by the inclusion of a Window menu item with submenus for
In determining which interface style is best, you need to look at the purpose of the application. An
application for processing insurance claims might lend itself to the MDI style — a clerk is likely to be
working on more than one claim at a time or might need to compare two claims. On the other hand, a
calendar application would be best suited to the SDI style — it's not likely that you would need more than
one calendar open at a time; in the rare event that you did, you could open a second instance of the SDI
application.
The SDI style is the more common; most of the examples in the Programmer's Guide assume an SDI
application. There are a number of considerations and techniques unique to creating MDI applications,
which are addressed in "Multiple-Document Interface (MDI) Applications" later in this chapter.
In addition to the two most common interface styles, SDI and MDI, a third interface style is becoming
more popular: the explorer-style interface (Figure 6.3). The explorer-style interface is a single window
containing two panes or regions, usually consisting of a tree or hierarchical view on the left and a display
area on the right, as in the Microsoft Windows Explorer. This type of interface lends itself to navigating or
In addition to the MDI and SDI application examples that accompany this chapter, the Application Wizard
provides a good way to compare the different interface styles. You can use the Wizard to generate a
framework for each style and view the forms and code that it generates.
For More Information To learn more about MDI applications, see "Multiple-Document Interface (MDI)
Applications." The basics of working with forms are covered in "Forms, Controls, and Menus." For
information on accessing the Application Wizard, see "Using Wizards and Add-Ins" in "Managing Projects."
The multiple-document interface (MDI) allows you to create an application that maintains multiple forms
within a single container form. Applications such as Microsoft Excel and Microsoft Word for Windows have
multiple-document interfaces.
An MDI application allows the user to display multiple documents at the same time, with each document
displayed in its own window. Documents or child windows are contained in a parent window, which
provides a workspace for all the child windows in the application. For example, Microsoft Excel allows you
to create and display multiple-document windows of different types. Each individual window is confined to
the area of the Excel parent window. When you minimize Excel, all of the document windows are
minimized as well; only the parent window's icon appears in the task bar.
172
A child form is an ordinary form that has its MDIChild property set to True. Your application can include
At run time, child forms are displayed within the workspace of the MDI parent form (the area inside the
form's borders and below the title and menu bars). When a child form is minimized, its icon appears within
the workspace of the MDI form instead of on the taskbar, as shown in Figure 6.4.
Figure 6.4 Child forms displayed within the workspace of the MDI form
Note Your application can also include standard, non-MDI forms that are not contained in the MDI form.
A typical use of a standard form in an MDI application is to display a modal dialog box.
An MDI form is similar to an ordinary form with one restriction. You can't place a control directly on a MDI
form unless that control has an Align property (such as a picture box control) or has no visible interface
Use the following procedure to create an MDI form and its child forms.
Note An application can have only one MDI form. If a project already has an MDI form, the Add MDI
To create an MDI child form, create a new form (or open an existing one) and set its MDIChild
property to True.
• Working with MDI Child Forms at Design Time A discussion of the design time behavior of child
forms.
• Run-Time Features of MDI Forms A discussion of the run time behavior of child forms.
• The MDI NotePad Application Details of the MDI Notepad sample application.
• Working with MDI Forms and Child Forms A discussion of the interaction between MDI parent and
child forms.
At design time, child forms are not restricted to the area inside the MDI form. You can add controls, set
properties, write code, and design the features of child forms just as you would with any other Visual
Basic form.
You can determine whether a form is an MDI child by looking at its MDIChild property, or by examining the
Project Explorer. If the form's MDIChild property is set to True, it is a child form. Visual Basic displays
special icons in the Project Explorer for the MDI and MDI child forms, as shown in Figure 6.5.
Figure 6.5 Icons in the Project Explorer identify MDI child, standard, and MDI forms
174
At run time, an MDI form and all of its child forms take on special characteristics:
• All child forms are displayed within the MDI form's workspace. The user can move and size child
forms like any other form; however, they are restricted to this workspace.
• When a child form is minimized, its icon appears on the MDI form instead of the taskbar. When the
MDI form is minimized, the MDI form and all of its child forms are represented by a single icon. When
the MDI form is restored, the MDI form and all the child forms are displayed in the same state they
• When a child form is maximized, its caption is combined with the caption of the MDI form and is
• By setting the AutoShowChildren property, you can display child forms automatically when forms are
• The active child form's menus (if any) are displayed on the MDI form's menu bar, not on the child
form.
Figure 6.6 A child form caption combined with the caption of an MDI form
175
The MDI NotePad sample application is a simple text editor similar to the NotePad application included
with Microsoft Windows. The MDI NotePad application, however, uses a multiple-document interface
(MDI). At run time, when the user requests a new document (implemented with the New command on the
application's File menu), the application creates a new instance of the child form. This allows the user to
To create a document-centered application in Visual Basic, you need at least two forms — an MDI form
and a child form. At design time, you create an MDI form to contain the application and a single child form
2. From the Project menu, choose Add MDI Form to create the container form.
The project should now contain an MDI form (MDIForm1) and a standard form (Form1).
4. Set properties for the two forms and the text box as follows.
5.
6. Using the Menu Editor (from the Tools menu), create a File menu for MDIForm1.
&File mnuFile No
7.
13. NewDoc.Show
This procedure creates and then displays a new instance (or copy) of Form1, called NewDoc. Each
time the user chooses New from the File menu, an exact duplicate (instance) of Form1 is created,
15. Add the following code to the Form_Resize procedure for Form1:
17. ' Expand text box to fill the current child form.
The code for the Form_Resize event procedure, like all the code in Form1, is shared by each instance
of Form1. When several copies of a form are displayed, each form recognizes its own events. When
an event occurs, the code for that event procedure is called. Because the same code is shared by
177
each instance, you might wonder how to reference the form that has called the code — especially
since each instance has the same name (Form1). This is discussed in "Working with MDI Forms and
Tip The Mdinote.vbp sample application contains examples of many MDI techniques besides those
mentioned in this chapter. Take some time to step through the example code to discover these techniques.
The Sdinote.vbp sample application is an implementation of the same application converted to the SDI
style; compare the two samples to learn the differences between MDI and SDI techniques.
When users of your MDI application open, save, and close several child forms in one session, they should
be able to refer to the active form and maintain state information on child forms. This topic describes
coding techniques you can use to specify the active child form or control, load and unload MDI and child
Sometimes you want to provide a command that operates on the control with the focus on the currently
active child form. For example, suppose you want to copy selected text from the child form's text box onto
the Clipboard. In the Mdinote.vbp sample application, the Click event of the Copy item on the Edit menu
calls EditCopyProc, a procedure that copies selected text onto the Clipboard.
Because the application can have many instances of the same child form, EditCopyProc needs to know
which form to use. To specify this, use the MDI form's ActiveForm property, which returns the child form
Note At least one MDI child form must be loaded and visible when you access the ActiveForm property,
or an error is returned.
When you have several controls on a form, you also need to specify which control is active. Like the
ActiveForm property, the ActiveControl property returns the control with the focus on the active child
form. Here's an example of a copy procedure that can be called from a child form menu, a menu on the
ClipBoard.SetText _
frmMDI.ActiveForm.ActiveControl.SelText
End Sub
If you're writing code that will be called by multiple instances of a form, it's a good idea to not use a form
identifier when accessing the form's controls or properties. For example, refer to the height of the text box
on Form1 as Text1.Height instead of Form1.Text1.Height. This way, the code always affects the
current form.
Another way to specify the current form in code is to use the Me keyword. You use Me to reference the
form whose code is currently running. This keyword is useful when you need to pass a reference to the
For More Information For information on creating multiple instances of a form using the New keyword
with the Dim statement, see "Introduction to Variables, Constants and Data Types" in "Programming
When you load a child form, its parent form (the MDI form) is automatically loaded and displayed. When
you load the MDI form, however, its children are not automatically loaded.
In the MDI NotePad example, the child form is the default startup form, so both the child and MDI forms
are loaded when the application is run. If you change the startup form in the MDI NotePad application to
frmMDI (on the General tab of Project Properties) and then run the application, only the MDI form is
loaded. The first child form is loaded when you choose New from the File menu.
You can use the AutoShowChildren property to load MDI child windows as hidden, and leave them hidden
until you display them using the Show method. This allows you to update various details such as captions,
You can't show an MDI child form or the MDI form modally (using the Show method with an argument of
vbModal). If you want to use a modal dialog box in an MDI application, use a form with its MDIChild
When an MDI child form has a sizable border (BorderStyle = 2), Microsoft Windows determines its initial
height, width, and position when it is loaded. The initial size and position of a child form with a sizable
border depends on the size of the MDI form, not on the size of the child form at design time. When an
179
MDI child form's border is not sizable (BorderStyle = 0, 1, or 3), it is loaded using its design-time Height
If you set AutoShowChildren to False, you can change the position of the MDI child after you load it, but
For More Information See "AutoShowChildren Property and "Show Method" in the Language
Reference.
A user deciding to quit the MDI application must have the opportunity to save work. To make this possible,
the application needs to be able to determine, at all times, whether the data in the child form has changed
You can do this by declaring a public variable on each child form. For example, you can declare a variable
Each time the text changes in Text1, the child form's text box Change event sets boolDirty to True. You
can add this code to indicate that the contents of Text1 have changed since the last time it was saved:
boolDirty = True
End Sub
Conversely, for each time the user saves the contents of the child form, the text box's Change event sets
boolDirty to False to indicate that the contents of Text1 no longer need to be saved. In the following
code, it is assumed that there is a menu command called Save (mnuFileSave) and a procedure called
Sub mnuFileSave_Click ()
FileSave
boolDirty = False
End Sub
180
The boolDirty flag becomes useful when the user decides to exit the application. This can occur when
the user chooses Close from the MDI form's Control menu, or through a menu item you provide, such as
Exit on the File menu. If the user closes the application using the MDI form's Control menu, Visual Basic
When an MDI form is unloaded, the QueryUnload event is invoked first for the MDI form and then for
every child form that is open. If none of the code in these QueryUnload event procedures cancels the
Unload event, then each child is unloaded and finally, the MDI form is unloaded.
Because the QueryUnload event is invoked before a form is unloaded, you can give the user the
opportunity to save a form before unloading it. The following code uses the boolDirty flag to determine
if the user should be prompted to save the child before it is unloaded. Notice that you can access the
value of a public form-level variable anywhere in the project. This code assumes that there is a procedure,
Unload frmMDI
End
End Sub
UnloadMode As Integer)
If boolDirty Then
FileSave
End If
End Sub
181
In addition to the basics of form design, you need to think about the beginning and end of your
application. There are several techniques available for determining what the user will see when your
application starts. It's also important to be aware of the processes that occur when an application is
unloaded.
By default, the first form in your application is designated as the startup form. When your application
starts running, this form is displayed (so the first code to execute is the code in the Form_Initialize event
for that form). If you want a different form to display when your application starts, you must change the
startup form.
3. In the Startup Object list box, select the form you want as the new startup form.
4. Choose OK.
Sometimes you might want your application to start without any form initially loaded. For example, you
might want to execute code that loads a data file and then displays one of several different forms
depending on what is in the data file. You can do this by creating a Sub procedure called Main in a
Sub Main()
intStatus = GetUserStatus
If intStatus = 1 Then
182
frmMain.Show
Else
frmPassword.Show
End If
This procedure must be a Sub procedure, and it cannot be in a form module. To set the Sub Main
procedure as the startup object, from the Project menu, choose Project Properties, select the General tab,
If you need to execute a lengthy procedure on startup, such as loading a large amount of data from a
database or loading several large bitmaps, you might want to display a splash screen on startup. A splash
screen is a form, usually displaying information such as the name of the application, copyright
information, and a simple bitmap. The screen that is displayed when you start Visual Basic is a splash
screen.
To display a splash screen, use a Sub Main procedure as your startup object and use the Show method to
frmSplash.Show
' Show the main form and unload the splash screen.
frmMain.Show
Unload frmSplash
End Sub
The splash screen occupies the user's attention while your startup procedures are executing, giving the
illusion that the application is loading faster. When the startup procedures are completed, you can load
In designing a splash screen, it's a good idea to keep it simple. If you use large bitmaps or a lot of
Ending an Application
An event-driven application stops running when all its forms are closed and no code is executing. If a
hidden form still exists when the last visible form is closed, your application will appear to have ended
(because no forms are visible), but will in fact continue to run until all the hidden forms are closed. This
situation can arise because any access to an unloaded form's properties or controls implicitly loads that
The best way to avoid this problem when closing your application is to make sure all your forms are
unloaded. If you have more than one form, you can use the Forms collection and the Unload statement.
For example, on your main form you could have a command button named cmdQuit that lets a user exit
the program. If your application has only one form, the Click event procedure could be as simple as this:
Unload Me
End Sub
If your application uses multiple forms, you can unload the forms by putting code in the Unload event
procedure of your main form. You can use the Forms collection to make sure you find and close all your
forms. The following code uses the forms collection to unload all forms:
Dim i as integer
Unload Forms(i)
Next
End Sub
There may be cases where you need to end your application without regard for the state of any existing
forms or objects. Visual Basic provides the End statement for this purpose.
The End statement ends an application immediately: no code after the End statement is executed, and no
further events occur. In particular, Visual Basic will not execute the QueryUnload, Unload or Terminate
184
event procedures for any forms. Object references will be freed, but if you have defined your own classes,
Visual Basic will not execute the Terminate events of objects created from your classes.
In addition to the End statement, the Stop statement halts an application. However, you should use the
Stop statement only while debugging, because it does not free references to objects.
For More Information For information on the Stop statement, see "Using Break Mode" in "Error
Handling and Debugging," and "Stop Statement" in the Language Reference. For information on the forms
Many simple applications consist of one form and several controls, but you can enhance your Visual Basic
applications by adding menus. This section shows you how to create menus and use them in an
application.
• Creating Menus with the Menu Editor How to use the Menu Editor.
• Creating a Menu Control Array Using arrays to eliminate redundant menu code.
• Creating and Modifying Menus at Run Time Techniques for working with menus.
• Writing Code for Menu Controls A discussion of coding techniques for menus.
You can use the Menu Editor to create new menus and menu bars, add new commands to existing menus,
replace existing menu commands with your own commands, and change and delete existing menus and
menu bars.
185
–or–
While most menu control properties can be set using the Menu Editor, all menu properties are available in
the Properties window. The two most important properties for menu controls are:
• Name — This is the name you use to reference the menu control from code.
Other properties in the Menu Editor, including Index, Checked, and NegotiatePosition, are described later
in this chapter.
The menu control list box (the lower portion of the Menu Editor) lists all the menu controls for the current
form. When you type a menu item in the Caption text box, that item also appears in the menu control list
box. Selecting an existing menu control from the list box allows you to edit the properties for that control.
For example, Figure 6.7 shows the menu controls for a File menu in a typical application. The position of
the menu control in the menu control list box determines whether the control is a menu title, menu item,
• A menu control that appears flush left in the list box is displayed on the menu bar as a menu title.
• A menu control that is indented once in the list box is displayed on the menu when the user clicks the
• An indented menu control followed by menu controls that are further indented becomes a submenu
title. Menu controls indented below the submenu title become items of that submenu.
• A menu control with a hyphen (-) as its Caption property setting appears as a separator bar. A
Note A menu control cannot be a separator bar if it is a menu title, has submenu items, is checked or
–or–
3. In the Caption text box, type the text for the first menu title that you want to appear on the menu
bar. Also, place an ampersand (&) before the letter you want to be the access key for that menu item.
This letter will automatically be underlined in the menu.
The menu title text is displayed in the menu control list box.
4. In the Name text box, type the name that you will use to refer to the menu control in code. See
"Menu Title and Naming Guidelines" later in this chapter.
5. Click the left arrow or right arrow buttons to change the indentation level of the control.
187
6. Set other properties for the control, if you choose. You can do this in the Menu Editor or later, in the
Properties window.
–or–
You can also click the up arrow and down arrow buttons to move the control among the existing
menu controls.
8. Choose OK to close the Menu Editor when you have created all the menu controls for that form.
The menu titles you create are displayed on the form. At design time, click a menu title to drop down
A separator bar is displayed as a horizontal line between items on a menu. On a menu with many items,
you can use a separator bar to divide items into logical groups. For example, the File menu in Visual Basic
uses separator bars to divide its menu items into three groups, as shown in Figure 6.8.
1. If you are adding a separator bar to an existing menu, choose Insert to insert a menu control
between the menu items you want to separate.
2. If necessary, click the right arrow button to indent the new menu item to the same level as the menu
items it will separate.
Note Although separator bars are created as menu controls, they do not respond to the Click event, and
You can improve keyboard access to menu commands by defining access keys and shortcut keys.
Access Keys
Access keys allow the user to open a menu by pressing the ALT key and typing a designated letter. Once a
menu is open, the user can choose a control by pressing the letter (the access key) assigned to it. For
example, ALT+E might open the Edit menu, and P might select the Paste menu item. An access-key
assignment appears as an underlined letter in the menu control's caption, as shown in Figure 6.9.
1. Select the menu item to which you want to assign an access key.
2. In the Caption box, type an ampersand (&) immediately in front of the letter you want to be the
access key.
For example, if the Edit menu shown in Figure 6.9 is open, the following Caption property settings respond
Cut Cu&t t
189
Copy C&opy o
Paste &Paste p
Delete De&lete l
Time/Date Time/&Date d
Note Do not use duplicate access keys on menus. If you use the same access key for more than one
menu item, the key will not work. For example, if C is the access key for both Cut and Copy, when you
select the Edit menu and press C, the Copy command will be selected, but the application will not carry
out the command until the user presses ENTER. The Cut command will not be selected at all.
Shortcut Keys
Shortcut keys run a menu item immediately when pressed. Frequently used menu items may be assigned
a keyboard shortcut, which provides a single-step method of keyboard access, rather than a three-step
method of pressing ALT, a menu title access character, and then a menu item access character. Shortcut
key assignments include function key and control key combinations, such as CTRL+F1 or CTRL+A. They
appear on the menu to the right of the corresponding menu item, as shown in Figure 6.10.
To remove a shortcut key assignment, choose "(none)" from the top of the list.
190
Note Shortcut keys appear automatically on the menu; therefore, you do not have to enter CTRL+key in
To maintain consistency with other applications, it's a good idea to follow established naming guidelines
When assigning captions for menu items, you should try to follow these guidelines:
• Item names should be unique within a menu, but may be repeated in different menus to represent
similar actions.
• Each item name should have a unique mnemonic access character for users who choose commands
with keyboards. The access character should be the first letter of the menu title, unless another letter
offers a stronger mnemonic link; no two menu titles should use the same access character. For more
information about assigning access and shortcut keys, see "Creating Menus with the Menu Editor"
• An ellipsis () should follow names of commands that require more information before they can be
• Keep the item names short. If you are localizing your application, the length of words tends to
increase approximately thirty percent in foreign versions, and you may not have enough space to
adequately list all of your menu items. For more details on localizing your application, see
"International Issues."
To make your code more readable and easier to maintain, it's a good idea to follow established naming
conventions when setting the Name property in the Menu Editor. Most naming convention guidelines
suggest a prefix to identify the object (that is, mnu for a menu control) followed by the name of the top-
level menu (for example, File). For submenus, this would be followed by the caption of the submenu (for
example, mnuFileOpen).
191
For More Information For an example of suggested naming conventions, see "Visual Basic Coding
Conventions."
Creating Submenus
See Also
Each menu you create can include up to five levels of submenus. A submenu branches off another menu
to display its own menu items. You may want to use a submenu when:
If there is room on the menu bar, however, it's better to create an additional menu title instead of a
submenu. That way, all the controls are visible to the user when the menu is dropped down. It's also good
programming practice to restrict the use of submenus so users don't get lost trying to navigate your
application's menu interface. (Most applications use only one level of submenus.)
In the Menu Editor, any menu control indented below a menu control that is not a menu title is a submenu
control. In general, submenu controls can include submenu items, separator bars, and submenu titles.
To create a submenu
1. Create the menu item that you want to be the submenu title.
2. Create the items that will appear on the new submenu, and indent them by clicking the right arrow
button.
Each indent level is preceded by four dots (....) in the Menu Editor. To remove one level of
Note If you're considering using more than a single level of submenus, think about using a dialog box
instead. Dialog boxes allow users to specify several choices in one place. For information on using dialog
A menu control array is a set of menu items on the same menu that share the same name and event
• Create a new menu item at run time when it must be a member of a control array. The MDI Notepad
sample, for example, uses a menu control array to store a list of recently opened files.
• Simplify code, because common blocks of code can be used for all menu items.
Each menu control array element is identified by a unique index value, indicated in the Index property box
on the Menu Editor. When a member of a control array recognizes an event, Visual Basic passes its Index
property value to the event procedure as an additional argument. Your event procedure must include code
to check the value of the Index property, so you can determine which control you're using.
For More Information For more information on control arrays, see "Working with Control Arrays" in
–or–
3. In the Caption text box, type the text for the first menu title that you want to appear on the menu
bar.
The menu title text is displayed in the menu control list box.
4. In the Name text box, type the name that you will use to refer to the menu control in code. Leave
the Index box empty.
5. At the next indentation level, create the menu item that will become the first element in the array by
setting its Caption and Name.
7. Create a second menu item at the same level of indentation as the first.
8. Set the Name of the second element to the same as the first element and set its Index to 1.
Important Elements of a menu control array must be contiguous in the menu control list box and must
be at the same level of indentation. When you're creating menu control arrays, be sure to include any
The menus you create at design time can also respond dynamically to run-time conditions. For example, if
a menu item action becomes inappropriate at some point, you can prevent users from selecting that menu
item by disabling it. In the MDI NotePad application, for example, if the clipboard doesn't contain any text,
the Paste menu item is dimmed on the Edit menu, and users cannot select it.
You can also dynamically add menu items, if you have a menu control array. This is described in "Adding
You can also program your application to use a check mark to indicate which of several commands was
last selected. For example, the Options, Toolbar menu item from the MDI NotePad application displays a
check mark if the toolbar is displayed. Other menu control features described in this section include code
that makes a menu item visible or invisible and that adds or deletes menu items.
All menu controls have an Enabled property, and when this property is set to False, the menu is disabled
and does not respond to user actions. Shortcut key access is also disabled when Enabled is set to False. A
disabled menu control appears dimmed, like the Paste menu item in Figure 6.11.
For example, this statement disables the Paste menu item on the Edit menu of the MDI NotePad
application:
mnuEditPaste.Enabled = False
194
Disabling a menu title in effect disables the entire menu, because the user cannot access any menu item
without first clicking the menu title. For example, the following code would disable the Edit menu of the
mnuEdit.Enabled = False
Using the Checked property, you can place a check mark on a menu to:
• Tell the user the status of an on/off condition. Choosing the menu command alternately adds and
• Indicate which of several modes is in effect. The Options menu of the MDI Notepad application uses a
check mark to indicate the state of the toolbar, as shown in Figure 6.12.
You create check marks in Visual Basic with the Checked property. Set the initial value of the Checked
property in the Menu Editor by selecting the check box labeled Checked. To add or remove a check mark
from a menu control at run time, set its Checked property from code. For example:
mnuOptionsToolbar.Checked = picToolbar.Visible
End Sub
In the Menu Editor, you set the initial value of the Visible property for a menu control by selecting the
check box labeled Visible. To make a menu control visible or invisible at run time, set its Visible property
' visible.
195
' invisible.
When a menu control is invisible, the rest of the controls in the menu move up to fill the empty space. If
the control is on the menu bar, the rest of the controls on the menu bar move left to fill the space.
Note Making a menu control invisible effectively disables it, because the control is inaccessible from the
menu, access or shortcut keys. If the menu title is invisible, all the controls on that menu are unavailable.
A menu can grow at run time. In Figure 6.13, for example, as files are opened in the SDI NotePad
application, menu items are dynamically created to display the path names of the most recently opened
files.
Figure 6.13 Menu control array elements created and displayed at run time
You must use a control array to create a control at run time. Because the mnuRecentFile menu control is
assigned a value for the Index property at design time, it automatically becomes an element of a control
When you create mnuRecentFile(0), you actually create a separator bar that is invisible at run time. The
first time a user saves a file at run time, the separator bar becomes visible, and the first file name is
added to the menu. Each time you save a file at run time, additional menu controls are loaded into the
Controls created at run time can be hidden by using the Hide method or by setting the control's Visible
property to False. If you want to remove a control in a control array from memory, use the Unload
statement.
When the user chooses a menu control, a Click event occurs. You need to write a Click event procedure in
code for each menu control. All menu controls except separator bars (and disabled or invisible menu
The code that you write in a menu event procedure is no different than that which you would write in any
other control's event procedure. For example, the code in a File, Close menu's Click event might look like
this:
Sub mnuFileClose_Click()
Unload Me
End Sub
Visual Basic displays a menu automatically when the menu title is chosen; therefore, it is not necessary to
write code for a menu title's Click event procedure unless you want to perform another action, such as
Note At design time, the menus you create are displayed on the form when you close the Menu Editor.
Choosing a menu item on the form displays the Click event procedure for that menu control.
A pop-up menu is a floating menu that is displayed over a form, independent of the menu bar. The items
displayed on the pop-up menu depend on where the pointer was located when the right mouse button was
pressed; therefore, pop-up menus are also called context menus. In Microsoft Windows 95 or later
systems, you activate context menus by clicking the right mouse button.
Any menu that has at least one menu item can be displayed at run time as a pop-up menu. To display a
pop-up menu, use the PopupMenu method. This method uses the following syntax:
For example, the following code displays a menu named mnuFile when the user clicks a form with the
right mouse button. You can use the MouseUp or MouseDown event to detect when the user clicks the
right mouse button, although the standard is to use the MouseUp event:
End If
End Sub
Any code following a call to the PopupMenu method is not run until the user selects an item in the menu
Note Only one pop-up menu can be displayed at a time. While a pop-up menu is displayed, calls to the
PopupMenu method are ignored. Calls to the PopupMenu method are also ignored whenever a menu
control is active.
Often you want a pop-up menu to access options that are not usually available on the menu bar. To create
a menu that will not display on the menu bar, make the top-level menu item invisible at design time
(make sure the Visible check box in the Menu Editor is not checked). When Visual Basic displays a pop-up
You use the flags argument in the PopupMenu method to further define the location and behavior of a
pop-up menu. The following table lists the flags available to describe a pop-up menu's location.
vbPopupMenuLeftAlign Default. The specified x location defines the left edge of the pop-up
menu.
vbPopupMenuRightAlign The specified x location defines the right edge of the pop-up menu.
The following table lists the flags available to describe a pop-up menu's behavior.
198
vbPopupMenuLeftButton Default. The pop-up menu is displayed when the user clicks a
menu item with the left mouse button only.
vbPopupMenuRightButton The pop-up menu is displayed when the user clicks a menu item
with either the right or left mouse button.
To specify a flag, you combine one constant from each group using the Or operator. The following code
displays a pop-up menu with its top border centered on a form when the user clicks a command button.
The pop-up menu triggers Click events for menu items that are clicked with either the right or left mouse
button.
xloc = ScaleWidth / 2
yloc = ScaleHeight / 2
End Sub
You use the boldcommand argument to specify the name of a menu control in the displayed pop-up menu
that you want to appear in bold. Only one menu control in the pop-up menu can be bold.
In an MDI application, the menus for each child are displayed on the MDI form, rather than on the child
forms themselves. When a child form has the focus, that child's menu (if any) replaces the MDI form's
199
menu on the menu bar. If there are no child forms visible, or if the child with the focus does not have a
menu, the MDI form's menu is displayed (see Figures 6.14 and 6.15).
It is common for MDI applications to use several sets of menus. When the user opens a document, the
application displays the menu associated with that type of document. Usually, a different menu is
displayed when no child forms are visible. For example, when there are no files open, Microsoft Excel
displays only the File and Help menus. When the user opens a file, other menus are displayed (File, Edit,
You can create menus for your Visual Basic application by adding menu controls to the MDI form and to
the child forms. One way to manage the menus in your MDI application is to place the menu controls you
want displayed all of the time, even when no child forms are visible, on the MDI form. When you run the
application, the MDI form's menu is automatically displayed when there are no child forms visible, as
Figure 6.14 The MDI form menu is displayed when no child forms are loaded
Place the menu controls that apply to a child form on the child form. At run time, as long as there is at
least one child form visible, these menu titles are displayed in the menu bar of the MDI form.
Some applications support more than one type of document. For example, in Microsoft Access, you can
open tables, queries, forms, and other document types. To create an application such as this in Visual
Basic, use two child forms. Design one child with menus that perform spreadsheet tasks and the other
At run time, when an instance of a spreadsheet form has the focus, the spreadsheet menu is displayed,
and when the user selects a chart, that form's menu is displayed. If all the spreadsheets and charts are
closed, the MDI form's menu is displayed. For more information on creating menus, see "Using Menus in
Most MDI applications (for example, Microsoft Word for Windows and Microsoft Excel) incorporate a
Window menu. This is a special menu that displays the captions of all open child forms, as shown in Figure
6.15. In addition, some applications place commands on this menu that manipulate the child windows,
Figure 6.15 The Window menu displays the name of each open child form
Any menu control on an MDI form or MDI child form can be used to display the list of open child forms by
setting the WindowList property for that menu control to True. At run time, Visual Basic automatically
manages and displays the list of captions and displays a check mark next to the one that had the focus
most recently. In addition, a separator bar is automatically placed above the list of windows.
1. Select the form where you want the menu to appear, and from the Tools menu, choose Menu
Editor.
Note The WindowList property applies only to MDI forms and MDI child forms. It has no effect on
2. In the Menu Editor list box, select the menu where you want the list of open child forms to display.
201
At run time, this menu displays the list of open child forms. In addition, the WindowList property for this
As was mentioned earlier, some applications list actions such as Tile, Cascade, and Arrange Icons on a
menu, along with the list of open child forms. Use the Arrange method to rearrange child forms in the MDI
form. You can display child forms as cascading, as horizontally tiled, or as child form icons arranged along
the lower portion of the MDI form. The following example shows the Click event procedures for the
frmMDI.Arrange vbCascade
End Sub
frmMDI.Arrange vbTileHorizontal
End Sub
frmMDI.Arrange vbArrangeIcons
End Sub
Note The intrinsic constants vbCascade, vbTileHorizontal, and vbArrangeIcons are listed in the Visual
When you tile or cascade child forms that have a fixed border style, each child form is positioned as if it
Toolbars
See Also
You can further enhance your application's menu interface with toolbars. Toolbars contain toolbar buttons,
which provide quick access to the most frequently used commands in an application. For example, the
Visual Basic toolbar contains toolbar buttons to perform commonly used commands, such as opening
• Negotiating Menu and Toolbar Appearance Working with toolbars and menus for insertable objects.
Creating a Toolbar
See Also
The toolbar (also called a ribbon or control bar) has become a standard feature in many Windows-based
applications. A toolbar provides quick access to the most frequently used menu commands in an
application. Creating a toolbar is easy and convenient using the toolbar control, which is available with the
Professional and Enterprise editions of Visual Basic. If you are using the Learning Edition of Visual Basic,
you can create toolbars manually as described in "Negotiating Menu and Toolbar Appearance" later in this
chapter.
The following example demonstrates creating a toolbar for an MDI application; the procedure for creating
The width of the picture box automatically stretches to fill the width of the MDI form's workspace. The
workspace is the area inside a form's borders, not including the title bar, menu bar, or any toolbars,
Note You can place only those controls that support the Align property directly on an MDI form (the
picture box is the only standard control that supports this property).
2. Inside the picture box, place any controls you want to display on the toolbar.
203
Typically, you create buttons for the toolbar using command buttons or image controls. Figure 6.16
To add a control inside a picture box, click the control button in the toolbox, and then draw it inside
Note When an MDI form contains a picture box, the internal area of the MDI form does not include
the area of the picture box. For example, the ScaleHeight property of the MDI form returns the
internal height of the MDI form, which does not include the height of the picture box.
Figure 6.16 You can create buttons for the toolbar using image controls
One advantage of using a toolbar is that you can present the user with a graphical representation of a
command. The image control is a good choice as a toolbar button because you can use it to display a
bitmap. Set its Picture property at design time to display a bitmap; this provides the user with a
visual cue of the command performed when the button is clicked. You can also use ToolTips, which
display the name of the toolbar button when a user rests the mouse pointer over a button, by setting
4. Write code.
Because toolbar buttons are frequently used to provide easy access to other commands, most of the
time you call other procedures, such as a corresponding menu command, from within each button's
Click event.
204
Tip You can use controls that are invisible at run time (such as the timer control) with an MDI form
without displaying a toolbar. To do this, place a picture box on the MDI form, place the control in the
picture box, and set the picture box's Visible property to False.
Toolbars are used to provide the user with a quick way to access some of the application's commands. For
example, the first button on the toolbar in Figure 6.16 is a shortcut for the File New command. There are
now three places in the MDI NotePad sample application where the user can request a new file:
Rather than duplicate this code three times, you can take the original code from the child form's
mnuFileNew_Click event and place it in a public procedure in the child form. You can call this procedure
frmNewPad.Show
End Sub
' The user chooses New on the child form File menu.
FileNew
End Sub
' The user chooses New on the MDI form File menu.
frmNotePad.FileNew
205
End Sub
' The user clicks the File New button on the toolbar.
frmNotePad.FileNew
End Sub
When an object supplied by another application is activated on a form, there are a number of ways that
object's menus and toolbars may appear on the container form; therefore, you need to specify how they
will be displayed. This process is called user-interface negotiation because Visual Basic and the object you
have linked or embedded must negotiate for space in the container form.
You can determine whether a linked or embedded object's menu will appear in the container form by
setting a form's NegotiateMenus property. If the child form's NegotiateMenus property is set to True
(default) and the container has a menu bar defined, the object's menus are placed on the container's
menu bar when the object is activated. If the container has no menu bar, or the NegotiateMenus property
is set to False, the object's menus will not appear when it is activated.
The MDI form's NegotiateToolbars property determines whether the linked or embedded object's toolbars
will be floating palettes or placed on the parent form. This behavior does not require toolbars to be
present on the MDI parent form. If the MDI form's NegotiateToolbars property is True, the object's toolbar
appears on the MDI parent form. If NegotiateToolbars is False, the object's toolbar will be a floating
palette.
If an MDI form includes a toolbar, it is usually contained in a picture box control on the parent form. The
picture box's Negotiate property determines whether the container's toolbar is still displayed or is replaced
206
by the object's toolbar when activated. If Negotiate is True, the object's toolbar is displayed in addition to
the container's toolbar. If Negotiate is False, the object's toolbar replaces the container's toolbar.
Note Menu and toolbar negotiation will occur only for insertable objects that support in-place activation.
For more information on in-place activation, see "Programming with ActiveX Components."
You can see how these three properties interact by using the following procedure.
1. Add a toolbar to an MDI form. This is described in "Creating a Toolbar" earlier in this chapter.
Dialog Boxes
See Also
In Visual Basic, for example, you use the File Open dialog box to display existing projects. The About
dialog box in Visual Basic is also an example of how you can use a dialog box to display information. When
the user clicks the Help, About Visual Basic menu item on the menu bar, the About dialog box is displayed.
• Using Predefined Dialog Boxes Techniques for using message and input boxes.
• Using Forms as Custom Dialog Boxes Creating your own dialog boxes.
Dialog boxes are either modal or modeless. A modal dialog box must be closed (hidden or unloaded)
before you can continue working with the rest of the application. For example, a dialog box is modal if it
requires you to click OK or Cancel before you can switch to another form or dialog box.
The About dialog box in Visual Basic is modal. Dialog boxes that display important messages should
always be modal — that is, the user should always be required to close the dialog box or respond to its
Modeless dialog boxes let you shift the focus between the dialog box and another form without having to
close the dialog box. You can continue to work elsewhere in the current application while the dialog box is
displayed. Modeless dialog boxes are rare. From the Edit menu, the Find dialog box in Visual Basic is an
example of a modeless dialog box. Use modeless dialog boxes to display frequently used commands or
information.
• Use the Show method with a style argument of vbModal (a constant for the value 1).
For example:
frmAbout.Show vbModal
For example:
frmAbout.Show
Note If a form is displayed as modal, the code following the Show method is not executed until the
dialog box is closed. However, when a form is shown as modeless, the code following the Show method is
The Show method has another optional argument, owner, that can be used to specify a parent-child
relationship for a form. You can pass the name of a form to this argument to make that form the owner of
• Use the Show method with both style and owner arguments.
For example:
Using the owner argument with the Show method ensures that the dialog box will be minimized when its
The easiest way to add a dialog box to your application is to use a predefined dialog, because you don't
have to worry about designing, loading, or showing the dialog box. However, your control over its
The following table lists the functions you can use to add predefined dialog boxes to your Visual Basic
application.
InputBox function Display a command prompt in a dialog box, and return whatever is entered
by the user.
MsgBox function Display a message in a dialog box, and return a value indicating the
command button was clicked by the user.
Use the InputBox function to solicit data from the user. This function displays a modal dialog box that asks
the user to enter some data. The text input box shown in Figure 6.17 prompts the user for the name of
The following code displays the input box shown in Figure 6.17:
Note Remember that when you use the InputBox function, you have little control over the components
of the dialog box. You can change only the text in the title bar, the command prompt displayed to the user,
the position of the dialog box on the screen, and whether or not it displays a Help button.
Use the MsgBox function to get yes or no responses from users, and to display brief messages, such as
errors, warnings, or alerts in a dialog box. After reading the message, the user chooses a button to close
An application named Text Editor might display the message dialog box shown in Figure 6.18 if a file
cannot be opened.
Figure 6.18 An error message dialog box created using the MsgBox function
The following code displays the message box shown in Figure 6.18:
Note Modality can either be limited to the application or the system. If a message box's modality is
limited to the application (default), then users cannot switch to another part of the application until the
dialog box is dismissed, but they can switch to another application. A system modal message box does not
allow the user to switch to another application until the message box is dismissed.
A custom dialog box is a form you create containing controls — including command buttons, option
buttons, and text boxes — that lets the user supply information to the application. You customize the
appearance of the form by setting property values. You also write code to display the dialog box at run
time.
To create a custom dialog box, you can start with a new form or customize an existing dialog box. Over
time, you can build up a collection of dialog boxes that can be used in many applications.
1. From the Project menu, choose Add Form to add an existing form to your project.
2. From the File menu, choose Save filename As and enter a new file name. (This prevents you from
making changes to the existing version of the form).
–or–
You have considerable freedom to define the appearance of a custom dialog box. It can be fixed or
movable, modal or modeless. It can contain different types of controls; however, dialog boxes do not
211
usually include menu bars, window scroll bars, Minimize and Maximize buttons, status bars, or sizable
borders. The remainder of this topic discusses ways to create typical dialog box styles.
Adding a Title
A dialog box should always have a title that identifies it. To create a title, set the form's Caption property
to the text string that will appear in the title bar. Usually, this is done at design time using the Properties
window, but you can also do this from code. For example:
frmAbout.Caption = "About"
Tip If you want to remove the title bar completely, set the form's ControlBox, MinButton, and MaxButton
properties to False; set the BorderStyle to a nonsizable setting (0, 1, or 3); and set the Caption equal to
Generally, the user responds to a dialog box by providing information and then closing the dialog box with
an OK or Cancel command button. Because a dialog box is temporary, users usually don't need to move,
size, maximize, or minimize it. As a result, the sizable border style, Control menu box, Maximize button,
and Minimize button that come with a new form are unnecessary on most dialog boxes.
You can remove these items by setting the BorderStyle, ControlBox, MaxButton, and MinButton properties.
For example, an About dialog box might use the following property settings.
Remember that if you remove the Control menu box (ControlBox = False), you must provide the user with
another way to exit the dialog box. This is commonly done by adding an OK, Cancel, or Exit command
button to the dialog box and adding code in the Click event for the button that hides or unloads the dialog.
Modal dialog boxes must contain at least one command button to exit the dialog box. Usually, two
command buttons are used: one button to let the user start an action, and one button to close the dialog
212
box without making any changes. Typically, the Caption property settings for these buttons are OK and
Cancel. In this scenario, the OK command button has its Default property set to True, and the Cancel
button has its Cancel property set to True. Although OK and Cancel are the most commonly used buttons,
Dialog boxes that display messages usually use a label control to display the error message or command
prompt, and one or two command buttons to perform an action. For example, you might assign the error
message or command prompt to the Caption property of the label, and Yes and No to the Caption property
of two command button controls. When users choose Yes, one action takes place; when they choose No,
Command buttons on this type of dialog are usually placed on the bottom or right side of the dialog box,
with the top or left button being the default button, as shown in Figure 6.19.
• Default
• Cancel
• TabIndex
• TabStop
The Default button is selected when the user presses ENTER. Only one command button on a form can
have its Default property set to True. Pressing the ENTER key invokes the Click event for the default
command button. This feature works in conjunction with an edit control, such as a text box. For example,
213
the user can type data in a text box and then press ENTER to generate a Click event instead of choosing
an OK button.
The Cancel button is selected when the user presses ESC. Only one command button on a form can have
its Cancel property set to True. Pressing the ESC key invokes the Click event for the Cancel command
button. The Cancel button can also be the default command button. To specify the Cancel button for a
Tip In general, the button that indicates the most likely or safest action should be the default action. For
example, in a Text Replace dialog box, Cancel should be the default button, not Replace All.
You can also specify the button that will have the focus when the dialog is displayed. The control with the
lowest TabIndex setting receives the focus when the form is displayed. Pressing the ENTER key invokes
the Click event for the default command button or for the command button that has the focus. To give a
command button the focus when the form is displayed, set the command button's TabIndex to 0 and its
TabStop property to True. You can also use the SetFocus method to give a specific control the focus when
a form is displayed.
For More Information See "TabIndex Property" and "TabStop Property" in the Language Reference.
Sometimes controls need to be disabled because their actions would be inappropriate in the current
context. For example, when the Visual Basic Find dialog box is first displayed, the Find Next button is
disabled, as shown in Figure 6.20. You can disable a control on a dialog by setting its Enabled property to
False.
• cmdFindNext.Enabled = False
• cmdReplace.Enabled = False
You display a dialog box in the same way you display any other form in an application. The startup form
loads automatically when the application is run. When you want a second form or dialog box to appear in
the application, you write code to load and display it. Similarly, when you want the form or dialog box to
The following code displays the About dialog box when the user selects the Help, About menu item:
frmAbout.Show vbModal
End Sub
Display Options
The code you write determines how a dialog box is loaded into memory and displayed. The following table
describes various form displaying tasks and the keywords that are used to perform them.
Task Keyword
Load a form into memory, but do not display Use the Load statement, or reference a property or control
it. on the form.
Load and display a modal form. Use the Show method with style = vbModal.
Display a loaded form. Set its Visible property to True, or use the Show method.
Hide a form from view. Set its Visible property to False, or use the Hide method.
Hide a form from view and unload from Use the Unload statement.
memory.
The Show method loads the form and sets its Visible property to True. The argument passed to the Show
method indicates the style of the dialog box. If the style argument is omitted or set to vbModeless or 0
(default), the dialog box is modeless; if it is vbModal or 1, the dialog box is modal.
215
To exit the dialog box when the user chooses OK or Cancel, use either the Unload statement or the Hide
Unload frmAbout
–or–
frmAbout.Hide
The Unload statement removes the dialog box from memory, while the Hide method merely removes the
dialog box from view by setting its Visible property to False. When you unload a form, the form itself and
its controls are unloaded from memory (including any controls that were loaded at run time). When you
When you need to save space in memory, it's better to unload a form, because unloading a form frees
memory. If you use the dialog box often, you can choose to hide the form. Hiding a form retains any data
attached to it, including property values, print output, and dynamically created controls. By hiding a form,
you can continue to refer to the properties and controls of a hidden form in code.
computers with different display resolutions and color depths. The applications that you write in Visual
Basic are likely to be run on different display types as well; you need to be aware of this when designing
an application.
By default, Microsoft Visual Basic doesn't change your form and control sizes as you change screen
resolutions. What this means is that a form that you design at 1024 by 768 resolution may extend past
the edges of the screen when run at 640 by 480 resolution. If you want to create forms and controls that
have the same proportions no matter what screen resolution you use, you must either design your forms
at the lowest resolution, or add code to your program that changes the forms.
The easiest way to avoid sizing problems is to design your forms at 640 by 480 resolution. If you prefer to
work at a higher resolution, you still need to be aware of how your form will appear at a lower resolution.
One way to do this is to use the Form Layout window to preview the size and location of your form. You
can use Resolution Guides to see what portion of the screen will be visible at a lower resolution. To toggle
216
the Resolution Guides, right click in the Form Layout window and select the Resolution Guides menu item
Visual Basic also places your form at run time based on its location at design time. If you are running at
1024 by 768 resolution at design time and you place a form in the lower right-hand corner of the screen,
it may not be visible when run at a lower resolution. To avoid this, set the startup position of your form at
design time by selecting the Startup Position menu item from the Form Layout window popup menu.
Alternatively, you can set a forms position at runtime with code in the Form Load event:
Me.Move 0, 0
End Sub
This has the same effect as setting both the Left and Top properties of the form to 0, but the Move method
Visual Basic uses a device-independent unit of measurement, a twip, for calculating size and position. Two
properties of the Screen object, TwipsPerPixelX and TwipsPerPixelY, can be used to determine the size of
the display at run time. Using these properties, you can write code to adjust the size and position of your
Dim X As Integer
Dim Y As Integer
X = Screen.TwipsPerPixelX
Y = Screen.TwipsPerPixelY
Select Case X, Y
Case 15, 15
txtName.Height = 200
txtName.Width = 500
End Sub
You also need to be aware of the position of Visual Basic's own windows at design time. If you position the
Project window to the right side of the screen at high resolution, you may find that it is no longer
In designing an application, you also need to consider the color display capabilities of the computers that
may be running your application. Some computers can display 256 or more colors, others are limited to
16. If you design a form using a 256-color palette, dithering (a process used to simulate colors that are
not available) may cause some of the elements on the form to disappear when displayed at 16 colors.
To avoid this situation, it's best to limit the colors used in your application to the 16 standard Windows
colors. These are represented by the Visual Basic color constants (vbBlack, vbBlue, vbCyan, and so on). If
it's necessary to use more than 16 colors in your application, you should still stick with the standard colors
Unless you're creating Visual Basic applications strictly for your own use, the value of your creations is
going to be judged by others. The user interface of your application has the greatest impact on the user's
opinion — no matter how technically brilliant or well optimized your code may be, if the user finds your
As a programmer, you are undoubtedly familiar with the technological aspects of computers. It's easy to
forget that most users don't understand (and probably don't care) about the technology behind an
application. They see an application as a means to an end: a way to accomplish a task, ideally more easily
than they would without the aid of a computer. A well-designed user interface insulates the user from the
In designing the user interface for your application, you need to keep the user in mind. How easily can a
user discover the various features of your application without instruction? How will your application
respond when errors occur? What will you provide in terms of help or user assistance? Is the design
218
aesthetically pleasing to the user? The answers to these and other questions relating to user-focused
• When Things Go Wrong: Interacting with Users Techniques for gracefully handling user and system
errors.
• Designing a User Assistance Model Providing help for learning and using your application.
You don't need to be an artist to create a great user interface — most of the principles of user interface
design are the same as the basic design principles taught in any elementary art class. The elementary
design principles of composition, color, and so forth apply equally well to a computer screen as they do to
Although Visual Basic makes it easy to create a user interface by simply dragging controls onto a form, a
little planning up front can make a big difference in the usability of your application. You might consider
drawing your form designs on paper first, determining which controls are needed, the relative importance
The composition or layout of your form not only influences its aesthetic appeal, it also has a tremendous
impact on the usability of your application. Composition includes such factors as positioning of controls,
Positioning of Controls
In most interface designs, not all elements are of equal importance. Careful design is necessary to ensure
that the more important elements are readily apparent to the user. Important or frequently accessed
elements should be given a position of prominence; less important elements should be relegated to less
prominent locations.
In most languages, we are taught to read from left to right, top to bottom of a page. The same holds true
for a computer screen — most user's eyes will be drawn to the upper left portion of the screen first, so the
219
most important element should go there. For example, if the information on a form is related to a
customer, the name field should be displayed where it will be seen first. Buttons, such as OK or Next,
should be placed in the lower right portion of the screen; the user normally won't access these until they
Grouping of elements and controls is also important. Try to group information logically according to
function or relationship. Because their functions are related, buttons for navigating a database should be
grouped together visually rather than scattered throughout a form. The same applies to information; fields
for name and address are generally grouped together, as they are closely related. In many cases, you can
Consistency is a virtue in user interface design. A consistent look and feel creates harmony in an
application — everything seems to fit together. A lack of consistency in your interface can be confusing,
and can make an application seem chaotic, disorganized, and cheap, possibly even causing the user to
For visual consistency, establish a design strategy and style conventions before you begin development.
Design elements such as the types of controls, standards for size and grouping of controls, and font
choices should be established in advance. You can create prototypes of possible designs to help you make
design decisions.
The wide variety of controls available for use in Visual Basic make it tempting to use them all. Avoid this
temptation; choose a subset of controls that best fit your particular application. While list box, combo box,
grid, and tree controls can all be used to present lists of information, it's best to stick with a single style
where possible.
Also, try to use controls appropriately; while a text box control can be set to read-only and used to display
text, a label control is usually more appropriate for that purpose. Remain consistent in the setting of
properties for your controls — if you use a white back color for editable text in one place, don't use grey in
Consistency between different forms in your application is important to usability. If you use a grey
background and three-dimensional effects on one form and a white background on another, the forms will
appear to be unrelated. Pick a style and stick with it throughout your application, even if it means
Affordances are visual clues to the function of an object. Although the term may be unfamiliar, examples
of affordances are all around you. A handgrip on a bicycle has depressions where you place your fingers,
an affordance that makes it obvious that it is meant to be gripped. Push buttons, knobs, and light switches
are all affordances — just by looking at them you can discern their purpose.
A user interface also makes use of affordances. For instances, the three-dimensional effects used on
command buttons make them look like they are meant to be pushed. If you were to design a command
button with a flat border, you would lose this affordance and it wouldn't be clear to the user that it is a
command button. There are cases where flat buttons might be appropriate, such as games or multimedia
applications; this is okay as long as you remain consistent throughout your application.
Text boxes also provide a sort of affordance — users expect that a box with a border and a white
background will contain editable text. While it's possible to display a text box with no border (BorderStyle
= 0), this will make it look like a label and it won't be obvious to the user that it is editable.
The use of white space in your user interface can help to emphasize elements and improve usability. White
space doesn't necessarily have to be white — it refers to the use of blank space between and around
controls a form. Too many controls on a form can lead to a cluttered interface, making it difficult to find an
individual field or control. You need to incorporate white space in your design in order to emphasize your
design elements.
Consistent spacing between controls and alignment of vertical and horizontal elements can make your
design more usable as well. Just as text in a magazine is arranged in orderly columns with even spacing
Visual Basic provides several tools that make it easy to adjust the spacing, alignment, and size of controls.
Align, Make Same Size, Horizontal Spacing, Vertical Spacing, and Center in Form commands can all be
Keep It Simple
Perhaps the most important principle of interface design is one of simplicity. When it comes to
applications, if the interface looks difficult, it probably is. A little forethought can help you to create an
interface that looks (and is) simple to use. Also, from an aesthetic standpoint, a clean, simple design is
always preferable.
A common pitfall in interface design is to try and model your interface after real-world objects. Imagine,
for instance, that you were asked to create an application for completing insurance forms. A natural
221
reaction would be to design an interface that exactly duplicates the paper form on screen. This creates
several problems: the shape and dimensions of a paper form are different than those of the screen,
duplicating a form pretty much limits you to text boxes and check boxes, and there's no real benefit to the
user.
It's far better to design your own interface, perhaps providing a printed duplicate (with print preview) of
the original paper form. By creating logical groupings of fields from the original form and using a tabbed
interface or several linked forms, you can present all of the information without requiring the user to
scroll. You can also use additional controls, such as a list box preloaded with choices, which reduce the
You can also simplify many applications by taking infrequently used functions and moving them to their
own forms. Providing defaults can sometimes simplify an application; if nine out of ten users select bold
text, make the text bold by default rather than forcing the user to make a choice each time (don't forget
to provide an option to override the default). Wizards can also help to simplify complex or infrequent
tasks.
The best test of simplicity is to observe your application in use. If a typical user can't immediately
The use of color in your interface can add visual appeal, but it's easy to overuse it. With many displays
capable of displaying millions of colors, it's tempting to use them all. Color, like the other basic design
Preference for colors varies widely; the user's taste may not be the same as your own. Color can evoke
strong emotions, and if you're designing for international audiences, certain colors may have cultural
significance. It's usually best to stay conservative, using softer, more neutral colors.
Of course, your choice of colors may also be influenced by the intended audience and the tone or mood
you are trying to convey. Bright reds, greens, and yellows may be appropriate for a children's application,
Small amounts of bright color can be used effectively to emphasize or draw attention to an important
area. As a rule of thumb, you should try and limit the number of colors in an application, and your color
scheme should remain consistent. It's best to stick to a standard 16-color palette if possible; dithering can
Another consideration in the use of color is that of colorblindness. Many people are unable to tell the
difference between different combinations of primary colors such as red and green. To someone with this
The use of pictures and icons can also add visual interest to your application, but again, careful design is
essential. Images can convey information compactly without the need for text, but images are often
Toolbars with icons to represent various functions are a useful interface device, but if the user can't readily
identify the function represented by the icon, they can be counterproductive. In designing toolbar icons,
look at other applications to see what standards are already established. For example, many applications
use a sheet of paper with a folded corner to represent a New File icon. There may be a better metaphor
for this function, but representing it differently could confuse the user.
It's also important to consider the cultural significance of images. Many programs use a picture of a rural-
style mailbox with a flag (Figure 6.21) to represent mail functions. This is primarily an American icon;
In designing your own icons and images, try to keep them simple. Complex pictures with a lot of colors
don't degrade well when displayed as a 16-by-16 pixel toolbar icon, or when displayed at high screen
resolutions.
Choosing Fonts
Fonts are also an important part of your user interface, because they often communicate important
information to the user. You need to select fonts that will be easily readable at different resolutions and on
different types of displays. It's best to stick with simple sans serif or serif fonts where possible. Script and
other decorative fonts generally look better in print than on screen, and can be difficult to read at smaller
point sizes.
Unless you plan on distributing fonts along with your application, you should stick to standard Windows
fonts such as Arial, New Times Roman, or System. If the user's system doesn't include a specified font,
the system will make a substitution, resulting in a completely different appearance than what you
intended. If you're designing for an international audience, you'll need to investigate what fonts are
223
available in the intended languages. Also, you'll need to consider text expansion when designing for other
languages — text strings can take up to 50% more space in some languages.
Again, design consistency is important in choosing fonts. In most cases, you shouldn't use more than two
fonts at two or three different point sizes in a single application. Too many fonts can leave your application
The usability of any application is ultimately determined by the user. Interface design is an iterative
process; rarely is the first pass at designing an interface for your application going to yield a perfect
interface. By getting users involved early in the design process, you can create a better, more usable
The best place to start when designing a user interface is to look at some of the best-selling applications
from Microsoft or other companies; after all, they probably didn't get to be best-sellers because of poor
interfaces. You'll find many things in common, such as toolbars, status bars, ToolTips, context-sensitive
menus, and tabbed dialogs. It's no coincidence that Visual Basic provides the capabilities for adding all of
You can also borrow from your own experience as a user of software. Think about some of the applications
that you have used; what works, what doesn't, and how you would fix it. Remember, however, that your
personal likes and dislikes may not match those of your users; you'll need to validate your ideas with
them.
You may have also noticed that most successful applications provide choices to accommodate varying user
preferences. For instance, the Microsoft Windows Explorer allows users to copy files with menus, keyboard
commands, or by drag and drop. Providing options will broaden the appeal of your application; as a
minimum you should make all functions accessible by both mouse and keyboard.
One of the main advantages of the Windows operating system is that it presents a common interface
across all applications. A user that knows how to use one Windows-based application should be able to
easily learn any other. Unfortunately, applications that stray too far from the established interface
Menus are a good example of this — most Windows-based applications follow the standard of a File menu
on the left, then optional menus such as Edit and Tools, followed by Help on the right. It could be argued
that Documents would be a better name than File, or that the Help menu should come first. There's
nothing to prevent you from doing this, but by doing so you will confuse your users and decrease the
usability of your application. Users will have to stop and think every time they switch between your
The placement of submenus is also important. Users expect to find Copy, Cut and Paste beneath the Edit
menu; moving them to the File menu would be confusing at best. Don't deviate from the established
The best way to test the usability of your interface is to involve users throughout the design phase.
Whether you're designing a major shrink-wrap application or a small application for limited use, the design
process should be pretty much the same. Using your established design guidelines, you'll want to start by
The next step is to create one or more prototypes, designing your forms in Visual Basic. You'll need to add
just enough code to make the prototype functional: displaying forms, filling list boxes with sample data,
Usability testing can be an informal process, reviewing your design with a few users, or a formal process
in an established usability lab. Either way, the purpose is the same — learning first-hand from the users
where your design works and where it needs improvement. Rather than questioning the user, it's more
effective to simply turn the user loose with the application and observe them. Have the user verbalize
their thought process as they attempt to perform a set of tasks: "I want to open a new document, so I will
look under the File menu." Make note of where the interface design doesn't respond to their thought
processes. Test with multiple users; if you see several users having difficulty with a particular task, that
Next, you'll want to review your notes and consider how you can change the interface to make it more
usable. Make the changes to your interface and test it again. Once you are satisfied that your application
is usable, you're ready to start coding. You'll also want to test occasionally during the development
process to make sure that the assumptions for the prototype were valid.
Discoverability of Features
225
One of the key concepts in usability testing is that of discoverability. If a user can't discover how to use a
feature (or even that a feature exists), that feature is of little use. For example, the majority of Windows
3.1 users were never aware that the ALT, TAB key combination could be used to switch between open
applications. There was no clue anywhere in the interface to help users discover this feature.
To test the discoverability of a feature, ask the user to perform a task without explaining how to do it (for
example, "Create a new document using a Form Letter Template"). If they can't accomplish the task, or if
In an ideal world, software and hardware would always work flawlessly, and users would never make
mistakes. Reality dictates that mistakes can and will happen. A part of user interface design involves
A common response is to display a dialog box, asking for user input as to how the application should deal
with the problem. A less common (but preferable) response would be to simply resolve the problem
without bothering the user. After all, the user is primarily concerned with performing a task, not with
technical details. In designing your user interface, think about the potential errors and determine which
ones require user interaction and which ones can be resolved programmatically.
Occasionally an error occurs in your application and it's necessary to make a decision in order to resolve
the situation. This usually occurs as a branch in your code — an IfThen statement or a Case statement. If
the decision requires user interaction, the question is usually posed to the user with a dialog box. Dialog
boxes are a part of your user interface, and like the other parts of the interface, their design plays a role
Sometimes it seems as if many dialog boxes were designed by programmers who have never had an
intelligent conversation with another human being. A message such as "A sector of fixed disk C: is
corrupted or inaccessible. Abort, Retry, Ignore?" (see Figure 6.22) has little meaning to the average user.
It's kind of like a waitress asking you "We're out of soup or the kitchen is on fire. Abort, Retry, Ignore?"
How would you answer? It's important to phrase questions (and choices) in a manner that the user can
understand. In the prior example, a better message might be "There is a problem saving your file on drive
When creating dialog boxes for your application, keep the user in mind. Does the message convey useful
information to the user? Is it easily understandable? Do the command buttons present clear choices? Are
the choices appropriate for the given situation? Keep in mind that it only takes one annoying message box
If you're designing your own custom dialog forms, try to stick to a standard style. If you vary too far from
the standard message box layout, users may not recognize it as a dialog box.
For More Information To learn more about dialogs, see "Dialog Boxes" earlier in this chapter.
It isn't always necessary to interrupt the user when an error occurs. Sometimes it's preferable to handle
the error in code without notifying the user, or to warn the user in a way that doesn't stop their work flow.
A good example of this technique is the AutoCorrect feature in Microsoft Word: if a common word is
mistyped, Word fixes it automatically; if a less common word is misspelled, it is underlined in red so the
There are a number of techniques that you can use; it's up to you to decide which techniques are
• Add an Undo function to the Edit menu. Rather than interrupting the user with a confirmation dialog
for deletions and so forth, trust that they are making the right decision and provide a Undo function
• Display a message on a status bar or icon. If the error doesn't affect the user's current task, don't
stop the application. Use a status bar or a brightly colored warning icon to warn the user — they can
• Correct the problem. Sometimes the solution to an error is obvious. For instance, if a disk is full when
the user tries to save a file, check the system for space on other drives. If space is available, save the
file; put a message on the status bar to let the user know what you did.
• Save the message until later. Not all errors are critical or demand immediate attention; consider
logging these to a file and displaying them to the user when they exit the application or at another
convenient time. If the user makes a possible entry error (for example, Mian St. instead of Main St.),
log it. Add a Review Entries button and a function to display the discrepancies so the user can correct
them.
• Don't do anything. Sometimes an error isn't important enough to warrant a warning. For instance, the
fact that a printer on LPT1 is out of paper doesn't mean much until you're ready to print. Wait until
For More Information To learn more about error handling techniques, see "Debugging Your Code and
Handling Errors."
No matter how great your user interface, there will be times that a user needs assistance. The user
assistance model for your application includes such things as online Help and printed documentation; it
may also contain user assistance devices such as ToolTips, Status Bars, What's This help, and Wizards.
The user assistance model should be designed just like any other part of your application: before you start
developing. The contents of your model will vary depending on the complexity of the application and the
intended audience.
Online Help is an important part of any application — it's usually the first place a user will look when they
have a question. Even a simple application should provide Help; failing to provide it is like assuming that
In designing your Help system, keep in mind that its primary purpose is to answer questions. Try to think
in terms of the user when creating topic names and index entries; for example, "How do I format a page?"
rather than "Edit, Page Format menu" will make your topic easier to locate. Don't forget about context
sensitivity; it's frustrating to most users if they press the F1 key for help on a specific field and find
Conceptual documentation, whether printed and/or provided on compact disc, is helpful for all but the
simplest applications. It can provide information that may be difficult to convey in the shorter Help topic.
At the very least, you should provide documentation in the form of a ReadMe file that the user can print if
desired.
Within the user interface, there are several techniques for providing assistance to the user. Visual Basic
makes it easy to add ToolTips, What's This help, Status displays, and Wizards to your applications. It's up
to you to decide which of these devices are appropriate for your application.
ToolTips
ToolTips (Figure 6.23) are a great way to display information to the user as they navigate the user
interface. A ToolTip is a small label that is displayed when the mouse pointer is held over a control for a
set length of time, usually containing a description of the control's function. Normally used in conjunction
with toolbars, ToolTips also work well in most any part of the interface.
Most Visual Basic controls contain a single property for displaying ToolTips: ToolTipText. The following code
As with other parts of the interface, make sure that the text clearly conveys the intended message to the
user.
229
For More Information To learn more about ToolTips, see "ToolTipText Property" in the Language
Reference.
What's this Help provides a link to a pop-up Help topic (see Figure 6.24) when the user selects What's This
Help and clicks the What's This cursor on a control. What's This Help can be initiated from a toolbar
7. In the Click event of the menu or toolbar button, enter the following:
8. formname.WhatsThisHelpMode
When the user clicks the button or menu, the mouse pointer will change to the What's This pointer.
To enable What's This Help on the title bar of a custom dialog form, set the form's WhatsThisButton and
For More Information To learn more about What's This Help, see "WhatsThisHelp Property" and
Status Displays
A status display can also be used to provide user assistance in much the same way as a ToolTip. Status
displays are a good way to provide instructions or messages that may not fit easily into a ToolTip. The
230
status bar control included in the Professional and Enterprise editions of Visual Basic works well for
The text displayed in a status display can be updated in one of two ways: in the GotFocus event of a
control or form, or in the MouseMove event. If you want to use the display as a learning device, add an
item to the Help menu to toggle its Visible property on and off.
3. Add the following code to the control's MouseMove (or GotFocus) event:
When the user moves the mouse over the control, the message will be displayed in the label control.
Wizards
A wizard is a user assistance device that takes the user step by step through a procedure, working with
the user's actual data. Wizards are usually used to provide task-specific assistance. They help a user
accomplish a task that would otherwise require a considerable (and undesirable) learning curve; they
provide expert information to a user that has not yet become an expert.
The Professional and Enterprise editions of Visual Basic include the Wizard Manager, a tool for creating
wizards.
For More Information To learn more about wizards, see "Using Wizards and Add-Ins" in "Managing
Projects."
You use controls to get user input and to display output. Some of the controls you can use in your
applications include text boxes, command buttons, and list boxes. Other controls let you access other
applications and process data as if the remote application was part of your code. Each control has its own
set of properties, methods, and events. This chapter introduces you to the standard controls in Visual
Basic.
231
For More Information See "Using ActiveX Controls" in the Component Tools Guide for more
information about the ActiveX controls available in the Professional and Enterprise versions of Visual Basic.
Topics
Introduction to Visual Basic Controls
Explains how to use the Validate event with the CausesValidation property.
Describes control arrays and how they are used in Visual Basic.
Use the ADO Data Control to create simple database applications without writing any code.
Use check box controls in groups to display multiple choices from which the user can select one or
more.
Use the combined features of a text box and a list box to allow the user to select an item either by
typing text into the combo box, or by selecting it from the list.
Use the command button control to begin, interrupt, or end a process. When clicked, it invokes the
Use the common dialog control to provide a standard set of dialog boxes for operations such as
opening and saving files, setting print options, and selecting colors and fonts.
Use the intrinsic Data control to connect to desktop databases, such as Access.
232
Use the DataCombo and DataList controls with the ADO Data Control to display information from a
database.
Use the DataGrid control to create an application that allows the end user to read and write to most
databases.
Using the File-System Controls (Directory List Box, Drive List Box, and File List Box)
Use the drive list box, the directory list box, and the file list box controls to allow users of your
Use the frame control to provide an identifiable grouping for other controls.
Use the horizontal and vertical scroll bar controls to provide scrolling to applications or controls when
Use the image control to display graphics in the following formats: bitmap, icon, metafile, enhanced
Use the label control to display text that cannot be edited by the user or to provide a description of
Use the line control to create simple line segments on a form, a frame, or in a picture box.
Use the list box control to display a list of items from which the user can select one or more.
Use the OLE container control to display and manipulate data from other Windows–based
Use the option button control to display options in option button groups from which the user can
choose one.
Use the picture box control to display graphics, to act as a container for other controls, and to display
Use the Shape control to draw predefined shapes on forms, frames, or picture boxes.
Use the text box control to display information entered by the user at run time, or assigned to the
Use the timer control to execute timer events at specified time intervals.
Sample Applications
Controls.vbp, MSFlexGd.vbp, Winseek.vbp
Many of the code examples in this chapter are taken from the Controls.vbp, MSFlexGd.vbp, and
See Also
The Visual Basic toolbox contains the tools you use to draw controls on your forms.
Control Categories
• Intrinsic controls, such as the command button and frame controls. These controls are contained
inside the Visual Basic .exe file. Intrinsic controls are always included in the toolbox, unlike ActiveX
controls and insertable objects, which can be removed from or added to the toolbox.
• ActiveX controls, which exist as separate files with a .ocx file name extension. These include controls
that are available in all editions of Visual Basic (DataCombo, DataList controls, and so on) and those
that are available only in the Professional and Enterprise editions (such as Listview, Toolbar,
Animation, and Tabbed Dialog). Many third-party ActiveX controls are also available.
Note Controls with the .vbx file name extension use older technology and are found in applications
written in earlier versions of Visual Basic. When Visual Basic opens a project containing a .vbx control,
the default behavior is to replace the .vbx control with an .ocx control, but only if an .ocx version of
the control is available. See "Updating Older Versions of Visual Basic Controls" later in this chapter for
• Insertable Objects, such as a Microsoft Excel Worksheet object containing a list of all your company's
employees, or a Microsoft Project Calendar object containing the scheduling information for a project.
235
Since these can be added to the toolbox, they can be considered controls. Some of these objects also
support Automation (formerly called OLE Automation), which allows you to program another
application's objects from within a Visual Basic application. See "Programming with Objects," for more
information on Automation.
For More Information See "Using ActiveX Controls" in the Component Tools Guide for more
information about the ActiveX controls available in the Professional and Enterprise versions of Visual Basic.
Intrinsic Controls
See Also
The following table summarizes the intrinsic controls found in the Visual Basic toolbox.
Drive list box DriveListBox Displays and allows a user to select valid
disk drives.
File list box FileListBox Displays and allows a user to select from
a list of files.
Horizontal and vertical HScrollBar and Allow a user to add scroll bars to controls
scroll bars VScrollBar that do not automatically provide them.
(These are not the same as the built-in
scroll bars found with many controls.)
Note The pointer tool (the first tool in the toolbox) provides a way to move and resize forms and
The Learning edition of Visual Basic contains a number of ActiveX controls (referred to as standard ActiveX
controls) that allow you to add advanced features to your applications. ActiveX controls have the file name
extension .ocx and can be used in your project by manually adding them to the toolbox.
The following table summarizes the standard ActiveX controls available in the Learning edition of Visual
Basic.
For More Information See "Using ActiveX Controls" in the Component Tools Guide for more
information about the ActiveX controls available in the Professional and Enterprise versions of Visual Basic.
Other Controls
Other ActiveX controls included with all versions of Visual Basic are documented in the Component Tools
Guide, and include the following: ImageCombo, ImageList, ListView, ProgressBar, Slider, Statusbar,
You move ActiveX controls to and from the toolbox using the following procedures.
2. Select the check box next to the name of the .ocx control, and then choose OK. Once a control is
placed in the toolbox, you can add it to a form just as you would an intrinsic control.
1. Remove all instances of the control from the forms in your project. Delete any references to the
control in the project's code. If references to a deleted control are left in your code, an error message
will display when you compile the application.
Clear the check box next to the name of the .ocx control, and then choose OK. An error message will
For More Information See "Adding Controls to a Project" in "Managing Projects" for more information
about adding and removing controls and insertable objects to and from the Toolbox.
Older 16-bit versions of Visual Basic controls with the file extension .vbx are incompatible with this version
of Visual Basic. If you attempt to load an older project containing .vbx controls, Visual Basic will warn you
that the controls are unavailable or incompatible. You have the option of continuing to load the project
without the .vbx controls but, of course, the application will not function properly.
If you have older Visual Basic projects that contain third-party .vbx controls, contact the control's
When you first create an object (form or control), Visual Basic sets its Name property to a default value.
For example, all command buttons have their Name property initially set to Commandn, where n is 1, 2,
3, and so on. Visual Basic names the first command button drawn on a form Command1, the second
You may choose to keep the default name; however, when you have several controls of the same type, it
makes sense to change their Name properties to something more descriptive. Because it may be difficult
to distinguish the Command1 button on MyForm from the Command1 button on YourForm, a naming
convention can help. This is especially true when an application consists of several form, standard, and
class modules.
You can use a prefix to describe the class, followed by a descriptive name for the control. Using this
naming convention makes the code more self-descriptive and alphabetically groups similar objects in the
Object list box. For example, you might name a Check Box control like this:
chkReadOnly
• must contain only letters, numbers, and the underscore character (_); punctuation characters and
For More Information See "Visual Basic Coding Conventions" for more information on naming
conventions.
All controls have a property that you can use to store or retrieve values just by referring to the control,
without using the property name. This is called the value of the control and is usually the most important
or most commonly used property of the control. The following table lists the property that is considered to
Control Value
Data Caption
DataCombo Text
DataGrid Text
DataList Text
FlexGrid Text
Frame Caption
Image Picture
Label Caption
Line Visible
Shape Shape
Timer Enabled
Whenever you want to refer to a property on a control that happens to be the value of that control, you
can do so without specifying the property name in your code. For example, this line sets the value of the
of Text1"
In this example, the Caption property of Label1 is set to the FileName property of File1 whenever the user
Label1 = File1
End Sub
Note Because using the value of a control makes your code somewhat less readable, the examples in
this guide do not use it but instead refer explicitly to the properties on all controls. You may want to try
writing your code both ways, and decide to use the value of controls in your code if you have no trouble
reading it.
The Validate event and CausesValidation property are used in tandem to verify the input to a control
before allowing the user to shift focus away from that control. For example, imagine an application with
several text boxes and a Help button. When each text box receives the focus, you want to prevent the
user from shifting the focus until the text box's particular validation criteria are met; however, you also
want to allow users to click the Help button at any time. To do this, set the validation criteria in the
Validate event and set the CausesValidation property of the Help button to False. If the property is set to
241
True (the default setting), the Validate event will occur on the first control. If the property is set to False,
the Validate event on the first control will be preempted from occurring.
The Validate event is more suited to validating data entry than the LostFocus event because the LostFocus
event (by definition) occurs after the focus has shifted. In contrast, by using the Validate event you can
prevent the focus from ever shifting to another control until all validation rules have been met.
Possible Uses
• A data entry application needs to perform more sophisticated data entry validation than can be
provided by the Masked Edit control, or the validation occurs in a business rule.
• A form needs to prevent users from moving off a control using the TAB key or an accelerator until
• An ActiveX document running inside Internet Explorer needs a way for the user to finish an operation
The Validate event includes a keepfocus argument. When the argument is set to True, the control will
retain the focus. This effectively prevents the user from clicking any other control.
A control array is a group of controls that share the same name and type. They also share the same event
procedures. A control array has at least one element and can grow to as many elements as your system
resources and memory permit; its size also depends on how much memory and Windows resources each
control requires. The maximum index you can use in a control array is 32767. Elements of the same
control array have their own property settings. Common uses for control arrays include menu controls and
Note Visual Basic includes the ability to dynamically add unreferenced controls to the Controls collection
at run time. This topic refers only to referenced controls added at design time by cutting and pasting a
control onto the form. For more information about adding controls at run time, see the reference topic
Adding controls with control arrays uses fewer resources than simply adding multiple controls of the same
type to a form at design time. Control arrays are also useful if you want several controls to share code.
For example, if three option buttons are created as a control array, the same code is executed regardless
If you want to create a new instance of a control at run time, that control must be a member of a control
array. With a control array, each new element inherits the common event procedures of the array.
Using the control array mechanism, each new control inherits the common event procedures already
written for the array. For example, if your form has several text boxes that each receive a date value, a
control array can be set up so that all of the text boxes share the same validation code.
The Calculator sample application (which is listed in the Samples directory) shown in Figure 7.2 contains
two control arrays — the number buttons and the operator buttons.
The Name and Index property values for the control arrays in the Calculator example are listed in the
following table.
Number(n) Operator(n)
0 = Number(0) + = Operator(1)
1 = Number(1) – = Operator(2)
2 = Number(2) X = Operator(3)
243
3 = Number(3) / = Operator(4)
4 = Number(4) = = Operator(5)
5 = Number(5)
6 = Number(6)
7 = Number(7)
8 = Number(8)
9 = Number(9)
Notice how each control is referred to with the syntax object(index). You specify the index of a control
when you create it. In fact, specifying any index for a control at design time makes that control part of an
array.
The Index property distinguishes one element of the control array from another. When one of the controls
in the array recognizes an event, Visual Basic calls a common event procedure and passes an argument
(the value of the Index property) to identify which control actually recognizes the event.
For example, the first line of the Number_Click event procedure is:
If Number(0) recognizes the event, Visual Basic passes 0 as the index argument, and if Number(1)
recognizes the event, Visual Basic passes 1 as the index argument. Other than the index value, the
remainder of the Number_Click code that is executed is the same for both Number(0) through Number(9).
Note You must create menu control arrays in the Menu Editor. For details on how to do this, see
1. Draw the controls you want to be in the control array. (The controls must all be of the same type.)
Decide which control will become the first element in the array.
2. Select one of the controls and change its Name setting to the Name setting for the first element in
the array.
3. When you type an existing name for a control in the array, Visual Basic displays a dialog box asking
you to confirm that you want to create a control array. Choose Yes to confirm the action.
For example, if the name of the first element in a control array is cmdCtlArr, you would choose a command
button to add to the array and then set its name to cmdCtlArr. The message "You already have a control
named 'cmdCtlArr.' Do you want to create a control array?" is displayed. Choose Yes to confirm the
operation.
Controls added this way share only their Name property and control type; all other properties remain the
2. While the control has the focus, choose Copy from the Edit menu.
3. From the Edit menu, choose Paste. Visual Basic displays a dialog box asking you to confirm that you
want to create a control array. Choose Yes to confirm the action.
This control is assigned an index value of 1. The first control you drew has a value of 0.
The index value of each new array element corresponds to the order in which the element was added to
the control array. When controls are added this way, most of the visual properties, such as height, width,
and color, are copied from the first control in the control array to the new controls.
You can add and remove controls in a control array at run time using the Load and Unload statements.
However, the control to be added must be an element of an existing control array. You must have created
a control at design time with the Index property set, in most cases, to 0. Then, at run time, use this
syntax:
Load object(index%)
245
Unload object(index%)
Argument Description
object Name of the control to add to or delete from the control array.
When you load a new element of a control array, most of the property settings are copied from the lowest
existing element in the array — in this example, the element with the 0 index value. The Visible, Index,
and TabIndex property settings are not automatically copied to new elements of a control array, so to
make the newly added control visible, you must set its Visible property to True.
Note Visual Basic generates an error if you attempt to use the Load statement with an index number
Important You can use the Unload statement to remove any control created with Load. However, you
cannot use Unload to remove controls created at design time, regardless of whether or not they are part
of a control array.
The control array example demonstrates how controls — in this case, option buttons — are added and
deleted at run time. The example allows the user to add option buttons that change the background color
of a picture box.
Start with a form, and then draw a picture box, a label, two option buttons, and three command buttons,
The following table lists the property settings for the objects in the application.
Next, you need to add the event procedures for the option buttons and command buttons. Start by adding
picDisplay.BackColor = QBColor(Index + 1)
247
End Sub
New option buttons are added by the Click event procedure for the Add command button. In this example,
the code checks that no more than ten option buttons are loaded before the Load statement is executed.
' buttons.
' allowed.
Top + 400
' button.
End Sub
Option buttons are removed by the Click event procedure for the Delete command button:
' buttons.
End Sub
248
Unload Me
End Sub
The ADO Data control uses Microsoft ActiveX Data Objects (ADO) to quickly create connections between
data-bound controls and data providers. Data-bound controls are any controls that feature a DataSource
property. Data providers can be any source written to the OLE DB specification. You can also easily create
Although you can use the ActiveX Data Objects directly in your applications, the ADO Data control has the
advantage of being a graphic control (with Back and Forward buttons) and an easy-to-use interface that
Several of the controls found in Visual Basic's Toolbox can be data-bound, including the CheckBox,
ComboBox, Image, Label, ListBox, PictureBox, and TextBox controls. Additionally, Visual Basic includes
several data-bound ActiveX controls such as the DataGrid, DataCombo, Chart, and DataList controls. You
can also create your own data-bound ActiveX controls, or purchase controls from other vendors.
Previous versions of Visual Basic featured the intrinsic Data control and the Remote Data control (RDC) for
data access. Both controls are still included with Visual Basic for backward compatibility. However, because
of the flexibility of ADO, it's recommended that new database applications be created using the ADO Data
Control.
For More Information A complete list of data-bound controls can be found in "Controls That Bind to the
ADO Data Control." To find out how to use the intrinsic Data control or the Remote Data control, see
"Using the Data Control" or "Using the Remote Data Control." For details about creating a data provider,
Possible Uses
249
• Open a specified database table or define a set of records based on a Structured Query Language
• Pass data field values to data-bound controls, where you can display or change the values.
• Add new records or update a database based on any changes you make to data displayed in the
bound controls.
To create a client, or front-end database application, add the ADO Data control to your forms just as you
would any other Visual Basic control. You can have as many ADO Data controls on your form as you need.
Be aware, however, that the control is a comparatively "expensive" method of creating connections, using
at least two connections for the first control, and one more for each subsequent control.
It's possible to create a database application using a minimum of code by setting a few properties at
design time. If you are using an OLE DB data source, the Microsoft Data Link Name (.UDL) must be
created on your machine. See "Creating the Northwind OLE DB Data Link" for a step-by-step example.
If the control is not available in the Toolbox, press CTRL+T to display the Components dialog box. In
2. On the Toolbox, click the ADO Data Control to select it. Then press F4 to display the Properties
window.
3. In the Properties window, click ConnectionString to display the ConnectionString dialog box.
4. If you have created a Microsoft Data Link file (.UDL), select Use OLE DB File and click Browse to
find the file on the computer. If you use a DSN, click Use ODBC Data Source Name and select a
DSN from the box, or click New to create one. If you wish to use create a connection string, select
Use ConnectionString, and then click Build, and use the Data Link Properties dialog box to
create a connection string. After creating the connection string, click OK. The ConnectionString
property will be filled with a string like:
5. driver={SQL Server};server=bigsmile;uid=sa;pwd=pwd;database=pubs
6. In the Properties window, set the RecordSource property to a SQL statement. For example,
You should always include a WHERE clause when accessing a table. Failing to do so will lock the entire
9. In the Properties window, set the DataSource property for Text1 to the name of the ADO Data
control (ADODC1). This binds the text box to the ADO Data control.
10. In the Properties window, click DataField and a list of available fields will drop down. Click the
name of the field you want to display.
11. Repeat steps 6, 7, and 8 for each additional field you want to access.
12. Press F5 to run the application. You can use the four arrow buttons on the ADO Data control to move
to the beginning of the data, to the end of the data, or from record to record through the data.
The code below shows how to set these four properties programmatically. Note that setting the
With ADODC1
"server=bigsmile;uid=sa;pwd=pwd;database=pubs"
End With
Text1.DataField = "Title"
End Sub
The ADO Data control features several events that you can program. The table below shows the events
and when they occur; however the table is not meant to be a complete list all of the conditions when the
events occur. For complete information, see the reference topic for the individual event.
Event Occurs
Recordset.Resync
For More Information To try other step-by-step procedures using the ADO Data control, see "Creating
a Simple Database Application with the DataGrid and ADO Data Control," "Creating a Simple DataCombo
When creating a connection, you can use one of three sources: a Connection String, an OLE DB file
(.UDL), or an ODBC Data Source Name (DSN). When using a DSN, it's likely you will not have to alter any
However, if you are familiar with database technology, you can alter some of the other properties exposed
on the ADO Data Control. The following list describes database-related properties of the control. The list
Note Database technology is complex, and the suggestions below are not meant to be taken as rules.
1. ConnectionString — The ConnectionString property is a string that can contain all the settings
necessary to make a connection. The parameters passed in the string are driver-dependent. For
example, ODBC drivers allow the string to contain driver, provider, default database, server,
username, and password.
2. UserName — The name of the user, necessary if the database is password-protected. Like the
Provider property, this property can be specified in the ConnectionString. If you provide both a
ConnectionString and a UserName, the ConnnectionString value will override the UserName
property's value.
252
3. Password — Also needed when accessing a protected database. Like Provider and UserName, this
property's value will be overridden if the value is specified in the ConnectionString.
4. RecordSource — This property generally contains a statement that determines what will be retrieved
from the database.
5. CommandType — The CommandType property instructs the data provider if the Source is a SQL
statement, a table name, a stored procedure, or an unknown type.
6. CursorLocation — This property specifies where the cursor is located, on the client or on the server.
The consequences of this decision affect the next few properties you set.
7. CursorType — The CursorType property determines if the recordset is static, dynamic, or a keyset
cursor type.
8. LockType — The LockType determines how the data is locked when others attempt to change data
you are editing. How you set the LockType is a complex decision, dependent on many factors.
9. Mode — The Mode property determines what you intend to do with the recordset. For example, you
can achieve some performance gains by setting it to read-only, if you are only interested in creating
reports.
10. MaxRecords — This property determines how large the cursor will be. How you determine this
depends on the size of the records you are retrieving and the resources available on your computer
(memory). A large record (one with many columns and large strings) would take more resources than
a smaller record. Consequently the MaxRecords property should be no larger than necessary.
11. ConnectionTimeout — Set the ConnectionTimeout to the number of seconds to wait while
establishing the connection. An error is returned if the connection times out.
12. CacheSize — The CacheSize property specifies how many records can be retrieved from the cursor. If
you've set the CursorLocation to client side, then this property can be set to a smaller number (as
small as 1) with no adverse effects. If it's on the server side, you should optimize this figure to suit
the number of rows you want to view at any one time. For example, if you use the DataGrid control to
view 30 rows, set the CacheSize to 60, allowing you to scroll without retrieving more data.
13. BOFAction, EOFAction — These two properties determine what will happen when the control is at
the beginning and end of the cursor. Choices include staying at the beginning or end, moving to the
first or last record, or adding a new record (at the end only).
Any control that has the DataSource property can be bound to an ADO Data Control. The following
• CheckBox
• ComboBox
• Image
253
• Label
• ListBox
• PictureBox
• TextBox
The following data-bound ActiveX Controls are also supplied with all versions of Visual Basic:
• DataList
• DataCombo
• DataGrid
• RichTextBox
• Microsoft Chart
• DateTimePicker
• ImageCombo
• MonthView
Finally, you can create your own ActiveX controls that are data-bound using the BindingCollection object.
For More Information See "Creating Data-Bound User Controls" for details about creating your own
data-bound controls.
The check box control displays a check mark when it is selected. It is commonly used to present a Yes/No
or True/False selection to the user. You can use check box controls in groups to display multiple choices
The check box control is similar to the option button control in that each is used to indicate a selection
that is made by the user. They differ in that only one option button in a group can be selected at a time.
With the check box control, however, any number of check boxes may be selected.
For More Information See "Selecting Individual Options with Check Boxes" in "Forms, Controls, and
The Value property of the check box control indicates whether the check box is checked, unchecked, or
The following table lists the values and equivalent Visual Basic constants that are used to set the Value
property.
Unchecked 0 vbUnchecked
Checked 1 vbChecked
Unavailable 2 vbGrayed
The user clicks the check box control to indicate a checked or unchecked state. You can then test for the
state of the control and program your application to perform some action based on this information.
By default, the check box control is set to vbUnchecked. If you want to preselect several check boxes in a
series of check boxes, you can do so by setting the Value property to vbChecked in the Form_Load or
Form_Initialize procedures.
You can also set the Value property to vbGrayed to disable the check box. For example, you may want to
Whenever the user clicks on the check box control, the Click event is triggered. You can then program
your application to perform some action depending upon the state of the check box. In the following
example, the check box control's Caption property changes each time the control is clicked, indicating a
Check1.Caption = "Checked"
Check1.Caption = "Unchecked"
End If
End Sub
Note If the user attempts to double-click the check box control, each click will be processed separately;
that is, the check box control does not support the double-click event.
The Click event of the check box control is also triggered when the focus is shifted to the control with the
keyboard by using the TAB key and then by pressing the SPACEBAR.
You can toggle selection of the check box control by adding an ampersand character before a letter in the
In this example, pressing the ALT+C key combination toggles between the checked and unchecked states.
The check box control, like the command button and option button controls, may be visually enhanced by
altering the setting of the Style property and then using the Picture, DownPicture, and DisabledPicture
properties. For example, you may want to add an icon or bitmap to a check box or display a different
A combo box control combines the features of a text box and a list box. This control allows the user to
select an item either by typing text into the combo box, or by selecting it from the list.
Combo boxes present a list of choices to the user. If the number of items exceeds what can be displayed
in the combo box, scroll bars will automatically appear on the control. The user can then scroll up and
Generally, a combo box is appropriate when there is a list of suggested choices, and a list box is
appropriate when you want to limit input to what is on the list. A combo box contains an edit field, so
In addition, combo boxes save space on a form. Because the full list is not displayed until the user clicks
the down arrow (except for Style 1, which is always dropped down), a combo box can easily fit in a small
For More Information See "Using List Boxes and Combo Boxes" in "Forms, Controls, and Menus" for a
simple demonstration of these controls. Also see "Using the List Box Control" later in this chapter for more
Data-Bound Features
Visual Basic includes both standard and data-bound versions of the combo box control. While both
versions allow you to display, edit, and update information from most standard types of databases, the
data-bound combo box provides more advanced data access features. The Data-Bound combo box control
also supports a different set of properties and methods than the standard combo box control.
For More Information See "Using the DataCombo and DataList Controls" in "Using Visual Basic's
There are three combo box styles. Each style can be set at design time and uses values, or equivalent
With the default setting (Style = 0 – Dropdown Combo), a combo box is a drop-down combo box. The
user can either enter text directly (as in a text box) or click the detached arrow at the right of the combo
box to open a list of choices. Selecting one of the choices inserts it into the text portion at the top of the
combo box. The user also can open the list by pressing ALT+ DOWN ARROW when the control has the
focus.
Setting the Style property of a combo box to 1 – Simple Combo specifies a simple combo box in which the
list is displayed at all times. To display all entries in the list, you must draw the list box large enough to
display the entries. A vertical scroll bar is automatically inserted when there are more entries than can be
displayed. The user can still enter text directly or select from the list. As with a drop-down combo box, a
simple combo box also allows users to enter choices not on the list.
A drop-down list box (Style = 2 – Dropdown List) is like a regular list box — it displays a list of items from
which a user must choose. Unlike list boxes, however, the list is not displayed until you click the arrow to
the right of the box. The key difference between this and a drop-down combo box is that the user can't
258
type into the box, he can only select an item from the list. Use this type of list box when space is at a
premium.
Adding Items
To add items to a combo box, use the AddItem method, which has the following syntax:
Argument Description
While list items are commonly added in the Form_Load event procedure, you can use the AddItem method
at any time. This gives you the ability to add items to the list dynamically (in response to user actions).
The following code places "Chardonnay," "Fum Blanc," "Gewrztraminer," and "Zinfandel" into a combo box
Combo1.AddItem "Chardonnay"
Combo1.AddItem "Gewrztraminer"
Combo1.AddItem "Zinfandel"
End Sub
Whenever the form is loaded at run time and the user clicks the down arrow, the list appears as shown in
Figure 7.8.
You can also enter items into the list at design time by setting the List property in the Properties window
of the combo box control. When you select the List property option and then click the down arrow, you can
type list items and then press the CTRL+ENTER key combination to start a new line.
You can only add items to the end of the list. So, if you want to alphabetize the list, set the Sorted
To add an item to a list at a specific position, specify an index value after the new item. For example, the
next line of code inserts "Pinot Noir" into the first position, adjusting the position of the other items
downward:
Notice that it is 0, not 1, that specifies the first item in a list (see Figure 7.9).
Sorting a List
You can specify that items be added to a list in alphabetical order by setting the Sorted property to True
and omitting the index. The sort is not case-sensitive; thus, the words "chardonnay" and "Chardonnay"
When the Sorted property is set to True, using the AddItem method with the index argument can lead to
Removing Items
You can use the RemoveItem method to delete items from a combo box. RemoveItem has one argument,
box.RemoveItem index
The box and index arguments are the same as for AddItem.
260
For example, to remove the first entry in a list, you would add the following line of code:
Combo1.RemoveItem 0
To remove all list entries in a combo box, use the Clear method:
Combo1.Clear
Usually, the easiest way to get the value of the currently selected item is to use the Text property. The
Text property corresponds to whatever is entered in the text box portion of the control at run time. This
can be either a selected list item or a string that a user types in the text box.
For example, the following code displays information about Chardonnay if a user selects "Chardonnay"
white wine."
End If
End Sub
The Text property contains the currently selected item in the Combo1 list box. The code checks to see if
"Chardonnay" has been selected and, if so, displays the information in the text box.
The List property provides access to all items in the list. This property contains an array in which each
item in the list is an element of the array. Each item is represented in string form. To refer to an item in
box.List(index)
The box argument is a reference to a combo box, and index is the position of the item. The top item has
an index of 0, the next has an index of 1, and so on. For example, the following statement displays the
Text1.Text = Combo1.List(2)
If you want to know the position of the selected item in a list in a combo box, use the ListIndex property.
This property sets or returns the index of the currently selected item in the control and is available only at
run time. Setting the ListIndex property for a combo box also generates a Click event for the control.
The value of this property is 0 if the first (top) item is selected, 1 if the next item down is selected, and so
on. ListIndex is – 1 if no item is selected or if a user enters a choice in a combo box (Style 0 or 1) instead
Note The NewIndex property allows you to keep track of the index of the last item added to the list. This
To return the number of items in a combo box, use the ListCount property. For example, the following
statement uses the ListCount property to determine the number of entries in a combo box:
entries listed"
The command button control is used to begin, interrupt, or end a process. When clicked, it invokes a
command that has been written into its Click event procedure.
Most Visual Basic applications have command buttons that allow the user to simply click them to perform
actions. When the user chooses the button, it not only carries out the appropriate action, it also looks as if
it's being pushed in and released and is therefore sometimes referred to as a push button.
For More Information See "Clicking Buttons to Perform Actions" in "Forms, Controls, and Menus" for a
You will likely use one or more command buttons in your application. To add command buttons to a form,
draw them on as you would any other control. Command buttons can be sized with the mouse or by
To change the text displayed on the command button, use the Caption property. At design time, you can
set this property by selecting it from the control's Properties window. When you set the Caption property
You can set the Caption property up to 255 total characters. If your caption exceeds the width of the
command button, it will wrap to the next line. However, it will be clipped if the control cannot
You can change the font displayed on the command button by setting its Font property.
You can use the Caption property to create access key shortcuts for your command buttons by adding an
ampersand (&) before the letter you want to use as the access key. For example, to create an access key
for the caption "Print" you add an ampersand before the letter "P": "&Print". At run time, the letter "P" will
be underlined and the user can select the command button by simultaneously pressing ALT+P.
Note To include an ampersand in a caption without creating an access key, include two ampersands
(&&). A single ampersand is displayed in the caption and no characters are underlined.
On each form, you can select a command button to be the default command button — that is, whenever
the user presses the ENTER key the command button is clicked regardless of which other control on the
form has the focus. To specify a command button as default set the Default property to True.
You can also specify a default cancel button. When the Cancel property of a command button is set to
True, it will be clicked whenever the user presses the ESC key, regardless of which other control on the
A command button can be selected at run time by using the mouse or keyboard in the following ways:
• Move the focus to the button by pressing the TAB key, and then choose the button by pressing the
SPACEBAR or ENTER.
• Press an access key (ALT+ the underlined letter) for a command button.
263
• If the command button is the default command button for the form, pressing ENTER chooses the
• If the command button is the default Cancel button for the form, then pressing ESC chooses the
Whenever the command button is selected, its Value property is set to True and the Click event is
triggered. False (default) indicates the button isn't chosen. You can use the Value property in code to
cmdClose.Value = True
When clicked, the command button's Click event is triggered and the code you've written in the Click
Clicking a command button control also generates the MouseDown and MouseUp events. If you intend to
attach event procedures for these related events, be sure that their actions don't conflict. The order in
which these three events occur varies from control to control. In the command button control, these
Note If the user attempts to double-click the command button control, each click will be processed
separately; that is, the command button control does not support the double-click event.
For More Information See "Responding to Mouse and Keyboard Events" for more information on the
The command button control, like the check box and option button controls, may be visually enhanced by
altering the setting of the Style property and then using the Picture, DownPicture and DisabledPicture
properties. For example, you may want to add an icon or bitmap to a command button or display a
The common dialog control provides a standard set of dialog boxes for operations such as opening and
saving files, setting print options, and selecting colors and fonts. The control also has the ability to display
The common dialog control provides an interface between Visual Basic and the procedures in the Microsoft
Windows dynamic-link library Commdlg.dll. To create a dialog box using this control, Commdlg.dll must be
You use the common dialog control in your application by adding it to a form and setting its properties.
The dialog displayed by the control is determined by the methods of the control. At run time, a dialog box
is displayed or the Help engine is executed when the appropriate method is invoked; at design time, the
common dialog control is displayed as an icon on a form. This icon can't be sized.
The common dialog control allows you to display these commonly used dialog boxes:
• Open
• Save As
• Color
• Font
1. If you haven't already done so, add the common dialog control to the toolbox by selecting
Components from the Project menu. Locate and select the control in the Controls tabbed dialog,
then click the OK button.
When you draw a common dialog control on a form, it automatically resizes itself. Like the timer
3. At run time, use the appropriate method, as listed in the following table, to display the desired dialog.
265
ShowOpen Open
ShowSave Save As
ShowColor Color
ShowFont Font
ShowPrinter Print
4.
The Open dialog box allows the user to specify a drive, a directory, a file name extension, and a file name.
The Save As dialog box is identical to the Open dialog in appearance, except for the dialog's caption, and
file names appearing dimmed out. At run time, when the user chooses a file and closes the dialog box, the
1. Specify the list of file filters that are displayed in the Files of type list box.
You can do this by setting the Filter property using the following format:
266
Description is the string displayed in the list box — for example, "Text Files (*.txt)." Filter is the actual
After the user chooses a file, use the FileName property to get the name of the selected file.
With all the common dialog boxes, when the CancelError property is True, an error is generated when the
user clicks the dialog box's Cancel button. You detect that the Cancel button was pressed by trapping the
The following code displays an Open dialog box and uses the selected file name as an argument to a
CommonDialog1.FilterIndex = 2
CommonDialog1.ShowOpen
OpenFile (CommonDialog1.FileName)
Exit Sub
ErrHandler:
267
Exit Sub
End Sub
The Color dialog box allows the user to select a color from a palette or to create and select a custom color.
At run time, when the user chooses a color and closes the dialog box, you use the Color property to get
1. Set the Flags property for the common dialog control to the Visual Basic constant cdlCCRGBInit.
Use the Color property to get the RGB value of the color the user selects. The following code displays the
Color dialog box when a user clicks the Command1 command button:
CommonDialog1.CancelError = True
CommonDialog1.Flags = cdlCCRGBInit
CommonDialog1.ShowColor
' color.
Form1.BackColor = CommonDialog1.Color
Exit Sub
ErrHandler:
Exit Sub
End Sub
For More Information See "CommonDialog Control Constants" for a complete list of Flag property
constants.
The Font dialog box allows the user to select a font by its size, color, and style. Once the user makes
selections in the Font dialog box, the following properties contain information about the user's selection.
Property Determines
1. Set the Flags property to one of the following Visual Basic constant values:
Caution You must set the Flags property to one of these values before displaying the Font
The following code sets the font properties for a text box based on a user's selections in the Font dialog
box:
CommonDialog1.CancelError = True
CommonDialog1.ShowFont
' selections.
Text1.Font.Name = CommonDialog1.FontName
Text1.Font.Size = CommonDialog1.FontSize
Text1.Font.Bold = CommonDialog1.FontBold
Text1.Font.Italic = CommonDialog1.FontItalic
Text1.Font.Underline = CommonDialog1.FontUnderline
Text1.FontStrikethru = CommonDialog1.FontStrikethru
Text1.ForeColor = CommonDialog1.Color
Exit Sub
ErrHandler:
Exit Sub
End Sub
For More Information See "CommonDialog Control Constants" for a complete list of Flag property
constants.
The Print dialog box allows the user to specify how output should be printed. The user can specify a range
of pages to be printed, a print quality, a number of copies, and so on. This dialog box also displays
271
information about the currently installed printer and allows the user to configure or reinstall a new default
printer.
Note This dialog box does not actually send data to a printer. It allows users to specify how they want
data printed. You must write code to print the data in the format they select.
For More Information See "Working with Text and Graphics" for information on printing data.
At run time, when the user makes selections in the Print dialog box, the following properties contain
Property Determines
1. Set any desired default settings for the dialog by setting the appropriate Print dialog properties.
272
For example, to display 2 in the Copies box when the dialog is displayed, set the Copies property to
2:
CommonDialog1.Copies = 2
The following code displays the Print dialog box when the user clicks the Command1 command button:
CommonDialog1.CancelError = True
CommonDialog1.ShowPrinter
BeginPage = CommonDialog1.FromPage
EndPage = CommonDialog1.ToPage
NumCopies = CommonDialog1.Copies
Orientation = CommonDialog1.Orientation
For i = 1 to NumCopies
Next
Exit Sub
ErrHandler:
Exit Sub
End Sub
273
Note If the PrinterDefault property is set to True, you can print to the Visual Basic Printer object. In
addition, when the PrinterDefault property is True, any changes the user makes in the Setup portion of the
Print dialog box are used to change the printer settings in the user's Printer setup.
The ShowHelp method of the common dialog control allows you to display a Help file.
The following code displays the specified Help file when the user clicks the Command1 command button:
CommonDialog1.CancelError = True
CommonDialog1.HelpCommand = cdlHelpForceFile
CommonDialog1.HelpFile = "c:\Windows\Cardfile.hlp"
CommonDialog1.ShowHelp
Exit Sub
ErrHandler:
Exit Sub
End Sub
274
For More Information See "HelpCommand Property," "HelpFile Property," and "ShowHelp Method" for
more information on displaying Help files with the common dialog control.
The intrinsic Data control implements data access by using the Microsoft Jet Database engine –the same
database engine that powers Microsoft Access. This technology gives you seamless access to many
standard database formats and allows you to create data-aware applications without writing any code. The
intrinsic Data control is best suited to smaller (desktop) databases, such as Access and ISAM databases.
You can use the intrinsic Data control to create applications that display, edit, and update information from
many types of existing databases, including Microsoft Access, Btrieve, dBASE, Microsoft FoxPro, and
Paradox. You can also use it to access Microsoft Excel, Lotus 1-2-3, and standard ASCII text files as if they
were true databases. In addition, the data control allows you to access and manipulate remote Open
Database Connectivity (ODBC) databases such as Microsoft SQL Server and Oracle.
Note Both the Data control and Remote Data control are included with Visual Basic for backward
compatibility. However, because of the flexibility of ActiveX Data Objects (ADO), it's recommended that
you create new database applications using the ADO Data control. For more details, see "Using the ADO
Data Control."
The Data control, Remote Data control, and the ADO Data control are all conceptually similar: all three are
"data controls" that connect a data source to a data-bound control. All three also share the same
appearance — a set of four buttons that allow the user to go immediately to the beginning of the
recordset, end of the recordset, and scroll backwards and forwards through the recordset.
1. Draw a Data control on the form. The Data control is an intrinsic control and is always available.
2. Click the Data control to select it, and press F4 the display the Properties window.
3. In the Properties window, set the Connect property to the type of database you want to use.
4. In the Properties window, set the DatabaseName property to the file or directory name of the
database you want to connect to.
5. On the Properties window, set the RecordSource property to the name of the database table you
want to access.
275
7. Click the TextBox control to select it, and on the Properties window set the DataSource property
to the Data control.
8. On the Properties window, set the DataField property to the name of the field in the database you
want to view or modify.
9. Repeat steps 6, 7, and 8 for each additional field you want to access.
The following data-related properties can be set at design time. The list suggests a logical order for setting
the properties:
Note Database technology is a complex science, and the suggestions below are not meant to be taken
as rules.
2. DefaultType — The DefaultType property specifies whether JET or ODBCDirect workspaces are used.
3. DefaultCursorType — The DefaultCursorType property determines the location of the cursor. You
can allow the ODBC driver to determine the cursor location, or specify server or ODBC cursors. The
DefaultCursorType property is valid only when using ODBCDirect workspaces.
5. Options — The property determines the characteristics of the recordset. For example, in a multi-user
environment, you can set the Options property to deny changes made by others.
6. BOFAction, EOFAction — These two properties determine what will happen when the control is at
the beginning and end of the cursor. Choices include staying at the beginning or end, moving to the
first or last record, or adding a new record (at the end only).
At design time, trying to bind the Data control to a Microsoft Access 2000 database will result in an error:
"Unrecognized database format." The Data control can still be used, however, by following the example
below:
1. On the Project menu, click References. Clear the Microsoft DAO 3.51 Object Library check box.
276
4. On the Properties window, set the TextBox control's DataSource property to the Data control.
5. Type the name of the field CompanyName into the DataField property box.
7. Option Explicit
9. Private rs As Recordset
11.
13. sPath = _
The DataCombo and DataList controls strongly resemble the standard list box and combo box controls, but
there are some important differences that give them great flexibility and usefulness in database
applications. Both controls can be automatically filled from a database field from the data control to which
they are bound. In addition, they can optionally pass a selected field to a second data control, making
Possible Uses
• In a relational database, use the data from one table to supply values to be input into a second
(related) table. For example, in an inventory database, the names of suppliers are stored in one table
277
with each supplier having a unique ID. Another table showing products uses the unique ID to
designate which company supplies the product. Use the DataList control to show the name of the
supplier while (invisibly) supplying the ID of the supplier to the products table.
• Allow the user to narrow a search by selecting a criteria from a drop-down list. For example, a sales-
reporting database application might use a DataList control to let the user pick a State or Sales
Region. Once that selection is made, the choice is automatically passed to a second data control that
Like their built-in counterparts, the main difference between the DataList and the DataCombo controls is
that the DataCombo box control provides a text box into whose contents may be edited.
For More Information For an explanation of the DataList and DataCombo controls' ability to link
database tables, see "Linking Two Tables using the DataCombo and DataList Controls." To build a simple
Property Description
BoundText Contains the value of the field named in the BoundColumn property.
MatchEntry Enables extended search mode for locating items in a list generated
by the DataCombo control.
Note The DataFormat property of the DataCombo control is an Extender property. Therefore it's always
visible on the property sheet and can be set in code. However the DataCombo control only formats the top
item in its list. This can be disconcerting to the end user who sees a formatted top item, but is only given
a list of unformatted items to select from. The formatted item may also mislead end users who assume
the item will be entered in the database as formatted. For these reasons, it's advisable to not set the
For More Information To try a step-by-step tutorial that demonstrates the use of the BoundText
property, see "Creating a DataGrid Linked to a DataList Control." For a complete list of properties and
The distinguishing characteristic of the DataCombo and DataList controls is the ability to access two
different tables and link data from the first table to a field in the second. This is accomplished by using
two data sources (such as the ADO Data control or the Data Environment).
In a relational database, information that is used repeatedly is not stored in its entirety in multiple places.
Instead the bulk of the information is stored in a recordset comprised of many fields; among these fields
is an ID field that uniquely identifies the recordset. For example, the Biblio database supplied with Visual
Basic stores the names of several publishing companies in a table named "Publishers." The table contains
many fields, such as address, city, zip code, and phone number. But for the sake of simplicity, consider the
Name and PubID fields as the two essential fields in the table. The Name field stores the name of a
publisher, while the PubID field stores a comparatively "unfriendly" value such as a number or code. But
this unfriendly value is more important because it uniquely identifies the publisher, and serves as a link to
the entire recordset. And it's that value that is stored in multiple recordsets in a second table.
The second table is named "Titles," and each recordset contains information such as Title, year of
publication, and ISBN. Included among the fields is one named "PubID." This field is named exactly the
same as the corresponding field in the Publishers table because it stores the value that links the title to a
specific publisher.
This efficient scheme presents a small problem: Given a database application that allows users to insert
new titles, the user must somehow input integers that identify the publisher. This is fine if the user has
memorized each publisher's unique ID, but it would be easier for people to see the name of the publisher
instead, and have the application store the associated value in the database. The DataList and DataCombo
The DataList and DataCombo controls use two sources to surmount the problem. While displaying only the
name of the publisher (from the Publishers table), the DataList or DataCombo control writes only the
value of the PubID field to the Titles table. Through the Properties window, set the RowSource to the data
source that will supply the data to be written (the Publishers table). Then set the DataSource property to
the data source that will be written to (the Titles table). Finally, set the DataField, ListField, and
279