IID IID_IOPCServerList=__uuidof(IOPCServerList);
IOPCServerList *pServerList;
// запрос интерфейса у компонента должен вернуть S_OK
hRes=CoCreateInstance(clsid,NULL,CLSCTX_LOCAL_SERVER,
IID_IOPCServerList,(void**)&pServerList);
//перечислитель, в котором будут храниться GUID серверов
IOPCEnumGUID * pIOPCEnumGuid;
//запрос серверов спецификации OPC DA 2.0
pServerList->EnumClassesOfCategories(1, &clsidcat,0,
NULL,&pIOPCEnumGuid);
OLECHAR *pszProgID; // буфер для записи ProgID серверов
OLECHAR *pszUserType; // буфер для записи описания серверов
LVITEM lvItem; // подготовка элемента списка для вставки
ZeroMemory(&lvItem,sizeof(lvItem));
lvItem.cchTextMax=100;
lvItem.mask=LVIF_TEXT;
GUID guid; // Сюда будет записывать идентификатор текущего сервера
int nServerCnt=0; // общее количество доступных серверов
int iRetSvr; // количество серверов, предоставленных запросом
// получение первого доступного идентификатора сервера
pIOPCEnumGuid->Next(1,&guid,&iRetSvr);
while (iRetSvr!=0)
{
nServerCnt++;
pServerList->GetClassDetails(&guid,&pszProgID,&pszUserType);
lvItem.pszText=pszProgID;
int iItem=m_listOPCServers.InsertItem(&lvItem);
GUID *pGuid = new GUID;
//создаем область памяти, чтобы хранить идентификатор в привязке к
строке списка
memcpy(pGuid,&guid,sizeof(guid));
//связываем элемент списка и указатель на идентификатор
m_listOPCServers.SetItemData(iItem,(DWORD_PTR)pGuid);
pIOPCEnumGuid->Next(1,&guid,&iRetSvr); // получаем следующий сервер
}
return nServerCnt;
}
Теперь необходимо вставить вызов функции в методе InitDialog нашего
диалога и не забыть инициализировать COM. Функции, отвечающие за это,
выделены курсивом.
BOOL COPCClientDlg::OnInitDialog()
{
CDialog::OnInitDialog();
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);