home *** CD-ROM | disk | FTP | other *** search
/ Tricks of the Windows Gam…ming Gurus (2nd Edition) / Disc2.iso / msdn_vcb / samples / vc98 / sdk / com / oleaut / browseh / dispface.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  1997-07-31  |  7.6 KB  |  258 lines

  1. /*************************************************************************
  2. **
  3. **  This is a part of the Microsoft Source Code Samples.
  4. **
  5. **  Copyright (C) 1992-1997 Microsoft Corporation. All rights reserved.
  6. **
  7. **  This source code is only intended as a supplement to Microsoft Development
  8. **  Tools and/or WinHelp documentation.  See these sources for detailed
  9. **  information regarding the Microsoft samples programs.
  10. **
  11. **  OLE Automation TypeLibrary Browse Helper Sample
  12. **
  13. **  dispface.cpp
  14. **
  15. **  CDispinterface implementation
  16. **
  17. **  Written by Microsoft Product Support Services, Windows Developer Support
  18. **
  19. *************************************************************************/
  20.  
  21. #include <windows.h>
  22. #include <windowsx.h>
  23. #ifdef WIN16   
  24.   #include <ole2.h>
  25.   #include <compobj.h>    
  26.   #include <dispatch.h> 
  27.   #include <variant.h>
  28.   #include <olenls.h>  
  29. #endif 
  30. #include "browseh.h"  
  31.  
  32. /*
  33.  * CDispinterface::Create
  34.  *
  35.  * Purpose:
  36.  *  Creates an instance of the Dispinterface automation object and initializes it.
  37.  *
  38.  * Parameters:       
  39.  *  ptinfo             TypeInfo of dispinterface.
  40.  *  ppDispinterface    Returns Dispinterface automation object.
  41.  *
  42.  * Return Value:
  43.  *  HRESULT
  44.  *
  45.  */
  46. HRESULT 
  47. CDispinterface::Create(LPTYPEINFO ptinfo, CDispinterface FAR* FAR* ppDispinterface) 
  48. {   
  49.     HRESULT hr;
  50.     CDispinterface FAR* pDispinterface = NULL;
  51.      
  52.     *ppDispinterface = NULL;
  53.     
  54.     // Create object.
  55.     pDispinterface = new CDispinterface();
  56.     if (pDispinterface == NULL)
  57.     {
  58.         hr = E_OUTOFMEMORY; 
  59.         goto error;
  60.     }   
  61.     // Load type information for the object from type library. 
  62.     hr = pDispinterface->LoadTypeInfo(IID_IDispinterface);
  63.     if (FAILED(hr))
  64.         goto error;  
  65.     
  66.     // Ask base class (CTypeInfo) to initialize.    
  67.     hr = pDispinterface->_InitTypeInfo(ptinfo);
  68.     if (FAILED(hr))
  69.         goto error;
  70.     
  71.     ptinfo->AddRef();
  72.     pDispinterface->m_ptinfo = ptinfo;
  73.  
  74. #ifdef _DEBUG  
  75.     lstrcpyn(pDispinterface->m_szClassName, TEXT("Dispinterface"), 100);
  76. #endif
  77.         
  78.     *ppDispinterface = pDispinterface;
  79.     return NOERROR;
  80.     
  81. error:
  82.     if (pDispinterface == NULL) return E_OUTOFMEMORY;
  83.     if (pDispinterface->m_ptinfo) pDispinterface->m_ptinfo->Release();
  84.          
  85.     // Set to NULL to prevent destructor from attempting to free again  
  86.     pDispinterface->m_ptinfo = NULL;
  87.     
  88.     delete pDispinterface;
  89.     return hr;
  90. }
  91.  
  92. /*
  93.  * CDispinterface::CDispinterface
  94.  *
  95.  * Purpose:
  96.  *  Constructor for CDispinterface object. Initializes members to NULL.
  97.  *
  98.  */
  99. CDispinterface::CDispinterface()
  100. {
  101.     m_pdispProperties = NULL;
  102.     m_pdispMethods = NULL;
  103.     m_pdispInterface = NULL;
  104.     m_ptinfo = NULL;
  105. }
  106.  
  107. /*
  108.  * CDispinterface::~CDispinterface
  109.  *
  110.  * Purpose:
  111.  *  Destructor for CDispinterface object. 
  112.  *
  113.  */
  114. CDispinterface::~CDispinterface()
  115. {
  116.     if (m_pdispProperties) m_pdispProperties->Release();
  117.     if (m_pdispMethods) m_pdispMethods->Release();
  118.     if (m_pdispInterface) m_pdispInterface->Release();
  119.     if (m_ptinfo) m_ptinfo->Release();
  120. }  
  121.  
  122. STDMETHODIMP_(REFCLSID)
  123. CDispinterface::GetInterfaceID()
  124. {
  125.     return IID_IDispinterface;
  126. }
  127.  
  128. STDMETHODIMP_(ICollection FAR*)
  129. CDispinterface::get_Methods()    
  130. {      
  131.     HRESULT hr;
  132.     CFunction FAR* pFunction;
  133.     CCollection FAR* pCollection = NULL;
  134.     LPDISPATCH pdisp;  
  135.     LPTYPEATTR ptypeattr = NULL;
  136.     unsigned short n;
  137.     
  138.     if (m_pdispMethods == NULL)
  139.     {
  140.         hr = m_ptinfo->GetTypeAttr(&ptypeattr); 
  141.         if (FAILED(hr))
  142.             {RaiseException(IDS_Unexpected); return NULL;}   
  143.         hr = CCollection::Create(ptypeattr->cFuncs, 0, &pCollection);
  144.         if (FAILED(hr))
  145.             {RaiseException(IDS_Unexpected); goto error;}  
  146.         // Enumerate methods and return a collection of these.    
  147.         for (n=0; n<ptypeattr->cFuncs; n++)
  148.         {      
  149.             hr = CFunction::Create(m_ptinfo, n, &pFunction); 
  150.             if (FAILED(hr))
  151.                 {RaiseException(IDS_Unexpected); goto error;}
  152.             pFunction->QueryInterface(IID_IDispatch, (void FAR* FAR*)&pdisp);
  153.             pCollection->Add(pdisp);  
  154.             pdisp->Release();
  155.         }
  156.         pCollection->QueryInterface(IID_IDispatch, (void FAR* FAR*)&pdisp);
  157.         m_pdispMethods = pdisp; 
  158.         m_ptinfo->ReleaseTypeAttr(ptypeattr);
  159.     }
  160.     m_pdispMethods->AddRef();
  161.     return (ICollection FAR*)m_pdispMethods;     
  162.     
  163. error:    
  164.     if (ptypeattr) m_ptinfo->ReleaseTypeAttr(ptypeattr);   
  165.     if (pCollection) delete pCollection;  
  166.     return NULL;
  167. }  
  168.  
  169. STDMETHODIMP_(ICollection FAR*)
  170. CDispinterface::get_Properties()     
  171. {    
  172.     HRESULT hr;
  173.     CProperty FAR* pProperty;
  174.     CCollection FAR* pCollection = NULL;
  175.     LPDISPATCH pdisp;
  176.     LPVARDESC pvardesc = NULL;   
  177.     LPTYPEATTR ptypeattr = NULL;
  178.     unsigned short n;
  179.     
  180.     if (m_pdispProperties == NULL)
  181.     {    
  182.         hr = m_ptinfo->GetTypeAttr(&ptypeattr);
  183.         if (FAILED(hr))
  184.             {RaiseException(IDS_Unexpected); return NULL;}       
  185.         hr = CCollection::Create(ptypeattr->cVars, 0, &pCollection);  
  186.         if (FAILED(hr))
  187.             {RaiseException(IDS_Unexpected); goto error;}  
  188.         // Enumerate properties and return a collection of these.   
  189.         for (n=0; n<ptypeattr->cVars; n++)
  190.         {       
  191.             hr = m_ptinfo->GetVarDesc(n, &pvardesc);   
  192.             if (FAILED(hr))
  193.                 {RaiseException(IDS_Unexpected); goto error;}   
  194.             hr = CProperty::Create(m_ptinfo, pvardesc, &pProperty);
  195.             if (FAILED(hr))
  196.                 {RaiseException(IDS_Unexpected); goto error;}    
  197.             m_ptinfo->ReleaseVarDesc(pvardesc); 
  198.             pvardesc = NULL;
  199.             pProperty->QueryInterface(IID_IDispatch, (void FAR* FAR*)&pdisp);
  200.             pCollection->Add(pdisp);   
  201.             pdisp->Release();
  202.         }
  203.         pCollection->QueryInterface(IID_IDispatch, (void FAR* FAR*)&pdisp);
  204.         m_pdispProperties = pdisp;    
  205.         m_ptinfo->ReleaseTypeAttr(ptypeattr); 
  206.     }
  207.     m_pdispProperties->AddRef();
  208.     return (ICollection FAR*)m_pdispProperties;
  209.  
  210. error:  
  211.     if (ptypeattr) m_ptinfo->ReleaseTypeAttr(ptypeattr);   
  212.     if (pCollection) delete pCollection;   
  213.     if (pvardesc) m_ptinfo->ReleaseVarDesc(pvardesc);   
  214.     return NULL;
  215. }   
  216.  
  217. STDMETHODIMP_(IInterface FAR*)
  218. CDispinterface::get_Interface() 
  219.     HRESULT hr;
  220.     CInterface FAR* pInterface = NULL;
  221.     LPTYPEINFO ptinfoInterface = NULL;
  222.     HREFTYPE hreftype;
  223.  
  224.     // Check if this dispinterface is part of a dual interface.
  225.     // (A dual interface has an interface and a dispinterface.)
  226.     if ((m_wTypeFlags & TYPEFLAG_FDUAL) == 0)
  227.         {RaiseException(IDS_NotDualInterface); return NULL;}
  228.     if(m_pdispInterface == NULL)
  229.     {
  230.         // Get interface part of dual interface
  231. #ifdef WIN32
  232.         hr = m_ptinfo->GetRefTypeOfImplType(0xFFFFFFFF, &hreftype);
  233. #else
  234.         hr = m_ptinfo->GetRefTypeOfImplType(0xFFFF, &hreftype);
  235. #endif 
  236.         if (FAILED(hr))
  237.             {RaiseException(IDS_Unexpected); return NULL;}
  238.         hr = m_ptinfo->GetRefTypeInfo(hreftype, &ptinfoInterface);
  239.         if (FAILED(hr))
  240.             {RaiseException(IDS_Unexpected); return NULL;}
  241.         hr = CInterface::Create(ptinfoInterface, &pInterface); 
  242.         if (FAILED(hr))
  243.             {RaiseException(IDS_Unexpected); goto error;}
  244.         pInterface->QueryInterface(IID_IDispatch, (void FAR* FAR*)&m_pdispInterface);
  245.         ptinfoInterface->Release();
  246.     }
  247.     m_pdispInterface->AddRef();
  248.     return (IInterface FAR*)m_pdispInterface;
  249.  
  250. error:
  251.     if (ptinfoInterface) ptinfoInterface->Release();
  252.     if (pInterface) delete pInterface;
  253.     return NULL;
  254. }
  255.  
  256.  
  257.