With the template fully customized, I can start generating the code for the properties I want to add to the class. For now, I'm going to assume that I've retrieved a single connection string name from the application's configuration file and put the connection string's name in the variable PropertyName. I'm also going to assume that the single line of code that the property requires is in the variable PropertyReturnCode. In the next section, "Reading Input," I look both at retrieving the information from the configuration file and handling multiple connection strings. The code for this example is sufficiently simple that using the CodeDom to generate the code is overkill. In the next chapter, I look at a case study where the code is sufficiently complex to justify the CodeDom.
The following code adds a property using whatever name is in the variable PropertyName (I omit the name for the property's setter in order to create a read-only property):
CodeProperty cp; cp = cc.AddProperty(PropertyName, null, vsCMTypeRef.vsCMTypeRefString, -1, vsCMAccess.vsCMAccessPublic,null);
The design for the ConnectionManager requires the method to be static/shared. In theory, to make that change all I need to do is set the IsShared property on the CodeProperty2 object that represents my newly added property. Unfortunately, in some versions of Visual Studio, the AddProperty method returns a CodeProperty object that doesn't support the IsShared method and can't be cast to a CodeProperty2 object.
The solution is to use the CodeProperty object's Getter property to retrieve the CodeFunction object for the new property's getter, and because CodeFunctions do have an IsShared property, I can use that to make the property static/shared:
cp2.Getter.IsShared = true;
Now that the property has been added, I insert the code for the property using the CodeEditor object. The first step is to retrieve the StartPoint for the body of the property's Getter and, from it, create an EditPoint. Once the EditPoint is created, my next step is to delete any default code inserted into the property by the AddProperty method (in C#, for instance, the AddProperty method inserts a line of code that throws an exception):
EditPoint epGetter = cp.Getter.GetStartPoint( vsCMPart.vsCMPartBody).CreateEditPoint(); epGetter.Delete(cp.Getter.GetEndPoint(vsCMPart.vsCMPartBody));
After clearing any default code, the final step is to insert any new code: