Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chriss Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Subclassing Question

Status
Not open for further replies.

LuckyLuke

Programmer
Mar 28, 2001
188
NL
Hi,

I'm trying to make a dll for Visual Basic with ATL with my own control in it. I try to subclass the control created with CreateWindowEx by using SetWindowLong. However the compiler gives an type cast error when calling SetWindowLong. I was wondering if it's even possible to have a WindowProc inside a class and if so, how do you use it. If not or if there is a better way, please tell me how (I haven't got much experience with ATL or MFC). I think I can't use the built in message map macro's from ATL, since I've created my own window class with RegisterClass. Everything goes fine, until I want to subclass the windows I create with my dll. The code I use to subclass is this:

(Simplified test version)
[tt]
ToolWindow.h
class ATL_NO_VTABLE CToolWindow :
public CComObjectRootEx<CComSingleThreadModel>,
public CComCoClass<CToolWindow, &CLSID_ToolWindow>,
public IDispatchImpl<IToolWindow, &IID_IToolWindow, &LIBID_CTOOLWINDOWLib>
{
public:
CToolWindow()
{
}

DECLARE_REGISTRY_RESOURCEID(IDR_TOOLWINDOW)

DECLARE_PROTECT_FINAL_CONSTRUCT()

BEGIN_COM_MAP(CToolWindow)
COM_INTERFACE_ENTRY(IToolWindow)
COM_INTERFACE_ENTRY(IDispatch)
END_COM_MAP()

// IToolWindow
public:
LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
STDMETHOD(Create)(/*[in]*/ long hWndParent, /*[in]*/ long hInstance, /*[out,retval]*/ long *lpRetVal);
private:
WNDPROC m_wpProcAddress;
};

#endif //__TOOLWINDOW_H_

ToolWindow.cpp
STDMETHODIMP CToolWindow::Create(long hWndParent, long hInstance, long *lpRetVal)
{
// TODO: Add your implementation code here
HWND hWnd = CreateWindowEx(0, _T(&quot;Button&quot;), _T(&quot;Test&quot;), WS_VISIBLE | WS_CHILD, 10, 10, 100, 100, (HWND) hWndParent, 0, (HINSTANCE) hInstance, NULL);

if (hWnd != 0)
m_wpProcAddress = (WNDPROC) SetWindowLong(hWnd, GWL_WNDPROC, (WNDPROC) WindowProc); //This is line 16 :)

*lpRetVal = (long) hWnd;

return S_OK;
}

LRESULT CALLBACK CToolWindow::WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
return CallWindowProc(m_wpProcAddress, hWnd, uMsg, wParam, lParam);
}
[/tt]

The type cast error is:

[tt]
C:\Documents and Settings\Administrator\Desktop\Programmeren\CToolWindow\C\CToolWindow\ToolWindow.cpp(16) : error C2440: 'type cast' : cannot convert from '' to 'long (__stdcall *)(struct HWND__ *,unsigned int,unsigned int,long)'
None of the functions with this name in scope match the target type
[/tt]

Thanks in advance
 
Oh I spotted a mistake in my code (however it doesn't resolve the error):

line 16 should be:

[tt]
m_wpProcAddress = (WNDPROC) SetWindowLong(hWnd, GWL_WNDPROC, (LONG) WindowProc);
[\tt]

The error I get now is:
[tt]
C:\Documents and Settings\Administrator\Desktop\Programmeren\CToolWindow\C\CToolWindow\ToolWindow.cpp(16) : error C2440: 'type cast' : cannot convert from 'long (__stdcall CToolWindow::*)(struct HWND__ *,unsigned int,unsigned int,long)' to 'long'
Conversion is a valid standard conversion, which can be performed implicitly or by use of static_cast, C-style cast or function-style cast[/tt]
 
I have found a workaround. Thanks if you tried to help anyway :)

[tt]
LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
WNDPROC wpProcAddress;

STDMETHODIMP CToolWindow::Create(long hWndParent, long hInstance, long *lpRetVal) {

m_hWnd = CreateWindowEx(0, _T(&quot;Button&quot;), _T(&quot;Hiep Hoi&quot;), WS_VISIBLE | WS_CHILD, 10, 10, 100, 100, (HWND) hWndParent, 0, (HINSTANCE) hInstance, NULL);

if (m_hWnd != 0) {
SetProp(m_hWnd, _T(&quot;PROP_WNDPROC&quot;), (HANDLE) (this));
wpProcAddress = (WNDPROC) SetWindowLong(m_hWnd, GWL_WNDPROC, (LONG) WindowProc);
}

*lpRetVal = (long) m_hWnd;

return S_OK;

}

LRESULT CALLBACK CToolWindow::ToolwindowProc(UINT uMsg, WPARAM wParam, LPARAM lParam) {

if (uMsg == WM_LBUTTONDOWN)
MessageBeep(MB_ICONASTERISK);

return CallWindowProc(wpProcAddress, m_hWnd, uMsg, wParam, lParam);

}

LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {

CToolWindow * ToolWindow = (CToolWindow *) GetProp(hWnd, _T(&quot;PROP_WNDPROC&quot;));

if (ToolWindow != (CToolWindow *) 0)
return ToolWindow->ToolwindowProc(uMsg, wParam, lParam);

return CallWindowProc(wpProcAddress, hWnd, uMsg, wParam, lParam);

}
[/tt]
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top