![]() The list of all Microsoft WinForm tutorials using C# in Urdu are below. You can use Visual Studio 2005/2008/2010/2012/2013/2015 or later with these tutorials. How to get COM Server for Excel written in VB. NET installed and registered in Automation Servers list? ![]()
I took a shot at deploying an automation add- in over the weekend. It turns out that it is enormously complicated (not a surprise to you!) and I could find absolutely no sources on the internet on how to do this properly. None. There are sources that describe how to use Reg. Asm, but none how to correctly use a Setup Project to register an automation add- in, which is a little different from your standard COM add- in. Fortunately, I was able to solve it. Here's what I found out: If you read some of the articles on how to create and register your C# automation add- in, you'll see that you need to add a registry key named Programmable at HKEY\_CLASSES\_ROOT\CLSID\\{GUID}, where {GUID} is the GUID of your COM- visible class. This is generally done by adding a pair of methods marked by the Com. Register. Function. Attribute and the Com. Unregister. Function. Attribute. A good example of this comes from the article Writing Custom Excel Worksheet Functions in C# by Gabhan Berry: // C#. Com. Register. Function. Attribute]. public static void Register. Function(Type type) {. Registry. Classes. Root. Create. Sub. Key(Get. Sub. Key. Name(type)). [Com. Unregister. Function. Attribute]. public static void Unregister. Function(Type type) {. Registry. Classes. Root. Delete. Sub. Key(Get. Sub. Key. Name(type), false). Get. Sub. Key. Name(Type type) {. CLSID\{" + type. GUID. To. String(). To. Upper() + @"}\Programmable". Translated to VB. NET, this works out to: 'VB. NET. < Com. Register. Function. Attribute()> _. Public Shared Sub Register. Function(By. Val type As Type). Registry. Classes. Root. Create. Sub. Key(Get. Sub. Key. Name(type)). < Com. Unregister. Function. Attribute()> _. Public Shared Sub Unregister. Function(By. Val type As Type). Registry. Classes. Root. Delete. Sub. Key(Get. Sub. Key. Name(type), false). Private Shared Function Get. Sub. Key. Name(By. Val type As Type) As String. Dim s As String = ("CLSID\{" _. GUID. To. String. To. Upper + "}\Programmable")). The method marked by the Com. Register. Function. Attribute is automatically called by Reg. Asm when the assembly for this class is registered. The method marked by the Com. Unregister. Function. Attribute is automatically called by Reg. Asm when the assembly for this class is being unregistered via the /u switch. The problem is that the Com. Register. Function. Attribute and Com. Unregister. Function. Attribute are completely ignored when installing via a Visual Studio Setup Project. This seems surprising at first, because the Visual Studio Setup Project runs Reg. Asm using the /regfile switch in order to generate a . REG file containing all of the required registry keys. It is this . REG file that is then utilized then the . MSI package is run at the client site. From Build and Deploy a . NET COM Assembly by Phil Wilson: How does Visual Studio work out the. COM class registration entries? Well. if you have configured the Fusion Log. Viewer (Fuslogvw. NET 2. 0. SDK) to record assembly loading, run. Regasm. exe actually. However, it doesn't perform. What happens is that. Visual Studio runs Regasm with the. So if you want to see what. Visual. Studio will create in the MSI setup. Regasm yourself with the. Upon running Reg. Asm myself using the /regfile switch, however, I noticed that the Programmable switch was not being included. I then put logging within my methods marked by the Com. Register. Function. Attribute and Com. Unregister. Function. Attribute and found that they are both called when running Reg. Asm without the /regfile switch, but are not called when run with the /regfile switch, nor are they called when run via the . MSI package created by the Visual Studio Setup Project. The help files for Regasm. You can use the /regfile option to. You. can update the registry on a computer. Registry Editor tool (Regedit. Note that the . reg file does not contain any registry updates that can. The solution, then, is to add the Programmable key ourselves. This can be done as follows: Within the Setup Project, open up the Registry Editor. Create a new Key named CLSID under HKEY_CLASSES_ROOT by right- clicking on the HKEY_CLASSES_ROOT folder, then choosing 'New', and then 'Key'. Under the CLSID key, add a new key named for your GUID, including the curly braces. Under the new GUID key you added, add a key named Programmable. You don't need to put any value within this key; however, we do need to force it to be created. Therefore, right- click on the Programmable key and choose 'Properties Window'. Then change the Always. Create property to True. Once you've done this, you no longer need the methods marked with Com. Register. Function. Attribute and Com. Unregister. Function. Attribute, but I would still leave them in for those occasions when you intall via Reg. Asm and not via the Setup Project. At this point you are ready to deploy. Build your solution and then right click on your Setup Project and choose 'Build'. You can then use the created Setup. MSI files to deploy to a client machine. Something else to consider, however, is that when adding the automation add- in via Excel's add- ins dialog box, an error message will be shown stating that "Mscoree. This error message can be ignored, and your add- in will run no matter what you answer, but it can be alarming to a client installing your add- in. This situation, and the explanation of how to solve it, is well described in the article Writing user defined functions for Excel in . NET by Eric Carter. The problem is that the default value for the Inproc. Server. 32 key is simply mscorree. NET to find it, but causes Excel to complain. The solution is to make sure that the default value for the Inproc. Server. 32 key includes the full path to your system directory. For example, on 3. C: \Windows\system. This path needs to vary, however, depending on the system it is installed on. So this path should not be hard- coded. Eric Carter handles this by modifying the methods marked by the Com. Register. Function. Attribute and Com. Unregister. Function. Attribute to be the following: // C#. Com. Register. Function. Attribute]. public static void Register. Function(Type type). Registry. Classes. Root. Create. Sub. Key(. Get. Sub. Key. Name(type, "Programmable")). Registry. Key key = Registry. Classes. Root. Open. Sub. Key(. Get. Sub. Key. Name(type, "Inproc. Server. 32"), true). Set. Value("". System. Environment. System. Directory + @"\mscoree. Registry. Value. Kind. String). [Com. Unregister. Function. Attribute]. Unregister. Function(Type type). Registry. Classes. Root. Delete. Sub. Key(. Get. Sub. Key. Name(type, "Programmable"), false). Get. Sub. Key. Name(Type type. Key. Name). System. Text. String. Builder s =. System. Text. String. Builder(). s. Append(@"CLSID\{"). Append(type. GUID. To. String(). To. Upper()). s. Append(@"}\"). Append(sub. Key. Name). To. String(). Translated to VB. NET, this is equivalent to: 'VB. NET. < Com. Register. Function. Attribute()> _. Public Shared Sub Register. Function(By. Val type As Type). Registry. Classes. Root. Create. Sub. Key(Get. Sub. Key. Name(type, "Programmable")). Dim key As Registry. Key = Registry. Classes. Root. Open. Sub. Key(Get. Sub. Key. Name(type, "Inproc. Server. 32"), true). Set. Value("", (System. Environment. System. Directory + "\mscoree. Registry. Value. Kind. String). < Com. Unregister. Function. Attribute()> _. Public Shared Sub Unregister. Function(By. Val type As Type). Registry. Classes. Root. Delete. Sub. Key(Get. Sub. Key. Name(type, "Programmable"), false). Private Shared Function Get. Sub. Key. Name(By. Val type As Type, By. Val sub. Key. Name As String) As String. Dim s As System. Text. String. Builder = New System. Text. String. Builder. Append ("CLSID\{"). Append(type. GUID. To. String. To. Upper). Append ("}\"). s. Append (sub. Key. Name). Return s. To. String. This works, but has the same exact problem where the assembly is properly registered when running Reg. Asm on the local machine, but fails when attempting to use this within a Visual Studio Setup Project. The solution, again, is to add our own registry keys. This time, however, we'll have to create a default value that makes use of the [System. Folder] property, which is equivalent to the System. Environment. System. Directory call used within Eric Carter's code, above. To do this, add a Key named Inproc. Server. 32 under your CLSID\\{GUID} key that we created previously. Then right- click on the new Inproc. Server. 32 key and choose 'New' then 'String Value'.
0 Comments
Leave a Reply. |
AuthorWrite something about yourself. No need to be fancy, just an overview. Archives
November 2017
Categories |