Recent projects involve third-party interface calls. A third party is a WCF service implemented in C #. And our program is developed using the BCB6. Therefore, you intend to include the communication with WCF in the class library of C #, called to BCB6. BCB6 is a DLL that cannot call C # directly, but you can write a COM component in C # and call it BCB call this COM component.
- Writing COM in C #
The overall step is
- Create a new Class library project
- Set Assemblyinfo.cs
- Set project Properties
- Writing code
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Runtime.InteropServices; //1 Add rumtime.interopservices Assembly reference using System.Windows.Forms; //2 in order to demonstrate, I joined the Forms reference namespace Comimptest { [Guid("3cd116d4-18a1-4504-921b-57c053bad618")] //3 Main Menu , tools , creating GUID generation Public interface icominterface //4 interface must be defined first { [dispid(1)] //5 each function or property needs to be specified DispID void Hello (string name); [DispID(2)] int ADD (int x,int y); [DispID(3)] string cominfo{get;} } [Guid("1a8eb38c-e732-49b2-a897-b40ffd744e3d")] Public class comimp : icominterface //6 write a class that implements an interface { Public void Hello (string name) { Console. WriteLine (" Hello "+name); MessageBox. Show (" Hello "+name,"C # DLL Popup interface "); } Public int ADD (int x, int y) { return x + y; } Public string COMINFO { Get { return the COM Test "; } } } } |
- compiling DLL and TLB
- BCB Write call
- first BCB the development environment needs to install the. NET Framework, which is used in the. NET Framework 4.0, after installation,
in the directory will be RegAsm.exe (must be installed after the To the regasm copied from other places regasm may be incompatible with the version,
This is used when registering COM.
- Establish a BCB console project
- Bar RegAsm.exe (We are for registration convenience), the previously compiled comimptest.tlb, ComImpTest.dll copied to BCB project E XE
Output directory. (This is not necessary, in essence, com as long as it can register, and then BCB function can find the TLB to create the proxy class)
- start the command line with an administrator, register ComImpTest.dll
The essence of the is that the COM class is registered in the registry. Released to the system.
- generate proxy class with BCB
Open BCB Project, select Main Menu Projectà import type library
Get proxy class
Include this header file so we can call it.
But there is no known BCB bug or compatibility problem, BCB the GUID of the Comimp proxy class generated is wrong.
The correct GUID should be the GUID generated when writing C#dll
[Guid("1a8eb38c-e732-49b2-a897-b40ffd744e3d")] |
We just need to replace this GUID, and if we don't, the HRESULT will return to the implementation interface when it is called.
- BCB calling COM's code
- In the console project, add the proxy class header file Comimptest_tlb.h
- The code is as follows
//--------------------------------------------------------------------------- #pragma hdrstop #include <iostream> #include <vcl.h> // Note that iostream to be defined in front of vcl.h, otherwise cout<<ansistring error #include "Comimptest_tlb.h" using namespace std; //--------------------------------------------------------------------------- #pragma argsused int Main (int argc, Char* argv[]) { HRESULT hr; // Initialize COM CoInitialize (NULL); // Create a smart pointer The namespace can be found in the header file comimptest_tlb.h // the definition of an interface smart pointer can also find Comimptest_tlb::icominterfaceptr ptr; // Create an instance, The Comimp declaration can also be found in the header file. hr = ptr. CreateInstance (__uuidof (comimptest_tlb::comimp)); if (hr = = S_OK) { // called ADD method cout << Ptr->add (1, 2) <<endl; // called The Hello method, in BCB widestring corresponding to C # string widestring name = "Zakk Wylde and the oz " ; Ptr->hello (Name.c_bstr ()); // called COMINFO property, where COM has a name change, these functions can be found in the header file of the prototype definition. BSTR OUTP = NULL; Ptr->get_cominfo (&OUTP); // because it is a wide character, it is converted to ansistring for output Cout<<ansistring (OUTP) <<endl; } CoUninitialize (); System ("pause"); return 0; } |
4 Calling COM with VC
There are not so many things to call C # 's COM with VC. Here is the code for the VC call,
Copy the Comimptest.tlb and ComImpTest.dll to the debug directory of the VC project. Then use the Import directive (BCB cannot be recognized with import, it is estimated to be incompatible)
//testCOM3.cpp: Defines the entry point of the console application. //#include"stdafx.h"#include<iostream>#include<Windows.h>using namespacestd; #import".. /debug/comimptest.tlb"int_tmain (intARGC, _tchar*argv[]) {HRESULT hr;//Initialize COMCoInitialize (NULL); //Create a smart pointercomimptest::icominterfaceptr ptr; //Create an instancehr =ptr. CreateInstance (__uuidof (comimptest::comimp)); if(hr = =S_OK) {cout<< Ptr->add (1,2) <<Endl; PTR->hello (L"VC + + Call"); cout<<ptr->COMINFO<<Endl; } couninitialize (); System ("Pause"); return 0;}//---------------------------------------------------------------------------
BCB6 calling the C # DLL