View Full Version: Win32 API C++ style

C++ Learning Community > C++ Tips > Win32 API C++ style


Title: Win32 API C++ style
Description: part 1


Joel - October 24, 2005 03:28 AM (GMT)
Well... some people might say that API and C++ style code, don't mix... but...hey... is cool to use all the knowladge to make some things easier... right?

App.h
CODE

// App.h: interface for the App class.
//
//////////////////////////////////////////////////////////////////////

#if !defined(AFX_APP_H__7512E989_3B9C_4135_AE8E_6D2645612B80__INCLUDED_)
#define AFX_APP_H__7512E989_3B9C_4135_AE8E_6D2645612B80__INCLUDED_

#include <windows.h>

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

class App  
{
public:
void DoDlgLoop(HWND, LPMSG);
void EndDlg();
void DoWndLoop(LPMSG);
HWND BeginDlg(DLGPROC);
void SetTemplateDlg(char*);
int promptMessage(HWND, const char*, const char*, unsigned int);
int EndWnd();
bool BeginWnd(const char*, int, int, int, WNDPROC);
void SetBackground(HBRUSH);
void SetStyles(unsigned long);
void SetMenu(char*);
void SetCursor(HCURSOR);
void SetIcon(HICON);
void SetClassName(char*);
void SetInstance(HINSTANCE);
App();
operator HINSTANCE() const;
virtual ~App();
protected:
bool IsWin95();
HINSTANCE g_hInstance;
char* g_szClassname;
HICON g_hIcon;
HCURSOR g_hCursor;
char* g_lpszMenuName;
char* g_lpTemplateName;
unsigned long g_dwStyle;
HBRUSH g_hbrBrush;
};

#endif // !defined(AFX_APP_H__7512E989_3B9C_4135_AE8E_6D2645612B80__INCLUDED_)

App.cpp
CODE

// App.cpp: implementation of the App class.
//
//////////////////////////////////////////////////////////////////////

#include "App.h"

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

App::App()
{
g_hInstance = 0;
g_dwStyle = 0;
g_hbrBrush = 0;
g_hIcon = 0;
g_hCursor = 0;
g_szClassname = "";
g_lpTemplateName = new char[260];
g_lpszMenuName = new char[260];
}

App::~App()
{
g_dwStyle = 0;
g_hbrBrush = 0;
g_hIcon = 0;
g_hCursor = 0;
delete[] g_lpszMenuName;
delete[] g_lpTemplateName;
}

void App::SetInstance(HINSTANCE p_hInstance)
{
g_hInstance = p_hInstance;
return;
}

void App::SetClassName(char* szClassName)
{
g_szClassname = szClassName;
return;
}

void App::SetIcon(HICON hIcon)
{
g_hIcon = hIcon;
return;
}

void App::SetCursor(HCURSOR hCursor)
{
g_hCursor = hCursor;
return;
}

void App::SetMenu(char* lpszMenuName)
{
g_lpszMenuName = lpszMenuName;
return;
}

void App::SetStyles(unsigned long dwStyles)
{
g_dwStyle = dwStyles;
return;
}

void App::SetBackground(HBRUSH hbrBrush)
{
g_hbrBrush = hbrBrush;
return;
}

bool App::BeginWnd(const char * szTitle, int w, int h, int ShowCmd, WNDPROC WinProc)
{
WNDCLASSEX wcx;
wcx.cbSize = sizeof(WNDCLASSEX);
wcx.cbClsExtra = wcx.cbWndExtra = 0;
wcx.hbrBackground = g_hbrBrush ? g_hbrBrush : GetSysColorBrush(COLOR_3DFACE);
wcx.hCursor = g_hCursor ? g_hCursor : LoadCursor(NULL, IDC_ARROW);
wcx.hIcon = g_hIcon ? g_hIcon : LoadIcon(NULL, IDI_APPLICATION);
wcx.hIconSm = g_hIcon ? g_hIcon : LoadIcon(NULL, IDI_APPLICATION);
wcx.hInstance = g_hInstance;
wcx.lpfnWndProc = WinProc;
wcx.lpszMenuName = g_lpszMenuName;
wcx.lpszClassName = g_szClassname;
wcx.style = CS_DBLCLKS|CS_HREDRAW|CS_VREDRAW;
if (!RegisterClassEx(&wcx) || !IsWin95() ) return false;
HWND hwnd = CreateWindowEx(0, g_szClassname, szTitle, g_dwStyle, ((GetSystemMetrics(SM_CXSCREEN)-w)/2), ((GetSystemMetrics(SM_CYSCREEN)-h)/2), w, h, HWND_DESKTOP, 0, g_hInstance, 0);
if (!hwnd) return false;
ShowWindow(hwnd, ShowCmd);
UpdateWindow(hwnd);
return true;
}

App::operator HINSTANCE() const
{
return g_hInstance;
}

int App::EndWnd()
{
return UnregisterClass(g_szClassname, g_hInstance);
}

int App::promptMessage(HWND hwnd, const char* szmsg, const char* szt, unsigned int styles)
{
return MessageBox(hwnd, szmsg, szt, styles);
}

bool App::IsWin95()
{
OSVERSIONINFO osvi;
ZeroMemory(&osvi, sizeof(OSVERSIONINFO));
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
GetVersionEx(&osvi);
if (osvi.dwMajorVersion == 4 && osvi.dwMinorVersion == 0) return false;
return true;
}

void App::SetTemplateDlg(char * lpTemplateName)
{
g_lpTemplateName = lpTemplateName;
return;
}


HWND App::BeginDlg(DLGPROC lpDialogFunc)
{
return CreateDialogParam(g_hInstance, g_lpTemplateName, NULL, lpDialogFunc, 0);
}

void App::DoWndLoop(LPMSG lpmsg)
{
while(GetMessage(lpmsg, NULL, 0, 0))
{
 TranslateMessage(lpmsg);
 DispatchMessage(lpmsg);
}
return;
}

void App::EndDlg()
{
g_hInstance = 0;
g_lpTemplateName = 0;
if (g_hIcon) DestroyIcon(g_hIcon);
return;
}

void App::DoDlgLoop(HWND hDlg, LPMSG lpmsg)
{
while(GetMessage(lpmsg, NULL, 0, 0))
{
 if( !IsWindow(hDlg) || !IsDialogMessage(hDlg, lpmsg) )
 {
  TranslateMessage(lpmsg);
  DispatchMessage(lpmsg);
 }
}
return;
}

main.cpp
CODE

#include <windows.h>
#include "App.h"

App app;

LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
switch (uMsg)
{
case WM_CREATE:
 {
  char b[64];
  wsprintf(b, "%u", app);
  app.promptMessage(hWnd, b, "Your instance for today", 64);
  return TRUE;
 }
case WM_COMMAND:
 {
  return TRUE;
 }
case WM_CLOSE:
 {
  DestroyWindow(hWnd);
  return TRUE;
 }
case WM_DESTROY:
 {
  PostQuitMessage(0);
  return TRUE;
 }
default:
 {
  return DefWindowProc(hWnd, uMsg, wParam, lParam);
 }
}
return FALSE;
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nShowCmd)
{
app.SetInstance(hInstance);
app.SetClassName("Win32cpp");
app.SetStyles(WS_OVERLAPPEDWINDOW);

if (app.BeginWnd("Hola mundo", 250, 250, nShowCmd, WndProc))
{
 MSG msg;
 app.DoWndLoop(&msg);
 app.EndWnd();
 return msg.wParam;
}
else
{
 app.promptMessage(0, "Couldn't register main window class or you need Win98+", "oh no!", 16);
}

return 1;
}

Any suggestions or comments? ^_^

gnschmidt - October 24, 2005 11:38 AM (GMT)
This looks great! My only concern is that you'd need to add an awful lot of functionality before it's a full application programming framework.

I wrote wrapper classes for Win32 listviews, progress bars, etc. that did everything I wanted them to do, but after a while I felt that I'd be better off using a portable framework that is as nearly complete as possible. (My choice was wxWidgets and it has made writing small apps much easier and faster, even though I was reluctant to replace my std::strings with wxStrings.)





Hosted for free by InvisionFree