Valor Whisler
Applications Architect
June 10, 1997
Valor Whisler is an applications architect specializing in high quality UI and applications development using Visual Basic. Valor designed and developed the first commercial add-in for Visual Basic: VB AppFramework.
Click to open or copy the the source code for Expert Agent.
This document introduces add-ins and then develops the idea of an expert agent add-in. This expert agent is a vision of a set of comprehensive development services that take development with Microsoft® Visual Basic® to a new level. I hope that readers will agree and bring the agent to life.
This document provides a limited discussion of building an add-in; for more details, examine the Visual Basic sample add-in projects, projects generated using the add-in template (seen when creating a new project), or add-in projects created with the Wizard Manager.
Imagine that you could extend Visual Basic to provide new functionality and that you could customize the development environment so that it would be tailored to your particular needs. Imagine intelligent assistants that can make coding suggestions, help assure standardized code, or generally clean up your code. Imagine wizards that can automate those tedious tasks and provide "macro-like" functions to generate code and user interfaces. Now stop imagining this—all of these capabilities are here today with the Visual Basic 5.0 extensibility model and add-in interface.
Anything that you can do from the keyboard, you can do from an add-in. But even more important than the automation of repetitive tasks is the ability to embellish add-ins with high-level business, architectural, or procedural logic. An add-in can be used as a "wrapper" that provides the experience and expertise of key engineers to all developers—every minute of every day. We have all heard about artificial intelligence and we have also heard how distant a dream it really is. It is, however, possible today to provide intelligence assistance, and that's what the expert agent is all about.
Add-ins can be created with Visual Basic. In fact, the wizards that ship with Visual Basic are themselves add-ins created in Visual Basic. These wizards have been included to help automate several different kinds of programming tasks. To get a quick look at what an add-in can do, load the Visual Basic Wizard Manager add-in that comes with the product. This add-in assists in the development of new add-ins that use a wizard-style interface.
This is the second release of the Visual Basic extensibility model. The first release provided a solid base to work with. This release is a substantial upgrade from the original, providing many new features and more functionality, as well as a greatly enhanced object model. One of the most beneficial enhancements, the ability to manipulate code, is now available. There are features that allow you to extend your add-in interface directly into the Visual Basic IDE (Integrated Development Environment) so that it can be docked and linked like the Project Explorer, Properties window, and Toolbox. Other features leverage the new capability to have multiple projects open within the same instance of Visual Basic. Finally, there are less obvious features that address the needs of power users, such as the ability to iterate through all contained objects.
This section provides a brief discussion of how to create a simple add-in. The easiest way to create an add-in is to use the Visual Basic Addin template. To do this, from the File menu click New Project. When the New Project dialog box appears, select the Addin icon and proceed. Visual Basic will add three components:
Connecting an add-in to Visual Basic in version 5.0 is completely different than in version 4.0. In version 4.0, a developer had to write the connect and disconnect procedures from scratch. Using a new capability in version 5, a developer merely has to implement the IDTExtensibility add-in interface that is contained in the VBIDE (Visual Basic Integrated Development Environment) object. Once this interface is implemented, four methods are available in the class module that implements the interface. These methods are all that is needed to connect, disconnect, and manage the connection between Visual Basic and your add-in.
Note For more information on implementing another object's interface, see the Implements keyword in Visual Basic.
Once connected, most of the work the add-in will do will utilize the VBInst object that is passed into the add-in by Visual Basic within the OnConnection method. This object represents the root of a set of objects that allow you to query, manipulate, and receive session events regarding the Visual Basic IDE. This includes such things as adding components or controls and setting properties, or, in the case of the expert agent, reviewing and modifying code. A summarized version of the VBInstance object is shown below:
Figure 1. Summarized VBInstance object diagram
The objects on the left of the diagram (Events, Addins, CommandBars, Windows, and CodePanes) all function with reference to the VBIDE itself. The objects on the right of the diagram, starting with the VBProjects collection, all relate to manipulating Visual Basic projects. The Designer and VBForm objects are depicted with a wavy border to indicate that many possible types of designers belong here, one of which is the VBForm designer.
This section develops the idea of an expert agent. This is a mythical product that has yet to be produced, but which is possible, given the Visual Basic 5.0 extensibility model. Perhaps a reader of this paper will undertake the task of actually producing such an agent. All of the services provided by the agent pertain to core code, not interface. The expert agent will provide the following six services:
Figure 2. Six services provided by the expert agent
This section provides a discussion and code segments that illustrate how such an agent can be implemented. In addition, two working sample projects are provided: an agent add-in and an agent test project.
The agent will primarily use three kinds of objects supplied by the VBIDE: CodePanes, CodeModules, and Members. The CodePane object represents a visible code window. A given component can have several CodePane objects. The CodeModule object represents the code within a component. A component can only have one CodeModule object. A member of a code module is an identifier that has module-level scope and can be considered a property, method, or event of that code module. Using these objects it is possible to view and manipulate every line of code in a Visual Basic project.
Figure 3. Getting at Visual Basic code
A special code pane, the ActiveCodePane, represents the code window that has the focus in a project. The following code example gets a handle to the ActiveCodePane and its CodeModule objects when the expert agent form is activated. It sets the CodeModule to a modular-level variable: ThisCodeModule. This variable is then used in a later procedure to get all of the members for the module.
'<Private>---------------------------------------------
Private ThisCodeModule As VBIDE.CodeModule
'</Private>--------------------------------------------
Option Explicit
Private Sub Form_Activate()
Dim ThisCodePane As VBIDE.CodePane
On Error GoTo InvalidObject
'---- destroy previous CodeModule object
Set ThisCodeModule = Nothing
'---- get the active pane and its module
Set ThisCodePane = VBInstance.ActiveCodePane
Set ThisCodeModule = ThisCodePane.CodeModule
Cleanup:
Set ThisCodePane = Nothing
End Sub
The CodeModule object contains a Members collection that represents the actual code. There are seven types of member objects:
Type | Description |
vbext_mt_Method | Represents a method (procedure, or proc) |
vbext_mt_Property | Represents a property procedure |
vbext_mt_Variable | Represents a modular level variable |
vbext_mt_Event | Represents an event |
vbext_mt_Enum | Represents an enumerated value |
vbext_mt_Const | Represents a modular level constant |
vbext_mt_EventSink | Represents an event sink |
The Member object contains several properties—some of which define the starting location and number of lines of code belonging to the particular Member. This information is then supplied to the Lines method of a CodeModule object to retrieve the actual code. The following code example retrieves a line of code from ThisCodeModule, the variable that was set in the previous code example.
'-------------------------------------------------------
'<Purpose> retrieves lines of code
'-------------------------------------------------------
Private Function RetrieveCode(StartLine As Long, EndLine As Long) As String
RetrieveCode = ThisCodeModule.Lines(StartLine, EndLine)
End Function
Once the agent has access to all of the code, it can begin its analysis. Each service contains a set of rules that are used to analyze the code. These rules will provide ways to recognize patterns within the code and then to recommend alternative approaches. Experts in various programming domains will create the rules themselves. For instance, a set of database rules may be devised by a database expert and a set of object rules devised by an OOP expert. An important part of the expert agent system will be a facility to edit, store, and retrieve the rules.
A sample set of projects is provided to further illustrate the expert agent concept. The ExpertAgent.vbp project contains the add-in code and a simple example of how the agent can look for repeated references in code. The TextXAgent.vbp project contains some code that can be used to test the scanning of code for such references. The AgentIni.vbp project and .exe can be used to configure the expert agent as a Visual Basic add-in.
To use the projects:
Note If you wish to explore the add-in code, place breakpoints in the ExpertAgent Project.
The expert agent sample product has the ability to analyze every line of code in a Visual Basic project. Its ability to recognize and correct problems is entirely simplistic but does provide a framework to expand upon.
The extensibility model in Visual Basic 5.0 now provides a way to review and modify all of the code within a Visual Basic project. It is possible to build clever tools that analyze a code base and look for patterns. Domain experts could establish what patterns such a tool would look for and how they might be recognized. The domain experts could then recommend alternative patterns of code that might provide a more efficient or more standardized application of logic. The expert agent projects provide a simple proof-of-concept for such a system.