Although Microsoft Outlook uses the same CommandBars that other Microsoft Office applications use, CommandBars are implemented in a different manner in Outlook. This article describes the differences in CommandBar implementation, so that developers can better understand how to work with CommandBars when they design an Outlook solution.
In Office, each Office application's menus and toolbars are represented by a CommandBars object model. CommandBars are a shared Office component, and the object model is provided in the Microsoft Office 10.0Object Library. The CommandBars object model is not contained in the Outlook object model; instead, the Outlook object "tunnels" into the Microsoft Office 10.0 Object Library for this functionality.
Outlook CommandBar Architecture
Other Office applications support one set of CommandBars, but Outlook supports two: one set at the main application window, and a second set in each individual item.
From a developer's point of view, the main window in Outlook (theapplication window) is referred to as an "explorer."IMPORTANT
: These windows can also be considered folder-level windows because you can right-click any folder, and then click Open in New Window
to open different windows to work with different folders.
In addition to these explorer windows, each Outlook item has a form window that is referred to as an "inspector." These inspector windows also have a set of CommandBars because items have menus and toolbars.
Use the different objects as follows:
- Use the Explorer objects (ActiveExplorer/GetExplorer) to refer to the main application window in Outlook.
- Use the Inspector objects (ActiveInspector/GetInspector) to refer to an Outlook item's window.
| To refer to the | To refer to a folder Window type | "active" window | or item's window --------------------------------------------------------------------------------- Application | Use the ActiveExplorer method. | Use the GetExplorer method. | | Item or Form | Use the ActiveInspector method. | Use the GetInspector method.
Considerations When You Use Microsoft Word as the E-Mail Editor
When you are designing an Outlook CommandBar solution for mail items, it is important that you understand that different CommandBars are used when Microsoft Word is set as the e-mail editor. Some key points that you must consider when you use Word as the e-mail editor are:
- CommandBars are part of Word, not Outlook.
- Different CommandBars are available based on the message editor and format.
- Custom buttons may disappear when you change message editor or format.
- The special Envelope CommandBar is not designed to be customized.
- There is no Inspector object for the HTML and Plain Text formats with Office 2000 if Word is set as the e-mail editor.
The available CommandBars may change based on the different editors (Outlook versus Word) and different message formats (Rich Text Format, HTML, and Plain Text); therefore, it is important that you test your solution thoroughly in each configuration. Because different CommandBars are available in different configurations, it is common for a button that you add in one configuration to no longer be displayed after you change to another configuration. With Word set as the e-mail editor, the Word application provides the item-level (inspector) CommandBars. Although some of these Word CommandBars are accessible through the Inspector object if you use Microsoft Office 2002, this is not the case in Microsoft Office 2000. In Office 2000, the HTML and Plain Text messages do not have Inspector objects if you use Word as the e-mail editor; therefore, you need to access the CommandBars by using the Word object model. The storage location for CommandBar customizations also changes based on which application provides the CommandBars. Customizations that you make to the standard Outlook CommandBars are stored in the Outcmd.dat file. Customizations that you make to the Word CommandBars are stored in the Word Normal.dot global template.
Word also provides two different sets of CommandBar technologies based on the format of the e-mail message. In Office 2002, all of the message formats use the specialized Envelope
CommandBar by default, but in Office 2000, only HTML and Plain Text messages use the Envelope
CommandBar. The Envelope
CommandBar contains features that are specific to e-mail, such as the Send
button and message fields (To
, and Subject
). The Envelope
CommandBar is not displayed in the Word Toolbars list and is not designed to be customized. Therefore, you must make any modifications to other CommandBars. Office 2000 handles Rich Text Format messages differently and uses the Outlook Send Mail
and Outlook Read Mail
CommandBars for composing and reading messages. Although Office 2002 message formats do not use the Outlook Send Mail
and Outlook Read Mail
CommandBars by default, you can design a custom Outlook form that uses these CommandBars. To configure the form so that it uses Word as the e-mail editor, in form design mode, click the Properties
tab of the form, and then click to select Always use Microsoft Word as the e-mail editor
A History of Outlook Support for Customizable Menus and Toolbars
CommandBars were originally designed for document-centric applications, such as Word and Microsoft Excel, which support a single set of application-level CommandBars. The other applications fully support all of the features of the CommandBars design, and in Microsoft Office 97 and later, the other applications fully support many aspects of customizing CommandBars. However, Outlook has continued to support CommandBars is various ways:
- In Microsoft Outlook 97, you cannot customize toolbars and menus by using the Outlook user interface. Outlook 97 is not designed to store changes to CommandBars. Although the CommandBars object model is exposed in the Outlook object model, you cannot use the CommandBars object model to modify the menus or toolbars because they are in a "read-only" state. However, you can use the Execute method to programmatically run a built-in Outlook command. The only way to create additional toolbar buttons or menu commands in Outlook 97 is to create a Microsoft Exchange Client Extension in C or C++.
- In Microsoft Outlook 98, Microsoft recommends that you do not programmatically make changes to the CommandBars object model. Toolbars and menus are customizable in the Outlook user interface. Customizations are stored in a file called Outcmd.dat. However, although the CommandBars object model is exposed in the Outlook object model, and you can programmatically add new toolbar buttons and menu commands, this feature was not designed or tested to actually work. As a result, you may experience issues if you use the CommandBars object model in Outlook 98. Outlook 98 does not support Microsoft Visual Basic for Applications (VBA), or application-level code. Therefore, if you programmatically add a custom command to an application-level window, or explorer, there is no way to attach custom code to the button. If you programmatically add a custom command to an item-level window, or inspector, you can have the button run custom Microsoft Visual Basic Scripting Edition (VBScript) script in the form, but issues will occur that cause the button to be displayed on other types of items, and there may be differences between opening new items and existing items.
- Outlook 2000 is the first version of Outlook that is designed to support programmatically customizable toolbars and menus. This coincides with the addition of support for VBA and Component Object Model (COM) add-ins.
CommandBars and the Outlook Object Model
In the object models of other Office applications, the CommandBars collection is located off the Application object because those applications support only one set of application-level CommandBars. However, the Outlook object model is designed to support the two sets of CommandBars that Outlook supports (Inspector and Explorer).
In the Outlook object model, the CommandBars collection is located off Explorer and Inspector objects, not the Outlook Application object. Many code examples are available that illustrate how to programmatically make changes to CommandBars; however, most of these examples are designed for other Office applications. To use these examples in Outlook, you must modify the code appropriately to reflect the difference in the Outlook object model.
Custom Form Solutions
In a custom form solution that uses VBScript, you typically access the form-level CommandBars by using code that is similar to:
Set objCBs = Item.GetInspector.CommandBars
A VBScript Sample to Run an Outlook Command
You can use the following sample code with a CommandButton control on a contact form to easily create a new letter for a Contact:
Sub CommandButton1_Click() Set MyCB = Item.GetInspector.CommandBars.Item("Menu Bar") Set MyMenu = MyCB.Controls("Actions") Set MyMenuItem = MyMenu.Controls("New Letter to Contact") MyMenuItem.Execute()End Sub
A VBScript Sample That Uses the "FindControl" Method
If you know the internal value that Outlook has assigned for each command, you can use the FindControl
method to reference any Outlook commands (or controls, in relation to the CommandBars object model). If you use the internal ID, you can use more concise syntax when running CommandBar commands, and you can access commands that may not be on the menu or toolbar that is displayed.
For example, consider a custom Outlook form that uses a custom command button to print the form. Assuming that the command button is named cmdPrint, either of the following two VBScript code examples displays the File Print
Sub cmdPrint_Click() Item.GetInspector.CommandBars.FindControl(,4).ExecuteEnd SubSub cmdPrint_Click() Item.GetInspector.CommandBars.Item("Menu Bar").Controls("File") _ .Controls("Print...").ExecuteEnd Sub
For an example of how to generate a list of Outlook CommandBar control IDs, see the Excel example in the "Using an Excel Utility to Generate a List of Outlook CommandBar IDs
" section of this article.
In an application-level solution, such as Outlook VBA or a COM add-in, the typical method to access the application-level CommandBars is to use code that is similar to:
Set objCBs = Application.ActiveExplorer.CommandBars
Visual Basic for Applications
Outlook VBA is designed to be a personal development tool; these types of solutions are not designed to be deployed. Therefore, typically, you would not programmatically customize CommandBars from Outlook VBA. Instead, manually create the custom CommandBar button:
- On the Tools menu, click Customize.
- Click the Commands tab, and then click Macros in the list of categories.
- Drag a macro to the menu or toolbar.
- To modify the appearance of the toolbar or menu command, in the Customize window, click Modify Selection, and then make any modifications to the custom toolbar or menu command.
- Click Close.
A VBA Sample to Add a CommandBar Control
To add a CommandBar control:
back to list of topics
- Create a sample custom Outlook Post form, and then publish it to your Inbox. Name it TestForm.
- On the Tools menu, point to Macro, and then click Visual Basic Editor.
- Under Project - Project1, double-click Project1, double-click Microsoft Outlook Objects, and then double-click ThisOutlookSession.
- In the code window, enter the following code:
Dim WithEvents myControl As CommandBarButtonPrivate Sub Application_Startup() Dim oExp As Outlook.Explorer Dim oBar As Office.CommandBar Set oExp = Outlook.ActiveExplorer Set oBar = oExp.CommandBars.Item("Standard") ' See if button already exists based on Tag value Set myControl = oBar.FindControl(, , "OpenForm") ' If not found then create button If myControl Is Nothing Then Set myControl = oBar.Controls.Add(, , , 2, True) With myControl .Caption = "Open Form" .FaceId = 59 .Style = msoButtonIconAndCaption .Tag = "OpenForm" .Visible = True End With End IfEnd SubPrivate Sub myControl_Click(ByVal Ctrl As _ Office.CommandBarButton, CancelDefault As Boolean) Dim myFolder As MAPIFolder Set myFolder = Session.GetDefaultFolder(olFolderInbox) Set MyItem = myFolder.Items.Add("IPM.Post.TestForm") MyItem.Display Set MyItem = Nothing Set myFolder = NothingEnd Sub
- Close the Visual Basic Editor.
- Close Outlook. When you are prompted to save changes to the VBA project, click Yes.
- Start Outlook.
A COM Add-In Sample to Add a CommandBar Control
The supported way to distribute application-level code to Outlook users is by creating a COM add-in. The following COM add-in code sample demonstrates how to add a new button to the first position on the Standard Outlook CommandBar (you can also set the OnAction
property of the button to load the COM add-in if it is not already loaded):
Dim OL As Outlook.ApplicationDim WithEvents objButton As Office.CommandBarButtonPrivate Sub AddinInstance_OnConnection(ByVal Application As Object, _ ByVal ConnectMode As AddInDesignerObjects.ext_ConnectMode, _ ByVal AddInInst As Object, custom() As Variant) Dim objBar As Office.CommandBar Set OL = Application Set objBar = OL.ActiveExplorer.CommandBars.Item("Standard") Set objButton = objBar.Controls.Add(, , , 1, True) With objButton .FaceId = 59 .Caption = "My Button" .Style = msoButtonIconAndCaption ' The OnAction property is optional but recommended. ' It should be set to the ProgID of the add-in, such that if ' the add-in is not loaded when a user presses the button, ' Outlook loads the add-in automatically and then raises ' the Click event for the add-in to handle. .OnAction = "!<" & AddInInst.ProgId & ">" End WithEnd SubPrivate Sub objButton_Click(ByVal Ctrl As Office.CommandBarButton, _ CancelDefault As Boolean) MsgBox "Hello World"End Sub
For additional information about available resources for creating COM Add-Ins for Outlook, click the article number below to view the article in the Microsoft Knowledge Base:
OL2000: How to Create a COM Add-in for Outlook
Using a Microsoft Excel Utility to Generate a List of Outlook CommandBar IDs
You can use the following Microsoft Excel VBA sample code to generate a spreadsheet that contains a list of Outlook commands and their corresponding CommandBar control IDs. The code adds an Excel AutoFilter to the spreadsheet so that you can easily find the ID that you are looking for.
To set up this utility:
- Start Excel. Make sure that you are in a new Excel workbook.
- On the Tools menu, point to Macro, and then click Visual Basic Editor.
- In the editor's Project Explorer window, double-click ThisWorkbook to open a code window.
- In the code window, enter the following code:
Option ExplicitDim oOutApp As Outlook.ApplicationDim I As LongDim iRowCount As LongDim oItm As Object ' so it'll handle varying item typesDim oSheet As Excel.WorksheetDim oNS As Outlook.NameSpaceDim oFld As Outlook.MAPIFolderSub GetOutlookCommandBarIDs()If MsgBox("This will clear the current worksheet, OK to continue?", vbOKCancel) = 1 Then Cells.Select Selection.ClearContents iRowCount = 0 Set oSheet = ActiveSheet Set oOutApp = New Outlook.Application Set oNS = oOutApp.Session Set oItm = oOutApp.CreateItem(olMailItem) GetInspectorIDs oItm, "Mail Message" Set oItm = oOutApp.CreateItem(olPostItem) GetInspectorIDs oItm, "Post" Set oItm = oOutApp.CreateItem(olContactItem) GetInspectorIDs oItm, "Contact" Set oItm = oOutApp.CreateItem(olDistributionListItem) GetInspectorIDs oItm, "Distribution List" Set oItm = oOutApp.CreateItem(olAppointmentItem) GetInspectorIDs oItm, "Appointment" Set oItm = oOutApp.CreateItem(olTaskItem) GetInspectorIDs oItm, "Task" Set oItm = oOutApp.CreateItem(olJournalItem) GetInspectorIDs oItm, "Journal Entry" Set oFld = oNS.GetDefaultFolder(olFolderInbox) GetExplorerIDs oFld, "Mail Folder" Set oFld = oNS.GetDefaultFolder(olFolderContacts) GetExplorerIDs oFld, "Contact Folder" Set oFld = oNS.GetDefaultFolder(olFolderCalendar) GetExplorerIDs oFld, "Calendar Folder" Set oFld = oNS.GetDefaultFolder(olFolderTasks) GetExplorerIDs oFld, "Task Folder" Set oFld = oNS.GetDefaultFolder(olFolderJournal) GetExplorerIDs oFld, "Journal Folder" Set oFld = oNS.GetDefaultFolder(olFolderNotes) GetExplorerIDs oFld, "Notes Folder" Selection.AutoFilter Cells.Select Cells.EntireColumn.AutoFit Range("A1").Select MsgBox "The spreadsheet is complete." End IfEnd SubSub GetInspectorIDs(oItm, sType As String) Dim oCBs As Office.CommandBars Dim oCtl As Office.CommandBarControl Set oCBs = oItm.GetInspector.CommandBars For I = 1 To 35000 Set oCtl = oCBs.FindControl(, I) If Not (oCtl Is Nothing) Then iRowCount = iRowCount + 1 oSheet.Cells(iRowCount, 1) = "Inspector" oSheet.Cells(iRowCount, 2) = sType oSheet.Cells(iRowCount, 3) = oCtl.Parent.Name oSheet.Cells(iRowCount, 4) = oCtl.Caption oSheet.Cells(iRowCount, 5) = CStr(I) End If NextEnd SubSub GetExplorerIDs(oFld As Outlook.MAPIFolder, sType As String) Dim oCBs As Office.CommandBars Dim sFilter As String Dim oCtl As Office.CommandBarControl Set oCBs = oFld.GetExplorer.CommandBars For I = 1 To 35000 Set oCtl = oCBs.FindControl(, I) If Not (oCtl Is Nothing) Then iRowCount = iRowCount + 1 oSheet.Cells(iRowCount, 1) = "Explorer" oSheet.Cells(iRowCount, 2) = sType oSheet.Cells(iRowCount, 3) = oCtl.Parent.Name oSheet.Cells(iRowCount, 4) = oCtl.Caption oSheet.Cells(iRowCount, 5) = CStr(I) End If NextEnd Sub
- On the Tools menu, click References. In the list of available object libraries, click Microsoft Outlook 10.0 Object Library, and then click OK.
- Close the Visual Basic Editor.
- Save the Excel workbook so that you have it for future use.
To generate the list of IDs:
- Make sure that the Excel security settings allow the macro to run. On the Tools menu, click Security, and then make sure that your settings are set to Medium or Low, at least temporarily. If you change the settings from High, you must restart Excel.
- Open the workbook that you created when you set up the Excel utility.
- On the Tools menu, point to Macro, and then click Macros. Click the GetOutlookCommandBarIDs macro, and then click Run.
- Wait while the spreadsheet is generated. This will take at least a couple of minutes. After the macro finishes runnning, you receive a message that states, "The spreadsheet is complete."
- After the spreadsheet is generated, save the workbook so that you do not have to run the macro again.
To use the spreadsheet, use the AutoFilter feature at the top to find the CommandBar ID that you are looking for. For example, in cell A1 you can select a command on an Explorer or Inspector object; in cell B1, you can then select the type of item or folder that contains the command.