BOOL AFXAPI AfxOleTypeMatchGuid( LPTYPEINFO pTypeInfo, TYPEDESC* pTypeDesc, REFGUID guidType, ULONG cIndirectionLevels) { ASSERT(pTypeInfo != NULL); ASSERT(pTypeDesc != NULL); ASSERT(cIndirectionLevels >= 0); LPTYPEINFO pTypeInfoRef = NULL; BOOL bMatch = FALSE; switch (pTypeDesc->vt) { case VT_USERDEFINED: // It's an alias: Expand the alias and try to match. if (SUCCEEDED(pTypeInfo->GetRefTypeInfo( pTypeDesc->hreftype, &pTypeInfoRef))) { ASSERT(pTypeInfoRef != NULL); LPTYPEATTR pTypeAttr = NULL; if (SUCCEEDED(pTypeInfoRef->GetTypeAttr(&pTypeAttr))) { ASSERT(pTypeAttr != NULL); // If we've dereferenced the correct number of times, // test the GUIDs for equality. if (cIndirectionLevels == 0) bMatch = IsEqualGUID(pTypeAttr->guid, guidType); if ((bMatch == FALSE) && (pTypeAttr->typekind == TKIND_ALIAS)) { // GUIDs didn't match, but type expanded to another alias! bMatch = AfxOleTypeMatchGuid(pTypeInfoRef, &pTypeAttr->tdescAlias, guidType, cIndirectionLevels); } pTypeInfoRef->ReleaseTypeAttr(pTypeAttr); } pTypeInfoRef->Release(); } break; case VT_PTR: // It's a pointer: Dereference and try to match with one less level // of indirection. ASSERT(pTypeDesc->lptdesc != NULL); bMatch = AfxOleTypeMatchGuid(pTypeInfo, pTypeDesc->lptdesc, guidType, cIndirectionLevels - 1); break; } return bMatch; }
int PolylineTest::writePersistFile() { ComPtr<IPolyline> pl; auto hr = CoCreateInstance(CLSID_PolylineObj, NULL, CLSCTX_INPROC_SERVER, IID_IPolyline, (void**)&pl); if (FAILED(hr)) { return -1; } LPTYPEINFO pTypeInfo = NULL; LPTYPELIB pTypelib = NULL; IRecordInfo* pRecInfo = NULL; hr = LoadRegTypeLib(LIBID_GraphicsLibrary, 1, 0, GetUserDefaultLCID(), &pTypelib); _ASSERT(SUCCEEDED(hr) && pTypelib); hr = pTypelib->GetTypeInfoOfGuid(__uuidof(PolyPoint), &pTypeInfo); _ASSERT(SUCCEEDED(hr) && pTypeInfo); hr = GetRecordInfoFromTypeInfo(pTypeInfo, &pRecInfo); _ASSERT(SUCCEEDED(hr) && pRecInfo); pTypeInfo->Release(); pTypelib->Release(); std::vector<POINT> points = { { 1, 2 }, { 100, 200 }, { 300, 400 } }; auto psa = SafeArrayCreateVectorEx(VT_RECORD, 0, points.size(), pRecInfo); PolyPoint* pps; SafeArrayAccessData(psa, (void**)&pps); _ASSERT(psa); for (size_t i = 0; i < points.size(); ++i) { pps[i].x = points[i].x; pps[i].y = points[i].y; } pl->put_Points(psa); outputPoints(pl); ComPtr<IPersistFile> pf; pl->QueryInterface(IID_IPersistFile, (void**)&pf); pf->Save(kFileName, TRUE); pf->SaveCompleted(kFileName); return 0; }
void CStockPropPage::FillPropnameList(REFGUID guid, int nIndirect, CComboBox& combo) { USES_CONVERSION; combo.ResetContent(); UINT cProps = 0; ULONG nObjects; LPDISPATCH* ppDisp = GetObjectArray(&nObjects); if (ppDisp != NULL) { LPTYPEINFO pTypeInfo; LPTYPEATTR pTypeAttr; LPVARDESC pVarDesc; ULONG iObj; WORD iProp; BSTR rgbstr[1]; UINT cName; // Get the property sheet locale LPPROPERTYPAGESITE pPageSite; if ((pPageSite = GetPageSite()) != NULL) if (FAILED(pPageSite->GetLocaleID(&m_lcid))) m_lcid = 0; // Iterate through all objects. for (iObj = 0; iObj < nObjects; iObj++) { pTypeInfo = NULL; if ((ppDisp[iObj] != NULL) && SUCCEEDED(ppDisp[iObj]->GetTypeInfo(0, m_lcid, &pTypeInfo))) { ASSERT(pTypeInfo != NULL); pTypeAttr = NULL; if (SUCCEEDED(pTypeInfo->GetTypeAttr(&pTypeAttr))) { ASSERT(pTypeAttr != NULL); // Iterate through all properties of object. for (iProp = 0; iProp < pTypeAttr->cVars; iProp++) { pVarDesc = NULL; if (SUCCEEDED(pTypeInfo->GetVarDesc(iProp, &pVarDesc))) { // Check whether property has desired type if (!(pVarDesc->wVarFlags & VARFLAG_FHIDDEN) && AfxOleTypeMatchGuid(pTypeInfo, &pVarDesc->elemdescVar.tdesc, guid, nIndirect)) { // Get property name and insert into list. if (SUCCEEDED(pTypeInfo->GetNames( pVarDesc->memid, rgbstr, 1, &cName))) { // Don't insert duplicates. LPCTSTR lpstr = OLE2CT(rgbstr[0]); if (combo.FindString(-1, lpstr) == CB_ERR) { int iItem = combo.AddString(lpstr); if (iItem >= 0) { combo.SetItemData(iItem, (DWORD)pVarDesc->memid); ++cProps; } } SysFreeString(rgbstr[0]); } } pTypeInfo->ReleaseVarDesc(pVarDesc); } } pTypeInfo->ReleaseTypeAttr(pTypeAttr); } pTypeInfo->Release(); } } } // Select the first one m_iPropName = 0; // Prevents save from happening if (combo.SetCurSel(0) != CB_ERR) combo.GetLBText(0, m_strPropName); // Disable or set the size of the combo, as appropriate if (cProps <= 1) combo.EnableWindow(FALSE); else _AfxSizeComboToContent(&combo); UpdateData(FALSE); SetModifiedFlag(FALSE); }