131 lines
2.8 KiB
C++
131 lines
2.8 KiB
C++
#include <windows.h>
|
|
|
|
|
|
template <class DERIVED_TYPE>
|
|
class BaseWindow
|
|
{
|
|
public:
|
|
static LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
|
|
{
|
|
DERIVED_TYPE *pThis = NULL;
|
|
|
|
if (uMsg == WM_NCCREATE)
|
|
{
|
|
CREATESTRUCT* pCreate = (CREATESTRUCT*)lParam;
|
|
pThis = (DERIVED_TYPE*)pCreate->lpCreateParams;
|
|
SetWindowLongPtr(hwnd, GWLP_USERDATA, (LONG_PTR)pThis);
|
|
|
|
pThis->m_hwnd = hwnd;
|
|
}
|
|
else
|
|
{
|
|
pThis = (DERIVED_TYPE*)GetWindowLongPtr(hwnd, GWLP_USERDATA);
|
|
}
|
|
if (pThis)
|
|
{
|
|
return pThis->HandleMessage(uMsg, wParam, lParam);
|
|
}
|
|
else
|
|
{
|
|
return DefWindowProc(hwnd, uMsg, wParam, lParam);
|
|
}
|
|
}
|
|
|
|
BaseWindow() : m_hwnd(NULL) { }
|
|
|
|
BOOL Create(
|
|
PCWSTR lpWindowName,
|
|
DWORD dwStyle,
|
|
DWORD dwExStyle = 0,
|
|
int x = CW_USEDEFAULT,
|
|
int y = CW_USEDEFAULT,
|
|
int nWidth = CW_USEDEFAULT,
|
|
int nHeight = CW_USEDEFAULT,
|
|
HWND hWndParent = 0,
|
|
HMENU hMenu = 0
|
|
)
|
|
{
|
|
WNDCLASS wc = {0};
|
|
|
|
wc.lpfnWndProc = DERIVED_TYPE::WindowProc;
|
|
wc.hInstance = GetModuleHandle(NULL);
|
|
wc.lpszClassName = ClassName();
|
|
|
|
RegisterClass(&wc);
|
|
|
|
m_hwnd = CreateWindowEx(
|
|
dwExStyle, ClassName(), lpWindowName, dwStyle, x, y,
|
|
nWidth, nHeight, hWndParent, hMenu, GetModuleHandle(NULL), this
|
|
);
|
|
|
|
return (m_hwnd ? TRUE : FALSE);
|
|
}
|
|
|
|
HWND Window() const { return m_hwnd; }
|
|
|
|
protected:
|
|
|
|
virtual PCWSTR ClassName() const = 0;
|
|
virtual LRESULT HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam) = 0;
|
|
|
|
HWND m_hwnd;
|
|
};
|
|
|
|
|
|
class MainWindow : public BaseWindow<MainWindow>
|
|
{
|
|
public:
|
|
PCWSTR ClassName() const { return L"Sample Window Class"; }
|
|
LRESULT HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
|
|
};
|
|
|
|
|
|
int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE, PWSTR pCmdLine, int nCmdShow)
|
|
{
|
|
MainWindow win;
|
|
|
|
if (!win.Create(L"Learn to Program Windows", WS_OVERLAPPEDWINDOW))
|
|
{
|
|
return 0;
|
|
}
|
|
|
|
ShowWindow(win.Window(), nCmdShow);
|
|
|
|
// Run the message loop.
|
|
|
|
MSG msg = { };
|
|
while (GetMessage(&msg, NULL, 0, 0))
|
|
{
|
|
TranslateMessage(&msg);
|
|
DispatchMessage(&msg);
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
|
|
LRESULT MainWindow::HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam)
|
|
{
|
|
switch (uMsg)
|
|
{
|
|
case WM_DESTROY:
|
|
PostQuitMessage(0);
|
|
return 0;
|
|
|
|
case WM_PAINT:
|
|
{
|
|
PAINTSTRUCT ps;
|
|
HDC hdc = BeginPaint(m_hwnd, &ps);
|
|
FillRect(hdc, &ps.rcPaint, (HBRUSH) (COLOR_WINDOW+1));
|
|
EndPaint(m_hwnd, &ps);
|
|
}
|
|
return 0;
|
|
|
|
default:
|
|
return DefWindowProc(m_hwnd, uMsg, wParam, lParam);
|
|
}
|
|
return TRUE;
|
|
}
|
|
|
|
|