object customOut, ref bool cancel)
{
TextWindow codeWindow = Connect.ApplicationObject.ActiveWindow.Object
as EnvDTE.TextWindow;
if (codeWindow != null)
{
rtbNotes.SelectedText = codeWindow.Selection.Text +
Environment.NewLine + Environment.NewLine;
}
}
Finally, you need to clean things up when the add-in is unloaded and release any event handlers
you have active (the CloseToolWindow method will be called from the Connect class in the
OnDisconnection method):
Vb
private void DisableAutoCopy()
{
if (cutEvent != null)
1022 .
chaPter 51 Add-inS
Marshal.ReleaseComObject(cutEvent);
if (copyEvent != null)
Marshal.ReleaseComObject(copyEvent);
cutEvent = null;
copyEvent = null;
}
public void CloseToolWindow()
{
DisableAutoCopy();
}
c#
private void DisableAutoCopy()
{
if (cutEvent != null)
Marshal.ReleaseComObject(cutEvent);
if (copyEvent != null)
Marshal.ReleaseComObject(copyEvent);
cutEvent = null;
copyEvent = null;
}
public void CloseToolWindow()
{
DisableAutoCopy();
}
dePloyinG add-ins
Despite being a COM component (which typically require registration in Windows), Visual Studio
add-ins are very easy to deploy thanks to the .AddIn file, which enables Visual Studio to discover
your add-in and use it.
As discussed earlier in the chapter, Visual Studio will look in each of the paths listed in the Options
dialog (see Figure 51-12) for files with an .AddIn extension. Therefore, when deploying your add-
in, you will need to place the .AddIn file and the add-in assembly (that is, the .dll file) into one of
these paths (typically a user profile’s My Documents\Visual Studio 2010\Addins folder), enabling
Visual Studio to discover and load your add-in when it starts up.
You can use a simple XCOPY operation to deploy your add-in to another user’s machine, but the
best way would be to create a setup program to do this for you. You could use a standard Windows
installer package (.msi), but in this instance it’s probably better to use a Visual Studio Content
Installer package. Unfortunately, it’s a manual process to create a Visual Studio Content Installer
package, but they’re very easy to create. They essentially consist of your files packed into a zip file,
summary .
1023
but with a .vsi extension, and a specially formatted XML file (also included in the zip file) with
a .vscontent extension that contains the details of the files to be installed (from the zip file) and
where they are to be installed to.
Start by creating an XML file in your project with the name MyNotesTool.vscontent, and add the
following content:
<VSContent xmlns="http://schemas.microsoft.com/developer/vscontent/2005">
<Content>
<FileName>MyNotesTool.Addin</FileName>
<FileName>MyNotesTool.dll</FileName>
<DisplayName>My Notes</DisplayName>
<Description>
Enables you to keep notes in a tool window in
Visual Studio while you code.
</Description>
<FileContentType>Addin</FileContentType>
<ContentVersion>2.0</ContentVersion>
</Content>
</VSContent>
Now, in Windows Explorer (or your favorite zip tool), combine the MyNotesTool.AddIn file, the
MyNotesTool.dll file, and the MyNotesTool.vscontent file into a zip file, and name it
MyNotesTool.vsi (do not include the .zip extension). Now when someone double-clicks this
.vsi file, the add-in will automatically be installed and ready for them to use when they next open
Visual Studio.
suMMary
In this chapter, you were introduced to Visual Studio add-ins, and went through the process of
creating one that displayed a dockable tool window, retrieved text from the code editor, and
responded to some code editor events. Finally, you looked at the best way to deploy your add-in to
other developers.
52
Macros
what’s in this chaPter?
.
Understanding macros
.
Creating macros
.
Testing and debugging macros
.
Deploying macros
Like add-ins, macros are another common extensibility option built into Visual Studio. As
discussed in Chapter 50, macros have many benefits over add-ins (quick to create, and Visual
Studio actions can be recorded to a macro), but also many downsides (they must be written in
VB, can’t be compiled, and have limited abilities). It’s a tradeoff as to which means you use to
automate Visual Studio based upon your requirements. If you perform the same set of actions
repetitively in Visual Studio, macros are a great way to reduce these down to a single action.
This chapter takes you through the process of recording a macro and running it again,
creating macros from scratch, and deploying macros to other developers once you’ve
created them.
understandinG Macros
A Visual Studio macro (it’s actually called VSMacro but is commonly known just as a macro
among developers) is code that can be run by the Visual Studio IDE to automate a task. The
code is not compiled, but is interpreted — it’s essentially a scripting language for Visual
Studio. A macro is implemented as a public method in a module that takes no parameters and
does not return a value. Like add-ins, macros use the Development Tools Extensibility (DTE)
API to automate the Visual Studio IDE. Macros can’t display any user interface elements in
1026 .
chaPter 52 mAcroS
Visual Studio (such as a tool window) — if you need this sort of functionality, you should consider
creating an add-in instead.
Macros exist in code modules, and these code modules are contained in macro projects. Macro
project files have a .vsmacros extension, and are much like a standard Visual Studio project file (in
concept); however, the various modules and associated files in the project are embedded into this
project file (rather than existing in their own individual files). In addition, a code module can contain
one or more macros, so you can include multiple macros in a module.
If you are a VB developer, you will have no problem coding macros, because VB is the native
language used by macros. Unfortunately, C# is not supported as a macro language, and therefore C#
developers will need to learn VB or create add-ins instead.
the Macro exPlorer tool window
Before you look at the tools for creating macros, take a look at
the Macro Explorer tool window that can help you manage and
run the macros available to you. If the tool window is not visible,
select the View . Other Windows . Macro Explorer menu item to
display it in the IDE.
As you can see from Figure 52-1, there is a top-level Macros node
under which macro projects live. Each macro within that project is
listed as well.
This dialog is very useful in enabling you to select and run a macro
(simply double-click the macro to run it), and edit a macro (rightclick
the macro and select Edit from the context menu). When you select to edit a macro, its code
will be opened in the Macros IDE, which is discussed in the next section of this chapter.
You’ll notice that two projects are already displayed in the Macro Explorer: MyMacros and
Samples. MyMacros is the default project in which to create your macros (although you can create
additional macro projects as required). The Samples macro project consists of example macros that
you can use to help you learn how to write macros and work with the Visual Studio automation
model.
the Macros ide
As you can see in Figure 52-2, the Visual Studio Macros IDE is quite similar to the Visual Studio
IDE, despite being a completely separate program. It being a somewhat familiar user interface
should help you navigate your way around the IDE.
fiGure 52-1
Creating a Macro .
1027
fiGure 52-2
Of particular note is the Project Explorer tool window (akin to the Solution Explorer tool window
in the Visual Studio IDE, on the right side of the screen). This window enables you to navigate the
various macro projects and the modules/files they contain. You’ll note that as opposed to the Macro
Explorer in the main Visual Studio IDE, which displays the available macros under each macro
project, this window displays the modules and files within each macro project. The Macro Explorer
hides the modules from you, and just collates all the macro functions across all the modules to be
displayed under the macro project. When you open a module, it’s just the same as opening a code
file in Visual Studio.
The Visual Studio Macros IDE can’t run as a standalone program and can only
be loaded via Visual Studio.
creatinG a Macro
You have two ways of creating a macro: one is to start from scratch and write the code yourself, and
the other is to record a set of actions in Visual Studio using the macro recorder for later playback.
This section looks at both methods, starting with recording macros because that’s the easiest way to
get started creating macros.
1028 .
chaPter 52 mAcroS
how to record a Macro
If you simply want to automate a predefined set of actions in Visual Studio, the easiest way to
create a macro to perform those actions is to use the macro recorder to record you performing those
actions, and then play it back when required. The macro recorder will take all the actions you do in
the Visual Studio IDE while it’s recording and document them in code form. If necessary, you can
then tweak the code that the macro recorder generated to work exactly the way you want. This can
save you having to learn the Visual Studio automation model and manually write code against it. It’s
also a great way of learning how to create macros.
To record a macro, select Tools . Macros . Record Temporary Macro (or press
Ctrl1Shift1R). This immediately starts the recorder, which will be recording
fiGure 52-3
everything you now do in the Visual Studio IDE. A toolbar (shown in Figure 52-3) is
displayed, enabling you to pause, stop, cancel, or continue recording the macro.
After performing the actions that you want to record, click the stop button in the macro recorder
toolbar (or press Ctrl1Shift1R again). Now, if you look in the
Macro Explorer you will see that a module has been created in the
MyMacros project (by default) called RecordingModule, and that
a macro called TemporaryMacro has been created (as shown
in Figure 52-4).
You should now rename the macro by right-clicking it, selecting
Rename from the context menu (or simply selecting it and pressing
F2), and entering a new name in the textbox for it so it isn’t
overwritten the next time you try to record a macro. You can now
run the macro by double-clicking its name and testing it.
fiGure 52-4
You can change the project that the macro is recorded to by right-clicking the
project in the Macro Explorer and selecting the Set as Recording Project menu
item. However, the module that the macro is recorded to cannot be set, and will
always go into RecordingModule.
Although the macro recorder can help a lot in creating a macro, it won’t capture every action you
perform in Visual Studio, and more than likely won’t be able to capture everything (such as all the
logic) that you want it to do. That’s when you will have to turn to modifying the code it outputs to
add the appropriate additional logic that you require.
how to develop a Macro
When you create a macro, you can choose to create a new macro project (useful if you want to
distribute this macro to other developers), or use an existing one. If you want to create a new macro
project, you will no doubt be surprised to find no option to create one within the Macros IDE.
Creating a Macro .
1029
Instead, you will have to do it back in the Visual Studio IDE from either the Macro Explorer by
right-clicking the root Macros node and selecting New Macro Project from the context menu, or
using the Tools . Macros . New Macro Project menu item. This will show a dialog enabling you
to give the project a name, and then the project will be created along with a default module called
Module1 (which you will ideally rename to something more meaningful). Otherwise, you can simply
use one of the existing macro projects (with the MyMacros project probably being the best choice).
Then you can start adding public functions to the code module — with each becoming a macro.
Two good ways exist to get up to speed with writing macros. The first is to look
at the samples (all the macros in the Samples macro project) and how they work.
Try to find one that does something similar to what you need to do and work
from that. Another good way to get started is to just use the macro recorder to
record various actions when working with Visual Studio, and then examine the
code that it generates. You can then take pieces of this code and use it in the
macro you are working on.
You can add additional modules as required by right-clicking the macro project and selecting Add
. Add New Item from the context menu. You can also import existing code modules (such as a
pre-existing code module from a standard VB project) into your macro project by right-clicking the
macro project and selecting Add . Add Existing Item from the context menu, then selecting
the module that you want to import from the dialog that is displayed. Of course, you could also
reference a .NET assembly (written in any .NET language) containing functions that you want to
use in your macro by right-clicking the References node under the macro project, selecting Add
Reference from the context menu, and then selecting the assembly in the dialog that’s displayed.
However, if you find yourself doing this and you think that you might deploy this macro to other
developers, it is probably better to create an add-in instead of a macro.
Let’s work through an example of creating a very simple macro that inserts some text at the
current cursor position in the code editor to state that the code below was modified (consisting of
// Modified by [Name] at [DateTime], with appropriate values replacing the square bracket