Non-MFC replacement for the AfxConnectionAdvise for Microsoft COM objects in mingw

StackOverflow https://stackoverflow.com/questions/23156816

  •  05-07-2023
  •  | 
  •  

سؤال

I am trying to implement a DDiskFormat2DataEvents class to listen to an IDiskFormat2Data's progress events. The only example I found of connecting those two uses AfxConnectionAdvise. This project builds in mingw64 so I need to find an alternative to this MFC method or how to manually connect the com object's source and sink. Any suggestions would be helpful. Thanks

هل كانت مفيدة؟

المحلول

It's a pretty straightforward connection point implementation. I found this (link in german, but the code's pretty straightforward) - needs error checking, though.

Most of the work is setting up an IDispatch implementation with ITypeInfo. You could directly implement GetIDsOfNames and Invoke (without using ITypeInfo), but I find it's simpler to use ITypeInfo with event interfaces (since the typeinfo is already built).

You might also want to look at the answers to this question, too.

// pConnectTo = IDiscFormat2Data-Interface 
// riid = IID_DDiscFormat2DataEvents 
// pUnknown = The Event Receiver ( see below)
void connect(IUnknown* pConnectTo, REFIID riid, IUnknown* pUnknown) 
{ 
// QI the container
 HRESULT hr = pConnectTo->QueryInterface(IID_IConnectionPointContainer, (void**)&m_connContainer); 

// Find the connection point:
 hr = m_connContainer->FindConnectionPoint(riid, &m_connPoint); 

// Set up advice link
 DWORD cookie; 
 hr = m_connPoint->Advise(pUnknown, &cookie); 

// Retain the cookie:
 m_dwCookie = cookie; 
} 


// The Event Receiver (implicitly derives from IDispatch): 
class EventReceiver : public DDiscFormat2DataEvents 
{ 
public: 
    EventReceiver();
    virtual HRESULT __stdcall Update(IDispatch* object, IDispatch* progress); 
private:
    com_ptr_t<ITypeInfo> m_ptinfo;
};

EventReceiver::EventReceiver()
{
    m_ptinfo = NULL; 

    HRESULT hr = 0; 
    LPTYPELIB ptlib = NULL; 

    hr = LoadRegTypeLib(LIBID_IMAPILib2, IMAPILib2_MajorVersion, IMAPILib2_MinorVersion, LOCALE_SYSTEM_DEFAULT, &ptlib)); 

    if (!FAILED(hr))
    { 
        hr = ptlib->GetTypeInfoOfGuid(IID_DDiscFormat2DataEvents, &m_ptinfo)); 
        ptlib->Release(); 
    }
}

// boilerplate IDispatch implementation based on Typeinfo
STDMETHODIMP EventReceiver::GetTypeInfoCount(UINT FAR *pctinfo) 
{ 
     *pctinfo = 1; 

     return NOERROR; 
} 

 STDMETHODIMP EventReceiver::GetTypeInfo(UINT itinfo, LCID lcid, ITypeInfo FAR * FAR *pptinfo) 
{ 
     *pptinfo = NULL; 

     if (itinfo != 0) return ResultFromScode(DISP_E_BADINDEX); 

     m_ptinfo->AddRef(); 

     *pptinfo = m_ptinfo; 

     return NOERROR; 
} 

 STDMETHODIMP EventReceiver::GetIDsOfNames(REFIID riid, OLECHAR FAR * FAR *rgszNames, UINT cNames, LCID lcid, DISPID FAR *rgdispid) 
{ 
     return DispGetIDsOfNames(m_ptinfo, rgszNames, cNames, rgdispid); 
} 

 STDMETHODIMP EventReceiver::Invoke(DISPID dispidMember, REFIID riid, LCID lcid, WORD wFlags, DISPPARAMS FAR *pdispparams, VARIANT FAR *pvarResult, EXCEPINFO FAR *pexcepinfo, UINT FAR *puArgErr) 
{ 
     return DispInvoke(this, m_ptinfo, dispidMember, wFlags, pdispparams, pvarResult, pexcepinfo, puArgErr); 
}
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top