Q: how to obtain interface pointer for ATL ActiveX control in an MFC app
-
OK, I'm relatively new to ATL/ActiveX/COM. We have an MFC application (CView and CDialog usage) built with VC++6 SP5. I am in the process of creating an ActiveX control (via ATL) that will be used by this application, but I'm having a problem. I can insert the control onto the template in the resource editor and it shows up. I run the application and the control functions properly. But I need to have access to the interface of that control. I used: CAxWindow m_axTheControlWindow; CComPtr m_ctlTheControl; CWnd* pControl = GetDlgItem(IDC_THECONTROLID); if (pControl) { m_axTheControlWindow.Attach(pControl->GetSafeHwnd()); hr = m_axTheControlWindow.QueryControl(&m_ctlTheControl); if (FAILED(hr) || !m_ctlTheControl) { ATLASSERT(false); } } but QueryControl returns E_FAIL and m_ctlTheControl is NULL. I guess it has something to do with how MFC keeps track of OLE controls (COleControlContainer) ??? Perhaps the only way I could communicate with this control would be via IDispatch? The control was create via the VC++ Insert | New ATL Object... wizard. It's a Full Control (Single Threaded, Dual interface, No aggregation, Support ISupportErrorInfo, support connection points, not based on another control, normalize dc, insertable, opaque, solid background, no stock properties). Now, this is just the bare-bones wizard code. Nothing has been implemented as far as IDispatch or ISupportErrorInfo or connection points beyond what the wizard gives, but I didn't want to go too far before finding out it wasn't going to work. Thanks for any help. Gil
-
OK, I'm relatively new to ATL/ActiveX/COM. We have an MFC application (CView and CDialog usage) built with VC++6 SP5. I am in the process of creating an ActiveX control (via ATL) that will be used by this application, but I'm having a problem. I can insert the control onto the template in the resource editor and it shows up. I run the application and the control functions properly. But I need to have access to the interface of that control. I used: CAxWindow m_axTheControlWindow; CComPtr m_ctlTheControl; CWnd* pControl = GetDlgItem(IDC_THECONTROLID); if (pControl) { m_axTheControlWindow.Attach(pControl->GetSafeHwnd()); hr = m_axTheControlWindow.QueryControl(&m_ctlTheControl); if (FAILED(hr) || !m_ctlTheControl) { ATLASSERT(false); } } but QueryControl returns E_FAIL and m_ctlTheControl is NULL. I guess it has something to do with how MFC keeps track of OLE controls (COleControlContainer) ??? Perhaps the only way I could communicate with this control would be via IDispatch? The control was create via the VC++ Insert | New ATL Object... wizard. It's a Full Control (Single Threaded, Dual interface, No aggregation, Support ISupportErrorInfo, support connection points, not based on another control, normalize dc, insertable, opaque, solid background, no stock properties). Now, this is just the bare-bones wizard code. Nothing has been implemented as far as IDispatch or ISupportErrorInfo or connection points beyond what the wizard gives, but I didn't want to go too far before finding out it wasn't going to work. Thanks for any help. Gil
OK, now that this is buried deep it probably won't be seen, but a co-worker of mine has helped me figure this out. CWnd* pControl = GetDlgItem(IDC_THECONTROLID); if (pControl) { pControl->EnableAutomation(); IUnknown* pUnk = pControl->GetControlUnknown(); CComQIPtr pIFace(pUnk); if(pIFace) { pIFace->AControlMethod(value); } }