For objects that have dual interfaces, the first seven members of the VTBL are the members of IUnknown and IDispatch, and the subsequent members are standard COM entries for the interface's member functions. You can call these entries directly from C++.
The code sample that follows shows how to access a property of the Hello object. Error handling has been omitted for brevity (Hello.vbp).
HRESULT hr;
CLSID clsid; // Class ID of Hello object.
LPUNKNOWN punk = NULL; // Unknown of Hello object.
IHello* phello = NULL; // IHello interface of Hello object.
// Initialize OLE.
hr = OleInitialize(NULL);
// Retrieve CLSID from the ProgID for Hello.
hr = CLSIDFromProgID("Hello.Application", &clsid);
// Create an instance of the Hello object and ask for its
// IDispatch interface.
hr = CoCreateInstance(clsid, NULL, CLSCTX_SERVER,
IID_IUnknown, (void FAR* FAR*)&punk);
hr = punk->QueryInterface(IID_IHello, (void FAR* FAR*)&pHello);
punk->Release(); // Release when no longer needed.
hr = pHello->put_Visible (TRUE);
// Additional code to work with other methods and properties
// (omitted).
OleUninitialize();
The example initializes OLE, and then calls the CLSIDFromProgID function to obtain the class identifier (CLSID) for the Hello application. With the CLSID, the example can call CoCreateInstance to create an instance of the Hello Application object. CoCreateInstance returns a pointer to the object's IUnknown interface (punk
), and this, in turn, is used to call QueryInterface to get pHello
, a pointer to the IID_IHello dual interface. The punk
is no longer needed, so the example releases it. The example then sets the value of the Visible property to True.
If the function returns an error HRESULT, you can get detailed, contextual information through the IErrorInfo interface. For details, see Chapter 11, "Error Handling Interfaces."