Step 2: Getting an Object Interface
In this step we just get an IOleObject interface—it exists on any of the controls we can insert—and we print the user type name through an accelerator bound to Ctrl-i.
The IlvGraphicCOMAdapter class uses only two interfaces directly: IOleObject and IViewObject (the ATL API uses more). However, it is possible to ask for a new interface in order to use the functionalities offered by the control. You can do this with the queryInterface member function. This function is simply an encapsulation for the COM QueryInterface function, with the same parameters and the same return value.
Here is the code:
// --------------------------------------------------------------------------
// This function, associated to an accelerator, gets the user type name of
// the control and prints it.
static void
GetTypeAccelerator(IlvManager* man, IlvView*, IlvEvent& ev, IlvAny)
{
// Gets the object above which is the mouse pointer.
IlvGraphic* graphic = man->lastContains(IlvPoint(ev.x(), ev.y()));
// Any object?
 
if (graphic) {
// Is it an IlvGraphicCOMAdapter?
IlvGraphicCOMAdapter* adapt=
ILVDYNAMICCAST(IlvGraphicCOMAdapter*, graphic);
 
if (adapt) {
// Queries for the IOleObject interface.
IOleObject* pInterface;
HRESULT hr =
adapt->queryInterface(IID_IOleObject, (void**)&pInterface);
// Smart pointer.
IlvCOMInterface<IOleObject> oleObject(pInterface);
 
// Succeeded?
if (SUCCEEDED(hr)) {
// Asks for the user type name.
LPOLESTR userType;
hr = oleObject->GetUserType(USERCLASSTYPE_FULL, &userType);
 
// Succeeded?
if (SUCCEEDED(hr)) {
// Prints the result.
IlvCOut << "The type is: " << userType << ".\n";
// Asks for the global allocator.
LPMALLOC pMalloc;
if (SUCCEEDED(CoGetMalloc(1, &pMalloc))) {
// Releases the memory allocated by GetUserType.
pMalloc->Free(userType);
// Releases the global allocator.
pMalloc->Release();
}
}
}
}
}
}
We also define the following operator in order to be able to print a string in UNICODE:
// --------------------------------------------------------------------------
// This operator prints wchar_t strings into a standard ostream.
ostream&
operator<<(ostream& o, const wchar_t* str)
{
size_t len = wcslen(str);
size_t size = wcstombs(0, str, len) + 1;
char* buf = new char[size];
wcstombs(buf, str, len+1);
o << buf;
delete[] buf;
return o;
}
As you can see, most of the code is pure COM one. In this code, we use a smart pointer that prevents worrying about the release of the interface.
This code uses the class IlvCOut. So you have to include the header file ilviews/base/error.h.
Published date: 05/24/2022
Last modified date: 02/24/2022